mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-01-10 11:57:28 -03:00
[validation] don't package validate if not policy or missing inputs
Package validation policy only differs from individual policy in its evaluation of feerate. Minimize DoS surface; don't validate all over again if we know the result will be the same.
This commit is contained in:
parent
51edcffa0e
commit
9bebf35e26
1 changed files with 14 additions and 1 deletions
|
@ -1342,6 +1342,7 @@ PackageMempoolAcceptResult MemPoolAccept::AcceptPackage(const Package& package,
|
|||
// the new transactions. This ensures we don't double-count transaction counts and sizes when
|
||||
// checking ancestor/descendant limits, or double-count transaction fees for fee-related policy.
|
||||
ATMPArgs single_args = ATMPArgs::SingleInPackageAccept(args);
|
||||
bool quit_early{false};
|
||||
std::vector<CTransactionRef> txns_new;
|
||||
for (const auto& tx : package) {
|
||||
const auto& wtxid = tx->GetWitnessHash();
|
||||
|
@ -1375,6 +1376,18 @@ PackageMempoolAcceptResult MemPoolAccept::AcceptPackage(const Package& package,
|
|||
// in package validation, because its fees should only be "used" once.
|
||||
assert(m_pool.exists(GenTxid::Wtxid(wtxid)));
|
||||
results.emplace(wtxid, single_res);
|
||||
} else if (single_res.m_state.GetResult() != TxValidationResult::TX_MEMPOOL_POLICY &&
|
||||
single_res.m_state.GetResult() != TxValidationResult::TX_MISSING_INPUTS) {
|
||||
// Package validation policy only differs from individual policy in its evaluation
|
||||
// of feerate. For example, if a transaction fails here due to violation of a
|
||||
// consensus rule, the result will not change when it is submitted as part of a
|
||||
// package. To minimize the amount of repeated work, unless the transaction fails
|
||||
// due to feerate or missing inputs (its parent is a previous transaction in the
|
||||
// package that failed due to feerate), don't run package validation. Note that this
|
||||
// decision might not make sense if different types of packages are allowed in the
|
||||
// future. Continue individually validating the rest of the transactions, because
|
||||
// some of them may still be valid.
|
||||
quit_early = true;
|
||||
} else {
|
||||
txns_new.push_back(tx);
|
||||
}
|
||||
|
@ -1382,7 +1395,7 @@ PackageMempoolAcceptResult MemPoolAccept::AcceptPackage(const Package& package,
|
|||
}
|
||||
|
||||
// Nothing to do if the entire package has already been submitted.
|
||||
if (txns_new.empty()) {
|
||||
if (quit_early || txns_new.empty()) {
|
||||
// No package feerate when no package validation was done.
|
||||
return PackageMempoolAcceptResult(package_state, std::move(results));
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue