fix(2fa): widen recovery code entropy to 80 bits (BUNYIP-202) #244
Loading…
Reference in a new issue
No description provided.
Delete branch "fix/bunyip-202-recovery-code-entropy"
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?
Recovery codes were drawn from only 4 random bytes (32 bits) and rendered
as an 8-hex-char XXXX-XXXX string. With 8 live codes per account and a 2FA
verify rate limit an attacker can sidestep by rotating source IPs, the
~2^32/8 search to hit any valid code was brute-forceable against the 2FA
challenge endpoint, bypassing the second factor.
Generate recovery codes from 10 CSPRNG bytes (80 bits) base32-encoded into
16 characters, grouped as XXXX-XXXX-XXXX-XXXX for readability. 80 bits
clears the OWASP >=64-bit bar for backup codes. Hyphens stay display-only:
generation and verify_recovery_code both normalise by stripping hyphens
and upper-casing before Argon2id hashing, so existing stored codes and the
verify path are unaffected by the format change.
The per-account failed-attempt lockout the audit also called for (key the
rate limit on user_id, not just source IP) already landed in BUNYIP-201, so
this change covers the remaining weak-entropy acceptance criterion.
#BUNYIP-202