Plotting, more parameters, logs in local timezone
This commit is contained in:
parent
09891a42c9
commit
bdc817f277
3 changed files with 481 additions and 105 deletions
305
Cargo.lock
generated
305
Cargo.lock
generated
|
|
@ -11,6 +11,21 @@ dependencies = [
|
|||
"memchr",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "android-tzdata"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0"
|
||||
|
||||
[[package]]
|
||||
name = "android_system_properties"
|
||||
version = "0.1.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "anstream"
|
||||
version = "0.6.14"
|
||||
|
|
@ -47,7 +62,7 @@ version = "1.0.3"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a64c907d4e79225ac72e2a354c9ce84d50ebb4586dee56c82b3ee73004f537f5"
|
||||
dependencies = [
|
||||
"windows-sys",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
|
@ -57,7 +72,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "61a38449feb7068f52bb06c12759005cf459ee52bb4adc1d5a7c4322d716fb19"
|
||||
dependencies = [
|
||||
"anstyle",
|
||||
"windows-sys",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
|
@ -66,6 +81,12 @@ version = "1.0.86"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b3d1d046238990b9cf5bcde22a3fb3584ee5cf65fb2765f454ed428c7a0063da"
|
||||
|
||||
[[package]]
|
||||
name = "autocfg"
|
||||
version = "1.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0"
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "1.3.2"
|
||||
|
|
@ -78,6 +99,24 @@ version = "2.5.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cf4b9d6a944f767f8e5e0db018570623c85f3d925ac718db4e06d0187adb21c1"
|
||||
|
||||
[[package]]
|
||||
name = "bumpalo"
|
||||
version = "3.16.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "79296716171880943b8470b5f8d03aa55eb2e645a4874bdbb28adb49162e012c"
|
||||
|
||||
[[package]]
|
||||
name = "bytemuck"
|
||||
version = "1.16.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "78834c15cb5d5efe3452d58b1e8ba890dd62d21907f867f383358198e56ebca5"
|
||||
|
||||
[[package]]
|
||||
name = "cc"
|
||||
version = "1.0.98"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "41c270e7540d725e65ac7f1b212ac8ce349719624d7bcff99f8e2e488e8cf03f"
|
||||
|
||||
[[package]]
|
||||
name = "cfg-if"
|
||||
version = "1.0.0"
|
||||
|
|
@ -90,6 +129,20 @@ version = "0.1.1"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "fd16c4719339c4530435d38e511904438d07cce7950afa3718a84ac36c10e89e"
|
||||
|
||||
[[package]]
|
||||
name = "chrono"
|
||||
version = "0.4.38"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a21f936df1771bf62b77f047b726c4625ff2e8aa607c01ec06e5a05bd8463401"
|
||||
dependencies = [
|
||||
"android-tzdata",
|
||||
"iana-time-zone",
|
||||
"js-sys",
|
||||
"num-traits",
|
||||
"wasm-bindgen",
|
||||
"windows-targets 0.52.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "clap"
|
||||
version = "4.5.4"
|
||||
|
|
@ -136,6 +189,16 @@ version = "1.0.1"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0b6a852b24ab71dffc585bcb46eaf7959d175cb865a7152e35b348d1b2960422"
|
||||
|
||||
[[package]]
|
||||
name = "colored"
|
||||
version = "2.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cbf2150cce219b664a8a70df7a1f933836724b503f8a413af9365b4dcc4d90b8"
|
||||
dependencies = [
|
||||
"lazy_static",
|
||||
"windows-sys 0.48.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "core-foundation-sys"
|
||||
version = "0.8.6"
|
||||
|
|
@ -164,7 +227,17 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|||
checksum = "672465ae37dc1bc6380a6547a8883d5dd397b0f1faaad4f265726cc7042a5345"
|
||||
dependencies = [
|
||||
"nix 0.28.0",
|
||||
"windows-sys",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "drawille"
|
||||
version = "0.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e64e461c3f1e69d99372620640b3fd5f0309eeda2e26e4af69f6760c0e1df845"
|
||||
dependencies = [
|
||||
"colored",
|
||||
"fnv",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
|
@ -190,18 +263,27 @@ dependencies = [
|
|||
"log",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fnv"
|
||||
version = "1.0.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
|
||||
|
||||
[[package]]
|
||||
name = "hailsens_logger"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"chrono",
|
||||
"clap",
|
||||
"colored",
|
||||
"crc",
|
||||
"ctrlc",
|
||||
"env_logger",
|
||||
"hound",
|
||||
"log",
|
||||
"serialport",
|
||||
"textplots",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
|
@ -222,6 +304,29 @@ version = "2.1.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4"
|
||||
|
||||
[[package]]
|
||||
name = "iana-time-zone"
|
||||
version = "0.1.60"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e7ffbb5a1b541ea2561f8c41c087286cc091e21e556a4f09a8f6cbf17b69b141"
|
||||
dependencies = [
|
||||
"android_system_properties",
|
||||
"core-foundation-sys",
|
||||
"iana-time-zone-haiku",
|
||||
"js-sys",
|
||||
"wasm-bindgen",
|
||||
"windows-core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "iana-time-zone-haiku"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f"
|
||||
dependencies = [
|
||||
"cc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "io-kit-sys"
|
||||
version = "0.4.1"
|
||||
|
|
@ -238,6 +343,21 @@ version = "1.70.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f8478577c03552c21db0e2724ffb8986a5ce7af88107e6be5d2ee6e158c12800"
|
||||
|
||||
[[package]]
|
||||
name = "js-sys"
|
||||
version = "0.3.69"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "29c15563dc2726973df627357ce0c9ddddbea194836909d655df6a75d2cf296d"
|
||||
dependencies = [
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "lazy_static"
|
||||
version = "1.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
|
||||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.155"
|
||||
|
|
@ -288,6 +408,21 @@ dependencies = [
|
|||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num-traits"
|
||||
version = "0.2.19"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "071dfc062690e90b734c0b2273ce72ad0ffa95f0c74596bc250dcfd960262841"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.19.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3fdb12b2476b595f9358c5161aa467c2438859caa136dec86c26fdd2efe17b92"
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.83"
|
||||
|
|
@ -335,6 +470,15 @@ version = "0.8.3"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "adad44e29e4c806119491a7f06f03de4d1af22c3a680dd47f1e6e179439d1f56"
|
||||
|
||||
[[package]]
|
||||
name = "rgb"
|
||||
version = "0.8.37"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "05aaa8004b64fd573fc9d002f4e632d51ad4f026c2b5ba95fcb6c2f32c2c47d8"
|
||||
dependencies = [
|
||||
"bytemuck",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "scopeguard"
|
||||
version = "1.2.0"
|
||||
|
|
@ -376,6 +520,16 @@ dependencies = [
|
|||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "textplots"
|
||||
version = "0.8.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f59b64803118dbff62f92842b3154a2c802dfd8e18660132bbcbfb141c637ae3"
|
||||
dependencies = [
|
||||
"drawille",
|
||||
"rgb",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror"
|
||||
version = "1.0.61"
|
||||
|
|
@ -417,6 +571,60 @@ version = "0.2.1"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a"
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen"
|
||||
version = "0.2.92"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4be2531df63900aeb2bca0daaaddec08491ee64ceecbee5076636a3b026795a8"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"wasm-bindgen-macro",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-backend"
|
||||
version = "0.2.92"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "614d787b966d3989fa7bb98a654e369c762374fd3213d212cfc0251257e747da"
|
||||
dependencies = [
|
||||
"bumpalo",
|
||||
"log",
|
||||
"once_cell",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"wasm-bindgen-shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-macro"
|
||||
version = "0.2.92"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a1f8823de937b71b9460c0c34e25f3da88250760bec0ebac694b49997550d726"
|
||||
dependencies = [
|
||||
"quote",
|
||||
"wasm-bindgen-macro-support",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-macro-support"
|
||||
version = "0.2.92"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e94f17b526d0a461a191c78ea52bbce64071ed5c04c9ffe424dcb38f74171bb7"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"wasm-bindgen-backend",
|
||||
"wasm-bindgen-shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-shared"
|
||||
version = "0.2.92"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "af190c94f2773fdb3729c55b007a722abb5384da03bc0986df4c289bf5567e96"
|
||||
|
||||
[[package]]
|
||||
name = "winapi"
|
||||
version = "0.3.9"
|
||||
|
|
@ -439,13 +647,46 @@ version = "0.4.0"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
|
||||
|
||||
[[package]]
|
||||
name = "windows-core"
|
||||
version = "0.52.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "33ab640c8d7e35bf8ba19b884ba838ceb4fba93a4e8c65a9059d08afcfc683d9"
|
||||
dependencies = [
|
||||
"windows-targets 0.52.5",
|
||||
]
|
||||
|
||||
[[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-sys"
|
||||
version = "0.52.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d"
|
||||
dependencies = [
|
||||
"windows-targets",
|
||||
"windows-targets 0.52.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows-targets"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm 0.48.5",
|
||||
"windows_aarch64_msvc 0.48.5",
|
||||
"windows_i686_gnu 0.48.5",
|
||||
"windows_i686_msvc 0.48.5",
|
||||
"windows_x86_64_gnu 0.48.5",
|
||||
"windows_x86_64_gnullvm 0.48.5",
|
||||
"windows_x86_64_msvc 0.48.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
|
@ -454,28 +695,46 @@ version = "0.52.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6f0713a46559409d202e70e28227288446bf7841d3211583a4b53e3f6d96e7eb"
|
||||
dependencies = [
|
||||
"windows_aarch64_gnullvm",
|
||||
"windows_aarch64_msvc",
|
||||
"windows_i686_gnu",
|
||||
"windows_aarch64_gnullvm 0.52.5",
|
||||
"windows_aarch64_msvc 0.52.5",
|
||||
"windows_i686_gnu 0.52.5",
|
||||
"windows_i686_gnullvm",
|
||||
"windows_i686_msvc",
|
||||
"windows_x86_64_gnu",
|
||||
"windows_x86_64_gnullvm",
|
||||
"windows_x86_64_msvc",
|
||||
"windows_i686_msvc 0.52.5",
|
||||
"windows_x86_64_gnu 0.52.5",
|
||||
"windows_x86_64_gnullvm 0.52.5",
|
||||
"windows_x86_64_msvc 0.52.5",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_gnullvm"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7088eed71e8b8dda258ecc8bac5fb1153c5cffaf2578fc8ff5d61e23578d3263"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc"
|
||||
|
||||
[[package]]
|
||||
name = "windows_aarch64_msvc"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9985fd1504e250c615ca5f281c3f7a6da76213ebd5ccc9561496568a2752afb6"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_gnu"
|
||||
version = "0.52.5"
|
||||
|
|
@ -488,24 +747,48 @@ version = "0.52.5"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "87f4261229030a858f36b459e748ae97545d6f1ec60e5e0d6a3d32e0dc232ee9"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406"
|
||||
|
||||
[[package]]
|
||||
name = "windows_i686_msvc"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "db3c2bf3d13d5b658be73463284eaf12830ac9a26a90c717b7f771dfe97487bf"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnu"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4e4246f76bdeff09eb48875a0fd3e2af6aada79d409d33011886d3e1581517d9"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_gnullvm"
|
||||
version = "0.52.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "852298e482cd67c356ddd9570386e2862b5673c85bd5f88df9ab6802b334c596"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.48.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538"
|
||||
|
||||
[[package]]
|
||||
name = "windows_x86_64_msvc"
|
||||
version = "0.52.5"
|
||||
|
|
|
|||
|
|
@ -7,8 +7,11 @@ edition = "2021"
|
|||
serialport = {version="4.3.0", default-features=false}
|
||||
log = "0.4.21"
|
||||
env_logger = "0.11.3"
|
||||
chrono = "0.4"
|
||||
colored = "2.1.0"
|
||||
hound = "3.5.1"
|
||||
clap = { version = "4.5.4", features = ["derive"] }
|
||||
ctrlc = "3.2.0"
|
||||
anyhow = "1.0.86"
|
||||
crc = "3.2.1"
|
||||
textplots = "0.8.6"
|
||||
|
|
|
|||
278
src/main.rs
278
src/main.rs
|
|
@ -1,8 +1,10 @@
|
|||
use anyhow::{Context, Result};
|
||||
use chrono::Local;
|
||||
use clap::{arg, Parser};
|
||||
use crc::{Crc, CRC_16_IBM_3740};
|
||||
use env_logger::Builder;
|
||||
use hound::{SampleFormat, WavSpec, WavWriter};
|
||||
use log::{debug, error, info, trace, warn, LevelFilter};
|
||||
use log::{debug, error, info, trace, warn, Level, LevelFilter};
|
||||
use serialport::SerialPort;
|
||||
use std::collections::HashMap;
|
||||
use std::io::{BufRead, BufReader, Read, Write};
|
||||
|
|
@ -12,9 +14,28 @@ use std::sync::atomic::{AtomicBool, Ordering};
|
|||
use std::sync::Arc;
|
||||
use std::time::Duration;
|
||||
use std::time::{SystemTime, UNIX_EPOCH};
|
||||
use textplots::{Chart, Plot, Shape};
|
||||
|
||||
const MAX_DATA_LEN: usize = 1024 * 2 + 4 + 2;
|
||||
|
||||
#[derive(Debug, Clone, Copy)]
|
||||
struct Stats {
|
||||
goert_since_startup: u32,
|
||||
goert_in_10min: u32,
|
||||
amp_since_startup: u32,
|
||||
amp_in_10min: u32,
|
||||
}
|
||||
|
||||
impl Stats {
|
||||
fn eq(&self, other: &Self, noise_logging: bool) -> bool {
|
||||
let hail_cmp = (self.goert_in_10min == other.goert_in_10min)
|
||||
&& (self.goert_since_startup == other.goert_since_startup);
|
||||
let noise_cmp = (self.amp_in_10min == other.amp_in_10min)
|
||||
&& (self.amp_since_startup == other.amp_since_startup);
|
||||
hail_cmp && (!noise_logging || noise_cmp)
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Parser, Debug)]
|
||||
#[command(name = "Hailsens Logger", version, about, long_about = None)]
|
||||
struct Args {
|
||||
|
|
@ -27,18 +48,33 @@ struct Args {
|
|||
#[arg(short, long, default_value_t = 115_200)]
|
||||
baud_rate: u32,
|
||||
|
||||
#[arg(long)]
|
||||
adcthresh: Option<u32>,
|
||||
#[arg(long, help = "Goertzel threshold")]
|
||||
goert_thresh: Option<u32>,
|
||||
|
||||
#[arg(long, help = "Amplitude threshold")]
|
||||
amp_thresh: Option<u32>,
|
||||
|
||||
#[arg(long)]
|
||||
winsize: Option<u32>,
|
||||
|
||||
#[arg(short = 's', help = "Save data to wav files")]
|
||||
save_to_wav: bool,
|
||||
|
||||
#[arg(long = "plot", help = "Plot data")]
|
||||
plot_data: bool,
|
||||
|
||||
#[arg(long, default_value_t = 5, help = "Value in Hz")]
|
||||
request_rate: u32,
|
||||
|
||||
#[arg(short = 'f', long)]
|
||||
first_sample: bool,
|
||||
|
||||
#[arg(short = 'r', long)]
|
||||
reset_counters: bool,
|
||||
|
||||
#[arg(short = 'n', long)]
|
||||
noise_logging: bool,
|
||||
|
||||
#[arg(long, default_value = "wave")]
|
||||
name: String,
|
||||
|
||||
|
|
@ -56,9 +92,22 @@ fn main() {
|
|||
1 => LevelFilter::Debug,
|
||||
_ => LevelFilter::Trace,
|
||||
};
|
||||
env_logger::builder()
|
||||
.filter_level(log_level)
|
||||
.format_timestamp_millis()
|
||||
let mut builder = Builder::new();
|
||||
builder
|
||||
.format(|buf, record| {
|
||||
use colored::*;
|
||||
let timestamp = Local::now().format("%Y-%m-%d %H:%M:%S,%3f");
|
||||
let level = match record.level() {
|
||||
Level::Error => "ERROR".red(),
|
||||
Level::Warn => "WARN".yellow(),
|
||||
Level::Info => "INFO".green(),
|
||||
Level::Debug => "DEBUG".blue(),
|
||||
Level::Trace => "TRACE".purple(),
|
||||
};
|
||||
|
||||
writeln!(buf, "{} [{}] - {}", timestamp, level, record.args())
|
||||
})
|
||||
.filter(None, log_level)
|
||||
.init();
|
||||
|
||||
assert!(
|
||||
|
|
@ -88,11 +137,49 @@ fn main() {
|
|||
panic!("Couldn't detect hailsens!")
|
||||
}
|
||||
|
||||
get_set_threshold(&mut port, args.device_id, args.adcthresh).expect("Couldn't get threshold");
|
||||
let winsize = get_set_winsize(&mut port, args.device_id, args.winsize)
|
||||
.expect("Couldn't get winsize") as usize;
|
||||
get_set_param(
|
||||
&mut port,
|
||||
args.device_id,
|
||||
args.goert_thresh,
|
||||
"goertthresh",
|
||||
"Goertzel threshold",
|
||||
)
|
||||
.expect("Couldn't get Goertzel threshold");
|
||||
get_set_param(
|
||||
&mut port,
|
||||
args.device_id,
|
||||
args.amp_thresh,
|
||||
"ampthresh",
|
||||
"amplitude threshold",
|
||||
)
|
||||
.expect("Couldn't get amplitude threshold");
|
||||
let winsize = get_set_param(
|
||||
&mut port,
|
||||
args.device_id,
|
||||
args.winsize,
|
||||
"winsize",
|
||||
"window size",
|
||||
)
|
||||
.expect("Couldn't get winsize") as usize;
|
||||
debug!("Expected buf size is: {}", exp_buf_size(winsize));
|
||||
|
||||
info!("Setting correct date/time on hailsens...");
|
||||
let formatted_date_time = Local::now().format("%Y-%m-%dT%H:%M:%S").to_string();
|
||||
let request_str = format!("@{} date {}\n", args.device_id, formatted_date_time);
|
||||
let response = process_command(&mut port, request_str).expect("Couldn't set date/time!");
|
||||
info!(
|
||||
"Hailsens date/time: {}",
|
||||
response
|
||||
.split_whitespace()
|
||||
.nth(1)
|
||||
.expect("Couldn't get date/time!")
|
||||
);
|
||||
|
||||
if args.reset_counters {
|
||||
info!("Resetting counters...");
|
||||
process_command(&mut port, format!("@{} rstcnt\n", args.device_id));
|
||||
}
|
||||
|
||||
let spec = WavSpec {
|
||||
channels: 1,
|
||||
sample_rate: get_sample_rate(&mut port, args.device_id),
|
||||
|
|
@ -111,8 +198,10 @@ fn main() {
|
|||
.unwrap();
|
||||
debug!("Press Ctrl-C to stop");
|
||||
|
||||
let mut last_chunk_id: Option<u32> = None;
|
||||
let mut last_chunk_id: Option<Stats> = None;
|
||||
let mut err_counter: u32 = 0;
|
||||
let samples_needed = args.save_to_wav || args.plot_data;
|
||||
let mut needed_retry = false;
|
||||
|
||||
while running.load(Ordering::SeqCst) {
|
||||
// getting stats
|
||||
|
|
@ -127,48 +216,70 @@ fn main() {
|
|||
value
|
||||
}
|
||||
};
|
||||
if (last_chunk_id != Some(cur_chunk_id) && last_chunk_id.is_some())
|
||||
|| (args.first_sample && last_chunk_id.is_none())
|
||||
{
|
||||
debug!("New data available: {}", cur_chunk_id);
|
||||
debug!("Getting new chunk!");
|
||||
match get_chunk(&mut port, args.device_id, args.baud_rate, winsize) {
|
||||
Some(data) => {
|
||||
debug!("Received new data with len: {}", data.len());
|
||||
|
||||
let timestamp_ms = current_timestamp_ms();
|
||||
let path = Path::new(&args.path);
|
||||
let filename = format!("{}_{}.wav", args.name, timestamp_ms);
|
||||
let path = path.join(filename);
|
||||
|
||||
// Create a new WAV file
|
||||
let mut writer =
|
||||
WavWriter::create(&path, spec).expect("Can't create new WAV file!");
|
||||
let mut i16_writer = writer.get_i16_writer(data.len() as u32);
|
||||
for sample in data {
|
||||
unsafe {
|
||||
i16_writer.write_sample_unchecked(sample);
|
||||
}
|
||||
}
|
||||
i16_writer
|
||||
.flush()
|
||||
.expect("Something went wrong while writing WAV file");
|
||||
info!(
|
||||
"Sample: {cur_chunk_id}. WAV file {} has been written.",
|
||||
path.display()
|
||||
);
|
||||
|
||||
err_counter = err_counter.saturating_sub(1);
|
||||
last_chunk_id = Some(cur_chunk_id);
|
||||
if last_chunk_id.map_or(true, |v| !v.eq(&cur_chunk_id, args.noise_logging)) {
|
||||
info!(
|
||||
"Hail detected (total/10 min): {}/{}. Noise detected (total/10 min): {}/{}.",
|
||||
cur_chunk_id.goert_since_startup,
|
||||
cur_chunk_id.goert_in_10min,
|
||||
cur_chunk_id.amp_since_startup,
|
||||
cur_chunk_id.amp_in_10min
|
||||
);
|
||||
if samples_needed && (last_chunk_id.is_some() || args.first_sample) {
|
||||
if needed_retry {
|
||||
info!("Retrying...");
|
||||
} else {
|
||||
debug!("New data available: {}", cur_chunk_id.goert_since_startup);
|
||||
debug!("Getting new chunk!");
|
||||
}
|
||||
_ => {
|
||||
error!("Couldn't receive new data!");
|
||||
handle_error_with_timeout(&mut err_counter);
|
||||
match get_chunk(&mut port, args.device_id, args.baud_rate, winsize) {
|
||||
Some(data) => {
|
||||
debug!("Received new data with len: {}", data.len());
|
||||
|
||||
if args.plot_data {
|
||||
let points: Vec<(f32, f32)> = data.iter()
|
||||
.enumerate()
|
||||
.map(|(i, &x)| (i as f32, x as f32))
|
||||
.collect();
|
||||
Chart::new(280, 50, 0.0, 100.0).lineplot(&Shape::Lines(&points)).display();
|
||||
}
|
||||
|
||||
if args.save_to_wav {
|
||||
let path = Path::new(&args.path);
|
||||
let filename = format!("{}_{}.wav", args.name, current_timestamp_ms());
|
||||
let path = path.join(filename);
|
||||
|
||||
// Create a new WAV file
|
||||
let mut writer =
|
||||
WavWriter::create(&path, spec).expect("Can't create new WAV file!");
|
||||
let mut i16_writer = writer.get_i16_writer(data.len() as u32);
|
||||
for sample in data {
|
||||
unsafe {
|
||||
i16_writer.write_sample_unchecked(sample);
|
||||
}
|
||||
}
|
||||
i16_writer
|
||||
.flush()
|
||||
.expect("Something went wrong while writing WAV file");
|
||||
info!(
|
||||
"Sample: {}. WAV file {} has been written.",
|
||||
cur_chunk_id.goert_since_startup,
|
||||
path.display()
|
||||
);
|
||||
}
|
||||
|
||||
err_counter = err_counter.saturating_sub(1);
|
||||
needed_retry = false;
|
||||
}
|
||||
_ => {
|
||||
error!("Couldn't receive new data!");
|
||||
handle_error_with_timeout(&mut err_counter);
|
||||
needed_retry = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if !args.first_sample && last_chunk_id.is_none() {
|
||||
last_chunk_id = Some(cur_chunk_id)
|
||||
if !needed_retry {
|
||||
last_chunk_id = Some(cur_chunk_id);
|
||||
}
|
||||
std::thread::sleep(Duration::from_millis((1000 / args.request_rate) as u64));
|
||||
}
|
||||
|
|
@ -183,63 +294,42 @@ fn handle_error_with_timeout(err_counter: &mut u32) {
|
|||
std::thread::sleep(Duration::from_millis(100));
|
||||
}
|
||||
|
||||
fn get_stats(port: &mut Box<dyn SerialPort>, id: u32) -> Result<u32> {
|
||||
fn get_stats(port: &mut Box<dyn SerialPort>, id: u32) -> Result<Stats> {
|
||||
let command = format!("@{} adcstats\n", id);
|
||||
let response = process_command(port, command).unwrap_or_default();
|
||||
let mut split = response.split_whitespace();
|
||||
let num_since_startup: u32 = split.next().context("Missing value")?.parse()?;
|
||||
let _num_since_last_read: u32 = split.next().context("Missing value")?.parse()?;
|
||||
let _num_in_10min: u32 = split.next().context("Missing value")?.parse()?;
|
||||
trace!("Got num_since_startup: {}", num_since_startup);
|
||||
Ok(num_since_startup)
|
||||
let goert_since_startup: u32 = split.next().context("Missing value")?.parse()?;
|
||||
let goert_in_10min: u32 = split.next().context("Missing value")?.parse()?;
|
||||
let amp_since_startup: u32 = split.next().context("Missing value")?.parse()?;
|
||||
let amp_in_10min: u32 = split.next().context("Missing value")?.parse()?;
|
||||
Ok(Stats {
|
||||
goert_since_startup,
|
||||
goert_in_10min,
|
||||
amp_since_startup,
|
||||
amp_in_10min,
|
||||
})
|
||||
}
|
||||
|
||||
fn get_set_winsize(
|
||||
fn get_set_param(
|
||||
port: &mut Box<dyn SerialPort>,
|
||||
id: u32,
|
||||
new_winsize: Option<u32>,
|
||||
new_param: Option<u32>,
|
||||
cmd: &str,
|
||||
debug_name: &str,
|
||||
) -> Option<u32> {
|
||||
let command;
|
||||
if let Some(i) = new_winsize {
|
||||
debug!("Setting new winsize: {i}");
|
||||
command = format!("@{id} winsize {i}\n");
|
||||
} else {
|
||||
command = format!("@{} winsize\n", id);
|
||||
let mut request_str = format!("@{id} {cmd}");
|
||||
if let Some(i) = new_param {
|
||||
debug!("Setting new {debug_name}: {i}");
|
||||
request_str.push_str(&format!(" {i}"))
|
||||
}
|
||||
debug!("Getting window size...");
|
||||
let response = process_command(port, command).unwrap_or_default();
|
||||
let winsize_str = response.split_whitespace().nth(3);
|
||||
match winsize_str {
|
||||
request_str.push('\n');
|
||||
debug!("Getting {debug_name}...");
|
||||
let response = process_command(port, request_str).unwrap_or_default();
|
||||
let result_str = response.split_whitespace().nth(3);
|
||||
match result_str {
|
||||
Some(num_str) => {
|
||||
if let Ok(number) = num_str.parse::<u32>() {
|
||||
info!("The current window size is: {}", number);
|
||||
Some(number)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
}
|
||||
None => None,
|
||||
}
|
||||
}
|
||||
|
||||
fn get_set_threshold(
|
||||
port: &mut Box<dyn SerialPort>,
|
||||
id: u32,
|
||||
new_threshold: Option<u32>,
|
||||
) -> Option<u32> {
|
||||
let command;
|
||||
if let Some(i) = new_threshold {
|
||||
debug!("Setting new threshold: {i}");
|
||||
command = format!("@{id} adcthresh {i}\n");
|
||||
} else {
|
||||
command = format!("@{} adcthresh\n", id);
|
||||
}
|
||||
let response = process_command(port, command).unwrap_or_default();
|
||||
let number_str = response.split_whitespace().nth(3);
|
||||
match number_str {
|
||||
Some(num_str) => {
|
||||
if let Ok(number) = num_str.parse::<u32>() {
|
||||
info!("The current Goertzel threshold is: {}", number);
|
||||
info!("The current {debug_name} is: {number}",);
|
||||
Some(number)
|
||||
} else {
|
||||
None
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue