From da9f8c2459685390d74c5781068d74de9e33a7b5 Mon Sep 17 00:00:00 2001 From: Dustin Black Date: Mon, 1 Jun 2026 11:59:21 +0000 Subject: [PATCH 1/3] fix: Update BlockingTransportFactory::create calls for 3-arg signature PR #116 added a send_delay parameter to BlockingTransportFactory::create but did not update the callers in standalone_server.rs and standalone_client.rs (introduced by PR #110). This caused compilation failures on main after both PRs merged. Co-Authored-By: Claude Opus 4.6 (1M context) --- src/standalone_client.rs | 19 +++++---- src/standalone_server.rs | 87 ++++++++++++++++++++-------------------- 2 files changed, 56 insertions(+), 50 deletions(-) diff --git a/src/standalone_client.rs b/src/standalone_client.rs index 67849e13..80f5e9ec 100644 --- a/src/standalone_client.rs +++ b/src/standalone_client.rs @@ -206,7 +206,8 @@ pub fn run_standalone_client_blocking_single( results_manager: &mut BlockingResultsManager, config: &BenchmarkConfig, ) -> Result<()> { - let mut transport = BlockingTransportFactory::create(&mechanism, args.shm_direct)?; + let mut transport = + BlockingTransportFactory::create(&mechanism, args.shm_direct, args.send_delay)?; info!("Connecting to server..."); connect_blocking_with_retry(&mut transport, &transport_config)?; @@ -461,7 +462,11 @@ pub fn run_standalone_client_blocking_concurrent( // exits before round-trip workers connect. let sentinel: Option> = if config.one_way && config.round_trip { - let mut transport = BlockingTransportFactory::create(&mechanism, args.shm_direct)?; + let mut transport = BlockingTransportFactory::create( + &mechanism, + args.shm_direct, + args.send_delay, + )?; connect_blocking_with_retry(&mut transport, &transport_config)?; debug!("Sentinel connection established to keep server alive across phases"); Some(transport) @@ -491,7 +496,7 @@ pub fn run_standalone_client_blocking_concurrent( }; std::thread::spawn(move || -> Result { - let mut transport = BlockingTransportFactory::create(&mech, shm_direct)?; + let mut transport = BlockingTransportFactory::create(&mech, shm_direct, send_delay)?; connect_blocking_with_retry(&mut transport, &tc)?; debug!("Worker {} connected (one-way)", worker_id); @@ -587,7 +592,7 @@ pub fn run_standalone_client_blocking_concurrent( }; std::thread::spawn(move || -> Result<(PerformanceMetrics, Vec)> { - let mut transport = BlockingTransportFactory::create(&mech, shm_direct)?; + let mut transport = BlockingTransportFactory::create(&mech, shm_direct, send_delay)?; connect_blocking_with_retry(&mut transport, &tc)?; debug!("Worker {} connected (round-trip)", worker_id); @@ -1360,7 +1365,7 @@ mod tests { let client_config = transport_config.clone(); let client_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &client_config).unwrap(); transport.close_blocking().unwrap(); }); @@ -1368,7 +1373,7 @@ mod tests { // Wait, then start server std::thread::sleep(std::time::Duration::from_millis(500)); let mut server_transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); server_transport .start_server_blocking(&transport_config) .unwrap(); @@ -1641,7 +1646,7 @@ mod tests { // Start server first let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); let config = TransportConfig { host: "127.0.0.1".to_string(), port, diff --git a/src/standalone_server.rs b/src/standalone_server.rs index 8e8bb8d3..157dd5b3 100644 --- a/src/standalone_server.rs +++ b/src/standalone_server.rs @@ -268,7 +268,8 @@ pub fn run_standalone_server_blocking_single( transport_config: &TransportConfig, config: &BenchmarkConfig, ) -> Result<()> { - let mut transport = BlockingTransportFactory::create(&mechanism, args.shm_direct)?; + let mut transport = + BlockingTransportFactory::create(&mechanism, args.shm_direct, args.send_delay)?; transport .start_server_blocking(transport_config) .context("Server failed to start transport")?; @@ -1164,7 +1165,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); while let Ok(message) = transport.receive_blocking() { @@ -1184,7 +1185,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Run round-trip for a short duration @@ -1230,7 +1231,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); let mut received = 0u64; @@ -1249,7 +1250,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Run one-way for a short duration @@ -1299,7 +1300,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); // Handle messages until client disconnects @@ -1322,7 +1323,7 @@ mod tests { // Client: connect with retry and do round-trip let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send round-trip messages @@ -1357,7 +1358,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); let mut received = 0u64; @@ -1376,7 +1377,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send one-way messages @@ -1413,7 +1414,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); while let Ok(message) = transport.receive_blocking() { @@ -1430,7 +1431,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send ping, expect pong @@ -1457,7 +1458,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); // Server loop: should exit on Shutdown @@ -1472,7 +1473,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send shutdown @@ -1551,7 +1552,7 @@ mod tests { }; std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &config).unwrap(); for i in 0..msgs_per_client { @@ -1592,7 +1593,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); let args = Args::parse_from(["ipc-benchmark", "-m", "tcp", "-s", "64"]); @@ -1607,7 +1608,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send round-trip messages (should NOT be recorded as one-way) @@ -1637,7 +1638,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); let args = Args::parse_from(["ipc-benchmark", "-m", "tcp", "-s", "64"]); @@ -1655,7 +1656,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send one-way messages @@ -1723,7 +1724,7 @@ mod tests { }; std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &config).unwrap(); for i in 0..msgs_per_client { @@ -1776,7 +1777,7 @@ mod tests { }; let client_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &config).unwrap(); for i in 0..msgs_per_client { @@ -2011,7 +2012,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); while let Ok(message) = transport.receive_blocking() { @@ -2030,7 +2031,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Create a payload with recognizable pattern @@ -2064,7 +2065,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); let args = Args::parse_from(["ipc-benchmark", "-m", "tcp", "-s", "64"]); @@ -2082,7 +2083,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Send canary (warmup), real messages, another canary, then shutdown @@ -2116,7 +2117,7 @@ mod tests { let server_config = transport_config.clone(); let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); transport.start_server_blocking(&server_config).unwrap(); let args = Args::parse_from(["ipc-benchmark", "-m", "tcp", "-s", "64"]); @@ -2134,7 +2135,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(100)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); // Interleave OneWay and Request messages @@ -2184,7 +2185,7 @@ mod tests { let tc = transport_config.clone(); let h = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); crate::standalone_server::connect_blocking_with_retry(&mut transport, &tc).unwrap(); for i in 0..5u64 { let msg = Message::new(worker * 100 + i, vec![0u8; 64], MessageType::Request); @@ -2227,7 +2228,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(200)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); for i in 0..5u64 { @@ -2272,7 +2273,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(200)); let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &transport_config).unwrap(); let msg = Message::new(0, vec![0u8; 64], MessageType::Request); @@ -2369,7 +2370,7 @@ mod tests { }; join_set.spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); for i in 0..5u64 { let msg = Message::new( @@ -2435,7 +2436,7 @@ mod tests { let client_tc = transport_config.clone(); let client_handle = tokio::task::spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &client_tc).unwrap(); for i in 0..5u64 { @@ -2530,7 +2531,7 @@ mod tests { let tc = transport_config.clone(); let h = tokio::task::spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); for i in 0..5u64 { let msg = Message::new(worker * 100 + i, vec![0u8; 64], MessageType::Request); @@ -2576,7 +2577,7 @@ mod tests { let client_tc = transport_config.clone(); let client_handle = tokio::task::spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &client_tc).unwrap(); // Send one-way messages @@ -2608,7 +2609,7 @@ mod tests { let client_tc = transport_config.clone(); let client_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &client_tc).unwrap(); transport.close_blocking().unwrap(); }); @@ -2617,7 +2618,7 @@ mod tests { std::thread::sleep(std::time::Duration::from_millis(300)); let mut server_transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); server_transport .start_server_blocking(&transport_config) .unwrap(); @@ -2757,7 +2758,7 @@ mod tests { ..Default::default() }; let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let msg = Message::new(0, vec![0u8; 64], MessageType::Request); @@ -2779,7 +2780,7 @@ mod tests { let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); let config = TransportConfig { host: "127.0.0.1".to_string(), port, @@ -2896,7 +2897,7 @@ mod tests { let tc = transport_config.clone(); let good_client = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let msg = Message::new(42, vec![0u8; 64], MessageType::Request); @@ -2923,7 +2924,7 @@ mod tests { let server_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); let config = TransportConfig { host: "127.0.0.1".to_string(), port, @@ -2977,7 +2978,7 @@ mod tests { let tc = transport_config.clone(); let client_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); // Send messages with 10ms delay between each @@ -3025,7 +3026,7 @@ mod tests { let tc = transport_config.clone(); let h = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let start = std::time::Instant::now(); @@ -3079,7 +3080,7 @@ mod tests { let tc = transport_config.clone(); let h = tokio::task::spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let start = std::time::Instant::now(); @@ -3160,7 +3161,7 @@ mod tests { ..Default::default() }; let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let shutdown = Message::new(u64::MAX, Vec::new(), MessageType::Shutdown); From 48efe05e0aafac08bfc5217a71f6c437a660b771 Mon Sep 17 00:00:00 2001 From: Dustin Black Date: Mon, 1 Jun 2026 12:13:31 +0000 Subject: [PATCH 2/3] fix: Update BlockingTransportFactory::create calls and switch MSRV to rustup - Add missing send_delay parameter to all BlockingTransportFactory::create callers in standalone_server.rs and standalone_client.rs. PR #116 changed the signature to 3 arguments but did not update callers from PR #110, breaking compilation on main. - Switch MSRV pre-commit check from container (podman/docker) to rustup. The container approach failed in environments without container privileges, causing contributors to bypass pre-commit hooks entirely. The rustup approach reads the MSRV from Cargo.toml and works in any standard Rust development environment. Co-Authored-By: Claude Opus 4.6 (1M context) --- scripts/msrv-check.sh | 32 +++++++++++++++++--------------- src/standalone_client.rs | 10 ++++------ src/standalone_server.rs | 24 ++++++++++++++++-------- 3 files changed, 37 insertions(+), 29 deletions(-) diff --git a/scripts/msrv-check.sh b/scripts/msrv-check.sh index ccc502de..c0805494 100755 --- a/scripts/msrv-check.sh +++ b/scripts/msrv-check.sh @@ -1,26 +1,28 @@ #!/usr/bin/env bash set -euo pipefail -echo "[MSRV] Running Rust 1.70 build/tests in container..." - -# Find container runtime -RUNTIME="$(command -v podman || command -v docker || true)" -if [[ -z "${RUNTIME}" ]]; then - echo "[MSRV] No container runtime (podman/docker) found. Skipping MSRV check." +MSRV="$(awk -F '"' '/rust-version/ {print $2}' Cargo.toml)" +if [[ -z "${MSRV}" ]]; then + echo "[MSRV] No rust-version found in Cargo.toml. Skipping." exit 0 fi -IMAGE="docker.io/library/rust:1.70" -WORKDIR="/work" -MOUNT="$(pwd):${WORKDIR}" -if [[ "${RUNTIME}" == *podman ]]; then - MOUNT="${MOUNT}:Z" -fi +echo "[MSRV] Checking Rust ${MSRV} compatibility..." -CMD='. /usr/local/cargo/env && cargo -V && rustc -V && cargo build --locked -q && cargo test --locked -q' +if ! command -v rustup &>/dev/null; then + echo "[MSRV] rustup not found. Skipping MSRV check." + exit 0 +fi -"${RUNTIME}" run --rm -v "${MOUNT}" -w "${WORKDIR}" "${IMAGE}" bash -lc "${CMD}" +if ! rustup toolchain list | grep -q "${MSRV}"; then + echo "[MSRV] Installing Rust ${MSRV} toolchain..." + rustup toolchain install "${MSRV}" --profile minimal +fi -echo "[MSRV] Rust 1.70 build/tests passed." +echo "[MSRV] Building with Rust ${MSRV}..." +rustup run "${MSRV}" cargo build --locked -q +echo "[MSRV] Testing with Rust ${MSRV}..." +rustup run "${MSRV}" cargo test --locked -q +echo "[MSRV] Rust ${MSRV} build/tests passed." diff --git a/src/standalone_client.rs b/src/standalone_client.rs index 80f5e9ec..dea5cced 100644 --- a/src/standalone_client.rs +++ b/src/standalone_client.rs @@ -462,11 +462,8 @@ pub fn run_standalone_client_blocking_concurrent( // exits before round-trip workers connect. let sentinel: Option> = if config.one_way && config.round_trip { - let mut transport = BlockingTransportFactory::create( - &mechanism, - args.shm_direct, - args.send_delay, - )?; + let mut transport = + BlockingTransportFactory::create(&mechanism, args.shm_direct, args.send_delay)?; connect_blocking_with_retry(&mut transport, &transport_config)?; debug!("Sentinel connection established to keep server alive across phases"); Some(transport) @@ -496,7 +493,8 @@ pub fn run_standalone_client_blocking_concurrent( }; std::thread::spawn(move || -> Result { - let mut transport = BlockingTransportFactory::create(&mech, shm_direct, send_delay)?; + let mut transport = + BlockingTransportFactory::create(&mech, shm_direct, send_delay)?; connect_blocking_with_retry(&mut transport, &tc)?; debug!("Worker {} connected (one-way)", worker_id); diff --git a/src/standalone_server.rs b/src/standalone_server.rs index 157dd5b3..2e385955 100644 --- a/src/standalone_server.rs +++ b/src/standalone_server.rs @@ -1552,7 +1552,8 @@ mod tests { }; std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &config).unwrap(); for i in 0..msgs_per_client { @@ -1724,7 +1725,8 @@ mod tests { }; std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &config).unwrap(); for i in 0..msgs_per_client { @@ -1777,7 +1779,8 @@ mod tests { }; let client_handle = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &config).unwrap(); for i in 0..msgs_per_client { @@ -2185,7 +2188,8 @@ mod tests { let tc = transport_config.clone(); let h = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); crate::standalone_server::connect_blocking_with_retry(&mut transport, &tc).unwrap(); for i in 0..5u64 { let msg = Message::new(worker * 100 + i, vec![0u8; 64], MessageType::Request); @@ -2370,7 +2374,8 @@ mod tests { }; join_set.spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); for i in 0..5u64 { let msg = Message::new( @@ -2531,7 +2536,8 @@ mod tests { let tc = transport_config.clone(); let h = tokio::task::spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); for i in 0..5u64 { let msg = Message::new(worker * 100 + i, vec![0u8; 64], MessageType::Request); @@ -3026,7 +3032,8 @@ mod tests { let tc = transport_config.clone(); let h = std::thread::spawn(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let start = std::time::Instant::now(); @@ -3080,7 +3087,8 @@ mod tests { let tc = transport_config.clone(); let h = tokio::task::spawn_blocking(move || { let mut transport = - BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None).unwrap(); + BlockingTransportFactory::create(&IpcMechanism::TcpSocket, false, None) + .unwrap(); connect_blocking_with_retry(&mut transport, &tc).unwrap(); let start = std::time::Instant::now(); From 03d3eed27b6ba10fcfd43458030f2ede73fa58f8 Mon Sep 17 00:00:00 2001 From: Dustin Black Date: Mon, 1 Jun 2026 12:26:24 +0000 Subject: [PATCH 3/3] docs: Add AGENTS.md and optimize pre-commit hook for non-code changes Add project guidelines for AI-assisted development covering MSRV, measurement accuracy, pre-commit hooks, testing, and commit standards. Optimize pre-commit hook to skip expensive checks (tests, audit, MSRV) when only Cargo.toml, Cargo.lock, or non-code files change. Fast checks (cargo check, clippy, fmt) still run for all Rust-related changes. AI-Assisted-By: Claude Opus 4.6 (1M context) --- .githooks/pre-commit | 19 +++++++++++---- AGENTS.md | 58 +++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 71 insertions(+), 6 deletions(-) diff --git a/.githooks/pre-commit b/.githooks/pre-commit index a48c45cb..b71dc11e 100755 --- a/.githooks/pre-commit +++ b/.githooks/pre-commit @@ -8,8 +8,6 @@ EXIT_CODE=0 # --- Rust Checks --- run_rust_checks() { - echo "Rust files changed. Running Rust-specific checks..." - run_check() { echo "Running '$@'..." if ! "$@"; then @@ -18,11 +16,22 @@ run_rust_checks() { fi } - run_check cargo audit + run_check cargo check run_check cargo clippy --all-targets --all-features -- -D warnings run_check cargo fmt --all -- --check - run_check cargo test --all-features - run_check scripts/msrv-check.sh + + # Only run the expensive checks (tests, audit, MSRV) when source + # code actually changed. Cargo.toml/Cargo.lock-only changes and + # non-code files skip these. + RUST_SOURCE_CHANGED=$(git diff --cached --name-only --diff-filter=ACMRT | grep -E '\.rs$' || true) + if [ -n "$RUST_SOURCE_CHANGED" ]; then + echo "Rust source changed. Running tests, audit, and MSRV checks..." + run_check cargo audit + run_check cargo test --all-features + run_check scripts/msrv-check.sh + else + echo "No .rs files changed. Skipping tests, audit, and MSRV." + fi } # --- Python Checks --- diff --git a/AGENTS.md b/AGENTS.md index 0519ecba..3e30b1a6 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -1 +1,57 @@ - \ No newline at end of file +# AGENTS.md + +IPC benchmark suite in Rust. Measures latency and throughput across +multiple transport mechanisms on embedded Linux platforms (ARM/aarch64). + +## Constraints + +- MSRV is defined by `rust-version` in Cargo.toml. That is the single + source of truth — do not hardcode the version elsewhere. +- Pin transitive dependencies that pull in editions or features above MSRV. +- Do not add `.cargo/config.toml` with `target-cpu=native` — binaries + must be portable across ARM variants. Apply CPU tuning at build time. +- No customer or partner names in code, comments, issues, or PR descriptions. + +## Pre-commit hooks + +Pre-commit hooks run cargo check, clippy, fmt, tests, and MSRV validation. +Never use `--no-verify` without stating the reason and getting user +confirmation. If a required tool is missing, install it rather than +skipping the check. + +## Measurement accuracy + +This is a benchmarking tool — results must be comparable to equivalent +C programs making the same syscalls. Overhead in the measurement path +directly affects results. Avoid allocations in send/receive hot loops. +Prefer direct libc calls over wrapper crates for timing-critical +syscalls (e.g., `clock_gettime`). Minimize abstraction layers between +the application and the kernel interface. Timestamp capture points +must be documented and placed as close to the actual IPC operation +as possible. + +## Code style + +- Minimize comments. Don't explain what code does — explain why when + non-obvious. +- Don't add features or abstractions beyond what the task requires. +- Prefer editing existing files over creating new ones. + +## Testing + +- AI-assisted code requires measurable test coverage. Library code + should be testable by tarpaulin — avoid putting testable logic in + the binary crate (`main.rs`). +- Verify changes on target hardware when performance claims are made. + +## Commits + +- Include an `AI-Assisted-By:` trailer in commit messages identifying + the model and tool used. + +## PRs + +- Reference related issues. Provide evidence (before/after data) for + performance or correctness claims. +- Keep scope focused. Don't bundle unrelated fixes. +- Rebase on main before requesting review.