doc: IsFinalTx comment about nSequence & OP_CLTV

It's somewhat surprising that a transaction's nLockTime field is ignored
when all nSequence fields are final, so this change aims to clarify this
behavior and cross reference relevant details of OP_CHECKLOCKTIMEVERIFY.
pull/826/head
Yuval Kogman 5 years ago
parent c6d6bc8abb
commit f9e37f33ce

@ -20,6 +20,15 @@ bool IsFinalTx(const CTransaction &tx, int nBlockHeight, int64_t nBlockTime)
return true; return true;
if ((int64_t)tx.nLockTime < ((int64_t)tx.nLockTime < LOCKTIME_THRESHOLD ? (int64_t)nBlockHeight : nBlockTime)) if ((int64_t)tx.nLockTime < ((int64_t)tx.nLockTime < LOCKTIME_THRESHOLD ? (int64_t)nBlockHeight : nBlockTime))
return true; return true;
// Even if tx.nLockTime isn't satisfied by nBlockHeight/nBlockTime, a
// transaction is still considered final if all inputs' nSequence ==
// SEQUENCE_FINAL (0xffffffff), in which case nLockTime is ignored.
//
// Because of this behavior OP_CHECKLOCKTIMEVERIFY/CheckLockTime() will
// also check that the spending input's nSequence != SEQUENCE_FINAL,
// ensuring that an unsatisfied nLockTime value will actually cause
// IsFinalTx() to return false here:
for (const auto& txin : tx.vin) { for (const auto& txin : tx.vin) {
if (!(txin.nSequence == CTxIn::SEQUENCE_FINAL)) if (!(txin.nSequence == CTxIn::SEQUENCE_FINAL))
return false; return false;

@ -1741,9 +1741,9 @@ bool GenericTransactionSignatureChecker<T>::CheckLockTime(const CScriptNum& nLoc
if (nLockTime > (int64_t)txTo->nLockTime) if (nLockTime > (int64_t)txTo->nLockTime)
return false; return false;
// Finally the nLockTime feature can be disabled and thus // Finally the nLockTime feature can be disabled in IsFinalTx()
// CHECKLOCKTIMEVERIFY bypassed if every txin has been // and thus CHECKLOCKTIMEVERIFY bypassed if every txin has
// finalized by setting nSequence to maxint. The // been finalized by setting nSequence to maxint. The
// transaction would be allowed into the blockchain, making // transaction would be allowed into the blockchain, making
// the opcode ineffective. // the opcode ineffective.
// //

Loading…
Cancel
Save