Fix rekey dual-initiation, parent selection, peer reconnect, and control socket

Rekey dual-initiation race (FMP + FSP):
When both sides' rekey timers fire simultaneously on high-latency links
(Tor ~700ms RTT), both msg1s cross in flight before dampening can
suppress the second initiation. Each node acts as both initiator and
responder, with set_pending_session() from the responder path destroying
the initiator's in-progress state. Each side ends up with a
pending_new_session from a different Noise handshake, causing AEAD
verification failure after cutover and link death. Fix: deterministic
tie-breaker in both FMP msg1 handler and FSP SessionSetup handler
(smaller NodeAddr wins as initiator). Also guard against pending session
overwrite from retransmitted msg1s.

Parent selection SRTT gate:
Peers without MMP RTT data are excluded from parent candidacy via
has_srtt() filter, preventing freshly reconnected peers from appearing
artificially attractive. First-RTT triggers immediate parent re-eval.
The gate in evaluate_parent() skips unmeasured candidates when any peer
has cost data, but falls back to default cost 1.0 during cold start
when no peer has MMP data yet.

Auto-reconnect on all peer removal paths:
The excessive-decryption-failure and peer-restart epoch-mismatch removal
paths were missing schedule_reconnect() calls, causing auto-connect peers
to be permanently abandoned after those events.

Control socket accessibility:
Socket and parent directory chowned to root:fips with mode 0770/0750 so
group members can use fipsctl/fipstop without root.

Log level changes:
Default RUST_LOG changed to debug in systemd service files. "Unknown
session index" log reduced from debug to trace.
This commit is contained in:
Johnathan Corgan
2026-03-16 00:51:55 +00:00
parent 324535e76d
commit 5f7fe989f3
12 changed files with 214 additions and 17 deletions
+2 -3
View File
@@ -10,11 +10,10 @@ Restart=on-failure
RestartSec=5
# Logging: RUST_LOG controls verbosity.
# Use "info" for production, "debug" for troubleshooting.
Environment=RUST_LOG=info
Environment=RUST_LOG=debug
# Control socket directory (/run/fips/).
# Group-readable so 'fips' group members can use fipsctl/fipstop.
# Group-accessible so 'fips' group members can use fipsctl/fipstop.
RuntimeDirectory=fips
RuntimeDirectoryMode=0750
+2 -3
View File
@@ -10,11 +10,10 @@ Restart=on-failure
RestartSec=5
# Logging: RUST_LOG controls verbosity.
# Use "info" for production, "debug" for troubleshooting.
Environment=RUST_LOG=info
Environment=RUST_LOG=debug
# Control socket directory (/run/fips/).
# Group-readable so 'fips' group members can use fipsctl/fipstop.
# Group-accessible so 'fips' group members can use fipsctl/fipstop.
RuntimeDirectory=fips
RuntimeDirectoryMode=0750