Commit Graph

83 Commits

Author SHA1 Message Date
Suhas Daftuar
2d88966e43 miner: replace "package" with "chunk"
This makes the terminology consistent with other parts of the codebase, as part
of the cluster mempool implementation.
2025-11-30 13:50:04 -05:00
Suhas Daftuar
6f3e8eb300 Add a GetFeePerVSize() accessor to CFeeRate, and use it in the BlockAssembler 2025-11-30 13:50:04 -05:00
merge-script
fa283d28e2 Merge bitcoin/bitcoin#33629: Cluster mempool
17cf9ff7ef Use cluster size limit for -maxmempool bound, and allow -maxmempool=0 in general (Suhas Daftuar)
315e43e5d8 Sanity check `GetFeerateDiagram()` in CTxMemPool::check() (Suhas Daftuar)
de2e9a24c4 test: extend package rbf functional test to larger clusters (Suhas Daftuar)
4ef4ddb504 doc: update policy/packages.md for new package acceptance logic (Suhas Daftuar)
79f73ad713 Add check that GetSortedScoreWithTopology() agrees with CompareMiningScoreWithTopology() (Suhas Daftuar)
a86ac11768 Update comments for CTxMemPool class (Suhas Daftuar)
9567eaa66d Invoke TxGraph::DoWork() at appropriate times (Suhas Daftuar)
6c5c44f774 test: add functional test for new cluster mempool RPCs (Suhas Daftuar)
72f60c877e doc: Update mempool_replacements.md to reflect feerate diagram checks (Suhas Daftuar)
21693f031a Expose cluster information via rpc (Suhas Daftuar)
72e74e0d42 fuzz: try to add more code coverage for mempool fuzzing (Suhas Daftuar)
f107417490 bench: add more mempool benchmarks (Suhas Daftuar)
7976eb1ae7 Avoid violating mempool policy limits in tests (Suhas Daftuar)
84de685cf7 Stop tracking parents/children outside of txgraph (Suhas Daftuar)
88672e205b Rewrite GatherClusters to use the txgraph implementation (Suhas Daftuar)
1ca4f01090 Fix miniminer_tests to work with cluster limits (Suhas Daftuar)
1902111e0f Eliminate CheckPackageLimits, which no longer does anything (Suhas Daftuar)
3a646ec462 Rework RBF and TRUC validation (Suhas Daftuar)
19b8479868 Make getting parents/children a function of the mempool, not a mempool entry (Suhas Daftuar)
5560913e51 Rework truc_policy to use descendants, not children (Suhas Daftuar)
a4458d6c40 Use txgraph to calculate descendants (Suhas Daftuar)
c8b6f70d64 Use txgraph to calculate ancestors (Suhas Daftuar)
241a3e666b Simplify ancestor calculation functions (Suhas Daftuar)
b9cec7f0a1 Make removeConflicts private (Suhas Daftuar)
0402e6c780 Remove unused limits from CalculateMemPoolAncestors (Suhas Daftuar)
08be765ac2 Remove mempool logic designed to maintain ancestor/descendant state (Suhas Daftuar)
fc4e3e6bc1 Remove unused members from CTxMemPoolEntry (Suhas Daftuar)
ff3b398d12 mempool: eliminate accessors to mempool entry ancestor/descendant cached state (Suhas Daftuar)
b9a2039f51 Eliminate use of cached ancestor data in miniminer_tests and truc_policy (Suhas Daftuar)
ba09fc9774 mempool: Remove unused function CalculateDescendantMaximum (Suhas Daftuar)
8e49477e86 wallet: Replace max descendant count with cluster_count (Suhas Daftuar)
e031085fd4 Eliminate Single-Conflict RBF Carve Out (Suhas Daftuar)
cf3ab8e1d0 Stop enforcing descendant size/count limits (Suhas Daftuar)
89ae38f489 test: remove rbf carveout test from mempool_limit.py (Suhas Daftuar)
c0bd04d18f Calculate descendant information for mempool RPC output on-the-fly (Suhas Daftuar)
bdcefb8a8b Use mempool/txgraph to determine if a tx has descendants (Suhas Daftuar)
69e1eaa6ed Add test case for cluster size limits to TRUC logic (Suhas Daftuar)
9cda64b86c Stop enforcing ancestor size/count limits (Suhas Daftuar)
1f93227a84 Remove dependency on cached ancestor data in mini-miner (Suhas Daftuar)
9fbe0a4ac2 rpc: Calculate ancestor data from scratch for mempool rpc calls (Suhas Daftuar)
7961496dda Reimplement GetTransactionAncestry() to not rely on cached data (Suhas Daftuar)
feceaa42e8 Remove CTxMemPool::GetSortedDepthAndScore (Suhas Daftuar)
21b5cea588 Use cluster linearization for transaction relay sort order (Suhas Daftuar)
6445aa7d97 Remove the ancestor and descendant indices from the mempool (Suhas Daftuar)
216e693729 Implement new RBF logic for cluster mempool (Suhas Daftuar)
ff8f115dec policy: Remove CPFP carveout rule (Suhas Daftuar)
c3f1afc934 test: rewrite PopulateMempool to not violate mempool policy (cluster size) limits (Suhas Daftuar)
47ab32fdb1 Select transactions for blocks based on chunk feerate (Suhas Daftuar)
dec138d1dd fuzz: remove comparison between mini_miner block construction and miner (Suhas Daftuar)
6c2bceb200 bench: rewrite ComplexMemPool to not create oversized clusters (Suhas Daftuar)
1ad4590f63 Limit mempool size based on chunk feerate (Suhas Daftuar)
b11c89cab2 Rework miner_tests to not require large cluster limit (Suhas Daftuar)
95a8297d48 Check cluster limits when using -walletrejectlongchains (Suhas Daftuar)
95762e6759 Do not allow mempool clusters to exceed configured limits (Suhas Daftuar)
edb3e7cdf6 [test] rework/delete feature_rbf tests requiring large clusters (glozow)
435fd56711 test: update feature_rbf.py replacement test (Suhas Daftuar)
34e32985e8 Add new (unused) limits for cluster size/count (Suhas Daftuar)
838d7e3553 Add transactions to txgraph, but without cluster dependencies (Suhas Daftuar)
d5ed9cb3eb Add accessor for sigops-adjusted weight (Suhas Daftuar)
1bf3b51396 Add sigops adjusted weight calculator (Suhas Daftuar)
c18c68a950 Create a txgraph inside CTxMemPool (Suhas Daftuar)
29a94d5b2f Make CTxMemPoolEntry derive from TxGraph::Ref (Suhas Daftuar)
92b0079fe3 Allow moving CTxMemPoolEntry objects, disallow copying (Suhas Daftuar)
6c73e47448 mempool: Store iterators into mapTx in mapNextTx (Suhas Daftuar)
51430680ec Allow moving an Epoch::Marker (Suhas Daftuar)

