0010 — Denial-of-service hardening of the frame and node layers
Date: 2026-08-08. Status: accepted. Arose from an adversarial review of the v1 implementation.
Three unauthenticated- or single-frame denial-of-service vectors were found and closed. All are "works in the wild" concerns, not lab theatre.
-
Non-ASCII signature crash (critical).
decode()validated only thatsigwas a string, then calledhmac.compare_digest(sig, expected), which raisesTypeErroron a non-ASCII str operand. Every caller catches onlyFrameDrop, so one crafted datagram — in open OR keyed mode, since the crash precedes verification — took down the receive loop of every agent and the snooper. Fix:sigmust match^([0-9a-f]{64})?$(SHA-256 hex, or empty in open mode) before the compare; anything else drops asauth. A non-strsigremainsmalformed. -
Spoofed sequence high-water (major). A frame carrying a victim's origin id and an absurd seq poisoned every receiver's per-origin replay high-water, stale-dropping the real node's later frames until each peer rebooted. Fix: sequence numbers are Unix nanoseconds (ADR 0007), and a frame whose seq runs more than
SEQ_FUTURE_MARGIN_S(1 h) ahead of the receiver's clock is rejected without advancing the mark. This also forced the seq unit to be consistent between agents (int(now) * 1e9, exact integer math) and the CLI (time.time_ns()). -
Unbounded per-origin maps (major).
_replay,_peers,_rejected, and_intent_cacheare keyed by attacker-choosable node ids and were never pruned; a device cycling ids exhausted memory. Fix (_prune, run each poll): forget peers lost/departed longer thanPEER_FORGET(5 min) and FIFO-cap every map atMAX_TRACKED(4096), never evicting the currently paired producer.
Residual, accepted: a PSK-holding device is already trusted to forge intents (ADR 0005), so these bounds harden against unauthenticated and buggy senders and cap the blast radius of a compromised one; they do not make a key-holder harmless. Per-device keys remain the v2 answer to that. The seq bound assumes NTP-sane clocks, already a deployment prerequisite.