Audit finding from #300 (commit 679f9fe)
Severity: low (informational; auth was out of scope for the validation/DoS pass — see SEC-A-01 for the medium-severity version)
Category: security / timing oracle
File: crates/agent/src/server.rs:235
Obvious fix: yes
Description
bearer_auth_middleware does if provided == expected_token { ... } — Rust's default &str equality is not constant-time, enabling a byte-wise timing oracle.
Impact / Threat
Network-adjacent attacker can mount a timing oracle to recover the agent's MCP bearer token character by character.
Suggested fix
Compare via subtle::ConstantTimeEq::ct_eq(provided.as_bytes(), expected_token.as_bytes()), or hash both sides and compare fixed-length digests.
Verify
rg "provided == expected_token" crates/agent/src/server.rs
Audit finding from #300 (commit 679f9fe)
Severity: low (informational; auth was out of scope for the validation/DoS pass — see SEC-A-01 for the medium-severity version)
Category: security / timing oracle
File: crates/agent/src/server.rs:235
Obvious fix: yes
Description
bearer_auth_middlewaredoesif provided == expected_token { ... }— Rust's default&strequality is not constant-time, enabling a byte-wise timing oracle.Impact / Threat
Network-adjacent attacker can mount a timing oracle to recover the agent's MCP bearer token character by character.
Suggested fix
Compare via
subtle::ConstantTimeEq::ct_eq(provided.as_bytes(), expected_token.as_bytes()), or hash both sides and compare fixed-length digests.Verify
rg "provided == expected_token" crates/agent/src/server.rs