From 4cdd4b5343e5c40d4f3b1473226f4d55da11c24e Mon Sep 17 00:00:00 2001 From: M1 Date: Wed, 18 Mar 2026 23:24:17 +0400 Subject: [PATCH] fix: derive LTC as P2WPKH (native segwit ltc1q) not legacy P2PKH --- apps/pay/src/address.ts | 21 ++++++++++----------- 1 file changed, 10 insertions(+), 11 deletions(-) diff --git a/apps/pay/src/address.ts b/apps/pay/src/address.ts index 86d86a4..3ba77a8 100644 --- a/apps/pay/src/address.ts +++ b/apps/pay/src/address.ts @@ -83,17 +83,16 @@ export function deriveAddressSafe(coin: string, index: number): string { return addr.replace(/^bitcoincash:/, "ecash:"); } if (coin === "ltc") { - // zpub uses BIP84 version bytes — convert to Ltub so bitcore-lib-ltc can parse it - let key = xpub; - if (xpub.startsWith("zpub") || xpub.startsWith("Zpub") || xpub.startsWith("Ltub") || xpub.startsWith("Mtub")) { - // bitcore-lib-ltc only understands standard xpub version bytes (0x0488b21e). - // Convert zpub/Ltub/Mtub → xpub by swapping the 4-byte version prefix. - const decoded = Buffer.from(bs58check.decode(xpub)); - decoded[0] = 0x04; decoded[1] = 0x88; decoded[2] = 0xb2; decoded[3] = 0x1e; - key = bs58check.encode(decoded); - } - const hd = new bitcoreLtc.HDPublicKey(key); - return hd.deriveChild(0).deriveChild(index).publicKey.toAddress().toString(); + // All zpub/Ltub/Mtub/xpub variants share the same key data — only version bytes differ. + // Remap to the standard xpub version (0x0488b21e) so bitcore-lib-ltc can parse it, + // then derive a native segwit P2WPKH (bech32 ltc1q...) address. + const decoded = Buffer.from(bs58check.decode(xpub)); + decoded[0] = 0x04; decoded[1] = 0x88; decoded[2] = 0xb2; decoded[3] = 0x1e; + const normalized = bs58check.encode(decoded); + const hd = new bitcoreLtc.HDPublicKey(normalized); + const pubkey = hd.deriveChild(0).deriveChild(index).publicKey; + // Derive as P2WPKH (native segwit, bech32 ltc1q...) + return new bitcoreLtc.Address(pubkey, bitcoreLtc.Networks.mainnet, bitcoreLtc.Address.PayToWitnessPublicKeyHash).toString(); } if (coin === "doge") { const hd = new bitcoreDoge.HDPublicKey(xpub);