Pull request description:

  [Reopening #28676 here as a new PR, because GitHub is slow to load the page making it hard to scroll through and see comments.  Also, that PR was originally opened with a prototype implementation which has changed significantly with the introduction of `TxGraph`.]

  This is an implementation of the [cluster mempool proposal](https://delvingbitcoin.org/t/an-overview-of-the-cluster-mempool-proposal/393).

  This branch implements the following observable behavior changes:

   - Maintains a partitioning of the mempool into connected clusters (via the `txgraph` class), which are limited in vsize to 101 kvB by default, and limited in count to 64 by default.
   - Each cluster is sorted ("linearized") to try to optimize for selecting highest-feerate-subsets of a cluster first
   - Transaction selection for mining is updated to use the cluster linearizations, selecting highest feerate "chunks" first for inclusion in a block template.
   - Mempool eviction is updated to use the cluster linearizations, selecting lowest feerate "chunks" first for removal.
   - The RBF rules are updated to: (a) drop the requirement that no new inputs are introduced; (b) change the feerate requirement to instead check that the feerate diagram of the mempool will strictly improve; (c) replace the direct conflicts limit with a directly-conflicting-clusters limit.
   - The CPFP carveout rule is eliminated (it doesn't make sense in a cluster-limited mempool)
   - The ancestor and descendant limits are no longer enforced.
   - New cluster count/cluster vsize limits are now enforced instead.
   - Transaction relay now uses chunk feerate comparisons to determine the order that newly received transactions are announced to peers.

  Additionally, the cached ancestor and descendant data are dropped from the mempool, along with the multi_index indices that were maintained to sort the mempool by ancestor and descendant feerates. For compatibility (eg with wallet behavior or RPCs exposing this), this information is now calculated dynamically instead.

ACKs for top commit:
  instagibbs:
    reACK 17cf9ff7ef
  glozow:
    reACK 17cf9ff7ef
  sipa:
    ACK 17cf9ff7ef

Tree-SHA512: bbde46d913d56f8d9c0426cb0a6c4fa80b01b0a4c2299500769921f886082fb4f51f1694e0ee1bc318c52e1976d7ebed8134a64eda0b8044f3a708c04938eee7
2025-11-25 10:35:11 +00:00
Suhas Daftuar
47ab32fdb1 Select transactions for blocks based on chunk feerate
Co-Authored-By: Gregory Sanders <gsanders87@gmail.com>
2025-11-18 08:53:58 -05:00
merge-script
3c3c6adb72 Merge bitcoin/bitcoin#33745: mining: check witness commitment in submitBlock
6eaa00fe20 test: clarify submitBlock() mutates the template (Sjors Provoost)
862bd43283 mining: ensure witness commitment check in submitBlock (Sjors Provoost)
00d1b6ef4b doc: clarify UpdateUncommittedBlockStructures (Sjors Provoost)

Pull request description:

  When an IPC client requests a new block template via the Mining interface, we hold on to its `CBlock`. That way when they call `submitSolution()` we can modify it in place, rather than having to reconstruct the full block like the `submitblock` RPC does.

  Before this commit however we forgot to invalidate `m_checked_witness_commitment`, which we should since the client brings a new coinbase.

  This would cause us to accept an invalid chaintip.

  Fix this and add a test to confirm that we now reject such a block. As a sanity check, we add a second node to the test and confirm that will accept our mined block.

  As first noticed in #33374 the IPC code takes the coinbase as provided, unlike the `submitblock` RPC which calls `UpdateUncommittedBlockStructures()` and adds witness commitment to the coinbase if it was missing.

  Although that could have been an alternative fix, we instead document that IPC clients are expected to provide the full coinbase including witness commitment.

  Patch to produce the original issue:

  ```diff
  diff --git a/src/node/miner.cpp b/src/node/miner.cpp
  index b988e28a3f..28e9048a4d 100644
  --- a/src/node/miner.cpp
  +++ b/src/node/miner.cpp
  @@ -450,15 +450,10 @@ void AddMerkleRootAndCoinbase(CBlock& block, CTransactionRef coinbase, uint32_t
       }
       block.nVersion = version;
       block.nTime = timestamp;
       block.nNonce = nonce;
       block.hashMerkleRoot = BlockMerkleRoot(block);
  -
  -    // Reset cached checks
  -    block.m_checked_witness_commitment = false;
  -    block.m_checked_merkle_root = false;
  -    block.fChecked = false;
   }

   std::unique_ptr<CBlockTemplate> WaitAndCreateNewBlock(ChainstateManager& chainman,
                                                         KernelNotifications& kernel_notifications,
                                                         CTxMemPool* mempool,
  diff --git a/test/functional/interface_ipc.py b/test/functional/interface_ipc.py
  index cce56e3294..bf1b7048ab 100755
  --- a/test/functional/interface_ipc.py
  +++ b/test/functional/interface_ipc.py
  @@ -216,22 +216,22 @@ class IPCInterfaceTest(BitcoinTestFramework):
               assert_equal(res.result, True)

               # The remote template block will be mutated, capture the original:
               remote_block_before = await self.parse_and_deserialize_block(template, ctx)

  -            self.log.debug("Submitted coinbase must include witness")
  +            self.log.debug("Submitted coinbase with missing witness is accepted")
               assert_not_equal(coinbase.serialize_without_witness().hex(), coinbase.serialize().hex())
               res = await template.result.submitSolution(ctx, block.nVersion, block.nTime, block.nNonce, coinbase.serialize_without_witness())
  -            assert_equal(res.result, False)
  +            assert_equal(res.result, True)

               self.log.debug("Even a rejected submitBlock() mutates the template's block")
               # Can be used by clients to download and inspect the (rejected)
               # reconstructed block.
               remote_block_after = await self.parse_and_deserialize_block(template, ctx)
               assert_not_equal(remote_block_before.serialize().hex(), remote_block_after.serialize().hex())

  -            self.log.debug("Submit again, with the witness")
  +            self.log.debug("Submit again, with the witness - does not replace the invalid block")
               res = await template.result.submitSolution(ctx, block.nVersion, block.nTime, block.nNonce, coinbase.serialize())
               assert_equal(res.result, True)

               self.log.debug("Block should propagate")
               assert_equal(self.nodes[1].getchaintips()[0]["height"], current_block_height + 1)
  ```

ACKs for top commit:
  ryanofsky:
    Code review ACK 6eaa00fe20. Just documentation updates and test clarifications since last review, also splitting up a commit.
  TheCharlatan:
    Re-ACK 6eaa00fe20
  ismaelsadeeq:
    Code review and tested ACK   6eaa00fe20

Tree-SHA512: 3a6280345b0290fe8300ebc63c13ad4058d24ceb35b7d7a784b974d5f04f420860ac03a9bf2fc6a799ef3fc55552ce033e879fa369298f976b9a01d72bd55d9e
2025-11-12 10:03:48 -05:00
merge-script
ddd2afac10 Merge bitcoin/bitcoin#33676: interfaces: enable cancelling running waitNext calls
dcb56fd4cb interfaces: add interruptWait method (ismaelsadeeq)

Pull request description:

  This is an attempt to fix #33575 see the issue for background and the usefulness of this feature.

  This PR uses one of the suggested approaches: adding a new `interruptWaitNext()` method to the mining interface.

  It introduces a new boolean variable, `m_interrupt_wait`, which is set to `false` when the thread starts waiting. The `interruptWaitNext()` method wakes the thread and sets `m_interrupt_wait` to `true`.
  Whenever the thread wakes up, it checks whether the wait was aborted; if so, it simply set ` m_interrupt_wait ` to false and return`nullptr`.

  This PR also adds a functional test for the new method. The test uses `asyncio` to spawn two tasks and attempts to ensure that the wait is executed before the interrupt by using an event monitor. It adds a 0.1-second buffer to ensure the wait has started executing.
  If that buffer elapses without `waitNext` executing, the test will fail because a transaction is created after the buffer.

ACKs for top commit:
  furszy:
    Code ACK dcb56fd4cb
  ryanofsky:
    Code review ACK dcb56fd4cb, just tweaking semantics slightly since last review so if an `interruptWait` call is made shortly after a `waitNext` call it will reliably cause the `waitNext` call to return right away without blocking, even if the `waitNext` call had not begun to execute or wait yet.
  Sjors:
    tACK dcb56fd4cb
  TheCharlatan:
    ACK dcb56fd4cb

Tree-SHA512: a03f049e1f303b174a9e5d125733b6583dfd8effa12e7b6c37bd9b2cff9541100f5f4514e80f89005c44a57d7e47804afe87aa5fdb6831f3b0cd9b01d83e42be
2025-11-10 09:56:27 +00:00
Sjors Provoost
862bd43283 mining: ensure witness commitment check in submitBlock
When an IPC client requests a new block template via the Mining interface,
we hold on to its CBlock. That way when they call submitSolution() we can
modify it in place, rather than having to reconstruct the full block like
the submitblock RPC does.

Before this commit however we forgot to invalidate
m_checked_witness_commitment, which we should since the client brings a
new coinbase.

This would cause us to accept an invalid chaintip.

Fix this and add a test to confirm that we now reject such a block.
As a sanity check, we add a second node to the test and confirm that will
accept our mined block.

Note that the IPC code takes the coinbase as provided, unlike the
submitblock RPC which calls UpdateUncommittedBlockStructures() and adds
witness commitment to the coinbase if it was missing.

Although that could have been an alternative fix, we instead document that
IPC clients are expected to provide the full coinbase including witness
commitment.
2025-10-31 11:53:12 +01:00
ismaelsadeeq
dcb56fd4cb interfaces: add interruptWait method
- This method can be used to cancel a running
  waitNext().

- This commit also adds a test case for interruptWait method
2025-10-27 19:22:12 +01:00
Sjors Provoost
8f7673257a miner: fix empty mempool case for waitNext()
Block template fees are calculated by looping over new_tmpl->vTxFees
and return (early) once the fee_threshold is exceeded.

This left an edge case when the mempool is empty, which this commit
fixes and adds a test for. It does so by using std::accumulate instead
of manual loops.

Also update interface_ipc.py to account for the new behavior.

Co-authored-by: Raimo33 <claudio.raimondi@protonmail.com>
2025-10-13 18:39:18 +02:00
ismaelsadeeq
b807dfcdc5 miner: fix addPackageTxs unsigned integer overflow 2025-09-24 17:10:51 +02:00
Pieter Wuille
7392b8b084 miner: clamp options instead of asserting 2025-08-19 16:52:02 -04:00
Sjors Provoost
74690f4ed8 validation: refactor TestBlockValidity
Comments are expanded.

Return BlockValidationState instead of passing a reference.
Lock Chainman mutex instead of cs_main.
Remove redundant chainparams and pindexPrev arguments.
Drop defaults for checking proof-of-work and merkle root.

The ContextualCheckBlockHeader check is moved to after CheckBlock,
which is more similar to normal validation where context-free checks
are done first.

Validation failure reasons are no longer printed through LogError(),
since it depends on the caller whether this implies an actual bug
in the node, or an externally sourced block that happens to be invalid.
When called from getblocktemplate, via BlockAssembler::CreateNewBlock(),
this method already throws an std::runtime_error if validation fails.

Additionally it moves the inconclusive-not-best-prevblk check from RPC
code to TestBlockValidity.

There is no behavior change when callling getblocktemplate with proposal.
Previously this would return a BIP22ValidationResult which can throw for
state.IsError(). But CheckBlock() and the functions it calls only use
state.IsValid().

The final assert is changed into Assume, with a LogError.

Co-authored-by: <Ryan Ofsky <ryan@ofsky.org>
2025-06-14 14:32:45 +02:00
Ava Chow
e7a9372376 Merge bitcoin/bitcoin#32378: interfaces: refactor: move Mining and BlockTemplate implementation to miner
62fc42d475 interfaces: refactor: move `waitTipChanged` implementation to miner (ismaelsadeeq)
c39ca9d4f7 interfaces: move getTip implementation to miner (Sjors Provoost)
720f201e65 interfaces: refactor: move `waitNext` implementation to miner (ismaelsadeeq)
e6c2f4ce7a interfaces: refactor: move `submitSolution` implementation to miner (ismaelsadeeq)
02d4bc776b interfaces: remove redundant coinbase fee check in `waitNext` (ismaelsadeeq)

Pull request description:

  #### Motivation

  In  [Internal interface guidelines](https://github.com/bitcoin/bitcoin/blob/master/doc/developer-notes.md#internal-interface-guidelines)

  It's stated that

  > Interface method definitions should wrap existing functionality instead of implementing new functionality. Any substantial new node or wallet functionality should be implemented in [src/node/](https://github.com/bitcoin/bitcoin/blob/master/src/node) or [src/wallet/](https://github.com/bitcoin/bitcoin/blob/master/src/wallet) and just exposed in [src/interfaces/](https://github.com/bitcoin/bitcoin/blob/master/src/interfaces) instead of being implemented there, so it can be more modular and accessible to unit tests.

  However the some methods in the newly added  `BlockTemplateImpl` and `MinerImpl`  classes partially enforces this guideline, as the implementations of the `submitSolution`, `waitNext`, and `waitTipChanged` methods reside within the class itself.

  #### What the PR Does

  This PR introduces a simple refactor by moving certain method implementations from `BlockTemplateImpl` into the miner module. It introduces three new functions:

  1.  Remove rundundant coinbase fee check in `waitNext`
  2. **`AddMerkleRootAndCoinbase`**: Computes the block's Merkle root, inserts the coinbase transaction, and sets the Merkle root in the block. This function is called by `submitSolution` before the block is submitted for processing.

  3. **`WaitAndCreateNewBlock`**: Returns a new block template either when transaction fees reach a certain threshold or when a new tip is detected. If a timeout is reached, it returns `nullptr`. The `waitNext` method in `BlockTemplateImpl` now simply wraps this function.
  4. Move `GetTip` implementation to miner.

  5. **`WaitTipChanged`**: Returns the tip when the chain it changes, or `nullopt` if a timeout or interrupt occurs. The `waitTipChanged` method in `MinerImpl` now calls `GetTip` after invoking `ChainTipChanged`, and returns the tip.

  #### Behavior Change

  - We now only `Assert` for  a valid chainman and notifications pointer once.

ACKs for top commit:
  achow101:
    ACK 62fc42d475
  Sjors:
    ACK 62fc42d475
  ryanofsky:
    Code review ACK 62fc42d475. Lots of suggest suggest changes made since last review, altering function names and signatures and also adding new commit to drop negative fee handling. I like the idea of making the wait function return a BlockRef, that is clearer than what I suggested. Left some comments below but they are not important and this looks good as-is

Tree-SHA512: 502632f94ced81f576b2c43cf015f1527e2c259e6ca253f670f5a6889171e2246372b4e709575701afa3f01d488d6633557fef54f48fe83bbaf1836ac5326c4f
2025-05-14 12:57:50 -07:00
ismaelsadeeq
62fc42d475 interfaces: refactor: move waitTipChanged implementation to miner
- This commit creates a function `WaitTipChanged` that waits for the connected
  tip to change until timeout elapsed.

- This function is now used by `waitTipChanged`

Co-authored-by: Ryan Ofsky <ryan@ofsky.org>
2025-05-14 13:55:12 +01:00
Sjors Provoost
c39ca9d4f7 interfaces: move getTip implementation to miner 2025-05-14 13:55:05 +01:00
ismaelsadeeq
720f201e65 interfaces: refactor: move waitNext implementation to miner
- We now assert for a valid chainman and notifications once when
 invoking WaitAndCreateNewBlock function.
2025-05-13 16:22:56 +01:00
ismaelsadeeq
e6c2f4ce7a interfaces: refactor: move submitSolution implementation to miner
- Create a new function `AddMerkleRootAndCoinbase` that compute the
  block's merkle root, insert the coinbase transaction and the merkle
  root into the block.
2025-05-13 16:22:56 +01:00
Ava Chow
19b1e177d6 Merge bitcoin/bitcoin#32155: miner: timelock the coinbase to the mined block's height
a58cb3b1c1 qa: sanity check mined block have their coinbase timelocked to height (Antoine Poinsot)
8f2078af6a miner: timelock coinbase transactions (Antoine Poinsot)
788aeebf34 qa: use prev height as nLockTime for coinbase txs created in unit tests (Antoine Poinsot)
c76dbe9b8b qa: timelock coinbase transactions created in fuzz targets (Antoine Poinsot)
9c94069d8b contrib: timelock coinbase transactions in signet miner (Antoine Poinsot)
a5f52cfcc4 qa: timelock coinbase transactions created in functional tests (Antoine Poinsot)

Pull request description:

  The Consensus Cleanup soft fork proposal includes enforcing that coinbase transactions set their
  nLockTime field to the block height minus 1, as well as their nSequence such as to not disable the
  timelock. If such a fork were to be activated by Bitcoin users, miners need to be ready to produce
  compliant blocks at the risk of losing substantial amounts mining would-be invalid blocks. As miners
  are unfamously slow to upgrade, it's good to make this change as early as possible.

  Although Bitcoin Core's GBT implementation does not provide the `coinbasetxn` field, and mining
  pool software crafts the coinbase on its own, updating the Bitcoin Core mining code is a first step
  toward convincing pools to update their (often closed source) code. A possible followup is also to
  introduce new fields to GBT. In addition, this first step also makes it possible to test future
  Consensus Cleanup changes.

  The commit making the change also updates a bunch of seemingly-unrelated tests. This is because those tests were asserting error messages based on the txid of transactions involved, and changing the coinbase transaction structure necessarily changes the txid of all tests' transactions.

ACKs for top commit:
  Sjors:
    Code review ACK a58cb3b1c1
  achow101:
    ACK a58cb3b1c1
  TheCharlatan:
    Re-ACK a58cb3b1c1

Tree-SHA512: a2aae009a187eb760d34435f518a895ee76c6b02a667eb030ddf6bd584da6e8eae2737d974dbf81a928d60c07bcb4820f055adc067e18d8819640db0240bb513
2025-05-09 15:09:27 -07:00
Ava Chow
a60445cd04 Merge bitcoin/bitcoin#32355: Bugfix: Miner: Don't reuse block_reserved_weight for "block is full enough to give up" weight delta
524f981bb8 Bugfix: Miner: Don't reuse block_reserved_weight for "block is full enough to give up" weight delta (Luke Dashjr)

Pull request description:

  PR #30356 incorrectly changed a constant of `4000` to `m_options.coinbase_max_additional_weight` in the check for when to give up finding another transaction to fill the block:

  ```diff
               if (nConsecutiveFailed > MAX_CONSECUTIVE_FAILURES && nBlockWeight >
  -                    m_options.nBlockMaxWeight - 4000) {
  +                    m_options.nBlockMaxWeight - m_options.block_reserved_weight) {
                   // Give up if we're close to full and haven't succeeded in a while
                   break;
               }
  ```

  But this constant did not deal with the reserved weight at all. It was in fact simply checking if the block was close to full, and if so, giving up finding another transaction to pad it with after `MAX_CONSECUTIVE_FAILURES` failed attempts.

  It doesn't seem very logical to reuse the reserve weight for this purpose, and it would be overcomplicated to add yet another setting, so this PR changes it to a new constexpr.

ACKs for top commit:
  achow101:
    ACK 524f981bb8
  darosior:
    utACK 524f981bb8
  ismaelsadeeq:
    ACK 524f981bb8

Tree-SHA512: c066debc34a021380424bd21b40444071b736325e41779a41590c2c8a6822ceeaf910fe067817c1dba108210b24c574977b0350b29520502e7af79d3b405928b
2025-04-29 15:51:18 -07:00
Luke Dashjr
524f981bb8 Bugfix: Miner: Don't reuse block_reserved_weight for "block is full enough to give up" weight delta
PR #30356 incorrectly changed a constant of `4000` to `m_options.coinbase_max_additional_weight` in the check for when to give up finding another transaction to fill the block:

```diff
             if (nConsecutiveFailed > MAX_CONSECUTIVE_FAILURES && nBlockWeight >
-                    m_options.nBlockMaxWeight - 4000) {
+                    m_options.nBlockMaxWeight - m_options.block_reserved_weight) {
                 // Give up if we're close to full and haven't succeeded in a while
                 break;
             }
```

But this constant did not deal with the reserved weight at all. It was in fact simply checking if the block was close to full, and if so, giving up finding another transaction to pad it with after `MAX_CONSECUTIVE_FAILURES` failed attempts.

It doesn't seem very logical to reuse the reserve weight for this purpose, and it would be overcomplicated to add yet another setting, so this PR changes it to a new constexpr.
2025-04-26 07:45:12 +00:00
Antoine Poinsot
8f2078af6a miner: timelock coinbase transactions
The Consensus Cleanup soft fork proposal includes enforcing that coinbase transactions set their
locktime field to the block height, minus 1 (as well as their nSequence such as to not disable the
timelock). If such a fork were to be activated by Bitcoin users, miners need to be ready to produce
compliant blocks at the risk of losing substantial amounts mining would-be invalid blocks. As miners
are unfamously slow to upgrade, it's good to make this change as early as possible.

Although Bitcoin Core's GBT implementation does not provide the "coinbasetxn" field, and mining
pool software crafts the coinbase on its own, updating the Bitcoin Core mining code is a first step
toward convincing pools to update their (often closed source) code. A possible followup is also to
introduce new fields to GBT. In addition, this first step also makes it possible to test future
Consensus Cleanup changes.

The changes to the seemingly-unrelated RBF tests is because these tests assert an error message
which may vary depending on the txid of the transactions used in the test. This commit changes the
coinbase transaction structure and therefore impact the txid of transactions in all tests.

The change to the "Bad snapshot" error message in the assumeutxo functional test is because this
specific test case reads into the txid of the next transaction in the snapshot and asserts the error
message based it gets on deserializing this txid as a coin for the previous transaction. As this
commit changes this txid it impacts the deserialization error raised.
2025-04-25 12:44:08 -04:00
Sjors Provoost
226d81f8b7 mining: drop unused -nFees and sigops from CBlockTemplate
For the coinbase vTxFees used a dummy value of -nFees. This
value was never returned by the RPC or used in a test.

Similarly the fist vTxSigOpsCost entry was calculated from
the dummy coinbase transaction.

Drop both and add code comments to prevent confusion.
2025-03-13 11:16:57 +01:00
glozow
6b165f5906 Merge bitcoin/bitcoin#31384: mining: bugfix: Fix duplicate coinbase tx weight reservation
386eecff5f doc: add release notes (ismaelsadeeq)
3eaa0a3b66 miner: init: add `-blockreservedweight` startup option (ismaelsadeeq)
777434a2cd doc: rpc: improve `getmininginfo` help text (ismaelsadeeq)
c8acd4032d init: fail to start when `-blockmaxweight` exceeds `MAX_BLOCK_WEIGHT` (ismaelsadeeq)
5bb31633cc test: add `-blockmaxweight` startup option functional test (ismaelsadeeq)
2c7d90a6d6 miner: bugfix: fix duplicate weight reservation in block assembler (ismaelsadeeq)

Pull request description:

  * This PR attempts to fix the duplicate coinbase weight reservation issue we currently have.
  * Fixes #21950

  We reserve 4000 weight units for coinbase transaction in `DEFAULT_BLOCK_MAX_WEIGHT`

  7590e93bc7/src/policy/policy.h (L23)

  And also reserve additional `4000` weight units in the default `BlockCreationOptions` struct.

  7590e93bc7/src/node/types.h (L36-L40)

  **Motivation**

  - This issue was first noticed during a review here https://github.com/bitcoin/bitcoin/pull/11100#discussion_r136157411)
  - It was later reported in issue #21950.
  - I also came across the bug while writing a test for building the block template. I could not create a block template above `3,992,000` in the block assembler, and this was not documented anywhere. It took me a while to realize that we were reserving space for the coinbase transaction weight twice.

  ---
  This PR fixes this by consolidating the reservation to be in a single location in the codebase.

  This PR then adds a new startup option `-blockreservedweight` whose default is `8000` that can be used to lower or increase the block reserved weight for block header, txs count, coinbase tx.

ACKs for top commit:
  Sjors:
    ACK 386eecff5f
  fjahr:
    Code review ACK 386eecff5f
  glozow:
    utACK 386eecff5f, nonblocking nits. I do think the release notes should be clarified more
  pinheadmz:
    ACK 386eecff5f

Tree-SHA512: f27efa1da57947b7f4d42b9322b83d13afe73dd749dd9cac49360002824dd41c99a876a610554ac2d67bad7485020b9dcc423a8e6748fc79d6a10de6d4357d4c
2025-02-10 08:26:01 -05:00
ismaelsadeeq
3eaa0a3b66 miner: init: add -blockreservedweight startup option
- Prevent setting the value of `-blockreservedweight` below
  a safety value of 2000.
2025-02-04 11:53:11 -05:00
ismaelsadeeq
2c7d90a6d6 miner: bugfix: fix duplicate weight reservation in block assembler
- This commit renamed coinbase_max_additional_weight to block_reserved_weight.

- Also clarify that the reservation is for block header, transaction count
  and coinbase transaction.
2025-02-04 11:53:03 -05:00
Sjors Provoost
0713548137 refactor: add GetMinimumTime() helper
Before bip94 there was an assumption that the minimum permitted
timestamp is GetMedianTimePast() + 1.

This commit splits a helper function out of UpdateTime() to
obtain the minimum time in a way that takes the
timewarp attack rule into account.
2025-01-29 09:39:32 +01:00
merge-script
59876b3ad7 Merge bitcoin/bitcoin#31376: Miner: never create a template which exploits the timewarp bug
733fa0b0a1 miner: never create a template which exploits the timewarp bug (Antoine Poinsot)

Pull request description:

  This check was introduced in #30681 but only enabled for testnet4. To avoid potentially creating an invalid block template if a soft fork to fix the timewarp attack were to activate in the future, we should have this check on all networks. It also seems wise for our miner to not support it whether or not a soft fork activates to fix it at the consensus level.

ACKs for top commit:
  Sjors:
    ACK 733fa0b0a1
  fjahr:
    utACK 733fa0b0a1
  TheCharlatan:
    ACK 733fa0b0a1

Tree-SHA512: 9b3bc8b26a57f93425b17dda80bcfac4ecb750a3d26bc3eb8df619135634e369ac15982fac0c9770b1df207bd2e418ffe02a98f37968f024e55262d97715a4f5
2025-01-23 10:54:47 +00:00
ismaelsadeeq
7c123c08dd miner: add package feerate vector to CBlockTemplate
- The package feerates are ordered by the sequence in which
  packages are selected for inclusion in the block template.

- The commit also tests this new behaviour.

Co-authored-by: willcl-ark <will@256k1.dev>
2025-01-07 15:29:17 -05:00
Sjors Provoost
ff41b9e296 Drop script_pub_key arg from createNewBlock
Providing a script for the coinbase transaction is only done in test code
and for CPU solo mining.

Production miners use the getblocktemplate RPC which omits the coinbase
transaction entirely from its block template, leaving it to external (pool)
software to construct it.

A coinbase script can still be passed via BlockCreateOptions instead.

A temporary overload is added so that the test can be modified in the
next commit.
2024-12-04 12:44:57 +07:00
Antoine Poinsot
733fa0b0a1 miner: never create a template which exploits the timewarp bug 2024-11-26 12:48:29 -05:00
Ava Chow
1a8f51e745 Merge bitcoin/bitcoin#28843: [refactor] Cleanup BlockAssembler mempool usage
192dac1d33 [refactor] Cleanup BlockAssembler mempool usage (TheCharlatan)

Pull request description:

  The `addPackageTxs` method of the `BlockAssembler` currently has access to two mempool variables, as an argument and as a member. Clean this up and clarify that they both are the same mempool instance by removing the argument and instead only using the member variable in the method.

  This was noticed in this PR review: https://github.com/bitcoin/bitcoin/pull/25223#discussion_r898164322.

ACKs for top commit:
  achow101:
    ACK 192dac1d33
  danielabrozzoni:
    re-ACK 192dac1
  stickies-v:
    ACK 192dac1d33

Tree-SHA512: a5ae7d6d771fbb5b54f23624b4d3429acf07bbe38179a462a078c825d60c89a725ad4e13fe7067eebea7dfec63c56c8f39b5077b0d949d594f500affcc1272d1
2024-11-14 16:30:48 -05:00
TheCharlatan
192dac1d33 [refactor] Cleanup BlockAssembler mempool usage
The `addPackageTxs` method of the `BlockAssembler` currently has access
to two mempool variables, as an argument and as a member. Clean this up
and clarify that they both are the same mempool instance by removing the
argument and instead only using the member variable in the method.

Co-Authored-By: Anthony Towns <aj@erisian.com.au>
Co-authored-by: stickies-v <stickies-v@protonmail.com>
2024-10-21 15:55:35 +02:00
Sjors Provoost
a93c171faa Drop unneeded nullptr check from CreateNewBlock() 2024-09-13 10:14:53 +02:00
MarcoFalke
3333415890 scripted-diff: LogPrint -> LogDebug
-BEGIN VERIFY SCRIPT-
 sed -i 's/\<LogPrint\>/LogDebug/g' $( git grep -l '\<LogPrint\>'  -- ./contrib/ ./src/ ./test/ ':(exclude)src/logging.h' )
-END VERIFY SCRIPT-
2024-08-29 13:49:57 +02:00
Sjors Provoost
59ff17e5af miner: adjust clock to timewarp rule 2024-08-20 18:51:37 +02:00
Sjors Provoost
c504b6997b refactor: add coinbase constraints to BlockCreateOptions
When generating a block template through e.g. getblocktemplate RPC,
we reserve 4000 weight units and 400 sigops. Pools use this space
for their coinbase outputs.

At least one pool patched their Bitcoin Core node to adjust
these hardcoded values. They eventually produced an invalid
block which exceeded the sigops limit.
https://bitcoin.stackexchange.com/questions/117837/how-many-sigops-are-in-the-invalid-block-783426

The existince of such patches suggests it may be useful to
make this value configurable. This commit would make such a
change easier.

The main motivation however is that the Stratum v2 spec
requires the pool to communicate the maximum bytes they intend
to add to the coinbase outputs. A proposed change to the spec
would also require them to communicate the maximum number of sigops.

This commit also documents what happens when
-blockmaxweight is lower than the coinbase
reserved value.

Co-authored-by: Ryan Ofsky <ryan@ofsky.org>
2024-07-17 18:33:15 +02:00
Sjors Provoost
6b4c817d4b refactor: pass BlockCreateOptions to createNewBlock
Rather than pass options individually to createNewBlock and then
combining them into BlockAssembler::Options, this commit introduces
BlockCreateOptions and passes that instead.

Currently there's only one option (use_mempool) but the next
commit adds more.

Co-authored-by: Ryan Ofsky <ryan@ofsky.org>
2024-07-16 10:27:57 +02:00
Lőrinc
323ce30308 Moved the repeated -printpriority fetching out of AddToBlock
AddToBlock was called repeatedly from `addPackageTxs` where the constant value of `printpriority` is recalculated every time.
Since its behavior was changed in 400b151, I've named the variable accordingly.

This showed up during profiling of AssembleBlock, fetching it once in the constructor results in a measurable speed increase for many iterations.

> ./src/bench/bench_bitcoin --filter='AssembleBlock' --min-time=1000

before:
|               ns/op |                op/s |    err% |     total | benchmark
|--------------------:|--------------------:|--------:|----------:|:----------
|          155,558.97 |            6,428.43 |    0.1% |      1.10 | `AssembleBlock`

after:
|               ns/op |                op/s |    err% |     total | benchmark
|--------------------:|--------------------:|--------:|----------:|:----------
|          148,083.68 |            6,752.94 |    0.1% |      1.10 | `AssembleBlock`

Co-authored-by: furszy <mfurszy@protonmail.com>
2024-06-30 23:00:13 +02:00
Sjors Provoost
64ebb0f971 Always pass options to BlockAssembler constructor
This makes the options argument for BlockAssembler constructor mandatory,
dropping implicit use of ArgsManager. The caller i.e. the Mining
interface implementation now handles this.

In a future Stratum v2 change the Options object needs to be
mofified after arguments have been processed. Specifically
the pool communicates how many extra bytes it needs for
its own outputs (payouts, extra commitments, etc). This will need
to be substracted from what the user set as -blockmaxweight.

Such a change can be implemented in createNewBlock, after
ApplyArgsManOptions.
2024-06-18 18:47:51 +02:00
MarcoFalke
fad0fafd5a refactor: Fix timedata includes 2024-02-01 13:52:05 +01:00
dergoegge
ff9039f6ea Remove GetAdjustedTime 2024-01-05 17:16:38 +00:00
glozow
d0cd2e804e [refactor] rewrite BlockAssembler inBlock and failedTx as sets of txids 2023-11-10 16:44:45 +01:00
TheCharlatan
a5c2eb5748 refactor: Fix logging.h includes
These were uncovered as missing by the next commit.
2023-08-05 10:42:56 +02:00
TheCharlatan
be55f545d5 move-only: Extract common/args and common/config.cpp from util/system
This is an extraction of ArgsManager related functions from util/system
into their own common file.

Config file related functions are moved to common/config.cpp.

The background of this commit is an ongoing effort to decouple the
libbitcoinkernel library from the ArgsManager. The ArgsManager belongs
into the common library, since the kernel library should not depend on
it. See doc/design/libraries.md for more information on this rationale.
2023-04-19 10:48:30 +02:00
stickies-v
6a5e88e5cf miner: don't re-apply default Options value if argument is unset
ApplyArgsManOptions does not need to set default values for missing
arguments, these are already defined in the BlockAssembler::Options.

This commit changes the interface of ApplyArgsManOptions(). If
ApplyArgsManOptions() is called again after a option is changed,
this option will no longer be reset to the default value.

There is no observed behaviour change due to how
ApplyArgsManOptions() is currently used, and the new interface is
consistent with e.g. ValidationCacheSizes and MemPoolLimits.
2023-01-16 18:58:11 +00:00
stickies-v
ea72c3d9d5 refactor: avoid duplicating BlockAssembler::Options members
Add Options as a member to BlockAssembler to avoid having to assign
all the options individually.

Additionally brings the struct more in line with how we typically
define default and ArgManager values, as e.g. with
ChainstateManager::Options and and CTxMemPool::Options
2023-01-16 18:58:10 +00:00
stickies-v
cba749a9b7 refactor: rename local gArgs to args
Avoid confusion with the global gArgs
2023-01-12 11:16:17 +00:00
Andrew Chow
2f6a8e5e02 Merge bitcoin/bitcoin#26695: bench: BlockAssembler on a mempool with packages
04528054fc [bench] BlockAssembler with mempool packages (glozow)
6ce265acf4 [test util] lock cs_main before pool.cs in PopulateMempool (glozow)
8791410662 [test util] randomize fee in PopulateMempool (glozow)
cba5934eb6 [miner] allow bypassing TestBlockValidity (glozow)
c058852308 [refactor] parameterize BlockAssembler::Options in PrepareBlock (glozow)
a2de971ba1 [refactor] add helper to apply ArgsManager to BlockAssembler::Options (glozow)

Pull request description:

  Performance of block template building matters as miners likely want to be able to start mining on a block with transactions asap after a block is found. We would want to know if a mempool PR accidentally caused, for example, a 100x slowdown. An `AssembleBlock()` bench exists, but it operates on a mempool with 101 transactions, each with 0 ancestors or descendants and with the same fee. Adding a bench with a more complex mempool is useful because (1) it's more realistic (2) updating packages can potentially cause the algorithm to take a long time.

ACKs for top commit:
  kevkevinpal:
    Tested ACK [0452805](04528054fc)
  achow101:
    ACK 04528054fc
  stickies-v:
    ACK 04528054f

Tree-SHA512: 38c138d6a75616651f9b1faf4e3a1cd833437a486f4e84308fbee958e8462bb570582c88f7ba7ab99d80191e97855ac2cf27c43cc21585d3e4b0e227effe2fb5
2023-01-11 18:11:11 -05:00
Andrew Chow
80fc1af096 Merge bitcoin/bitcoin#26289: Use util::Result in for calculating mempool ancestors
47c4b1f52a mempool: log/halt when CalculateMemPoolAncestors fails unexpectedly (stickies-v)
5481f65849 mempool: add AssumeCalculateMemPoolAncestors helper function (stickies-v)
f911bdfff9 mempool: use util::Result for CalculateMemPoolAncestors (stickies-v)
66e028f739 mempool: use util::Result for CalculateAncestorsAndCheckLimits (stickies-v)

Pull request description:

  Upon reviewing the documentation for `CTxMemPool::CalculateMemPoolAncestors`, I noticed `setAncestors` was meant to be an `out` parameter but actually is an `in,out` parameter, as can be observed by adding `assert(setAncestors.empty());` as the first line in the function and running `make check`. This PR fixes this unexpected behaviour and introduces refactoring improvements to make intents and effects of the code more clear.

  ## Unexpected behaviour
  This behaviour occurs only in the package acceptance path, currently only triggered by `testmempoolaccept` and `submitpackage` RPCs.

  In `MemPoolAccept::AcceptMultipleTransactions()`, we first call `PreChecks()` and then `SubmitPackage()` with the same `Workspace ws` reference. `PreChecks` leaves `ws.m_ancestors` in a potentially non-empty state, before it is passed on to `MemPoolAccept::SubmitPackage`. `SubmitPackage` is the only place where `setAncestors` isn't guaranteed to be empty before calling `CalculateMemPoolAncestors`. The most straightforward fix is to just forcefully clear `setAncestors` at the beginning of CalculateMemPoolAncestors, which is done in the first bugfix commit.

  ## Improvements
  ### Return value instead of out-parameters
  This PR updates the function signatures for `CTxMemPool::CalculateMemPoolAncestors` and `CTxMemPool::CalculateAncestorsAndCheckLimits` to use a `util::Result` return type and eliminate both the `setAncestors` `in,out`-parameter as well as the error string. It simplifies the code and makes the intent and effects more explicit.

  ### Observability
  There are 7 instances where we currently call `CalculateMemPoolAncestors` without actually checking if the function succeeded because we assume that it can't fail, such as in [miner.cpp](69b10212ea/src/node/miner.cpp (L399)). This PR adds a new wrapper `AssumeCalculateMemPoolAncestors` function that logs such unexpected failures, or in case of debug builds even halts the program. It's not crucial to the objective, more of an observability improvement that seems sensible to add on here.

ACKs for top commit:
  achow101:
    ACK 47c4b1f52a
  w0xlt:
    ACK 47c4b1f52a
  glozow:
    ACK 47c4b1f52a
  furszy:
    light code review ACK 47c4b1f5
  aureleoules:
    ACK 47c4b1f52a

Tree-SHA512: d908dad00d1a5645eb865c4877cc0bae74b9cd3332a3641eb4a285431aef119f9fc78172d38b55c592168a73dae83242e6af3348815f7b37cbe2d448a3a58648
2023-01-03 16:30:55 -05:00
Hennadii Stepanov
306ccd4927 scripted-diff: Bump copyright headers
-BEGIN VERIFY SCRIPT-
./contrib/devtools/copyright_header.py update ./
-END VERIFY SCRIPT-

Commits of previous years:
- 2021: f47dda2c58
- 2020: fa0074e2d8
- 2019: aaaaad6ac9
2022-12-24 23:49:50 +00:00