|
43 | 43 | #include <validationinterface.h>
|
44 | 44 | #include <walletinitinterface.h>
|
45 | 45 |
|
| 46 | +#include <algorithm> |
46 | 47 | #include <functional>
|
47 | 48 | #include <stdexcept>
|
48 | 49 |
|
@@ -161,7 +162,7 @@ ChainTestingSetup::ChainTestingSetup(const std::string& chainName, const std::ve
|
161 | 162 | GetMainSignals().RegisterBackgroundSignalScheduler(*m_node.scheduler);
|
162 | 163 |
|
163 | 164 | m_node.fee_estimator = std::make_unique<CBlockPolicyEstimator>();
|
164 |
| - m_node.mempool = std::make_unique<CTxMemPool>(m_node.fee_estimator.get(), 1); |
| 165 | + m_node.mempool = std::make_unique<CTxMemPool>(m_node.fee_estimator.get(), m_node.args->GetIntArg("-checkmempool", 1)); |
165 | 166 |
|
166 | 167 | m_cache_sizes = CalculateCacheSizes(m_args);
|
167 | 168 |
|
@@ -242,8 +243,8 @@ TestingSetup::TestingSetup(const std::string& chainName, const std::vector<const
|
242 | 243 | }
|
243 | 244 | }
|
244 | 245 |
|
245 |
| -TestChain100Setup::TestChain100Setup(const std::vector<const char*>& extra_args) |
246 |
| - : TestingSetup{CBaseChainParams::REGTEST, extra_args} |
| 246 | +TestChain100Setup::TestChain100Setup(const std::string& chain_name, const std::vector<const char*>& extra_args) |
| 247 | + : TestingSetup{chain_name, extra_args} |
247 | 248 | {
|
248 | 249 | SetMockTime(1598887952);
|
249 | 250 | constexpr std::array<unsigned char, 32> vchKey = {
|
@@ -357,6 +358,52 @@ CMutableTransaction TestChain100Setup::CreateValidMempoolTransaction(CTransactio
|
357 | 358 | return mempool_txn;
|
358 | 359 | }
|
359 | 360 |
|
| 361 | +std::vector<CTransactionRef> TestChain100Setup::PopulateMempool(FastRandomContext& det_rand, size_t num_transactions, bool submit) |
| 362 | +{ |
| 363 | + std::vector<CTransactionRef> mempool_transactions; |
| 364 | + std::deque<std::pair<COutPoint, CAmount>> unspent_prevouts; |
| 365 | + std::transform(m_coinbase_txns.begin(), m_coinbase_txns.end(), std::back_inserter(unspent_prevouts), |
| 366 | + [](const auto& tx){ return std::make_pair(COutPoint(tx->GetHash(), 0), tx->vout[0].nValue); }); |
| 367 | + while (num_transactions > 0 && !unspent_prevouts.empty()) { |
| 368 | + // The number of inputs and outputs are random, between 1 and 24. |
| 369 | + CMutableTransaction mtx = CMutableTransaction(); |
| 370 | + const size_t num_inputs = det_rand.randrange(24) + 1; |
| 371 | + CAmount total_in{0}; |
| 372 | + for (size_t n{0}; n < num_inputs; ++n) { |
| 373 | + if (unspent_prevouts.empty()) break; |
| 374 | + const auto& [prevout, amount] = unspent_prevouts.front(); |
| 375 | + mtx.vin.push_back(CTxIn(prevout, CScript())); |
| 376 | + total_in += amount; |
| 377 | + unspent_prevouts.pop_front(); |
| 378 | + } |
| 379 | + const size_t num_outputs = det_rand.randrange(24) + 1; |
| 380 | + // Approximately 1000sat "fee," equal output amounts. |
| 381 | + const CAmount amount_per_output = (total_in - 1000) / num_outputs; |
| 382 | + for (size_t n{0}; n < num_outputs; ++n) { |
| 383 | + CScript spk = CScript() << CScriptNum(num_transactions + n); |
| 384 | + mtx.vout.push_back(CTxOut(amount_per_output, spk)); |
| 385 | + } |
| 386 | + CTransactionRef ptx = MakeTransactionRef(mtx); |
| 387 | + mempool_transactions.push_back(ptx); |
| 388 | + if (amount_per_output > 2000) { |
| 389 | + // If the value is high enough to fund another transaction + fees, keep track of it so |
| 390 | + // it can be used to build a more complex transaction graph. Insert randomly into |
| 391 | + // unspent_prevouts for extra randomness in the resulting structures. |
| 392 | + for (size_t n{0}; n < num_outputs; ++n) { |
| 393 | + unspent_prevouts.push_back(std::make_pair(COutPoint(ptx->GetHash(), n), amount_per_output)); |
| 394 | + std::swap(unspent_prevouts.back(), unspent_prevouts[det_rand.randrange(unspent_prevouts.size())]); |
| 395 | + } |
| 396 | + } |
| 397 | + if (submit) { |
| 398 | + LOCK2(m_node.mempool->cs, cs_main); |
| 399 | + LockPoints lp; |
| 400 | + m_node.mempool->addUnchecked(CTxMemPoolEntry(ptx, 1000, 0, 1, false, 4, lp)); |
| 401 | + } |
| 402 | + --num_transactions; |
| 403 | + } |
| 404 | + return mempool_transactions; |
| 405 | +} |
| 406 | + |
360 | 407 | CTxMemPoolEntry TestMemPoolEntryHelper::FromTx(const CMutableTransaction& tx) const
|
361 | 408 | {
|
362 | 409 | return FromTx(MakeTransactionRef(tx));
|
|
0 commit comments