From ffb3a0a4f920f745831d258e458d59e40ebe274d Mon Sep 17 00:00:00 2001 From: Sachymetsu Date: Thu, 2 Apr 2026 10:37:00 +0200 Subject: [PATCH] Use BufferSlice for static buffer to reduce alloc pressure --- Cargo.lock | 48 ++++++++++++++++++++++-------------------- Cargo.toml | 1 + src/net.rs | 7 ++++++- src/net/crypto.rs | 53 ++++++++++++++++++++++++++++++----------------- src/net/rpc.rs | 6 +++--- 5 files changed, 69 insertions(+), 46 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 1df12ed..ba597fa 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1295,9 +1295,9 @@ dependencies = [ [[package]] name = "hybrid-array" -version = "0.4.9" +version = "0.4.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a79f2aff40c18ab8615ddc5caa9eb5b96314aef18fe5823090f204ad988e813" +checksum = "3944cf8cf766b40e2a1a333ee5e9b563f854d5fa49d6a8ca2764e97c6eddb214" dependencies = [ "subtle", "typenum", @@ -1456,9 +1456,9 @@ checksum = "09edd9e8b54e49e587e4f6295a7d29c3ea94d469cb40ab8ca70b288248a81db2" [[package]] name = "libc" -version = "0.2.183" +version = "0.2.184" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b5b646652bf6661599e1da8901b3b9522896f01e736bad5f723fe7a3a27f899d" +checksum = "48f5d2a454e16a5ea0f4ced81bd44e4cfc7bd3a507b61887c99fd3538b28e4af" [[package]] name = "linux-raw-sys" @@ -1709,6 +1709,7 @@ checksum = "5be167a7af36ee22fe3115051bc51f6e6c7054c9348e28deb4f49bd6f705a315" name = "pico-strike" version = "0.1.0" dependencies = [ + "aead", "cortex-m", "cortex-m-rt", "critical-section", @@ -2020,9 +2021,9 @@ dependencies = [ [[package]] name = "rustcrypto-ff" -version = "0.14.0-rc.0" +version = "0.14.0-rc.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c5db129183b2c139d7d87d08be57cba626c715789db17aec65c8866bfd767d1f" +checksum = "fd2a8adb347447693cd2ba0d218c4b66c62da9b0a5672b17b981e4291ec65ff6" dependencies = [ "rand_core 0.10.0", "subtle", @@ -2030,9 +2031,9 @@ dependencies = [ [[package]] name = "rustcrypto-group" -version = "0.14.0-rc.0" +version = "0.14.0-rc.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "57c4b1463f274a3ff6fb2f44da43e576cb9424367bd96f185ead87b52fe00523" +checksum = "369f9b61aa45933c062c9f6b5c3c50ab710687eca83dd3802653b140b43f85ed" dependencies = [ "rand_core 0.10.0", "rustcrypto-ff", @@ -2071,7 +2072,7 @@ dependencies = [ [[package]] name = "sachy-crypto" version = "0.1.0" -source = "git+https://tangled.org/sachy.dev/sachy-embed-core#2485a1626c11ec976be8ec402b26a8812f72d3e4" +source = "git+https://tangled.org/sachy.dev/sachy-embed-core#7e8218e9f40024412b7d813bf5052ed83036e3f3" dependencies = [ "chacha20poly1305", "dhkem", @@ -2083,7 +2084,7 @@ dependencies = [ [[package]] name = "sachy-fmt" version = "0.1.0" -source = "git+https://tangled.org/sachy.dev/sachy-embed-core#2485a1626c11ec976be8ec402b26a8812f72d3e4" +source = "git+https://tangled.org/sachy.dev/sachy-embed-core#7e8218e9f40024412b7d813bf5052ed83036e3f3" dependencies = [ "defmt 1.0.1", ] @@ -2091,7 +2092,7 @@ dependencies = [ [[package]] name = "sachy-mdns" version = "0.1.0" -source = "git+https://tangled.org/sachy.dev/sachy-embed-core#2485a1626c11ec976be8ec402b26a8812f72d3e4" +source = "git+https://tangled.org/sachy.dev/sachy-embed-core#7e8218e9f40024412b7d813bf5052ed83036e3f3" dependencies = [ "defmt 1.0.1", "embassy-time", @@ -2102,7 +2103,7 @@ dependencies = [ [[package]] name = "sachy-sntp" version = "0.1.0" -source = "git+https://tangled.org/sachy.dev/sachy-embed-core#2485a1626c11ec976be8ec402b26a8812f72d3e4" +source = "git+https://tangled.org/sachy.dev/sachy-embed-core#7e8218e9f40024412b7d813bf5052ed83036e3f3" dependencies = [ "defmt 1.0.1", "embassy-net", @@ -2134,9 +2135,9 @@ checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" [[package]] name = "sec1" -version = "0.8.0" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f46b9a5ab87780a3189a1d704766579517a04ad59de653b7aad7d38e8a15f7dc" +checksum = "d56d437c2f19203ce5f7122e507831de96f3d2d4d3be5af44a0b0a09d8a80e4d" dependencies = [ "base16ct", "ctutils", @@ -2323,8 +2324,9 @@ dependencies = [ [[package]] name = "striker-proto" version = "0.1.0" -source = "git+https://tangled.org/sachy.dev/striker#5acc302dd224720aa9bf40305425994de38e861a" +source = "git+https://tangled.org/sachy.dev/striker#b63cfe725e4258c02d364f403baa9c0dc0697b72" dependencies = [ + "aead", "dhkem", "postcard", "sachy-crypto", @@ -2480,18 +2482,18 @@ dependencies = [ [[package]] name = "toml_datetime" -version = "1.1.0+spec-1.1.0" +version = "1.1.1+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "97251a7c317e03ad83774a8752a7e81fb6067740609f75ea2b585b569a59198f" +checksum = "3165f65f62e28e0115a00b2ebdd37eb6f3b641855f9d636d3cd4103767159ad7" dependencies = [ "serde_core", ] [[package]] name = "toml_edit" -version = "0.25.8+spec-1.1.0" +version = "0.25.10+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "16bff38f1d86c47f9ff0647e6838d7bb362522bdf44006c7068c2b1e606f1f3c" +checksum = "a82418ca169e235e6c399a84e395ab6debeb3bc90edc959bf0f48647c6a32d1b" dependencies = [ "indexmap", "toml_datetime", @@ -2502,18 +2504,18 @@ dependencies = [ [[package]] name = "toml_parser" -version = "1.1.0+spec-1.1.0" +version = "1.1.2+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2334f11ee363607eb04df9b8fc8a13ca1715a72ba8662a26ac285c98aabb4011" +checksum = "a2abe9b86193656635d2411dc43050282ca48aa31c2451210f4202550afb7526" dependencies = [ "winnow 1.0.1", ] [[package]] name = "toml_writer" -version = "1.1.0+spec-1.1.0" +version = "1.1.1+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d282ade6016312faf3e41e57ebbba0c073e4056dab1232ab1cb624199648f8ed" +checksum = "756daf9b1013ebe47a8776667b466417e2d4c5679d441c26230efd9ef78692db" [[package]] name = "tracing" diff --git a/Cargo.toml b/Cargo.toml index d7859cf..54db55b 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -52,6 +52,7 @@ sachy-mdns = { git = "https://tangled.org/sachy.dev/sachy-embed-core", package = ] } sachy-fmt = { git = "https://tangled.org/sachy.dev/sachy-embed-core", package = "sachy-fmt" } sachy-crypto = { git = "https://tangled.org/sachy.dev/sachy-embed-core" } +aead = "=0.6.0-rc.10" striker-proto = { git = "https://tangled.org/sachy.dev/striker", package = "striker-proto" } embassy-strike-driver = { git = "https://tangled.org/sachy.dev/strike-sensor", package = "embassy-strike-driver", features = [ "rp2040", diff --git a/src/net.rs b/src/net.rs index 04f9b1f..fa34ffa 100644 --- a/src/net.rs +++ b/src/net.rs @@ -68,6 +68,8 @@ pub async fn udp_stack(stack: embassy_net::Stack<'static>, rtc: GlobalRtc<'stati pub async fn tcp_stack(stack: embassy_net::Stack<'static>) { let rx_buffer = unwrap!(try_static_buffer_with(8192, Default::default)); let tx_buffer = unwrap!(try_static_buffer_with(8192, Default::default)); + let rpc_buffer = unwrap!(try_static_buffer_with(8192, Default::default)); + let mut tcp = TcpSocket::new(stack, rx_buffer, tx_buffer); tcp.set_keep_alive(Some(Duration::from_secs(1))); @@ -77,7 +79,10 @@ pub async fn tcp_stack(stack: embassy_net::Stack<'static>) { stack.wait_config_up().await; let rpc_fut = unwrap!( - try_box_future_within(|| select(stack.wait_link_down(), rpc::rpc_loop(&mut tcp))), + try_box_future_within(|| select( + stack.wait_link_down(), + rpc::rpc_loop(&mut tcp, rpc_buffer) + )), "Failed to alloc RPC LOOP" ); diff --git a/src/net/crypto.rs b/src/net/crypto.rs index 3cdf791..1df8e34 100644 --- a/src/net/crypto.rs +++ b/src/net/crypto.rs @@ -1,16 +1,14 @@ -use alloc::vec::Vec; +use aead::Buffer; use embassy_futures::select::{Either, select}; use embassy_net::tcp::{TcpReader, TcpSocket, TcpWriter}; use embedded_io_async::{Read, Write}; +use sachy_crypto::BufferSlice; use sachy_fmt::{error, unwrap}; use striker_proto::{Server, ServerBuilder, ServerReceiver, ServerSender}; use crate::{ - constants::NOISE_PSK, - errors::PicoError, - rpc::RpcServer, - updates::UpdateConnection, - utils::{try_box_future_within, try_buffer}, + constants::NOISE_PSK, errors::PicoError, rpc::RpcServer, updates::UpdateConnection, + utils::try_box_future_within, }; pub struct CryptoSession { @@ -26,8 +24,9 @@ impl CryptoSession { &'s self, mut reader: TcpReader<'device>, mut recv_state: ServerReceiver<'s>, + msg_buf: &mut [u8], ) -> Result<(), PicoError> { - let mut msg_buf: Vec = try_buffer(4096)?; + let mut msg_buf = BufferSlice::new(msg_buf); let mut len_buf = [0u8; 2]; loop { @@ -39,7 +38,7 @@ impl CryptoSession { msg_buf.truncate(msg_size); reader - .read_exact(&mut msg_buf) + .read_exact(msg_buf.as_mut()) .await .map_err(|_| PicoError::CryptoProtoError)?; @@ -54,7 +53,7 @@ impl CryptoSession { break; } - msg_buf.resize_with(4096, Default::default); + msg_buf.reset(); } Ok(()) @@ -64,8 +63,9 @@ impl CryptoSession { &'s self, mut writer: TcpWriter<'device>, mut send_state: ServerSender<'s>, + msg_buf: &mut [u8], ) -> Result<(), PicoError> { - let mut msg_buf: Vec = try_buffer(4096)?; + let mut msg_buf = BufferSlice::new(msg_buf); let outgoing = UpdateConnection::get_receiver(); loop { @@ -77,22 +77,23 @@ impl CryptoSession { let len = unwrap!(u16::try_from(msg_buf.len())); writer.write_all(&len.to_be_bytes()).await?; - writer.write_all(&msg_buf).await?; + writer.write_all(msg_buf.as_ref()).await?; writer.flush().await?; - msg_buf.resize_with(4096, Default::default); + msg_buf.reset(); } } - pub async fn run<'device>(self, tcp: &mut TcpSocket<'device>) { + pub async fn run<'device>(self, tcp: &mut TcpSocket<'device>, buf: &mut [u8]) { let (reader, writer) = tcp.split(); let (send_state, recv_state) = self.transport.split(); + let (send_buf, recv_buf) = buf.split_at_mut(4096); let selected = unwrap!( try_box_future_within(|| { select( - self.read_loop(reader, recv_state), - self.write_loop(writer, send_state), + self.read_loop(reader, recv_state, recv_buf), + self.write_loop(writer, send_state, send_buf), ) }), "Failed to allocate Session Loop" @@ -105,13 +106,27 @@ impl CryptoSession { } } -pub async fn initialise<'device>(tcp: &mut TcpSocket<'device>) -> Result { - let mut buf = try_buffer(1024)?; +pub async fn initialise<'device>( + tcp: &mut TcpSocket<'device>, + buf: &mut [u8], +) -> Result { + let mut len_buf = [0u8; 2]; - let read = tcp.read(buf.as_mut_slice()).await?; + tcp.read_exact(&mut len_buf) + .await + .map_err(|_| PicoError::CryptoProtoError)?; - let (ciphertext, handshake) = ServerBuilder::start(&buf[..read])?; + let msg_size = usize::from(u16::from_be_bytes(len_buf)); + tcp.read_exact(&mut buf[..msg_size]) + .await + .map_err(|_| PicoError::CryptoProtoError)?; + + let (ciphertext, handshake) = ServerBuilder::start(&buf[..msg_size])?; + + let len = unwrap!(u16::try_from(ciphertext.len())); + + tcp.write_all(&len.to_be_bytes()).await?; tcp.write_all(&ciphertext).await?; tcp.flush().await?; diff --git a/src/net/rpc.rs b/src/net/rpc.rs index 4c95fc4..2a7c36a 100644 --- a/src/net/rpc.rs +++ b/src/net/rpc.rs @@ -3,7 +3,7 @@ use sachy_fmt::{error, info}; use crate::{constants::HOST_PORT, updates::UpdateConnection}; -pub async fn rpc_loop<'device>(tcp: &mut TcpSocket<'device>) { +pub async fn rpc_loop<'device>(tcp: &mut TcpSocket<'device>, buf: &mut [u8]) { loop { UpdateConnection::disconnect(); @@ -11,12 +11,12 @@ pub async fn rpc_loop<'device>(tcp: &mut TcpSocket<'device>) { continue; } - match super::crypto::initialise(tcp).await { + match super::crypto::initialise(tcp, &mut buf[..1024]).await { Ok(session) => { info!("Connected!"); UpdateConnection::connect(); - session.run(tcp).await; + session.run(tcp, buf).await; UpdateConnection::get_receiver().clear(); -- 2.51.2