From ec45fba0e746896b07c80943ed5f651be2421b34 Mon Sep 17 00:00:00 2001 From: Stephen D <webmaster@scd31.com> Date: Thu, 30 Nov 2023 07:58:31 -0400 Subject: [PATCH] randomized tx timings --- Cargo.lock | 203 ++++++++++++++++++++++++++++++++++----------------- Cargo.toml | 1 + src/gate.rs | 85 ++++++++++++--------- src/main.rs | 9 ++- src/radio.rs | 128 ++++++++++++++++++++------------ src/util.rs | 135 ++-------------------------------- 6 files changed, 282 insertions(+), 279 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index c369378..c1304bf 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -76,7 +76,7 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b" dependencies = [ - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -86,7 +86,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f0699d10d2f4d628a98ee7b57b289abbc98ff3bad977cb3152709d4bf2330628" dependencies = [ "anstyle", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -275,7 +275,8 @@ dependencies = [ "futures-core", "half", "ham-cats", - "prost 0.12.2", + "prost 0.12.3", + "rand", "rf4463", "rppal", "serde", @@ -313,14 +314,14 @@ dependencies = [ "iana-time-zone", "num-traits", "serde", - "windows-targets", + "windows-targets 0.48.5", ] [[package]] name = "clap" -version = "4.4.8" +version = "4.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2275f18819641850fa26c89acc84d465c1bf91ce57bc2748b28c420473352f64" +checksum = "41fffed7514f420abec6d183b1d3acfd9099c79c3a10a06ade4f8203f1411272" dependencies = [ "clap_builder", "clap_derive", @@ -328,9 +329,9 @@ dependencies = [ [[package]] name = "clap_builder" -version = "4.4.8" +version = "4.4.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07cdf1b148b25c1e1f7a42225e30a0d99a615cd4637eae7365548dd4529b95bc" +checksum = "63361bae7eef3771745f02d8d892bec2fee5f6e34af316ba556e7f97a7069ff1" dependencies = [ "anstream", "anstyle", @@ -370,7 +371,7 @@ checksum = "2674ec482fbc38012cf31e6c42ba0177b431a0cb6f15fe40efa5aab1bda516f6" dependencies = [ "is-terminal", "lazy_static", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -510,12 +511,12 @@ checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5" [[package]] name = "errno" -version = "0.3.7" +version = "0.3.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f258a7194e7f7c2a7837a8913aeab7fd8c383457034fa20ce4dd3dcb813e8eb8" +checksum = "a258e46cdc063eb8519c00b9fc845fc47bcfca4130e2f08e88665ceda8474245" dependencies = [ "libc", - "windows-sys", + "windows-sys 0.52.0", ] [[package]] @@ -594,9 +595,9 @@ dependencies = [ [[package]] name = "gimli" -version = "0.28.0" +version = "0.28.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" +checksum = "4271d37baee1b8c7e4b708028c57d816cf9d2434acb33a549475f78c181f6253" [[package]] name = "h2" @@ -630,7 +631,7 @@ dependencies = [ [[package]] name = "ham-cats" version = "0.1.0" -source = "git+https://gitlab.scd31.com/cats/ham-cats#d32d0a72f3e5633a25cc6495b2fe7daed139fc84" +source = "git+https://gitlab.scd31.com/cats/ham-cats#cccc04c1c96ebe64681a59d9c2a7c66e00418067" dependencies = [ "arrayvec", "bitvec", @@ -650,9 +651,9 @@ checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" [[package]] name = "hashbrown" -version = "0.14.2" +version = "0.14.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f93e7192158dbcda357bdec5fb5788eebf8bbac027f3f33e719d29135ae84156" +checksum = "290f1a1d9242c78d09ce40a5e87e7554ee637af1351968159f4952f028f75604" [[package]] name = "heck" @@ -678,7 +679,7 @@ version = "0.5.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5444c27eef6923071f7ebcc33e3444508466a76f7a2b93da00ed6e19f30c1ddb" dependencies = [ - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -798,7 +799,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d530e1a18b1cb4c484e6e34556a0d948706958449fca0cab753d649f2bce3d1f" dependencies = [ "equivalent", - "hashbrown 0.14.2", + "hashbrown 0.14.3", "serde", ] @@ -810,7 +811,7 @@ checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b" dependencies = [ "hermit-abi", "rustix", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -839,9 +840,9 @@ checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38" [[package]] name = "js-sys" -version = "0.3.65" +version = "0.3.66" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "54c0c35952f67de54bb584e9fd912b3023117cbafc0a77d8f3dee1fb5f572fe8" +checksum = "cee9c64da59eae3b50095c18d3e74f8b73c0b86d2792824ff01bbce68ba229ca" dependencies = [ "wasm-bindgen", ] @@ -911,7 +912,7 @@ checksum = "3dce281c5e46beae905d4de1870d8b1509a9142b62eedf18b443b011ca8343d0" dependencies = [ "libc", "wasi", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -983,9 +984,9 @@ checksum = "de3145af08024dea9fa9914f381a17b8fc6034dfb00f3a84013f7ff43f29ed4c" [[package]] name = "percent-encoding" -version = "2.3.0" +version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" +checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" [[package]] name = "petgraph" @@ -1053,9 +1054,9 @@ dependencies = [ [[package]] name = "proc-macro2" -version = "1.0.69" +version = "1.0.70" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "134c189feb4956b20f6f547d2cf727d4c0fe06722b20a0eec87ed445a97f92da" +checksum = "39278fbbf5fb4f646ce651690877f89d1c5811a3d4acb27700c1cb3cdb78fd3b" dependencies = [ "unicode-ident", ] @@ -1072,12 +1073,12 @@ dependencies = [ [[package]] name = "prost" -version = "0.12.2" +version = "0.12.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5a5a410fc7882af66deb8d01d01737353cf3ad6204c408177ba494291a626312" +checksum = "146c289cda302b98a28d40c8b3b90498d6e526dd24ac2ecea73e4e491685b94a" dependencies = [ "bytes", - "prost-derive 0.12.2", + "prost-derive 0.12.3", ] [[package]] @@ -1117,9 +1118,9 @@ dependencies = [ [[package]] name = "prost-derive" -version = "0.12.2" +version = "0.12.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "065717a5dfaca4a83d2fe57db3487b311365200000551d7a364e715dbf4346bc" +checksum = "efb6c9a1dd1def8e2124d17e83a20af56f1570d6c2d2bd9e266ccb768df3840e" dependencies = [ "anyhow", "itertools 0.11.0", @@ -1230,16 +1231,16 @@ dependencies = [ [[package]] name = "ring" -version = "0.17.5" +version = "0.17.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fb0205304757e5d899b9c2e448b867ffd03ae7f988002e47cd24954391394d0b" +checksum = "684d5e6e18f669ccebf64a92236bb7db9a34f07be010e3627368182027180866" dependencies = [ "cc", "getrandom", "libc", "spin", "untrusted", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -1265,15 +1266,15 @@ checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" [[package]] name = "rustix" -version = "0.38.24" +version = "0.38.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ad981d6c340a49cdc40a1028d9c6084ec7e9fa33fcb839cab656a267071e234" +checksum = "dc99bc2d4f1fed22595588a013687477aedf3cdcfb26558c559edb67b4d9b22e" dependencies = [ "bitflags 2.4.1", "errno", "libc", "linux-raw-sys", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -1337,7 +1338,7 @@ version = "0.1.22" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0c3733bf4cf7ea0880754e19cb5a462007c4a8c1914bff372ccc95b464f1df88" dependencies = [ - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -1375,18 +1376,18 @@ dependencies = [ [[package]] name = "serde" -version = "1.0.192" +version = "1.0.193" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bca2a08484b285dcb282d0f67b26cadc0df8b19f8c12502c13d966bf9482f001" +checksum = "25dd9975e68d0cb5aa1120c288333fc98731bd1dd12f561e468ea4728c042b89" dependencies = [ "serde_derive", ] [[package]] name = "serde_derive" -version = "1.0.192" +version = "1.0.193" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d6c7207fbec9faa48073f3e3074cbe553af6ea512d7c21ba46e434e70ea9fbc1" +checksum = "43576ca501357b9b071ac53cdc7da8ef0cbd9493d8df094cd821777ea6e894d3" dependencies = [ "proc-macro2", "quote", @@ -1490,7 +1491,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7b5fac59a5cb5dd637972e5fca70daf0523c9067fcdc4842f053dae04a18f8e9" dependencies = [ "libc", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -1559,7 +1560,7 @@ dependencies = [ "fastrand", "redox_syscall", "rustix", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -1605,7 +1606,7 @@ dependencies = [ "pin-project-lite", "socket2 0.5.5", "tokio-macros", - "windows-sys", + "windows-sys 0.48.0", ] [[package]] @@ -1716,7 +1717,7 @@ dependencies = [ "hyper-timeout", "percent-encoding", "pin-project", - "prost 0.12.2", + "prost 0.12.3", "rustls", "rustls-native-certs", "rustls-pemfile", @@ -1831,9 +1832,9 @@ checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" [[package]] name = "uuid" -version = "1.5.0" +version = "1.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "88ad59a7560b41a70d191093a945f0b87bc1deeda46fb237479708a1d6b6cdfc" +checksum = "5e395fcf16a7a3d8127ec99782007af141946b4795001f876d54fb0d55978560" dependencies = [ "getrandom", ] @@ -1861,9 +1862,9 @@ checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" [[package]] name = "wasm-bindgen" -version = "0.2.88" +version = "0.2.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7daec296f25a1bae309c0cd5c29c4b260e510e6d813c286b19eaadf409d40fce" +checksum = "0ed0d4f68a3015cc185aff4db9506a015f4b96f95303897bfa23f846db54064e" dependencies = [ "cfg-if", "wasm-bindgen-macro", @@ -1871,9 +1872,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-backend" -version = "0.2.88" +version = "0.2.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e397f4664c0e4e428e8313a469aaa58310d302159845980fd23b0f22a847f217" +checksum = "1b56f625e64f3a1084ded111c4d5f477df9f8c92df113852fa5a374dbda78826" dependencies = [ "bumpalo", "log", @@ -1886,9 +1887,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro" -version = "0.2.88" +version = "0.2.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5961017b3b08ad5f3fe39f1e79877f8ee7c23c5e5fd5eb80de95abc41f1f16b2" +checksum = "0162dbf37223cd2afce98f3d0785506dcb8d266223983e4b5b525859e6e182b2" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -1896,9 +1897,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.88" +version = "0.2.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c5353b8dab669f5e10f5bd76df26a9360c748f054f862ff5f3f8aae0c7fb3907" +checksum = "f0eb82fcb7930ae6219a7ecfd55b217f5f0893484b7a13022ebb2b2bf20b5283" dependencies = [ "proc-macro2", "quote", @@ -1909,9 +1910,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-shared" -version = "0.2.88" +version = "0.2.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d046c5d029ba91a1ed14da14dca44b68bf2f124cfbaf741c54151fdb3e0750b" +checksum = "7ab9b36309365056cd639da3134bf87fa8f3d86008abf99e612384a6eecd459f" [[package]] name = "which" @@ -1953,7 +1954,7 @@ version = "0.51.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f1f8cf84f35d2db49a46868f947758c7a1138116f7fac3bc844f43ade1292e64" dependencies = [ - "windows-targets", + "windows-targets 0.48.5", ] [[package]] @@ -1962,7 +1963,16 @@ version = "0.48.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" dependencies = [ - "windows-targets", + "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 0.52.0", ] [[package]] @@ -1971,13 +1981,28 @@ version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c" dependencies = [ - "windows_aarch64_gnullvm", - "windows_aarch64_msvc", - "windows_i686_gnu", - "windows_i686_msvc", - "windows_x86_64_gnu", - "windows_x86_64_gnullvm", - "windows_x86_64_msvc", + "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]] +name = "windows-targets" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8a18201040b24831fbb9e4eb208f8892e1f50a37feb53cc7ff887feb8f50e7cd" +dependencies = [ + "windows_aarch64_gnullvm 0.52.0", + "windows_aarch64_msvc 0.52.0", + "windows_i686_gnu 0.52.0", + "windows_i686_msvc 0.52.0", + "windows_x86_64_gnu 0.52.0", + "windows_x86_64_gnullvm 0.52.0", + "windows_x86_64_msvc 0.52.0", ] [[package]] @@ -1986,42 +2011,84 @@ version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8" +[[package]] +name = "windows_aarch64_gnullvm" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cb7764e35d4db8a7921e09562a0304bf2f93e0a51bfccee0bd0bb0b666b015ea" + [[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.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bbaa0368d4f1d2aaefc55b6fcfee13f41544ddf36801e793edbbfd7d7df075ef" + [[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.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a28637cb1fa3560a16915793afb20081aba2c92ee8af57b4d5f28e4b3e7df313" + [[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.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ffe5e8e31046ce6230cc7215707b816e339ff4d4d67c65dffa206fd0f7aa7b9a" + [[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.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d6fa32db2bc4a2f5abeacf2b69f7992cd09dca97498da74a151a3132c26befd" + [[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.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a657e1e9d3f514745a572a6846d3c7aa7dbe1658c056ed9c3344c4109a6949e" + [[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.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dff9641d1cd4be8d1a070daf9e3773c5f67e78b4d9d42263020c057706765c04" + [[package]] name = "winnow" version = "0.5.19" diff --git a/Cargo.toml b/Cargo.toml index a0f1cb2..959253f 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -37,6 +37,7 @@ tokio-stream = "0.1.14" colored = "2.0.4" clap = { version = "4.4.7", features = ["derive"] } uuid = { version = "1.5.0", features = ["v4"] } +rand = "0.8.5" [build-dependencies] tonic-build = "0.9" diff --git a/src/gate.rs b/src/gate.rs index 546c929..c94d173 100644 --- a/src/gate.rs +++ b/src/gate.rs @@ -4,14 +4,11 @@ use crate::felinet::{ handler_client::HandlerClient, packet_filter::Filter, PacketFilter, PacketIn as SemiPacketIn, }; use crate::radio::MAX_PACKET_LEN; -use crate::util::{ - append_internet_to_packet_route, append_to_packet_route, attempt_decode, print_packet, - should_digipeat, -}; +use crate::util::{append_internet_to_packet_route, attempt_decode, print_packet}; use anyhow::{anyhow, Context}; -use arrayvec::ArrayVec; use async_stream::stream; use half::f16; +use ham_cats::buffer::Buffer; use ham_cats::{ packet::Packet, whisker::{Gps, Identification, Route}, @@ -28,7 +25,8 @@ pub fn beacon_forever( felinet_send: broadcast::Sender<SemiPacketIn>, uuid: Uuid, ) -> anyhow::Result<()> { - let mut packet: Packet<MAX_PACKET_LEN> = Packet::default(); + let mut buf = [0; MAX_PACKET_LEN]; + let mut packet = Packet::new(&mut buf); packet .add_identification( Identification::new(c.icon, &c.callsign, c.ssid).context( @@ -60,7 +58,8 @@ pub fn beacon_forever( .map_err(|e| anyhow!("Could not add gps to beacon packet: {e}"))?; } - let mut internet_packet = packet.clone(); + let mut internet_buf = [0; MAX_PACKET_LEN]; + let mut internet_packet = packet.clone_backing(&mut internet_buf); let mut rf_packet = packet; // internet route @@ -77,7 +76,6 @@ pub fn beacon_forever( .map_err(|e| anyhow!("Could not add route to beacon packet: {e}"))?; let semi = internet_packet - .clone() .semi_encode() .map_err(|(e, _)| anyhow!("Could not encode beacon packet: {e}"))? .to_vec(); @@ -86,10 +84,13 @@ pub fn beacon_forever( uuid: uuid.into(), }; - let full = rf_packet - .fully_encode() - .map_err(|e| anyhow!("Could not encode beacon packet: {e}"))? - .to_vec(); + let mut full = [0; MAX_PACKET_LEN]; + let mut full = Buffer::new_empty(&mut full); + rf_packet + .fully_encode(&mut full) + .map_err(|e| anyhow!("Could not encode beacon packet: {e}"))?; + + let full = full.to_vec(); tokio::task::spawn(async move { loop { @@ -117,9 +118,11 @@ pub async fn packet_handler( .await .context("Packet receive channel died")?; - match attempt_decode(packet) { + let mut buf = [0; MAX_PACKET_LEN]; + match attempt_decode(&packet, &mut buf) { Ok(mut packet) => { - let mut internet_packet = packet.clone(); + let mut buf2 = [0; MAX_PACKET_LEN]; + let mut internet_packet = packet.clone_backing(&mut buf2); match append_internet_to_packet_route(&callsign, ssid, &mut internet_packet) { Some(()) => match internet_packet.semi_encode() { Ok(encoded) => { @@ -140,25 +143,35 @@ pub async fn packet_handler( } } - if should_digipeat(&callsign, ssid, &packet, true) { - if append_to_packet_route(&callsign, ssid, &mut packet).is_none() { - eprintln!("Could not add routing to packet before digipeating. Skipping"); - continue; - }; + match packet.should_digipeat(&callsign, ssid) { + Ok(()) => { + if let Err(e) = packet.append_to_route(&callsign, ssid) { + eprintln!( + "Could not add routing to packet before digipeating: {e}. Skipping" + ); + continue; + }; - match packet.fully_encode() { - Ok(encoded) => { - packet_send - .send(encoded.to_vec()) - .await - .with_context(|| "Packet send channel died")?; - } + let mut encoded_buf = [0; MAX_PACKET_LEN]; + let mut encoded = Buffer::new_empty(&mut encoded_buf); + match packet.fully_encode(&mut encoded) { + Ok(()) => { + packet_send + .send(encoded.to_vec()) + .await + .with_context(|| "Packet send channel died")?; + } - Err(e) => { - eprintln!("Could not fully-encode packet: {e:?}"); + Err(e) => { + eprintln!("Could not fully-encode packet: {e:?}"); + } } } - } + + Err(e) => { + eprintln!("Not digipeating: {e}"); + } + }; } Err(e) => eprintln!("Recv error: {e}"), @@ -230,14 +243,20 @@ pub async fn felinet_receive_once( .into_inner(); while let Some(semi) = stream.next().await { - if let Some(pkt) = ArrayVec::try_from(&semi?.raw[..]) + let mut buf = [0; MAX_PACKET_LEN]; + let mut buf = Buffer::new_empty(&mut buf); + + if let Some(pkt) = buf + .try_extend_from_slice(&semi?.raw[..]) .ok() - .and_then(|av| Packet::<8191>::semi_decode(av).ok()) + .and_then(|_| Packet::semi_decode(buf).ok()) { - if should_digipeat(callsign, ssid, &pkt, false) { + if pkt.should_digipeat(callsign, ssid).is_ok() { print_packet(&pkt, false); - if let Ok(data) = pkt.fully_encode() { + let mut buf2 = [0; MAX_PACKET_LEN]; + let mut data = Buffer::new_empty(&mut buf2); + if let Ok(()) = pkt.fully_encode(&mut data) { modem_send.send(data.to_vec()).await?; } } diff --git a/src/main.rs b/src/main.rs index 7c976d8..1bf053d 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,6 +6,7 @@ use config::Config; use felinet::PingRequest; use gate::{beacon_forever, felinet_receive_forever, felinet_send_forever, packet_handler}; use ham_cats::{ + buffer::Buffer, packet::Packet, whisker::{Arbitrary, Identification}, }; @@ -64,7 +65,8 @@ async fn xmit_test( radio.set_channel(channel); - let mut pkt: Packet<MAX_PACKET_LEN> = Packet::default(); + let mut buf = [0; MAX_PACKET_LEN]; + let mut pkt = Packet::new(&mut buf); pkt.add_identification( Identification::new(config.icon, &config.callsign, config.ssid) .context("Invalid identification")?, @@ -78,8 +80,9 @@ async fn xmit_test( .map_err(|e| anyhow!("Could not add data to packet: {e}"))?; } - let data = pkt - .fully_encode() + let mut buf2 = [0; MAX_PACKET_LEN]; + let mut data = Buffer::new_empty(&mut buf2); + pkt.fully_encode(&mut data) .map_err(|e| anyhow!("Could not encode packet: {e}"))?; tokio::task::spawn(async move { diff --git a/src/radio.rs b/src/radio.rs index 0b2b1f9..c60cdd9 100644 --- a/src/radio.rs +++ b/src/radio.rs @@ -1,14 +1,12 @@ use anyhow::{anyhow, bail, Context}; +use rand::{thread_rng, Rng}; use rf4463::{config::RADIO_CONFIG_CATS, Rf4463}; use rppal::{ gpio::{Gpio, OutputPin}, hal::Delay, spi::{Bus, Mode, SlaveSelect, Spi}, }; -use std::{ - thread, - time::{Duration, Instant}, -}; +use std::time::{Duration, Instant}; use tokio::sync::mpsc::{error::TryRecvError, Receiver, Sender}; pub const MAX_PACKET_LEN: usize = 8191; @@ -18,6 +16,7 @@ pub struct RadioManager { tx: Sender<Vec<u8>>, rx: Receiver<Vec<u8>>, + rx_buf: [u8; MAX_PACKET_LEN], } impl RadioManager { @@ -33,7 +32,14 @@ impl RadioManager { .map_err(|e| anyhow!("{e:?}"))?; radio.set_channel(20); - Ok(Self { radio, tx, rx }) + let rx_buf = [0; MAX_PACKET_LEN]; + + Ok(Self { + radio, + tx, + rx, + rx_buf, + }) } pub fn set_channel(&mut self, channel: u8) { @@ -41,47 +47,16 @@ impl RadioManager { } pub async fn process_forever(&mut self) -> anyhow::Result<()> { - self.radio - .start_rx(None, true) - .map_err(|e| anyhow!("{e:?}"))?; - - let mut rx_buf = [0; MAX_PACKET_LEN]; - loop { - self.radio - .interrupt(Some(&mut rx_buf), None) - .map_err(|e| anyhow!("{e:?}"))?; - - let data = self - .radio - .finish_rx(&mut rx_buf) - .map_err(|e| anyhow!("{e:?}"))?; - - if let Some(data) = data { - self.radio - .start_rx(None, true) - .map_err(|e| anyhow!("{e:?}"))?; + self.tick().await?; - self.tx - .send(data.data().to_vec()) - .await - .ok() - .context("TX channel died")?; - } - - if !self.radio.is_busy_rxing()? { - match self.rx.try_recv() { - Ok(pkt) => { - self.send_packet(&pkt)?; - - self.radio - .start_rx(None, true) - .map_err(|e| anyhow!("{e:?}"))?; - } - Err(TryRecvError::Empty) => {} - Err(TryRecvError::Disconnected) => { - bail!("RX channel disconnected") - } + match self.rx.try_recv() { + Ok(pkt) => { + self.tx(&pkt).await?; + } + Err(TryRecvError::Empty) => {} + Err(TryRecvError::Disconnected) => { + bail!("RX channel disconnected") } } @@ -89,11 +64,47 @@ impl RadioManager { } } - fn send_packet(&mut self, data: &[u8]) -> anyhow::Result<()> { + async fn tick(&mut self) -> anyhow::Result<()> { + if self.radio.is_idle() { + self.radio + .start_rx(None, false) + .map_err(|e| anyhow!("{e}"))?; + + tokio::time::sleep(Duration::from_millis(25)).await; + } + + self.radio + .interrupt(Some(&mut self.rx_buf), None) + .map_err(|e| anyhow!("{e:?}"))?; + + if let Some(data) = self + .radio + .finish_rx(&mut self.rx_buf) + .map_err(|e| anyhow!("{e}"))? + { + self.radio + .start_rx(None, false) + .map_err(|e| anyhow!("{e}"))?; + + self.tx + .send(data.data().to_vec()) + .await + .ok() + .context("TX channel died")?; + } + + Ok(()) + } + + async fn tx(&mut self, data: &[u8]) -> anyhow::Result<()> { + // ensures we don't tx over a packet, + // and adds some random delay so that every node + // if offset slightly + self.tx_delay().await?; + self.radio.start_tx(data).map_err(|e| anyhow!("{e:?}"))?; const TIMEOUT: Duration = Duration::from_secs(10); - let start_time = Instant::now(); while !self.radio.is_idle() { self.radio @@ -104,9 +115,32 @@ impl RadioManager { bail!("Timeout while transmitting"); } - thread::sleep(Duration::from_millis(25)); + tokio::time::sleep(Duration::from_millis(25)).await; } Ok(()) } + + async fn tx_delay(&mut self) -> anyhow::Result<()> { + loop { + let delay_ms = thread_rng().gen_range(0..50); + + // since delay_ms < 100 we can safely sleep without calling tick + tokio::time::sleep(Duration::from_millis(delay_ms)).await; + + let mut rx = false; + + while self.radio.is_busy_rxing()? { + rx = true; + self.tick().await?; + + tokio::time::sleep(Duration::from_millis(25)).await; + } + + if !rx { + // didn't rx a packet, so we're safe to leave + break Ok(()); + } + } + } } diff --git a/src/util.rs b/src/util.rs index e50cb0a..a8273c9 100644 --- a/src/util.rs +++ b/src/util.rs @@ -6,80 +6,6 @@ use ham_cats::{ whisker::{Route, RouteNode}, }; -// RF to RF, also Internet to RF -pub fn should_digipeat( - callsign: &str, - ssid: u8, - packet: &Packet<MAX_PACKET_LEN>, - echo: bool, -) -> bool { - let route = match packet.route() { - Some(x) => x, - None => { - if echo { - println!("Not digipeating - Packet has no route") - }; - return false; - } - }; - - if let Some(ident) = packet.identification() { - if &ident.callsign == callsign && ident.ssid == ssid { - // this node is the source of the packet - if echo { - println!("Not digipeating - Packet ident is us"); - } - return false; - } - } - - let max_hops: usize = route.max_hops.into(); - let cur_hops = route - .iter() - .filter(|r| match r { - RouteNode::Internet => false, - RouteNode::Identity(_, _, is_future) => !is_future, - }) - .count(); - - if max_hops <= cur_hops { - // already hit our max hops - if echo { - println!("Not digipeating - Max hops hit"); - } - return false; - } - - let already_digipeated = route.iter().any(|r| match r { - RouteNode::Internet => false, - RouteNode::Identity(rc, rs, is_future) => rc == callsign && rs == ssid && !is_future, - }); - - if already_digipeated { - // this node has already digipeated this packet - if echo { - println!("Not digipeating - Already digipeated by this node") - }; - return false; - } - - let next_node = route.iter().find_map(|r| match r { - RouteNode::Identity(c, s, is_future) if is_future => Some((c, s)), - _ => None, - }); - - match next_node { - Some((rc, rs)) => { - let out = rc == callsign && rs == ssid; - if !out && echo { - println!("Not digipeating - This packet's destiny is set and does not involve us"); - } - out - } - None => true, - } -} - pub fn print_packet(pkt: &Packet<MAX_PACKET_LEN>, is_rf: bool) { let color = if is_rf { println!("----- RF -----"); @@ -137,9 +63,12 @@ pub fn print_packet(pkt: &Packet<MAX_PACKET_LEN>, is_rf: bool) { println!(); } -pub fn attempt_decode(packet: Vec<u8>) -> anyhow::Result<Packet<MAX_PACKET_LEN>> { +pub fn attempt_decode<'a>( + packet: &[u8], + buf: &'a mut [u8; MAX_PACKET_LEN], +) -> anyhow::Result<Packet<'a, MAX_PACKET_LEN>> { let packet: Packet<MAX_PACKET_LEN> = - Packet::fully_decode(&packet).map_err(|e| anyhow!("Could not decode packet: {e:?}"))?; + Packet::fully_decode(packet, buf).map_err(|e| anyhow!("Could not decode packet: {e:?}"))?; print_packet(&packet, true); @@ -169,7 +98,7 @@ pub fn append_internet_to_packet_route( if let Some((rc, rs)) = first_future { if rc == callsign && rs == ssid { // we can just do the normal thing - append_to_route(callsign, ssid, &mut route)?; + route.append_node(callsign, ssid).ok()?; } else { // rip off all the futures and add ourselves let mut new_route = Route::new(route.max_hops); @@ -190,7 +119,7 @@ pub fn append_internet_to_packet_route( route.push_callsign(callsign, ssid, false); } } else { - append_to_route(callsign, ssid, &mut route)?; + route.append_node(callsign, ssid).ok()?; } route.push_internet()?; @@ -199,53 +128,3 @@ pub fn append_internet_to_packet_route( Some(()) } - -#[must_use] -pub fn append_to_packet_route( - callsign: &str, - ssid: u8, - packet: &mut Packet<MAX_PACKET_LEN>, -) -> Option<()> { - let mut route = packet.route().unwrap_or(Route::new(0)); - append_to_route(callsign, ssid, &mut route)?; - packet.clear_route(); - packet.add_route(route).ok()?; - - Some(()) -} - -#[must_use] -fn append_to_route(callsign: &str, ssid: u8, r: &mut Route) -> Option<()> { - let replace_future = r.iter().any(|rn| match rn { - RouteNode::Identity(rc, rs, is_future) => rc == callsign && rs == ssid && is_future, - _ => false, - }); - - if replace_future { - let mut new_route = Route::new(r.max_hops); - let mut already_replaced = false; - - for rn in r.iter() { - match rn { - RouteNode::Identity(rc, rs, is_future) - if rc == callsign && rs == ssid && is_future && !already_replaced => - { - already_replaced = true; - new_route.push_callsign(callsign, ssid, false)?; - } - RouteNode::Identity(rc, rs, is_future) => { - new_route.push_callsign(rc, rs, is_future)?; - } - RouteNode::Internet => { - new_route.push_internet()?; - } - } - } - - *r = new_route; - } else { - r.push_callsign(callsign, ssid, false)?; - } - - Some(()) -} -- GitLab