Fix errors caused by P2TR inputs without witness data

This commit is contained in:
Vojtěch Strnad 2024-07-01 02:02:53 +02:00
parent 98e9d1a6c3
commit 7432e6e29b
2 changed files with 32 additions and 25 deletions

View File

@ -71,6 +71,10 @@ export function calcSegwitFeeGains(tx: Transaction) {
} }
if (isP2tr) { if (isP2tr) {
// every valid taproot input has at least one witness item, however transactions
// created before taproot activation don't need to have any witness data
// (see https://mempool.space/tx/b10c007c60e14f9d087e0291d4d0c7869697c6681d979c6639dbd960792b4d41)
if (vin.witness?.length) {
if (vin.witness.length === 1) { if (vin.witness.length === 1) {
// key path spend // key path spend
// we don't know if this was a multisig or single sig (the goal of taproot :)), // we don't know if this was a multisig or single sig (the goal of taproot :)),
@ -85,6 +89,7 @@ export function calcSegwitFeeGains(tx: Transaction) {
// but only assumptions can be made because the scripts themselves are unknown (again, the goal of taproot :)) // but only assumptions can be made because the scripts themselves are unknown (again, the goal of taproot :))
// TODO maybe add some complex scripts that are specified somewhere, so that size is known, such as lightning scripts // TODO maybe add some complex scripts that are specified somewhere, so that size is known, such as lightning scripts
} }
}
} else { } else {
const script = isP2shP2Wsh || isP2wsh ? vin.inner_witnessscript_asm : vin.inner_redeemscript_asm; const script = isP2shP2Wsh || isP2wsh ? vin.inner_witnessscript_asm : vin.inner_redeemscript_asm;
let replacementSize: number; let replacementSize: number;

View File

@ -335,10 +335,11 @@ export function getTransactionFlags(tx: Transaction, cpfpInfo?: CpfpInfo, replac
case 'v0_p2wpkh': flags |= TransactionFlags.p2wpkh; break; case 'v0_p2wpkh': flags |= TransactionFlags.p2wpkh; break;
case 'v0_p2wsh': flags |= TransactionFlags.p2wsh; break; case 'v0_p2wsh': flags |= TransactionFlags.p2wsh; break;
case 'v1_p2tr': { case 'v1_p2tr': {
if (!vin.witness?.length) {
throw new Error('Taproot input missing witness data');
}
flags |= TransactionFlags.p2tr; flags |= TransactionFlags.p2tr;
// every valid taproot input has at least one witness item, however transactions
// created before taproot activation don't need to have any witness data
// (see https://mempool.space/tx/b10c007c60e14f9d087e0291d4d0c7869697c6681d979c6639dbd960792b4d41)
if (vin.witness?.length) {
// in taproot, if the last witness item begins with 0x50, it's an annex // in taproot, if the last witness item begins with 0x50, it's an annex
const hasAnnex = vin.witness?.[vin.witness.length - 1].startsWith('50'); const hasAnnex = vin.witness?.[vin.witness.length - 1].startsWith('50');
// script spends have more than one witness item, not counting the annex (if present) // script spends have more than one witness item, not counting the annex (if present)
@ -350,6 +351,7 @@ export function getTransactionFlags(tx: Transaction, cpfpInfo?: CpfpInfo, replac
flags |= TransactionFlags.inscription; flags |= TransactionFlags.inscription;
} }
} }
}
} break; } break;
} }