Compare commits
9 Commits
82d11e868f
...
acf9b2c4c4
Author | SHA1 | Date | |
---|---|---|---|
|
acf9b2c4c4 | ||
|
d661bf27ae | ||
|
679a87bf45 | ||
|
d9cb5986ee | ||
|
fccc2ba2e5 | ||
|
17c7d0e555 | ||
|
7d75ad7596 | ||
|
45ec502eca | ||
|
fa5a16a8ea |
520
Cargo.lock
generated
520
Cargo.lock
generated
|
@ -2,12 +2,58 @@
|
|||
# It is not intended for manual editing.
|
||||
version = 3
|
||||
|
||||
[[package]]
|
||||
name = "ab_glyph"
|
||||
version = "0.2.23"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "80179d7dd5d7e8c285d67c4a1e652972a92de7475beddfb92028c76463b13225"
|
||||
dependencies = [
|
||||
"ab_glyph_rasterizer",
|
||||
"owned_ttf_parser",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ab_glyph_rasterizer"
|
||||
version = "0.1.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c71b1793ee61086797f5c80b6efa2b8ffa6d5dd703f118545808a7f2e27f7046"
|
||||
|
||||
[[package]]
|
||||
name = "addr2line"
|
||||
version = "0.21.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb"
|
||||
dependencies = [
|
||||
"gimli",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "adler"
|
||||
version = "1.0.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe"
|
||||
|
||||
[[package]]
|
||||
name = "ahash"
|
||||
version = "0.8.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "42cd52102d3df161c77a887b608d7a4897d7cc112886a9537b738a887a03aaff"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"once_cell",
|
||||
"version_check",
|
||||
"zerocopy",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "aho-corasick"
|
||||
version = "1.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b2969dcb958b36655471fc61f7e416fa76033bdd4bfed0678d8fee1e2d07a1f0"
|
||||
dependencies = [
|
||||
"memchr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "anyhow"
|
||||
version = "1.0.77"
|
||||
|
@ -20,12 +66,36 @@ version = "1.1.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
||||
|
||||
[[package]]
|
||||
name = "backtrace"
|
||||
version = "0.3.69"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837"
|
||||
dependencies = [
|
||||
"addr2line",
|
||||
"cc",
|
||||
"cfg-if",
|
||||
"libc",
|
||||
"miniz_oxide",
|
||||
"object",
|
||||
"rustc-demangle",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "1.3.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
|
||||
|
||||
[[package]]
|
||||
name = "cc"
|
||||
version = "1.0.83"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f1174fb0b6ec23863f8b971027804a42614e347eafb0a95bf0b12cdae21fc4d0"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cfg-if"
|
||||
version = "1.0.0"
|
||||
|
@ -48,7 +118,7 @@ dependencies = [
|
|||
"lazy_static",
|
||||
"libc",
|
||||
"unicode-width",
|
||||
"windows-sys",
|
||||
"windows-sys 0.45.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
@ -60,12 +130,70 @@ dependencies = [
|
|||
"cfg-if",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ecolor"
|
||||
version = "0.26.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "03cfe80b1890e1a8cdbffc6044d6872e814aaf6011835a2a5e2db0e5c5c4ef4e"
|
||||
|
||||
[[package]]
|
||||
name = "egui"
|
||||
version = "0.26.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "180f595432a5b615fc6b74afef3955249b86cfea72607b40740a4cd60d5297d0"
|
||||
dependencies = [
|
||||
"ahash",
|
||||
"epaint",
|
||||
"nohash-hasher",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "emath"
|
||||
version = "0.26.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6916301ecf80448f786cdf3eb51d9dbdd831538732229d49119e2d4312eaaf09"
|
||||
|
||||
[[package]]
|
||||
name = "encode_unicode"
|
||||
version = "0.3.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a357d28ed41a50f9c765dbfe56cbc04a64e53e5fc58ba79fbc34c10ef3df831f"
|
||||
|
||||
[[package]]
|
||||
name = "epaint"
|
||||
version = "0.26.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "77b9fdf617dd7f58b0c8e6e9e4a1281f730cde0831d40547da446b2bb76a47af"
|
||||
dependencies = [
|
||||
"ab_glyph",
|
||||
"ahash",
|
||||
"ecolor",
|
||||
"emath",
|
||||
"nohash-hasher",
|
||||
"parking_lot",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "errno"
|
||||
version = "0.2.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f639046355ee4f37944e44f60642c6f3a7efa3cf6b78c78a0d989a8ce6c396a1"
|
||||
dependencies = [
|
||||
"errno-dragonfly",
|
||||
"libc",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "errno-dragonfly"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "aa68f1b12764fab894d2755d2518754e71b4fd80ecfb822714a1206c2aab39bf"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fdeflate"
|
||||
version = "0.3.3"
|
||||
|
@ -85,12 +213,113 @@ dependencies = [
|
|||
"miniz_oxide",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "23342abe12aba583913b2e62f22225ff9c950774065e4bfb61a19cd9770fec40"
|
||||
dependencies = [
|
||||
"futures-channel",
|
||||
"futures-core",
|
||||
"futures-executor",
|
||||
"futures-io",
|
||||
"futures-sink",
|
||||
"futures-task",
|
||||
"futures-util",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-channel"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "955518d47e09b25bbebc7a18df10b81f0c766eaf4c4f1cccef2fca5f2a4fb5f2"
|
||||
dependencies = [
|
||||
"futures-core",
|
||||
"futures-sink",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-core"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4bca583b7e26f571124fe5b7561d49cb2868d79116cfa0eefce955557c6fee8c"
|
||||
|
||||
[[package]]
|
||||
name = "futures-executor"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ccecee823288125bd88b4d7f565c9e58e41858e47ab72e8ea2d64e93624386e0"
|
||||
dependencies = [
|
||||
"futures-core",
|
||||
"futures-task",
|
||||
"futures-util",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-io"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4fff74096e71ed47f8e023204cfd0aa1289cd54ae5430a9523be060cdb849964"
|
||||
|
||||
[[package]]
|
||||
name = "futures-macro"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "89ca545a94061b6365f2c7355b4b32bd20df3ff95f02da9329b34ccc3bd6ee72"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "futures-sink"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f43be4fe21a13b9781a69afa4985b0f6ee0e1afab2c6f454a8cf30e2b2237b6e"
|
||||
|
||||
[[package]]
|
||||
name = "futures-task"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "76d3d132be6c0e6aa1534069c705a74a5997a356c0dc2f86a47765e5617c5b65"
|
||||
|
||||
[[package]]
|
||||
name = "futures-util"
|
||||
version = "0.3.28"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "26b01e40b772d54cf6c6d721c1d1abd0647a0106a12ecaa1c186273392a69533"
|
||||
dependencies = [
|
||||
"futures-channel",
|
||||
"futures-core",
|
||||
"futures-io",
|
||||
"futures-macro",
|
||||
"futures-sink",
|
||||
"futures-task",
|
||||
"memchr",
|
||||
"pin-project-lite",
|
||||
"pin-utils",
|
||||
"slab",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "gimli"
|
||||
version = "0.28.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4271d37baee1b8c7e4b708028c57d816cf9d2434acb33a549475f78c181f6253"
|
||||
|
||||
[[package]]
|
||||
name = "heck"
|
||||
version = "0.4.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8"
|
||||
|
||||
[[package]]
|
||||
name = "hermit-abi"
|
||||
version = "0.3.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bd5256b483761cd23699d0da46cc6fd2ee3be420bbe6d020ae4a091e70b7e9fd"
|
||||
|
||||
[[package]]
|
||||
name = "indicatif"
|
||||
version = "0.17.7"
|
||||
|
@ -127,9 +356,19 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
|
|||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.151"
|
||||
version = "0.2.153"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "302d7ab3130588088d277783b1e2d2e10c9e9e4a16dd9050e6ec93fb3e7048f4"
|
||||
checksum = "9c198f91728a82281a64e1f4f9eeb25d82cb32a5de251c6bd1b5154d63a8e7bd"
|
||||
|
||||
[[package]]
|
||||
name = "libloading"
|
||||
version = "0.6.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "351a32417a12d5f7e82c368a66781e307834dae04c6ce0cd4456d52989229883"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "lock_api"
|
||||
|
@ -172,6 +411,23 @@ dependencies = [
|
|||
"simd-adler32",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "mio"
|
||||
version = "0.8.10"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8f3d0b296e374a4e6f3c7b0a1f5a51d748a0d34c85e7dc48fc3fa9a87657fe09"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"wasi",
|
||||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "nohash-hasher"
|
||||
version = "0.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2bf50223579dc7cdcfb3bfcacf7069ff68243f8c363f62ffa99cf000a6b9c451"
|
||||
|
||||
[[package]]
|
||||
name = "nom"
|
||||
version = "7.1.3"
|
||||
|
@ -182,18 +438,46 @@ dependencies = [
|
|||
"minimal-lexical",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num_cpus"
|
||||
version = "1.16.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43"
|
||||
dependencies = [
|
||||
"hermit-abi",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "number_prefix"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "830b246a0e5f20af87141b25c173cd1b609bd7779a4617d6ec582abaf90870f3"
|
||||
|
||||
[[package]]
|
||||
name = "object"
|
||||
version = "0.32.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a6a622008b6e321afc04970976f62ee297fdbaa6f95318ca343e3eebb9648441"
|
||||
dependencies = [
|
||||
"memchr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.19.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3fdb12b2476b595f9358c5161aa467c2438859caa136dec86c26fdd2efe17b92"
|
||||
|
||||
[[package]]
|
||||
name = "owned_ttf_parser"
|
||||
version = "0.20.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d4586edfe4c648c71797a74c84bacb32b52b212eff5dfe2bb9f2c599844023e7"
|
||||
dependencies = [
|
||||
"ttf-parser",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "parking_lot"
|
||||
version = "0.12.1"
|
||||
|
@ -217,6 +501,23 @@ dependencies = [
|
|||
"windows-targets 0.48.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pcap"
|
||||
version = "1.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "77452fdf9d211d9ca35d092aeefe4d4b3f0c4eb529ffb87a8a3b8fe2bb7c37c3"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"errno",
|
||||
"futures",
|
||||
"libc",
|
||||
"libloading",
|
||||
"pkg-config",
|
||||
"regex",
|
||||
"tokio",
|
||||
"windows-sys 0.36.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pcap-parser"
|
||||
version = "0.14.1"
|
||||
|
@ -228,6 +529,24 @@ dependencies = [
|
|||
"rusticata-macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "pin-project-lite"
|
||||
version = "0.2.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8afb450f006bf6385ca15ef45d71d2288452bc3683ce2e2cacc0d18e4be60b58"
|
||||
|
||||
[[package]]
|
||||
name = "pin-utils"
|
||||
version = "0.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
|
||||
|
||||
[[package]]
|
||||
name = "pkg-config"
|
||||
version = "0.3.30"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d231b230927b5e4ad203db57bbcbee2802f6bce620b1e4a9024a07d94e2907ec"
|
||||
|
||||
[[package]]
|
||||
name = "png"
|
||||
version = "0.17.10"
|
||||
|
@ -335,6 +654,41 @@ dependencies = [
|
|||
"bitflags",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "regex"
|
||||
version = "1.10.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b62dbe01f0b06f9d8dc7d49e05a0785f153b00b2c227856282f671e0318c9b15"
|
||||
dependencies = [
|
||||
"aho-corasick",
|
||||
"memchr",
|
||||
"regex-automata",
|
||||
"regex-syntax",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "regex-automata"
|
||||
version = "0.4.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5bb987efffd3c6d0d8f5f89510bb458559eab11e4f869acb20bf845e016259cd"
|
||||
dependencies = [
|
||||
"aho-corasick",
|
||||
"memchr",
|
||||
"regex-syntax",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "regex-syntax"
|
||||
version = "0.8.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c08c74e62047bb2de4ff487b251e4a92e24f48745648451635cec7d591162d9f"
|
||||
|
||||
[[package]]
|
||||
name = "rustc-demangle"
|
||||
version = "0.1.23"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76"
|
||||
|
||||
[[package]]
|
||||
name = "rusticata-macros"
|
||||
version = "4.1.0"
|
||||
|
@ -376,12 +730,31 @@ version = "0.3.7"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d66dc143e6b11c1eddc06d5c423cfc97062865baf299914ab64caa38182078fe"
|
||||
|
||||
[[package]]
|
||||
name = "slab"
|
||||
version = "0.4.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "smallvec"
|
||||
version = "1.11.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4dccd0940a2dcdf68d092b8cbab7dc0ad8fa938bf95787e1b916b0e3d0e8e970"
|
||||
|
||||
[[package]]
|
||||
name = "socket2"
|
||||
version = "0.5.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7b5fac59a5cb5dd637972e5fca70daf0523c9067fcdc4842f053dae04a18f8e9"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.43"
|
||||
|
@ -404,13 +777,48 @@ name = "thermaldecoder"
|
|||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"egui",
|
||||
"indicatif",
|
||||
"pcap",
|
||||
"pcap-parser",
|
||||
"png",
|
||||
"pyo3",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio"
|
||||
version = "1.36.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "61285f6515fa018fb2d1e46eb21223fff441ee8db5d0f1435e8ab4f5cdb80931"
|
||||
dependencies = [
|
||||
"backtrace",
|
||||
"libc",
|
||||
"mio",
|
||||
"num_cpus",
|
||||
"pin-project-lite",
|
||||
"socket2",
|
||||
"tokio-macros",
|
||||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "tokio-macros"
|
||||
version = "2.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5b8a1e28f2deaa14e508979454cb3a223b10b938b45af148bc0986de36f1923b"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "ttf-parser"
|
||||
version = "0.20.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "17f77d76d837a7830fe1d4f12b7b4ba4192c1888001c7164257e4bc6d21d96b4"
|
||||
|
||||
[[package]]
|
||||
name = "unicode-ident"
|
||||
version = "1.0.12"
|
||||
|
@ -429,6 +837,53 @@ version = "0.2.3"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c7de7d73e1754487cb58364ee906a499937a0dfabd86bcb980fa99ec8c8fa2ce"
|
||||
|
||||
[[package]]
|
||||
name = "version_check"
|
||||
version = "0.9.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f"
|
||||
|
||||
[[package]]
|
||||
name = "wasi"
|
||||
version = "0.11.0+wasi-snapshot-preview1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423"
|
||||
|
||||
[[package]]
|
||||
name = "winapi"
|
||||
version = "0.3.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419"
|
||||
dependencies = [
|
||||
"winapi-i686-pc-windows-gnu",
|
||||
"winapi-x86_64-pc-windows-gnu",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "winapi-i686-pc-windows-gnu"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6"
|
||||
|
||||
[[package]]
|
||||
name = "winapi-x86_64-pc-windows-gnu"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2"
|
||||
dependencies = [
|
||||
"windows_aarch64_msvc 0.36.1",
|
||||
"windows_i686_gnu 0.36.1",
|
||||
"windows_i686_msvc 0.36.1",
|
||||
"windows_x86_64_gnu 0.36.1",
|
||||
"windows_x86_64_msvc 0.36.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.45.0"
|
||||
|
@ -438,6 +893,15 @@ dependencies = [
|
|||
"windows-targets 0.42.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-sys"
|
||||
version = "0.48.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9"
|
||||
dependencies = [
|
||||
"windows-targets 0.48.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.42.2"
|
||||
|
@ -480,6 +944,12 @@ version = "0.48.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.42.2"
|
||||
|
@ -492,6 +962,12 @@ version = "0.48.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.42.2"
|
||||
|
@ -504,6 +980,12 @@ version = "0.48.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.42.2"
|
||||
|
@ -516,6 +998,12 @@ version = "0.48.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.42.2"
|
||||
|
@ -540,6 +1028,12 @@ version = "0.48.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.36.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.42.2"
|
||||
|
@ -551,3 +1045,23 @@ name = "windows_x86_64_msvc"
|
|||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538"
|
||||
|
||||
[[package]]
|
||||
name = "zerocopy"
|
||||
version = "0.7.32"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "74d4d3961e53fa4c9a25a8637fc2bfaf2595b3d3ae34875568a5cf64787716be"
|
||||
dependencies = [
|
||||
"zerocopy-derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "zerocopy-derive"
|
||||
version = "0.7.32"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9ce1b18ccd8e73a9321186f97e46f9f04b778851177567b1975109d26a08d2a6"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
]
|
||||
|
|
|
@ -11,7 +11,9 @@ crate-type = ["rlib", "cdylib"]
|
|||
|
||||
[dependencies]
|
||||
anyhow = "1.0.77"
|
||||
egui = "0.26.2"
|
||||
indicatif = "0.17.7"
|
||||
pcap = { version = "1.2.0", features = ["capture-stream"] }
|
||||
pcap-parser = { version = "0.14.1", features = ["data"] }
|
||||
png = "0.17.10"
|
||||
pyo3 = { version = "0.20.0", "features" = ["extension-module"] }
|
||||
|
|
25
README.md
25
README.md
|
@ -1,8 +1,31 @@
|
|||
### Thermal decoder
|
||||
|
||||
https://wiki.telavivmakers.org/tamiwiki/projects/thermalcam
|
||||
https://telavivmakers.org/tamiwiki/projects/thermalcam
|
||||
|
||||
|
||||
### Starting the stream
|
||||
|
||||
#### Enable jumbo frames
|
||||
|
||||
```
|
||||
sudo ip link set eth0 mtu 9000
|
||||
```
|
||||
|
||||
#### Send start packet
|
||||
You need to send a special packet.
|
||||
|
||||
Sending it via sudo because of raw sockets:
|
||||
```bash
|
||||
sudo ./venv/bin/python ./replay.py
|
||||
```
|
||||
|
||||
To send it you need the capability to open sockets in raw mode, but that does not work well with scripts (see [1]
|
||||
|
||||
[1] setcap for executables, not helpful for python scripts:
|
||||
```
|
||||
setcap cap_net_raw,cap_net_admin=eip ./replay.py
|
||||
```
|
||||
|
||||
### Rust lib usage
|
||||
|
||||
# if you don't already have a virtualenv. Linux specific, adjust to your OS.
|
||||
|
|
181
decode.py
Executable file → Normal file
181
decode.py
Executable file → Normal file
|
@ -1,9 +1,12 @@
|
|||
#!/usr/bin/env python3
|
||||
import argparse
|
||||
from pathlib import Path
|
||||
import os
|
||||
import subprocess
|
||||
from io import BytesIO
|
||||
import numpy as np
|
||||
from tqdm import tqdm
|
||||
from datetime import datetime
|
||||
import pandas as pd
|
||||
import pcapng
|
||||
from struct import unpack
|
||||
|
@ -12,6 +15,7 @@ from PIL import Image
|
|||
|
||||
# Create the parser
|
||||
parser = argparse.ArgumentParser(description="Process a pcap file.")
|
||||
parser.add_argument("--live", action="store_true", help="Process images live")
|
||||
|
||||
# Add an argument for the pcap file, with a default value
|
||||
parser.add_argument('input_file', nargs='?', default='in.pcap', help='The pcap file to process')
|
||||
|
@ -19,39 +23,41 @@ parser.add_argument('input_file', nargs='?', default='in.pcap', help='The pcap f
|
|||
# Parse the arguments
|
||||
args = parser.parse_args()
|
||||
|
||||
# Now use args.input_file as the file to process
|
||||
input_file = args.input_file
|
||||
basename = os.path.splitext(os.path.basename(input_file))[0]
|
||||
|
||||
|
||||
# Read packets from a pcap file
|
||||
scanner = pcapng.scanner.FileScanner(open(input_file, "rb"))
|
||||
blocks = tqdm(scanner)
|
||||
|
||||
# Helper function to safely get an attribute from an object
|
||||
def tryget(obj, att):
|
||||
if hasattr(obj, att):
|
||||
return getattr(obj, att)
|
||||
return None
|
||||
|
||||
# TODO - probably a better way to do this
|
||||
def live_capture_cb(cb):
|
||||
def outer(pkt):
|
||||
data = bytes(pkt)
|
||||
l = len(data)
|
||||
if l == 6972:
|
||||
cb(data)
|
||||
scapy.all.sniff(iface="enp1s0f0", filter='udp', prn=outer)
|
||||
|
||||
|
||||
def rightsize(it):
|
||||
for i, obj in enumerate(it):
|
||||
if isinstance(obj, bytes):
|
||||
l = len(obj)
|
||||
data = obj
|
||||
else:
|
||||
if not hasattr(obj, 'packet_len'):
|
||||
continue
|
||||
len = obj.packet_len
|
||||
if len != 6972:
|
||||
l = obj.packet_len
|
||||
data = obj.packet_data
|
||||
if l != 6972:
|
||||
continue
|
||||
yield obj.packet_data
|
||||
yield data
|
||||
|
||||
|
||||
def removestart(it):
|
||||
"Remove the UDP header from the packets"
|
||||
for x in it:
|
||||
yield x[0x2A:]
|
||||
yield removestart_inner(x)
|
||||
|
||||
|
||||
def removestart_inner(x):
|
||||
return x[0x2A:]
|
||||
|
||||
|
||||
# Function to parse packet data
|
||||
def parse(data):
|
||||
|
@ -70,42 +76,85 @@ def parsed(it):
|
|||
yield parse(x)
|
||||
|
||||
|
||||
class FrameCollector:
|
||||
def __init__(self):
|
||||
self.current = []
|
||||
|
||||
def handle(self, obj):
|
||||
ret = None
|
||||
if obj['part'] == 0:
|
||||
if len(self.current) > 0:
|
||||
ret = b"".join(self.current)
|
||||
self.current = []
|
||||
#otherdata = []
|
||||
self.current.append(obj["data"])
|
||||
return ret
|
||||
#otherdata.append(obj)
|
||||
|
||||
def last(self):
|
||||
if len(self.current) > 0:
|
||||
return b"".join(current)
|
||||
return None
|
||||
|
||||
|
||||
# Function to group data into frames
|
||||
def frames(it):
|
||||
current = []
|
||||
handler = FrameCollector()
|
||||
#otherdata = []
|
||||
for obj in it:
|
||||
if obj['part'] == 0:
|
||||
if len(current) > 0:
|
||||
yield b"".join(current)
|
||||
current = []
|
||||
current.append(obj["data"])
|
||||
if len(current) > 0:
|
||||
yield b"".join(current)
|
||||
ret = handler.handle(obj)
|
||||
if ret:
|
||||
yield ret
|
||||
last = handler.last()
|
||||
if last:
|
||||
yield last
|
||||
|
||||
|
||||
def iterimages(it, width, height, pixelformat=">H"):
|
||||
WIDTH = 384
|
||||
HEIGHT = 288
|
||||
|
||||
|
||||
def bad_frame(frame, width=WIDTH, height=HEIGHT):
|
||||
return len(frame) != width * height * 2 # 16 bpp
|
||||
|
||||
|
||||
def skip_bad_frames(it, width=WIDTH, height=HEIGHT):
|
||||
for frame in it:
|
||||
if len(frame) != width * height * 2: # 16 bpp
|
||||
if bad_frame(frame): # 16 bpp
|
||||
# Will be fixed when we stopped doing restarts
|
||||
#print(f'{len(frame)} != {width} * {height} * 2')
|
||||
continue
|
||||
yield frame
|
||||
|
||||
|
||||
def iterimages(it, width=WIDTH, height=HEIGHT, pixelformat=">H"):
|
||||
for frame in it:
|
||||
yield Image.fromarray(np.frombuffer(frame, dtype=pixelformat).reshape(width, height))
|
||||
|
||||
|
||||
# Get frames and convert them to images
|
||||
frames = frames(parsed(removestart(rightsize(blocks))))
|
||||
images = iterimages(it=frames, width=384, height=288)
|
||||
def process_video():
|
||||
# Now use args.input_file as the file to process
|
||||
input_file = args.input_file
|
||||
basename = os.path.splitext(os.path.basename(input_file))[0]
|
||||
stream = open(input_file, 'rb')
|
||||
# Read packets from a pcap file
|
||||
scanner = pcapng.scanner.FileScanner(stream)
|
||||
blocks = tqdm(scanner)
|
||||
|
||||
# Create the directory for frames if not exists
|
||||
frame_dir = f"frames/{basename}"
|
||||
if not os.path.exists(frame_dir):
|
||||
# Get frames and convert them to images
|
||||
frames = skip_bad_frames(frames(parsed(removestart(rightsize(blocks)))))
|
||||
|
||||
# Create the directory for frames if not exists
|
||||
frame_dir = f"frames/{basename}"
|
||||
if not os.path.exists(frame_dir):
|
||||
os.makedirs(frame_dir)
|
||||
|
||||
# Save each image as a PNG file
|
||||
for i, img in enumerate(images):
|
||||
# Save each image as a PNG file
|
||||
images = iterimages(it=frames)
|
||||
for i, img in enumerate(images):
|
||||
img.save(f'frames/{basename}/{basename}_{i:04}.png')
|
||||
|
||||
# Produce a video from the saved images
|
||||
ffmpeg_input = f"frames/{basename}/{basename}_%04d.png"
|
||||
command = [
|
||||
ffmpeg_input = f"frames/{basename}/{basename}_%04d.png"
|
||||
command = [
|
||||
"ffmpeg",
|
||||
"-y", # Overwrite output file without asking
|
||||
"-hide_banner", # Hide banner
|
||||
|
@ -115,11 +164,55 @@ command = [
|
|||
"-i", ffmpeg_input, # Input file pattern
|
||||
"-vf", "transpose=1", # Video filter for transposing
|
||||
"-s", "384x288", # Size of one frame
|
||||
"-vcodec", "libx264", # Video codec
|
||||
"-vcodec", "libopenh264", # Video codec
|
||||
"-pix_fmt", "yuv420p", # Pixel format: YUV 4:2:0
|
||||
"thermal.mp4", # Output file in MP4 container
|
||||
]
|
||||
]
|
||||
|
||||
subprocess.run(command)
|
||||
subprocess.run(command)
|
||||
print("to play: ffplay thermal.mp4")
|
||||
|
||||
|
||||
if args.live:
|
||||
# TODO: to video via ffmpeg; right now just a single png
|
||||
# of the last frame
|
||||
def todo_live_ffmpeg():
|
||||
output = 'to_ffmpeg'
|
||||
# live: write to named pipe
|
||||
if not Path(output).exists():
|
||||
print(f'making fifo at {output}')
|
||||
os.mkfifo(output)
|
||||
fd = open(output, 'wb')
|
||||
for frame in frames:
|
||||
fd.write(frame)
|
||||
|
||||
print('live stream, import scapy')
|
||||
import scapy.all
|
||||
print('open stream')
|
||||
|
||||
class PacketHandler:
|
||||
def __init__(self, cb):
|
||||
self.frame_collector = FrameCollector()
|
||||
self.cb = cb
|
||||
|
||||
def handle(self, pkt):
|
||||
pkt = removestart_inner(pkt)
|
||||
parsed = parse(pkt)
|
||||
frame_maybe = self.frame_collector.handle(parsed)
|
||||
if not frame_maybe or bad_frame(frame_maybe):
|
||||
return
|
||||
self.cb(frame_maybe)
|
||||
|
||||
progress = tqdm()
|
||||
|
||||
def on_frame(frame):
|
||||
progress.update(1)
|
||||
Image.fromarray(np.frombuffer(frame, dtype='>H').reshape(WIDTH, HEIGHT)).save(f'live.new.png')
|
||||
os.rename('live.new.png', 'live.png')
|
||||
|
||||
handler = PacketHandler(on_frame)
|
||||
live_capture_cb(handler.handle)
|
||||
|
||||
else:
|
||||
process_video()
|
||||
|
||||
print("to play: ffplay thermal.mp4")
|
||||
|
|
17
examples/replay.rs
Normal file
17
examples/replay.rs
Normal file
|
@ -0,0 +1,17 @@
|
|||
use std::net::UdpSocket;
|
||||
|
||||
fn main() -> std::io::Result<()> {
|
||||
{
|
||||
let socket = UdpSocket::bind("192.168.0.1:8091")?;
|
||||
|
||||
// Receives a single datagram message on the socket. If `buf` is too small to hold
|
||||
// the message, it will be cut off.
|
||||
let buf = [
|
||||
1, 0x20, 1, 0x80, 0x1b, 0x40, 0, 0x20, 0, 0, 0, 0, 0, 0, 0, 0x0f, 0, 0, 0, 1, 0, 0, 1,
|
||||
0, 0, 0x20, 0x2b, 0,
|
||||
];
|
||||
socket.set_broadcast(true)?;
|
||||
socket.send_to(&buf, "192.168.0.255:8092")?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
9
listen.py
Normal file
9
listen.py
Normal file
|
@ -0,0 +1,9 @@
|
|||
from socket import socket, AF_INET, SOCK_DGRAM
|
||||
|
||||
s = socket(AF_INET, SOCK_DGRAM)
|
||||
s.bind(('', 8090))
|
||||
|
||||
while True:
|
||||
d = s.recvfrom(1024)
|
||||
print(d)
|
||||
|
1
replay.py
Normal file → Executable file
1
replay.py
Normal file → Executable file
|
@ -1,3 +1,4 @@
|
|||
#!/usr/bin/env python3
|
||||
#replay the "trigger" packet.
|
||||
#this packets will start the source broadcasting its packets.
|
||||
|
||||
|
|
2
run_dhcp_server.sh
Executable file
2
run_dhcp_server.sh
Executable file
|
@ -0,0 +1,2 @@
|
|||
#!/bin/bash
|
||||
sudo dnsmasq -i enp1s0f0 --local-service --dhcp-range=192.168.0.10,192.168.0.100 --dhcp-leasefile=dhcp.lease -d
|
3
run_live.sh
Executable file
3
run_live.sh
Executable file
|
@ -0,0 +1,3 @@
|
|||
#!/bin/bash
|
||||
cd $(dirname $0)
|
||||
sudo ./venv/bin/python ./decode.py --live
|
12
src/lib.rs
12
src/lib.rs
|
@ -89,7 +89,7 @@ impl PacketsIterator {
|
|||
pub struct Header {
|
||||
c1: u32,
|
||||
c2: u16,
|
||||
part: u16,
|
||||
pub part: u16,
|
||||
a: u16,
|
||||
ffaa: u16,
|
||||
b: u16,
|
||||
|
@ -98,7 +98,7 @@ pub struct Header {
|
|||
}
|
||||
|
||||
impl Header {
|
||||
fn read(data: &[u8]) -> anyhow::Result<Self> {
|
||||
pub fn read(data: &[u8]) -> anyhow::Result<Self> {
|
||||
Ok(Header {
|
||||
c1: u32::from_be_bytes([data[0], data[1], data[2], data[3]]),
|
||||
c2: u16::from_be_bytes([data[4], data[5]]),
|
||||
|
@ -122,12 +122,12 @@ impl Header {
|
|||
}
|
||||
}
|
||||
|
||||
const HDR_SIZE: usize = std::mem::size_of::<Header>();
|
||||
pub const HDR_SIZE: usize = std::mem::size_of::<Header>();
|
||||
|
||||
pub struct Frame {
|
||||
#[allow(dead_code)]
|
||||
header: Header,
|
||||
raw: Vec<u8>,
|
||||
pub header: Header,
|
||||
pub raw: Vec<u8>,
|
||||
}
|
||||
|
||||
impl Frame {
|
||||
|
@ -184,7 +184,7 @@ impl Iterator for Decoder {
|
|||
}
|
||||
}
|
||||
|
||||
fn write_raw_frame(name: &str, data: &[u8]) -> anyhow::Result<()> {
|
||||
pub fn write_raw_frame(name: &str, data: &[u8]) -> anyhow::Result<()> {
|
||||
let path = Path::new(&name);
|
||||
let file = File::create(path)?;
|
||||
let ref mut w = BufWriter::new(file);
|
||||
|
|
30
test_rust.py
30
test_rust.py
|
@ -2,11 +2,31 @@
|
|||
from pathlib import Path
|
||||
from thermaldecoder import decode
|
||||
import numpy as np
|
||||
import subprocess
|
||||
import matplotlib.pyplot as plt
|
||||
|
||||
|
||||
# Create a directory to store the frames if it doesn't exist
|
||||
root = Path('frames')
|
||||
root.mkdir(exist_ok=True)
|
||||
frames = list(decode('in.pcap'))
|
||||
f = np.array(frames[0])
|
||||
f.shape = (384, 288)
|
||||
plt.imshow(f)
|
||||
plt.show()
|
||||
|
||||
# Decode the frames from the pcap file
|
||||
frames = list(decode('indesk.pcapng'))
|
||||
|
||||
# Iterate over the frames
|
||||
for i, frame in enumerate(frames):
|
||||
try:
|
||||
# Convert the frame to an image file
|
||||
img_path = root / f"frame_{i}.png"
|
||||
f = np.array(frame)
|
||||
f.shape = (384, 288)
|
||||
plt.imshow(f)
|
||||
plt.axis('off')
|
||||
plt.savefig(img_path, bbox_inches='tight', pad_inches=0)
|
||||
plt.close()
|
||||
|
||||
# Use ffmpeg to display the image
|
||||
subprocess.run(['ffmpeg', '-i', str(img_path), '-vf', 'scale=800:600', '-framerate', '25', '-f', 'image2pipe', '-'], check=True)
|
||||
|
||||
except ValueError as e:
|
||||
print(f"Error processing frame {i}: {e}")
|
||||
|
|
BIN
thermal.mp4
BIN
thermal.mp4
Binary file not shown.
Loading…
Reference in New Issue
Block a user