Red-team review of the (byte-exact) v1 port found replay, cross-session
frame portability, pre-auth allocation amplification, and a symmetric
key that let either peer forge as itself — flaws inherent to the v1
wire format. v2 closes them:
- fixed 69-byte OVX2 hello; server validates before replying; v1 and
wrong-version peers see an immediate close
- HKDF(ephemeral X25519 DH, PSK, transcript) -> direction-separated
session keys; forward secrecy per connection
- strictly increasing u64 sequence nonces: any replay or reorder drops
the connection (regression tests in tests/protocol_v2.rs)
- Config: message-size cap (64 KiB default), connection semaphore,
idle/body-stall/handshake/send timeouts on both roles (client-side
timers retire the old no-client-timeouts quirk)
- message processing inline per connection; user callbacks panic-
isolated; poison-tolerant mutexes; demo key refused in release builds
- PROTOCOL-V2.md supersedes PARITY-CONTRACT.md (retired, kept as port
history); Cereal payload encoding is unchanged
Payload serialization remains byte-exact with the original C++ (the
golden scrypt/cereal vectors still govern). Zero unsafe. Verified live:
server<->client handshake, encrypted echo, clean teardown.
Cuts over from the C++ implementation, which is deleted (phase 5 of the
port contract); it remains in the original gitea repository.