Skip to content

wallet: Encrypted descriptor backup keyed by the seed #55

Description

@BenWestgate

First-class restore evidence and the separate malicious-tampering defense. The release-gate fingerprint/no-record work in #28/#57 is intentionally only accident safety.

Descriptor-based authentication is a restore feature, not a creation requirement. Fresh wallet creation must not ask the operator to authenticate a wallet that did not previously exist.

The restore flow should prefer evidence in this order:

  1. This encrypted descriptor backup: decrypt with a key derived from the recovered master seed, then require the recovered seed to reproduce the backed-up single-sig wallet descriptors before any wallet is created, unlocked or imported into.
  2. Human wallet record: a matching typed master fingerprint and/or single-sig descriptor checksum (wallet: Add checksummed recovery-record evidence #43).
  3. No record: the explicit visual fingerprint + codex32/Bails identifier confirmation implemented by gui: Require the recorded fingerprint before import #28/wallet: Require the recorded fingerprint before import #57.

Design for this issue:

  • Key: derive 256 bits from the recovered master seed via a dedicated hardened BIP85-style path. This is for authenticating/decrypting the backup, not wallet interoperability; document the narrow carve-out from Remove internal hardened BIP32 derivation via Bitcoin Core HD-key RPCs #6 rather than reintroducing a general Python BIP32 wallet oracle.
  • Encryption/authentication: use symmetric authenticated encryption. gpg --symmetric is acceptable if the passphrase/key is supplied out of arguments (file descriptor/stdin), compression and embedded filename are disabled, and plaintext is padded to a fixed envelope size. A small, auditable standard primitive with no new secret-bearing argument channel is preferable if it avoids a GPG dependency.
  • Contents: the exact public descriptor set and timestamps needed to restore the wallet, account, wallet name, creation date, and the expected master fingerprint. Preserve enough canonical data to reproduce and compare the intended single-sig wallet, not merely one arbitrary receive descriptor.
  • Verification before mutation: successful decryption is necessary but not sufficient. Re-derive the recovered seed's expected xpubs/descriptors and compare them to the authenticated backup without creating or filling a Core wallet. Only then hand the verified fingerprint/descriptors to the import path.
  • Threat model: this protects against malicious replacement/tampering only to the extent an attacker cannot also replace every independently stored copy of the encrypted descriptor backup. Anyone who can replace a threshold of cards can already read the seed; therefore gui: Require the recorded fingerprint before import #28/wallet: Require the recorded fingerprint before import #57 do not pretend a 32-bit fingerprint is malicious-tampering resistance.
  • Creation output: after successful wallet creation, generate the encrypted descriptor backup and give it to the operator as a separate backup artifact. This output records the new wallet; it is not evidence that creation had to verify beforehand.
  • Copies: recommend at least N - M + 1 independent physical copies for an M-of-N recovery set, stored apart from the recovery cards. Additional cloud copies are encouraged for convenience because the artifact is encrypted, but they are not a substitute for independently controlled physical copies.
  • Printing: design a printable representation that can accompany the wallet recovery record, including a human-readable envelope identifier and a QR/text encoding with an integrity check. Confirm page capacity, error recovery, privacy, and restore scanning before choosing the final encoding.
  • Correction: a verified backup may later be used as a high-confidence oracle for ranking/testing repair candidates (correct: Rank repair candidates by seed-derived identifiers #56).

Authenticating coordinator/multisig policy data that the recovered seed cannot reproduce is a separate coordinator problem (Bails#236).

This issue requires human threat-model, format, UX, and dependency review before any implementation PR is opened. Do not create descriptor plumbing until those decisions are recorded here.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    area: securitySecurity invariants, hardening, and security-sensitive boundaries.area: wallet/coreWallet integration and Bitcoin Core boundaries.enhancementNew feature or requestquestionFurther information is requested

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions