#36133 wallet: store multipath descriptor

full analysis

https://github.com/bitcoin/bitcoin/pull/36133 · Sjors · +1071/-362 in 24 files, 18 commits · labels: Wallet, Needs rebase · draft

Goal

  • Preserve multipath descriptor representations when importing or creating wallets
  • Allows exporting unified descriptors needed by hardware wallets for BIP 388 multisig registration
  • Eliminates error-prone manual reconstruction of descriptors for external signer tools

This PR modifies descriptor parsing and the wallet to preserve multipath descriptor representations. When multipath descriptors are imported or created for receive and change pairs, a new database record tracks the original multipath string and links it to the resulting expanded single-path descriptors, exposing it in `getaddressinfo` and `listdescriptors`.

Problem: Bitcoin Core expands multipath descriptors into separate receive and change descriptors upon import or wallet creation, discarding the multipath form. External tools like HWI and hardware wallets requiring BIP 388 multisig registration need the unified multipath descriptor, forcing users into error-prone manual reconstruction.

Category: Wallet (#28 of 84)

P2 · new feature

  • P2 because it enables exporting multipath descriptors required for BIP 388 multisig registration
  • Improves multisig signing safety and removes user friction when using hardware wallets via HWI

Enables exporting multipath descriptors directly from bitcoind RPCs, a prerequisite for modern hardware signer multisig registration under BIP 388. Sjors notes: 'HWI recently added a registerdescriptor command... which some hardware wallets require in order to (more safely) support multisig... The only catch is that we need to provide a multipath descriptor... This PR makes that possible.' Resolves user friction and enhances multisig signing safety across the ecosystem.

Membership: Adds database records and RPC fields to the wallet, and modifies descriptor parsing for wallet key management.

Factors: security/stability 1, bug 0, performance 0, user value 2, leverage 2

Reviewability: Stale: Needs rebase

  • Merge conflicts against master require a rebase
  • Marked draft while architectural approach remains under discussion

The PR has merge conflicts against master and is also marked draft while architectural approach discussion remains open.

Author status: active; engaging with feedback, but PR has merge conflicts and is marked draft awaiting conceptual consensus

Open concerns:

  • achow101 raised a Concept NACKish objecting to storing multipath strings in the wallet database and having Parse emit them, arguing that multipath descriptors should instead be reconstructed on the fly by walking descriptor objects in parallel

Resolved concerns:

  • Preventing ambiguous multipath mappings when single-path descriptors overlap between multiple imported multipath descriptors
  • Consistently formatting hardened derivation indicators with 'h' across expanded and multipath strings

Agreement: Disputed

  • Disputed approach to multipath representation between storage and dynamic reconstruction
  • Objecting to storing multipath strings in the DB, favoring dynamic pairwise traversal (achow101)
  • Concept approval for matching existing wallet descriptors (jeanpablojp)

Disputed: achow101 opposes storing multipath strings in the DB and altering Parse, favoring in-memory object reconstruction

achow101 expressed a Concept NACKish against storing multipath strings as separate database records and having `Parse` output string representations, arguing that the wallet should not store or rely on multipath strings and that descriptors should instead be reconstructed dynamically from descriptor objects. The author defended the parser-level capture approach as preserving original intent without requiring reverse reconstruction.

  • jeanpablojp gave Concept ACK: 'Concept ACK... The matching approaches in #36075 work off descriptors a wallet already has...'
  • achow101: 'Concept NACKish... My suggestion was not to store an extra record, but rather an extra field in WalletDescriptor which contains the ids of the other descriptors in the multipath. Reconstructing the multipath can be done by doing a pairwise traversal in Descriptor::ToString()... Parse should never return strings.'

Review verdicts (DrahtBot): 0

Dependencies

Depends on: #36230

Enables:

  • HWI BIP 388 descriptor registration support (#841, #842)

Files

413 lines under test/bench/ci.

  • src/script/descriptor.cpp +372/-242
  • src/test/descriptor_tests.cpp +154/-38
  • src/wallet/wallet.cpp +84/-11
  • test/functional/wallet_importdescriptors.py +64/-1
  • src/wallet/test/walletload_tests.cpp +61/-0
  • src/wallet/walletutil.h +51/-2
  • src/wallet/rpc/backup.cpp +44/-7
  • src/wallet/walletutil.cpp +20/-19
  • src/wallet/walletdb.cpp +36/-1
  • test/functional/wallet_descriptor.py +35/-0
  • src/wallet/rpc/wallet.cpp +8/-22
  • src/wallet/wallet.h +27/-2
  • src/wallet/export.cpp +23/-0
  • test/functional/wallet_createwalletdescriptor.py +23/-0
  • src/script/descriptor.h +16/-6
  • test/functional/wallet_backwards_compatibility.py +17/-0
  • test/functional/wallet_listdescriptors.py +11/-0
  • test/functional/wallet_exported_watchonly.py +8/-1
  • src/wallet/scriptpubkeyman.cpp +3/-5
  • src/wallet/export.h +5/-2
  • src/script/miniscript.h +2/-2
  • src/wallet/rpc/addresses.cpp +4/-0
  • src/wallet/scriptpubkeyman.h +1/-1
  • src/wallet/walletdb.h +2/-0

Card

PR #36133 allows Bitcoin Core wallets to retain and expose multipath descriptors (e.g. BIP 389 receive/change combinations) via RPC methods like getaddressinfo and listdescriptors. Currently, Core permanently expands multipath descriptors into separate single-path descriptors, preventing users and tools like HWI from easily retrieving the multipath string needed for BIP 388 hardware wallet multisig registration. The change adds a dedicated database record and extends descriptor parsing, but achow101 has raised a Concept NACKish arguing for reconstructing multipath descriptors in memory from descriptor objects rather than storing strings in the DB. The PR is in draft and currently needs a rebase.

Data

dossier JSON · extract JSON · model openrouter/google/gemini-3.8-flash, generated 2026-09-17T16:23, confidence high, input hash 89115e0776c21dc4