From d6df9784d289501ccc8e6bb6c70e03a645d35a0c Mon Sep 17 00:00:00 2001 From: user Date: Sat, 28 Feb 2026 10:36:28 -0800 Subject: [PATCH] fix: derive xprv addresses from correct BIP44 path (m/44'/60'/0'/0) hdWalletFromXprv() and getSignerForAddress() for xprv type were deriving addresses directly from the root key (m/N) instead of the standard BIP44 Ethereum path (m/44'/60'/0'/0/N). This caused imported xprv wallets to generate completely wrong addresses. Navigate to the BIP44 Ethereum derivation path before deriving child addresses, matching the behavior of mnemonic-based wallet imports. --- src/shared/wallet.js | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/src/shared/wallet.js b/src/shared/wallet.js index 8abebf6..ff29648 100644 --- a/src/shared/wallet.js +++ b/src/shared/wallet.js @@ -25,10 +25,11 @@ function hdWalletFromMnemonic(mnemonic) { } function hdWalletFromXprv(xprv) { - const node = HDNodeWallet.fromExtendedKey(xprv); - if (!node.privateKey) { + const root = HDNodeWallet.fromExtendedKey(xprv); + if (!root.privateKey) { throw new Error("Not an extended private key (xprv)."); } + const node = root.derivePath("44'/60'/0'/0"); const xpub = node.neuter().extendedKey; const firstAddress = node.deriveChild(0).address; return { xpub, firstAddress }; @@ -58,7 +59,8 @@ function getSignerForAddress(walletData, addrIndex, decryptedSecret) { return node.deriveChild(addrIndex); } if (walletData.type === "xprv") { - const node = HDNodeWallet.fromExtendedKey(decryptedSecret); + const root = HDNodeWallet.fromExtendedKey(decryptedSecret); + const node = root.derivePath("44'/60'/0'/0"); return node.deriveChild(addrIndex); } return new Wallet(decryptedSecret);