3c.3 relay: unauthenticated obf discriminator is only ~21 bits (probabilistic probe-resistance; authenticated check via #37) #64
Labels
No labels
bug
documentation
duplicate
enhancement
good first issue
help wanted
invalid
question
wontfix
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
femboy/yip#64
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Summary
The 3c.3 relay's Trojan-front discriminator decides tunnel-vs-decoy by deobfuscating the first framed message with the network
obf_pskand checking it is a freshRegister. Butyip_obf::deobfuscateis an unauthenticated keystream XOR (SipHash-CTR, "NOT an AEAD" per its own docs) — there is no MAC. So the "proof ofobf_pskknowledge" reduces to a structural match on the recovered bytes:ptype == RDV_TYPE(8 bits) +Registertag0x00(8 bits) + a length field in a plausible range — only ~16–21 effective bits.Impact
A blind prober (no
obf_psk) sending a random frame over a completed TLS session lands a falseUpgradewith probability ≈ 2⁻²¹ per connection. On that event the relay writes an obfuscated, rendezvous-shaped reply and entersrun_tunnel— i.e. it emits the "tunnel behavior" the spec promises a non-holder never observes, instead of serving the decoy.This contradicts design §6.1's original "a prober without
obf_pskcannot forge aRegister" (corrected to a probabilistic statement in the spec, referencing this issue).Severity
Low in practice: each attempt costs a full real-cert TLS handshake, so ~10⁶ handshakes to unmask once, and the payoff is only "this endpoint answered non-decoy." But it means probe-resistance against a blind forger is probabilistic, not absolute.
Fix directions
Surfaced by the 3c.3 final whole-branch review.