MCPcopy Create free account
hub / github.com/ElementsProject/elements / SubmitPackage

Method SubmitPackage

src/validation.cpp:1174–1247  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

1172}
1173
1174bool MemPoolAccept::SubmitPackage(const ATMPArgs& args, std::vector<Workspace>& workspaces,
1175 PackageValidationState& package_state,
1176 std::map<const uint256, const MempoolAcceptResult>& results)
1177{
1178 AssertLockHeld(cs_main);
1179 AssertLockHeld(m_pool.cs);
1180 // Sanity check: none of the transactions should be in the mempool, and none of the transactions
1181 // should have a same-txid-different-witness equivalent in the mempool.
1182 assert(std::all_of(workspaces.cbegin(), workspaces.cend(), [this](const auto& ws){
1183 return !m_pool.exists(GenTxid::Txid(ws.m_ptx->GetHash())); }));
1184
1185 bool all_submitted = true;
1186 // ConsensusScriptChecks adds to the script cache and is therefore consensus-critical;
1187 // CheckInputsFromMempoolAndCache asserts that transactions only spend coins available from the
1188 // mempool or UTXO set. Submit each transaction to the mempool immediately after calling
1189 // ConsensusScriptChecks to make the outputs available for subsequent transactions.
1190 for (Workspace& ws : workspaces) {
1191 if (!ConsensusScriptChecks(args, ws)) {
1192 results.emplace(ws.m_ptx->GetWitnessHash(), MempoolAcceptResult::Failure(ws.m_state));
1193 // Since PolicyScriptChecks() passed, this should never fail.
1194 all_submitted = false;
1195 package_state.Invalid(PackageValidationResult::PCKG_MEMPOOL_ERROR,
1196 strprintf("BUG! PolicyScriptChecks succeeded but ConsensusScriptChecks failed: %s",
1197 ws.m_ptx->GetHash().ToString()));
1198 }
1199
1200 // Re-calculate mempool ancestors to call addUnchecked(). They may have changed since the
1201 // last calculation done in PreChecks, since package ancestors have already been submitted.
1202 std::string unused_err_string;
1203 if(!m_pool.CalculateMemPoolAncestors(*ws.m_entry, ws.m_ancestors, m_limit_ancestors,
1204 m_limit_ancestor_size, m_limit_descendants,
1205 m_limit_descendant_size, unused_err_string)) {
1206 results.emplace(ws.m_ptx->GetWitnessHash(), MempoolAcceptResult::Failure(ws.m_state));
1207 // Since PreChecks() and PackageMempoolChecks() both enforce limits, this should never fail.
1208 all_submitted = false;
1209 package_state.Invalid(PackageValidationResult::PCKG_MEMPOOL_ERROR,
1210 strprintf("BUG! Mempool ancestors or descendants were underestimated: %s",
1211 ws.m_ptx->GetHash().ToString()));
1212 }
1213 // If we call LimitMempoolSize() for each individual Finalize(), the mempool will not take
1214 // the transaction's descendant feerate into account because it hasn't seen them yet. Also,
1215 // we risk evicting a transaction that a subsequent package transaction depends on. Instead,
1216 // allow the mempool to temporarily bypass limits, the maximum package size) while
1217 // submitting transactions individually and then trim at the very end.
1218 if (!Finalize(args, ws)) {
1219 results.emplace(ws.m_ptx->GetWitnessHash(), MempoolAcceptResult::Failure(ws.m_state));
1220 // Since LimitMempoolSize() won't be called, this should never fail.
1221 all_submitted = false;
1222 package_state.Invalid(PackageValidationResult::PCKG_MEMPOOL_ERROR,
1223 strprintf("BUG! Adding to mempool failed: %s", ws.m_ptx->GetHash().ToString()));
1224 }
1225 }
1226
1227 // It may or may not be the case that all the transactions made it into the mempool. Regardless,
1228 // make sure we haven't exceeded max mempool size.
1229 LimitMempoolSize(m_pool, m_active_chainstate.CoinsTip(),
1230 gArgs.GetIntArg("-maxmempool", DEFAULT_MAX_MEMPOOL_SIZE) * 1000000,
1231 std::chrono::hours{gArgs.GetIntArg("-mempoolexpiry", DEFAULT_MEMPOOL_EXPIRY)});

Callers

nothing calls this directly

Calls 9

cbeginMethod · 0.80
cendMethod · 0.80
InvalidMethod · 0.80
GetIntArgMethod · 0.80
existsMethod · 0.45
GetHashMethod · 0.45
ToStringMethod · 0.45

Tested by

no test coverage detected