aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/release-notes/release-notes-24.0.1.md391
-rw-r--r--doc/release-notes/release-notes-24.0.md390
-rw-r--r--src/Makefile.am2
-rw-r--r--src/bench/mempool_eviction.cpp2
-rw-r--r--src/bench/mempool_stress.cpp2
-rw-r--r--src/bench/peer_eviction.cpp12
-rw-r--r--src/bench/rpc_mempool.cpp2
-rw-r--r--src/init.cpp2
-rw-r--r--src/kernel/mempool_entry.h (renamed from src/txmempool_entry.h)6
-rw-r--r--src/net_processing.cpp2
-rw-r--r--src/node/interfaces.cpp6
-rw-r--r--src/policy/fees.cpp2
-rw-r--r--src/policy/rbf.cpp2
-rw-r--r--src/psbt.h2
-rw-r--r--src/qt/coincontroldialog.cpp2
-rw-r--r--src/qt/psbtoperationsdialog.cpp6
-rw-r--r--src/qt/test/apptests.cpp2
-rw-r--r--src/qt/test/test_main.cpp2
-rw-r--r--src/qt/test/wallettests.cpp12
-rw-r--r--src/qt/walletmodel.cpp6
-rw-r--r--src/rpc/mempool.cpp2
-rw-r--r--src/rpc/server.cpp2
-rw-r--r--src/test/fuzz/policy_estimator.cpp2
-rw-r--r--src/test/fuzz/util/mempool.cpp2
-rw-r--r--src/test/fuzz/util/mempool.h2
-rw-r--r--src/test/sync_tests.cpp4
-rw-r--r--src/test/util/setup_common.cpp2
-rw-r--r--src/txmempool.h2
-rw-r--r--src/validation.cpp2
-rw-r--r--src/wallet/coinselection.cpp14
-rw-r--r--src/wallet/coinselection.h7
-rw-r--r--src/wallet/dump.cpp2
-rw-r--r--src/wallet/fees.cpp2
-rw-r--r--src/wallet/interfaces.cpp2
-rw-r--r--src/wallet/rpc/backup.cpp18
-rw-r--r--src/wallet/rpc/spend.cpp4
-rw-r--r--src/wallet/rpc/transactions.cpp8
-rw-r--r--src/wallet/spend.cpp35
-rw-r--r--src/wallet/test/coinselector_tests.cpp119
-rw-r--r--src/wallet/test/spend_tests.cpp2
-rw-r--r--src/wallet/test/wallet_tests.cpp2
-rw-r--r--src/wallet/wallet.cpp4
-rw-r--r--src/wallet/wallettool.cpp2
-rwxr-xr-xtest/functional/rpc_fundrawtransaction.py2
44 files changed, 625 insertions, 471 deletions
diff --git a/doc/release-notes/release-notes-24.0.1.md b/doc/release-notes/release-notes-24.0.1.md
new file mode 100644
index 0000000000..24920ba450
--- /dev/null
+++ b/doc/release-notes/release-notes-24.0.1.md
@@ -0,0 +1,391 @@
+24.0.1 Release Notes
+====================
+
+Due to last-minute issues (#26616), 24.0, although tagged, was never fully
+announced or released.
+
+Bitcoin Core version 24.0.1 is now available from:
+
+ <https://bitcoincore.org/bin/bitcoin-core-24.0.1/>
+
+This release includes new features, various bug fixes and performance
+improvements, as well as updated translations.
+
+Please report bugs using the issue tracker at GitHub:
+
+ <https://github.com/bitcoin/bitcoin/issues>
+
+To receive security and update notifications, please subscribe to:
+
+ <https://bitcoincore.org/en/list/announcements/join/>
+
+How to Upgrade
+==============
+
+If you are running an older version, shut it down. Wait until it has completely
+shut down (which might take a few minutes in some cases), then run the
+installer (on Windows) or just copy over `/Applications/Bitcoin-Qt` (on macOS)
+or `bitcoind`/`bitcoin-qt` (on Linux).
+
+Upgrading directly from a version of Bitcoin Core that has reached its EOL is
+possible, but it might take some time if the data directory needs to be migrated. Old
+wallet versions of Bitcoin Core are generally supported.
+
+Compatibility
+==============
+
+Bitcoin Core is supported and extensively tested on operating systems
+using the Linux kernel, macOS 10.15+, and Windows 7 and newer. Bitcoin
+Core should also work on most other Unix-like systems but is not as
+frequently tested on them. It is not recommended to use Bitcoin Core on
+unsupported systems.
+
+Notice of new option for transaction replacement policies
+=========================================================
+
+This version of Bitcoin Core adds a new `mempoolfullrbf` configuration
+option which allows users to change the policy their individual node
+will use for relaying and mining unconfirmed transactions. The option
+defaults to the same policy that was used in previous releases and no
+changes to node policy will occur if everyone uses the default.
+
+Some Bitcoin services today expect that the first version of an
+unconfirmed transaction that they see will be the version of the
+transaction that ultimately gets confirmed---a transaction acceptance
+policy sometimes called "first-seen".
+
+The Bitcoin Protocol does not, and cannot, provide any assurance that
+the first version of an unconfirmed transaction seen by a particular
+node will be the version that gets confirmed. If there are multiple
+versions of the same unconfirmed transaction available, only the miner
+who includes one of those transactions in a block gets to decide which
+version of the transaction gets confirmed.
+
+Despite this lack of assurance, multiple merchants and services today
+still make this assumption.
+
+There are several benefits to users from removing this *first-seen*
+simplification. One key benefit, the ability for the sender of a
+transaction to replace it with an alternative version paying higher
+fees, was realized in [Bitcoin Core 0.12.0][] (February 2016) with the
+introduction of [BIP125][] opt-in Replace By Fee (RBF).
+
+Since then, there has been discussion about completely removing the
+first-seen simplification and allowing users to replace any of their
+older unconfirmed transactions with newer transactions, a feature called
+*full-RBF*. This release includes a `mempoolfullrbf` configuration
+option that allows enabling full-RBF, although it defaults to off
+(allowing only opt-in RBF).
+
+Several alternative node implementations have already enabled full-RBF by
+default for years, and several contributors to Bitcoin Core are
+advocating for enabling full-RBF by default in a future version of
+Bitcoin Core.
+
+As more nodes that participate in relay and mining begin enabling
+full-RBF, replacement of unconfirmed transactions by ones offering higher
+fees may rapidly become more reliable.
+
+Contributors to this project strongly recommend that merchants and services
+not accept unconfirmed transactions as final, and if they insist on doing so,
+to take the appropriate steps to ensure they have some recourse or plan for
+when their assumptions do not hold.
+
+[Bitcoin Core 0.12.0]: https://bitcoincore.org/en/releases/0.12.0/#opt-in-replace-by-fee-transactions
+[bip125]: https://github.com/bitcoin/bips/blob/master/bip-0125.mediawiki
+
+Notable changes
+===============
+
+P2P and network changes
+-----------------------
+
+- To address a potential denial-of-service, the logic to download headers from peers
+ has been reworked. This is particularly relevant for nodes starting up for the
+ first time (or for nodes which are starting up after being offline for a long time).
+
+ Whenever headers are received from a peer that have a total chainwork that is either
+ less than the node's `-minimumchainwork` value or is sufficiently below the work at
+ the node's tip, a "presync" phase will begin, in which the node will download the
+ peer's headers and verify the cumulative work on the peer's chain, prior to storing
+ those headers permanently. Once that cumulative work is verified to be sufficiently high,
+ the headers will be redownloaded from that peer and fully validated and stored.
+
+ This may result in initial headers sync taking longer for new nodes starting up for
+ the first time, both because the headers will be downloaded twice, and because the effect
+ of a peer disconnecting during the presync phase (or while the node's best headers chain has less
+ than `-minimumchainwork`), will result in the node needing to use the headers presync mechanism
+ with the next peer as well (downloading the headers twice, again). (#25717)
+
+- With I2P connections, a new, transient address is used for each outbound
+ connection if `-i2pacceptincoming=0`. (#25355)
+
+Updated RPCs
+------------
+
+- The `-deprecatedrpc=softforks` configuration option has been removed. The
+ RPC `getblockchaininfo` no longer returns the `softforks` field, which was
+ previously deprecated in 23.0. (#23508) Information on soft fork status is
+ now only available via the `getdeploymentinfo` RPC.
+
+- The `deprecatedrpc=exclude_coinbase` configuration option has been removed.
+ The `receivedby` RPCs (`listreceivedbyaddress`, `listreceivedbylabel`,
+ `getreceivedbyaddress` and `getreceivedbylabel`) now always return results
+ accounting for received coins from coinbase outputs, without an option to
+ change that behaviour. Excluding coinbases was previously deprecated in 23.0.
+ (#25171)
+
+- The `deprecatedrpc=fees` configuration option has been removed. The top-level
+ fee fields `fee`, `modifiedfee`, `ancestorfees` and `descendantfees` are no
+ longer returned by RPCs `getmempoolentry`, `getrawmempool(verbose=true)`,
+ `getmempoolancestors(verbose=true)` and `getmempooldescendants(verbose=true)`.
+ The same fee fields can be accessed through the `fees` object in the result.
+ The top-level fee fields were previously deprecated in 23.0. (#25204)
+
+- The `getpeerinfo` RPC has been updated with a new `presynced_headers` field,
+ indicating the progress on the presync phase mentioned in the
+ "P2P and network changes" section above.
+
+Changes to wallet related RPCs can be found in the Wallet section below.
+
+New RPCs
+--------
+
+- The `sendall` RPC spends specific UTXOs to one or more recipients
+ without creating change. By default, the `sendall` RPC will spend
+ every UTXO in the wallet. `sendall` is useful to empty wallets or to
+ create a changeless payment from select UTXOs. When creating a payment
+ from a specific amount for which the recipient incurs the transaction
+ fee, continue to use the `subtractfeefromamount` option via the
+ `send`, `sendtoaddress`, or `sendmany` RPCs. (#24118)
+
+- A new `gettxspendingprevout` RPC has been added, which scans the mempool to find
+ transactions spending any of the given outpoints. (#24408)
+
+- The `simulaterawtransaction` RPC iterates over the inputs and outputs of the given
+ transactions, and tallies up the balance change for the given wallet. This can be
+ useful e.g. when verifying that a coin join like transaction doesn't contain unexpected
+ inputs that the wallet will then sign for unintentionally. (#22751)
+
+Updated REST APIs
+-----------------
+
+- The `/headers/` and `/blockfilterheaders/` endpoints have been updated to use
+ a query parameter instead of path parameter to specify the result count. The
+ count parameter is now optional, and defaults to 5 for both endpoints. The old
+ endpoints are still functional, and have no documented behaviour change.
+
+ For `/headers`, use
+ `GET /rest/headers/<BLOCK-HASH>.<bin|hex|json>?count=<COUNT=5>`
+ instead of
+ `GET /rest/headers/<COUNT>/<BLOCK-HASH>.<bin|hex|json>` (deprecated)
+
+ For `/blockfilterheaders/`, use
+ `GET /rest/blockfilterheaders/<FILTERTYPE>/<BLOCK-HASH>.<bin|hex|json>?count=<COUNT=5>`
+ instead of
+ `GET /rest/blockfilterheaders/<FILTERTYPE>/<COUNT>/<BLOCK-HASH>.<bin|hex|json>` (deprecated)
+
+ (#24098)
+
+Build System
+------------
+
+- Guix builds are now reproducible across architectures (x86_64 & aarch64). (#21194)
+
+New settings
+------------
+
+- A new `mempoolfullrbf` option has been added, which enables the mempool to
+ accept transaction replacement without enforcing BIP125 replaceability
+ signaling. (#25353)
+
+Wallet
+------
+
+- The `-walletrbf` startup option will now default to `true`. The
+ wallet will now default to opt-in RBF on transactions that it creates. (#25610)
+
+- The `replaceable` option for the `createrawtransaction` and
+ `createpsbt` RPCs will now default to `true`. Transactions created
+ with these RPCs will default to having opt-in RBF enabled. (#25610)
+
+- The `wsh()` output descriptor was extended with Miniscript support. You can import Miniscript
+ descriptors for P2WSH in a watchonly wallet to track coins, but you can't spend from them using
+ the Bitcoin Core wallet yet.
+ You can find more about Miniscript on the [reference website](https://bitcoin.sipa.be/miniscript/). (#24148)
+
+- The `tr()` output descriptor now supports multisig scripts through the `multi_a()` and
+ `sortedmulti_a()` functions. (#24043)
+
+- To help prevent fingerprinting transactions created by the Bitcoin Core wallet, change output
+ amounts are now randomized. (#24494)
+
+- The `listtransactions`, `gettransaction`, and `listsinceblock`
+ RPC methods now include a wtxid field (hash of serialized transaction,
+ including witness data) for each transaction. (#24198)
+
+- The `listsinceblock`, `listtransactions` and `gettransaction` output now contain a new
+ `parent_descs` field for every "receive" entry. (#25504)
+
+- A new optional `include_change` parameter was added to the `listsinceblock` command.
+
+- RPC `getreceivedbylabel` now returns an error, "Label not found
+ in wallet" (-4), if the label is not in the address book. (#25122)
+
+Migrating Legacy Wallets to Descriptor Wallets
+---------------------------------------------
+
+An experimental RPC `migratewallet` has been added to migrate Legacy (non-descriptor) wallets to
+Descriptor wallets. More information about the migration process is available in the
+[documentation](https://github.com/bitcoin/bitcoin/blob/master/doc/managing-wallets.md#migrating-legacy-wallets-to-descriptor-wallets).
+
+GUI changes
+-----------
+
+- A new menu item to restore a wallet from a backup file has been added (gui#471).
+
+- Configuration changes made in the bitcoin GUI (such as the pruning setting,
+proxy settings, UPNP preferences) are now saved to `<datadir>/settings.json`
+file rather than to the Qt settings backend (windows registry or unix desktop
+config files), so these settings will now apply to bitcoind, instead of being
+ignored. (#15936, gui#602)
+
+- Also, the interaction between GUI settings and `bitcoin.conf` settings is
+simplified. Settings from `bitcoin.conf` are now displayed normally in the GUI
+settings dialog, instead of in a separate warning message ("Options set in this
+dialog are overridden by the configuration file: -setting=value"). And these
+settings can now be edited because `settings.json` values take precedence over
+`bitcoin.conf` values. (#15936)
+
+Low-level changes
+=================
+
+RPC
+---
+
+- The `deriveaddresses`, `getdescriptorinfo`, `importdescriptors` and `scantxoutset` commands now
+ accept Miniscript expression within a `wsh()` descriptor. (#24148)
+
+- The `getaddressinfo`, `decodescript`, `listdescriptors` and `listunspent` commands may now output
+ a Miniscript descriptor inside a `wsh()` where a `wsh(raw())` descriptor was previously returned. (#24148)
+
+Credits
+=======
+
+Thanks to everyone who directly contributed to this release:
+
+- /dev/fd0
+- 0xb10c
+- Adam Jonas
+- akankshakashyap
+- Ali Sherief
+- amadeuszpawlik
+- Andreas Kouloumos
+- Andrew Chow
+- Anthony Towns
+- Antoine Poinsot
+- Antoine Riard
+- Aurèle Oulès
+- avirgovi
+- Ayush Sharma
+- Baas
+- Ben Woosley
+- BrokenProgrammer
+- brunoerg
+- brydinh
+- Bushstar
+- Calvin Kim
+- CAnon
+- Carl Dong
+- chinggg
+- Cory Fields
+- Daniel Kraft
+- Daniela Brozzoni
+- darosior
+- Dave Scotese
+- David Bakin
+- dergoegge
+- dhruv
+- Dimitri
+- dontbyte
+- Duncan Dean
+- eugene
+- Eunoia
+- Fabian Jahr
+- furszy
+- Gleb Naumenko
+- glozow
+- Greg Weber
+- Gregory Sanders
+- gruve-p
+- Hennadii Stepanov
+- hiago
+- Igor Bubelov
+- ishaanam
+- Jacob P.
+- Jadi
+- James O'Beirne
+- Janna
+- Jarol Rodriguez
+- Jeremy Rand
+- Jeremy Rubin
+- jessebarton
+- João Barbosa
+- John Newbery
+- Jon Atack
+- Josiah Baker
+- Karl-Johan Alm
+- KevinMusgrave
+- Kiminuo
+- klementtan
+- Kolby Moroz
+- kouloumos
+- Kristaps Kaupe
+- Larry Ruane
+- Luke Dashjr
+- MarcoFalke
+- Marnix
+- Martin Leitner-Ankerl
+- Martin Zumsande
+- Michael Dietz
+- Michael Folkson
+- Michael Ford
+- Murch
+- mutatrum
+- muxator
+- Oskar Mendel
+- Pablo Greco
+- pasta
+- Patrick Strateman
+- Pavol Rusnak
+- Peter Bushnell
+- phyBrackets
+- Pieter Wuille
+- practicalswift
+- randymcmillan
+- Robert Spigler
+- Russell Yanofsky
+- S3RK
+- Samer Afach
+- Sebastian Falbesoner
+- Seibart Nedor
+- Shashwat
+- Sjors Provoost
+- Smlep
+- sogoagain
+- Stacie
+- Stéphan Vuylsteke
+- Suhail Saqan
+- Suhas Daftuar
+- t-bast
+- TakeshiMusgrave
+- Vasil Dimov
+- W. J. van der Laan
+- w0xlt
+- whiteh0rse
+- willcl-ark
+- William Casarin
+- Yancy Ribbens
+
+As well as to everyone that helped with translations on
+[Transifex](https://www.transifex.com/bitcoin/bitcoin/).
diff --git a/doc/release-notes/release-notes-24.0.md b/doc/release-notes/release-notes-24.0.md
index a9240567d7..a0227aa17f 100644
--- a/doc/release-notes/release-notes-24.0.md
+++ b/doc/release-notes/release-notes-24.0.md
@@ -1,388 +1,4 @@
-24.0 Release Notes
-==================
+Due to last-minute issues (#26616), 24.0, although tagged, was never fully
+announced or released.
-Bitcoin Core version 24.0 is now available from:
-
- <https://bitcoincore.org/bin/bitcoin-core-24.0/>
-
-This release includes new features, various bug fixes and performance
-improvements, as well as updated translations.
-
-Please report bugs using the issue tracker at GitHub:
-
- <https://github.com/bitcoin/bitcoin/issues>
-
-To receive security and update notifications, please subscribe to:
-
- <https://bitcoincore.org/en/list/announcements/join/>
-
-How to Upgrade
-==============
-
-If you are running an older version, shut it down. Wait until it has completely
-shut down (which might take a few minutes in some cases), then run the
-installer (on Windows) or just copy over `/Applications/Bitcoin-Qt` (on macOS)
-or `bitcoind`/`bitcoin-qt` (on Linux).
-
-Upgrading directly from a version of Bitcoin Core that has reached its EOL is
-possible, but it might take some time if the data directory needs to be migrated. Old
-wallet versions of Bitcoin Core are generally supported.
-
-Compatibility
-==============
-
-Bitcoin Core is supported and extensively tested on operating systems
-using the Linux kernel, macOS 10.15+, and Windows 7 and newer. Bitcoin
-Core should also work on most other Unix-like systems but is not as
-frequently tested on them. It is not recommended to use Bitcoin Core on
-unsupported systems.
-
-Notice of new option for transaction replacement policies
-=========================================================
-
-This version of Bitcoin Core adds a new `mempoolfullrbf` configuration
-option which allows users to change the policy their individual node
-will use for relaying and mining unconfirmed transactions. The option
-defaults to the same policy that was used in previous releases and no
-changes to node policy will occur if everyone uses the default.
-
-Some Bitcoin services today expect that the first version of an
-unconfirmed transaction that they see will be the version of the
-transaction that ultimately gets confirmed---a transaction acceptance
-policy sometimes called "first-seen".
-
-The Bitcoin Protocol does not, and cannot, provide any assurance that
-the first version of an unconfirmed transaction seen by a particular
-node will be the version that gets confirmed. If there are multiple
-versions of the same unconfirmed transaction available, only the miner
-who includes one of those transactions in a block gets to decide which
-version of the transaction gets confirmed.
-
-Despite this lack of assurance, multiple merchants and services today
-still make this assumption.
-
-There are several benefits to users from removing this *first-seen*
-simplification. One key benefit, the ability for the sender of a
-transaction to replace it with an alternative version paying higher
-fees, was realized in [Bitcoin Core 0.12.0][] (February 2016) with the
-introduction of [BIP125][] opt-in Replace By Fee (RBF).
-
-Since then, there has been discussion about completely removing the
-first-seen simplification and allowing users to replace any of their
-older unconfirmed transactions with newer transactions, a feature called
-*full-RBF*. This release includes a `mempoolfullrbf` configuration
-option that allows enabling full-RBF, although it defaults to off
-(allowing only opt-in RBF).
-
-Several alternative node implementations have already enabled full-RBF by
-default for years, and several contributors to Bitcoin Core are
-advocating for enabling full-RBF by default in a future version of
-Bitcoin Core.
-
-As more nodes that participate in relay and mining begin enabling
-full-RBF, replacement of unconfirmed transactions by ones offering higher
-fees may rapidly become more reliable.
-
-Contributors to this project strongly recommend that merchants and services
-not accept unconfirmed transactions as final, and if they insist on doing so,
-to take the appropriate steps to ensure they have some recourse or plan for
-when their assumptions do not hold.
-
-[Bitcoin Core 0.12.0]: https://bitcoincore.org/en/releases/0.12.0/#opt-in-replace-by-fee-transactions
-[bip125]: https://github.com/bitcoin/bips/blob/master/bip-0125.mediawiki
-
-Notable changes
-===============
-
-P2P and network changes
------------------------
-
-- To address a potential denial-of-service, the logic to download headers from peers
- has been reworked. This is particularly relevant for nodes starting up for the
- first time (or for nodes which are starting up after being offline for a long time).
-
- Whenever headers are received from a peer that have a total chainwork that is either
- less than the node's `-minimumchainwork` value or is sufficiently below the work at
- the node's tip, a "presync" phase will begin, in which the node will download the
- peer's headers and verify the cumulative work on the peer's chain, prior to storing
- those headers permanently. Once that cumulative work is verified to be sufficiently high,
- the headers will be redownloaded from that peer and fully validated and stored.
-
- This may result in initial headers sync taking longer for new nodes starting up for
- the first time, both because the headers will be downloaded twice, and because the effect
- of a peer disconnecting during the presync phase (or while the node's best headers chain has less
- than `-minimumchainwork`), will result in the node needing to use the headers presync mechanism
- with the next peer as well (downloading the headers twice, again). (#25717)
-
-- With I2P connections, a new, transient address is used for each outbound
- connection if `-i2pacceptincoming=0`. (#25355)
-
-Updated RPCs
-------------
-
-- The `-deprecatedrpc=softforks` configuration option has been removed. The
- RPC `getblockchaininfo` no longer returns the `softforks` field, which was
- previously deprecated in 23.0. (#23508) Information on soft fork status is
- now only available via the `getdeploymentinfo` RPC.
-
-- The `deprecatedrpc=exclude_coinbase` configuration option has been removed.
- The `receivedby` RPCs (`listreceivedbyaddress`, `listreceivedbylabel`,
- `getreceivedbyaddress` and `getreceivedbylabel`) now always return results
- accounting for received coins from coinbase outputs, without an option to
- change that behaviour. Excluding coinbases was previously deprecated in 23.0.
- (#25171)
-
-- The `deprecatedrpc=fees` configuration option has been removed. The top-level
- fee fields `fee`, `modifiedfee`, `ancestorfees` and `descendantfees` are no
- longer returned by RPCs `getmempoolentry`, `getrawmempool(verbose=true)`,
- `getmempoolancestors(verbose=true)` and `getmempooldescendants(verbose=true)`.
- The same fee fields can be accessed through the `fees` object in the result.
- The top-level fee fields were previously deprecated in 23.0. (#25204)
-
-- The `getpeerinfo` RPC has been updated with a new `presynced_headers` field,
- indicating the progress on the presync phase mentioned in the
- "P2P and network changes" section above.
-
-Changes to wallet related RPCs can be found in the Wallet section below.
-
-New RPCs
---------
-
-- The `sendall` RPC spends specific UTXOs to one or more recipients
- without creating change. By default, the `sendall` RPC will spend
- every UTXO in the wallet. `sendall` is useful to empty wallets or to
- create a changeless payment from select UTXOs. When creating a payment
- from a specific amount for which the recipient incurs the transaction
- fee, continue to use the `subtractfeefromamount` option via the
- `send`, `sendtoaddress`, or `sendmany` RPCs. (#24118)
-
-- A new `gettxspendingprevout` RPC has been added, which scans the mempool to find
- transactions spending any of the given outpoints. (#24408)
-
-- The `simulaterawtransaction` RPC iterates over the inputs and outputs of the given
- transactions, and tallies up the balance change for the given wallet. This can be
- useful e.g. when verifying that a coin join like transaction doesn't contain unexpected
- inputs that the wallet will then sign for unintentionally. (#22751)
-
-Updated REST APIs
------------------
-
-- The `/headers/` and `/blockfilterheaders/` endpoints have been updated to use
- a query parameter instead of path parameter to specify the result count. The
- count parameter is now optional, and defaults to 5 for both endpoints. The old
- endpoints are still functional, and have no documented behaviour change.
-
- For `/headers`, use
- `GET /rest/headers/<BLOCK-HASH>.<bin|hex|json>?count=<COUNT=5>`
- instead of
- `GET /rest/headers/<COUNT>/<BLOCK-HASH>.<bin|hex|json>` (deprecated)
-
- For `/blockfilterheaders/`, use
- `GET /rest/blockfilterheaders/<FILTERTYPE>/<BLOCK-HASH>.<bin|hex|json>?count=<COUNT=5>`
- instead of
- `GET /rest/blockfilterheaders/<FILTERTYPE>/<COUNT>/<BLOCK-HASH>.<bin|hex|json>` (deprecated)
-
- (#24098)
-
-Build System
-------------
-
-- Guix builds are now reproducible across architectures (x86_64 & aarch64). (#21194)
-
-New settings
-------------
-
-- A new `mempoolfullrbf` option has been added, which enables the mempool to
- accept transaction replacement without enforcing BIP125 replaceability
- signaling. (#25353)
-
-Wallet
-------
-
-- The `-walletrbf` startup option will now default to `true`. The
- wallet will now default to opt-in RBF on transactions that it creates. (#25610)
-
-- The `replaceable` option for the `createrawtransaction` and
- `createpsbt` RPCs will now default to `true`. Transactions created
- with these RPCs will default to having opt-in RBF enabled. (#25610)
-
-- The `wsh()` output descriptor was extended with Miniscript support. You can import Miniscript
- descriptors for P2WSH in a watchonly wallet to track coins, but you can't spend from them using
- the Bitcoin Core wallet yet.
- You can find more about Miniscript on the [reference website](https://bitcoin.sipa.be/miniscript/). (#24148)
-
-- The `tr()` output descriptor now supports multisig scripts through the `multi_a()` and
- `sortedmulti_a()` functions. (#24043)
-
-- To help prevent fingerprinting transactions created by the Bitcoin Core wallet, change output
- amounts are now randomized. (#24494)
-
-- The `listtransactions`, `gettransaction`, and `listsinceblock`
- RPC methods now include a wtxid field (hash of serialized transaction,
- including witness data) for each transaction. (#24198)
-
-- The `listsinceblock`, `listtransactions` and `gettransaction` output now contain a new
- `parent_descs` field for every "receive" entry. (#25504)
-
-- A new optional `include_change` parameter was added to the `listsinceblock` command.
-
-- RPC `getreceivedbylabel` now returns an error, "Label not found
- in wallet" (-4), if the label is not in the address book. (#25122)
-
-Migrating Legacy Wallets to Descriptor Wallets
----------------------------------------------
-
-An experimental RPC `migratewallet` has been added to migrate Legacy (non-descriptor) wallets to
-Descriptor wallets. More information about the migration process is available in the
-[documentation](https://github.com/bitcoin/bitcoin/blob/master/doc/managing-wallets.md#migrating-legacy-wallets-to-descriptor-wallets).
-
-GUI changes
------------
-
-- A new menu item to restore a wallet from a backup file has been added (gui#471).
-
-- Configuration changes made in the bitcoin GUI (such as the pruning setting,
-proxy settings, UPNP preferences) are now saved to `<datadir>/settings.json`
-file rather than to the Qt settings backend (windows registry or unix desktop
-config files), so these settings will now apply to bitcoind, instead of being
-ignored. (#15936, gui#602)
-
-- Also, the interaction between GUI settings and `bitcoin.conf` settings is
-simplified. Settings from `bitcoin.conf` are now displayed normally in the GUI
-settings dialog, instead of in a separate warning message ("Options set in this
-dialog are overridden by the configuration file: -setting=value"). And these
-settings can now be edited because `settings.json` values take precedence over
-`bitcoin.conf` values. (#15936)
-
-Low-level changes
-=================
-
-RPC
----
-
-- The `deriveaddresses`, `getdescriptorinfo`, `importdescriptors` and `scantxoutset` commands now
- accept Miniscript expression within a `wsh()` descriptor. (#24148)
-
-- The `getaddressinfo`, `decodescript`, `listdescriptors` and `listunspent` commands may now output
- a Miniscript descriptor inside a `wsh()` where a `wsh(raw())` descriptor was previously returned. (#24148)
-
-Credits
-=======
-
-Thanks to everyone who directly contributed to this release:
-
-- /dev/fd0
-- 0xb10c
-- Adam Jonas
-- akankshakashyap
-- Ali Sherief
-- amadeuszpawlik
-- Andreas Kouloumos
-- Andrew Chow
-- Anthony Towns
-- Antoine Poinsot
-- Antoine Riard
-- Aurèle Oulès
-- avirgovi
-- Ayush Sharma
-- Baas
-- Ben Woosley
-- BrokenProgrammer
-- brunoerg
-- brydinh
-- Bushstar
-- Calvin Kim
-- CAnon
-- Carl Dong
-- chinggg
-- Cory Fields
-- Daniel Kraft
-- Daniela Brozzoni
-- darosior
-- Dave Scotese
-- David Bakin
-- dergoegge
-- dhruv
-- Dimitri
-- dontbyte
-- Duncan Dean
-- eugene
-- Eunoia
-- Fabian Jahr
-- furszy
-- Gleb Naumenko
-- glozow
-- Greg Weber
-- Gregory Sanders
-- gruve-p
-- Hennadii Stepanov
-- hiago
-- Igor Bubelov
-- ishaanam
-- Jacob P.
-- Jadi
-- James O'Beirne
-- Janna
-- Jarol Rodriguez
-- Jeremy Rand
-- Jeremy Rubin
-- jessebarton
-- João Barbosa
-- John Newbery
-- Jon Atack
-- Josiah Baker
-- Karl-Johan Alm
-- KevinMusgrave
-- Kiminuo
-- klementtan
-- Kolby Moroz
-- kouloumos
-- Kristaps Kaupe
-- Larry Ruane
-- Luke Dashjr
-- MarcoFalke
-- Marnix
-- Martin Leitner-Ankerl
-- Martin Zumsande
-- Michael Dietz
-- Michael Folkson
-- Michael Ford
-- Murch
-- mutatrum
-- muxator
-- Oskar Mendel
-- Pablo Greco
-- pasta
-- Patrick Strateman
-- Pavol Rusnak
-- Peter Bushnell
-- phyBrackets
-- Pieter Wuille
-- practicalswift
-- randymcmillan
-- Robert Spigler
-- Russell Yanofsky
-- S3RK
-- Samer Afach
-- Sebastian Falbesoner
-- Seibart Nedor
-- Shashwat
-- Sjors Provoost
-- Smlep
-- sogoagain
-- Stacie
-- Stéphan Vuylsteke
-- Suhail Saqan
-- Suhas Daftuar
-- t-bast
-- TakeshiMusgrave
-- Vasil Dimov
-- W. J. van der Laan
-- w0xlt
-- whiteh0rse
-- willcl-ark
-- William Casarin
-- Yancy Ribbens
-
-As well as to everyone that helped with translations on
-[Transifex](https://www.transifex.com/bitcoin/bitcoin/).
+See the release notes for 24.0.1 instead.
diff --git a/src/Makefile.am b/src/Makefile.am
index 2e2da54b2d..cff194b0fd 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -177,6 +177,7 @@ BITCOIN_CORE_H = \
kernel/checks.h \
kernel/coinstats.h \
kernel/context.h \
+ kernel/mempool_entry.h \
kernel/mempool_limits.h \
kernel/mempool_options.h \
kernel/mempool_persist.h \
@@ -263,7 +264,6 @@ BITCOIN_CORE_H = \
torcontrol.h \
txdb.h \
txmempool.h \
- txmempool_entry.h \
txorphanage.h \
txrequest.h \
undo.h \
diff --git a/src/bench/mempool_eviction.cpp b/src/bench/mempool_eviction.cpp
index 29feb42528..2b133f58f4 100644
--- a/src/bench/mempool_eviction.cpp
+++ b/src/bench/mempool_eviction.cpp
@@ -3,10 +3,10 @@
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
#include <bench/bench.h>
+#include <kernel/mempool_entry.h>
#include <policy/policy.h>
#include <test/util/setup_common.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
static void AddTx(const CTransactionRef& tx, const CAmount& nFee, CTxMemPool& pool) EXCLUSIVE_LOCKS_REQUIRED(cs_main, pool.cs)
diff --git a/src/bench/mempool_stress.cpp b/src/bench/mempool_stress.cpp
index 1e40d78aa5..67564508d9 100644
--- a/src/bench/mempool_stress.cpp
+++ b/src/bench/mempool_stress.cpp
@@ -3,10 +3,10 @@
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
#include <bench/bench.h>
+#include <kernel/mempool_entry.h>
#include <policy/policy.h>
#include <test/util/setup_common.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <validation.h>
#include <vector>
diff --git a/src/bench/peer_eviction.cpp b/src/bench/peer_eviction.cpp
index c3e3670de7..d83342be93 100644
--- a/src/bench/peer_eviction.cpp
+++ b/src/bench/peer_eviction.cpp
@@ -40,7 +40,7 @@ static void EvictionProtection0Networks250Candidates(benchmark::Bench& bench)
{
EvictionProtectionCommon(
bench,
- 250 /* num_candidates */,
+ /*num_candidates=*/250,
[](NodeEvictionCandidate& c) {
c.m_connected = std::chrono::seconds{c.id};
c.m_network = NET_IPV4;
@@ -51,7 +51,7 @@ static void EvictionProtection1Networks250Candidates(benchmark::Bench& bench)
{
EvictionProtectionCommon(
bench,
- 250 /* num_candidates */,
+ /*num_candidates=*/250,
[](NodeEvictionCandidate& c) {
c.m_connected = std::chrono::seconds{c.id};
c.m_is_local = false;
@@ -67,7 +67,7 @@ static void EvictionProtection2Networks250Candidates(benchmark::Bench& bench)
{
EvictionProtectionCommon(
bench,
- 250 /* num_candidates */,
+ /*num_candidates=*/250,
[](NodeEvictionCandidate& c) {
c.m_connected = std::chrono::seconds{c.id};
c.m_is_local = false;
@@ -85,7 +85,7 @@ static void EvictionProtection3Networks050Candidates(benchmark::Bench& bench)
{
EvictionProtectionCommon(
bench,
- 50 /* num_candidates */,
+ /*num_candidates=*/50,
[](NodeEvictionCandidate& c) {
c.m_connected = std::chrono::seconds{c.id};
c.m_is_local = (c.id == 28 || c.id == 47); // 2 localhost
@@ -103,7 +103,7 @@ static void EvictionProtection3Networks100Candidates(benchmark::Bench& bench)
{
EvictionProtectionCommon(
bench,
- 100 /* num_candidates */,
+ /*num_candidates=*/100,
[](NodeEvictionCandidate& c) {
c.m_connected = std::chrono::seconds{c.id};
c.m_is_local = (c.id >= 55 && c.id < 60); // 5 localhost
@@ -121,7 +121,7 @@ static void EvictionProtection3Networks250Candidates(benchmark::Bench& bench)
{
EvictionProtectionCommon(
bench,
- 250 /* num_candidates */,
+ /*num_candidates=*/250,
[](NodeEvictionCandidate& c) {
c.m_connected = std::chrono::seconds{c.id};
c.m_is_local = (c.id >= 140 && c.id < 160); // 20 localhost
diff --git a/src/bench/rpc_mempool.cpp b/src/bench/rpc_mempool.cpp
index 5ae4829d16..6bac6419e5 100644
--- a/src/bench/rpc_mempool.cpp
+++ b/src/bench/rpc_mempool.cpp
@@ -4,10 +4,10 @@
#include <bench/bench.h>
#include <chainparamsbase.h>
+#include <kernel/mempool_entry.h>
#include <rpc/mempool.h>
#include <test/util/setup_common.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <univalue.h>
diff --git a/src/init.cpp b/src/init.cpp
index 2fdc2717c9..f31a45aa9f 100644
--- a/src/init.cpp
+++ b/src/init.cpp
@@ -1571,7 +1571,7 @@ bool AppInitMain(NodeContext& node, interfaces::BlockAndHeaderTipInfo* tip_info)
}
if (args.GetBoolArg("-coinstatsindex", DEFAULT_COINSTATSINDEX)) {
- g_coin_stats_index = std::make_unique<CoinStatsIndex>(interfaces::MakeChain(node), /* cache size */ 0, false, fReindex);
+ g_coin_stats_index = std::make_unique<CoinStatsIndex>(interfaces::MakeChain(node), /*cache_size=*/0, false, fReindex);
if (!g_coin_stats_index->Start()) {
return false;
}
diff --git a/src/txmempool_entry.h b/src/kernel/mempool_entry.h
index dd71833200..e1ba4296ef 100644
--- a/src/txmempool_entry.h
+++ b/src/kernel/mempool_entry.h
@@ -2,8 +2,8 @@
// Distributed under the MIT software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
-#ifndef BITCOIN_TXMEMPOOL_ENTRY_H
-#define BITCOIN_TXMEMPOOL_ENTRY_H
+#ifndef BITCOIN_KERNEL_MEMPOOL_ENTRY_H
+#define BITCOIN_KERNEL_MEMPOOL_ENTRY_H
#include <consensus/amount.h>
#include <consensus/validation.h>
@@ -171,4 +171,4 @@ public:
mutable Epoch::Marker m_epoch_marker; //!< epoch when last touched, useful for graph algorithms
};
-#endif // BITCOIN_TXMEMPOOL_ENTRY_H
+#endif // BITCOIN_KERNEL_MEMPOOL_ENTRY_H
diff --git a/src/net_processing.cpp b/src/net_processing.cpp
index d7061b89e0..e31ca81a08 100644
--- a/src/net_processing.cpp
+++ b/src/net_processing.cpp
@@ -16,6 +16,7 @@
#include <hash.h>
#include <headerssync.h>
#include <index/blockfilterindex.h>
+#include <kernel/mempool_entry.h>
#include <merkleblock.h>
#include <netbase.h>
#include <netmessagemaker.h>
@@ -34,7 +35,6 @@
#include <timedata.h>
#include <tinyformat.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <txorphanage.h>
#include <txrequest.h>
#include <util/check.h> // For NDEBUG compile time check
diff --git a/src/node/interfaces.cpp b/src/node/interfaces.cpp
index 212780b259..c2c9adadbb 100644
--- a/src/node/interfaces.cpp
+++ b/src/node/interfaces.cpp
@@ -15,17 +15,18 @@
#include <interfaces/handler.h>
#include <interfaces/node.h>
#include <interfaces/wallet.h>
+#include <kernel/chain.h>
+#include <kernel/mempool_entry.h>
#include <mapport.h>
#include <net.h>
#include <net_processing.h>
#include <netaddress.h>
#include <netbase.h>
#include <node/blockstorage.h>
-#include <kernel/chain.h>
#include <node/coin.h>
#include <node/context.h>
-#include <node/transaction.h>
#include <node/interface_ui.h>
+#include <node/transaction.h>
#include <policy/feerate.h>
#include <policy/fees.h>
#include <policy/policy.h>
@@ -39,7 +40,6 @@
#include <support/allocators/secure.h>
#include <sync.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <uint256.h>
#include <univalue.h>
#include <util/check.h>
diff --git a/src/policy/fees.cpp b/src/policy/fees.cpp
index 899adc70ca..1cd9624000 100644
--- a/src/policy/fees.cpp
+++ b/src/policy/fees.cpp
@@ -8,6 +8,7 @@
#include <clientversion.h>
#include <consensus/amount.h>
#include <fs.h>
+#include <kernel/mempool_entry.h>
#include <logging.h>
#include <policy/feerate.h>
#include <primitives/transaction.h>
@@ -16,7 +17,6 @@
#include <streams.h>
#include <sync.h>
#include <tinyformat.h>
-#include <txmempool_entry.h>
#include <uint256.h>
#include <util/serfloat.h>
#include <util/system.h>
diff --git a/src/policy/rbf.cpp b/src/policy/rbf.cpp
index 994e13dd56..3a347b41ed 100644
--- a/src/policy/rbf.cpp
+++ b/src/policy/rbf.cpp
@@ -5,12 +5,12 @@
#include <policy/rbf.h>
#include <consensus/amount.h>
+#include <kernel/mempool_entry.h>
#include <policy/feerate.h>
#include <primitives/transaction.h>
#include <sync.h>
#include <tinyformat.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <uint256.h>
#include <util/moneystr.h>
#include <util/rbf.h>
diff --git a/src/psbt.h b/src/psbt.h
index 37bf142366..b636f0348b 100644
--- a/src/psbt.h
+++ b/src/psbt.h
@@ -875,7 +875,7 @@ struct PSBTOutput
throw std::ios_base::failure("Output Taproot tree has a leaf with an invalid leaf version");
}
m_tap_tree.push_back(std::make_tuple(depth, leaf_ver, script));
- builder.Add((int)depth, script, (int)leaf_ver, true /* track */);
+ builder.Add((int)depth, script, (int)leaf_ver, /*track=*/true);
}
if (!builder.IsComplete()) {
throw std::ios_base::failure("Output Taproot tree is malformed");
diff --git a/src/qt/coincontroldialog.cpp b/src/qt/coincontroldialog.cpp
index bd9a90a890..3bedbf29d8 100644
--- a/src/qt/coincontroldialog.cpp
+++ b/src/qt/coincontroldialog.cpp
@@ -477,7 +477,7 @@ void CoinControlDialog::updateLabels(CCoinControl& m_coin_control, WalletModel *
nBytes -= 34;
// Fee
- nPayFee = model->wallet().getMinimumFee(nBytes, m_coin_control, nullptr /* returned_target */, nullptr /* reason */);
+ nPayFee = model->wallet().getMinimumFee(nBytes, m_coin_control, /*returned_target=*/nullptr, /*reason=*/nullptr);
if (nPayAmount > 0)
{
diff --git a/src/qt/psbtoperationsdialog.cpp b/src/qt/psbtoperationsdialog.cpp
index 333766ce21..afffae0784 100644
--- a/src/qt/psbtoperationsdialog.cpp
+++ b/src/qt/psbtoperationsdialog.cpp
@@ -56,7 +56,7 @@ void PSBTOperationsDialog::openWithPSBT(PartiallySignedTransaction psbtx)
bool complete = FinalizePSBT(psbtx); // Make sure all existing signatures are fully combined before checking for completeness.
if (m_wallet_model) {
size_t n_could_sign;
- TransactionError err = m_wallet_model->wallet().fillPSBT(SIGHASH_ALL, false /* sign */, true /* bip32derivs */, &n_could_sign, m_transaction_data, complete);
+ TransactionError err = m_wallet_model->wallet().fillPSBT(SIGHASH_ALL, /*sign=*/false, /*bip32derivs=*/true, &n_could_sign, m_transaction_data, complete);
if (err != TransactionError::OK) {
showStatus(tr("Failed to load transaction: %1")
.arg(QString::fromStdString(TransactionErrorString(err).translated)),
@@ -80,7 +80,7 @@ void PSBTOperationsDialog::signTransaction()
WalletModel::UnlockContext ctx(m_wallet_model->requestUnlock());
- TransactionError err = m_wallet_model->wallet().fillPSBT(SIGHASH_ALL, true /* sign */, true /* bip32derivs */, &n_signed, m_transaction_data, complete);
+ TransactionError err = m_wallet_model->wallet().fillPSBT(SIGHASH_ALL, /*sign=*/true, /*bip32derivs=*/true, &n_signed, m_transaction_data, complete);
if (err != TransactionError::OK) {
showStatus(tr("Failed to sign transaction: %1")
@@ -245,7 +245,7 @@ size_t PSBTOperationsDialog::couldSignInputs(const PartiallySignedTransaction &p
size_t n_signed;
bool complete;
- TransactionError err = m_wallet_model->wallet().fillPSBT(SIGHASH_ALL, false /* sign */, false /* bip32derivs */, &n_signed, m_transaction_data, complete);
+ TransactionError err = m_wallet_model->wallet().fillPSBT(SIGHASH_ALL, /*sign=*/false, /*bip32derivs=*/false, &n_signed, m_transaction_data, complete);
if (err != TransactionError::OK) {
return 0;
diff --git a/src/qt/test/apptests.cpp b/src/qt/test/apptests.cpp
index 6fc7a52435..a5cef9a1bb 100644
--- a/src/qt/test/apptests.cpp
+++ b/src/qt/test/apptests.cpp
@@ -72,7 +72,7 @@ void AppTests::appTests()
qRegisterMetaType<interfaces::BlockAndHeaderTipInfo>("interfaces::BlockAndHeaderTipInfo");
m_app.parameterSetup();
- QVERIFY(m_app.createOptionsModel(true /* reset settings */));
+ QVERIFY(m_app.createOptionsModel(/*resetSettings=*/true));
QScopedPointer<const NetworkStyle> style(NetworkStyle::instantiate(Params().NetworkIDString()));
m_app.setupPlatformStyle();
m_app.createWindow(style.data());
diff --git a/src/qt/test/test_main.cpp b/src/qt/test/test_main.cpp
index 846fa519ee..3f582e7cf6 100644
--- a/src/qt/test/test_main.cpp
+++ b/src/qt/test/test_main.cpp
@@ -79,8 +79,6 @@ int main(int argc, char* argv[])
setenv("QT_QPA_PLATFORM", "minimal", 0 /* overwrite */);
#endif
- // Don't remove this, it's needed to access
- // QApplication:: and QCoreApplication:: in the tests
BitcoinApplication app;
app.setApplicationName("Bitcoin-Qt-test");
app.createNode(*init);
diff --git a/src/qt/test/wallettests.cpp b/src/qt/test/wallettests.cpp
index b71dfb0e9f..c32525b607 100644
--- a/src/qt/test/wallettests.cpp
+++ b/src/qt/test/wallettests.cpp
@@ -210,17 +210,17 @@ void TestGUI(interfaces::Node& node)
// Send two transactions, and verify they are added to transaction list.
TransactionTableModel* transactionTableModel = walletModel.getTransactionTableModel();
QCOMPARE(transactionTableModel->rowCount({}), 105);
- uint256 txid1 = SendCoins(*wallet.get(), sendCoinsDialog, PKHash(), 5 * COIN, false /* rbf */);
- uint256 txid2 = SendCoins(*wallet.get(), sendCoinsDialog, PKHash(), 10 * COIN, true /* rbf */);
+ uint256 txid1 = SendCoins(*wallet.get(), sendCoinsDialog, PKHash(), 5 * COIN, /*rbf=*/false);
+ uint256 txid2 = SendCoins(*wallet.get(), sendCoinsDialog, PKHash(), 10 * COIN, /*rbf=*/true);
QCOMPARE(transactionTableModel->rowCount({}), 107);
QVERIFY(FindTx(*transactionTableModel, txid1).isValid());
QVERIFY(FindTx(*transactionTableModel, txid2).isValid());
// Call bumpfee. Test disabled, canceled, enabled, then failing cases.
- BumpFee(transactionView, txid1, true /* expect disabled */, "not BIP 125 replaceable" /* expected error */, false /* cancel */);
- BumpFee(transactionView, txid2, false /* expect disabled */, {} /* expected error */, true /* cancel */);
- BumpFee(transactionView, txid2, false /* expect disabled */, {} /* expected error */, false /* cancel */);
- BumpFee(transactionView, txid2, true /* expect disabled */, "already bumped" /* expected error */, false /* cancel */);
+ BumpFee(transactionView, txid1, /*expectDisabled=*/true, /*expectError=*/"not BIP 125 replaceable", /*cancel=*/false);
+ BumpFee(transactionView, txid2, /*expectDisabled=*/false, /*expectError=*/{}, /*cancel=*/true);
+ BumpFee(transactionView, txid2, /*expectDisabled=*/false, /*expectError=*/{}, /*cancel=*/false);
+ BumpFee(transactionView, txid2, /*expectDisabled=*/true, /*expectError=*/"already bumped", /*cancel=*/false);
// Check current balance on OverviewPage
OverviewPage overviewPage(platformStyle.get());
diff --git a/src/qt/walletmodel.cpp b/src/qt/walletmodel.cpp
index c6f3f5b00c..ed0602594b 100644
--- a/src/qt/walletmodel.cpp
+++ b/src/qt/walletmodel.cpp
@@ -217,7 +217,7 @@ WalletModel::SendCoinsReturn WalletModel::prepareTransaction(WalletModelTransact
int nChangePosRet = -1;
auto& newTx = transaction.getWtx();
- const auto& res = m_wallet->createTransaction(vecSend, coinControl, !wallet().privateKeysDisabled() /* sign */, nChangePosRet, nFeeRequired);
+ const auto& res = m_wallet->createTransaction(vecSend, coinControl, /*sign=*/!wallet().privateKeysDisabled(), nChangePosRet, nFeeRequired);
newTx = res ? *res : nullptr;
transaction.setTransactionFee(nFeeRequired);
if (fSubtractFeeFromAmount && newTx)
@@ -258,7 +258,7 @@ void WalletModel::sendCoins(WalletModelTransaction& transaction)
}
auto& newTx = transaction.getWtx();
- wallet().commitTransaction(newTx, {} /* mapValue */, std::move(vOrderForm));
+ wallet().commitTransaction(newTx, /*value_map=*/{}, std::move(vOrderForm));
CDataStream ssTx(SER_NETWORK, PROTOCOL_VERSION);
ssTx << *newTx;
@@ -542,7 +542,7 @@ bool WalletModel::bumpFee(uint256 hash, uint256& new_hash)
if (retval == QMessageBox::Save) {
PartiallySignedTransaction psbtx(mtx);
bool complete = false;
- const TransactionError err = wallet().fillPSBT(SIGHASH_ALL, false /* sign */, true /* bip32derivs */, nullptr, psbtx, complete);
+ const TransactionError err = wallet().fillPSBT(SIGHASH_ALL, /*sign=*/false, /*bip32derivs=*/true, nullptr, psbtx, complete);
if (err != TransactionError::OK || complete) {
QMessageBox::critical(nullptr, tr("Fee bump error"), tr("Can't draft transaction."));
return false;
diff --git a/src/rpc/mempool.cpp b/src/rpc/mempool.cpp
index 039a4328e3..7a0c361ae0 100644
--- a/src/rpc/mempool.cpp
+++ b/src/rpc/mempool.cpp
@@ -10,6 +10,7 @@
#include <chainparams.h>
#include <core_io.h>
#include <fs.h>
+#include <kernel/mempool_entry.h>
#include <node/mempool_persist_args.h>
#include <policy/rbf.h>
#include <policy/settings.h>
@@ -18,7 +19,6 @@
#include <rpc/server_util.h>
#include <rpc/util.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <univalue.h>
#include <util/moneystr.h>
#include <util/time.h>
diff --git a/src/rpc/server.cpp b/src/rpc/server.cpp
index f57133f75b..80a22ff8ca 100644
--- a/src/rpc/server.cpp
+++ b/src/rpc/server.cpp
@@ -103,7 +103,7 @@ std::string CRPCTable::help(const std::string& strCommand, const JSONRPCRequest&
{
UniValue unused_result;
if (setDone.insert(pcmd->unique_id).second)
- pcmd->actor(jreq, unused_result, true /* last_handler */);
+ pcmd->actor(jreq, unused_result, /*last_handler=*/true);
}
catch (const std::exception& e)
{
diff --git a/src/test/fuzz/policy_estimator.cpp b/src/test/fuzz/policy_estimator.cpp
index 3788c36455..17c340695f 100644
--- a/src/test/fuzz/policy_estimator.cpp
+++ b/src/test/fuzz/policy_estimator.cpp
@@ -2,6 +2,7 @@
// Distributed under the MIT software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
+#include <kernel/mempool_entry.h>
#include <policy/fees.h>
#include <policy/fees_args.h>
#include <primitives/transaction.h>
@@ -11,7 +12,6 @@
#include <test/fuzz/util/mempool.h>
#include <test/util/setup_common.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <cstdint>
#include <optional>
diff --git a/src/test/fuzz/util/mempool.cpp b/src/test/fuzz/util/mempool.cpp
index c6a6943603..4baca5ec77 100644
--- a/src/test/fuzz/util/mempool.cpp
+++ b/src/test/fuzz/util/mempool.cpp
@@ -4,11 +4,11 @@
#include <consensus/amount.h>
#include <consensus/consensus.h>
+#include <kernel/mempool_entry.h>
#include <primitives/transaction.h>
#include <test/fuzz/FuzzedDataProvider.h>
#include <test/fuzz/util.h>
#include <test/fuzz/util/mempool.h>
-#include <txmempool_entry.h>
#include <cassert>
#include <cstdint>
diff --git a/src/test/fuzz/util/mempool.h b/src/test/fuzz/util/mempool.h
index ada657d970..31b578dc4b 100644
--- a/src/test/fuzz/util/mempool.h
+++ b/src/test/fuzz/util/mempool.h
@@ -5,7 +5,7 @@
#ifndef BITCOIN_TEST_FUZZ_UTIL_MEMPOOL_H
#define BITCOIN_TEST_FUZZ_UTIL_MEMPOOL_H
-#include <txmempool_entry.h>
+#include <kernel/mempool_entry.h>
#include <validation.h>
class CTransaction;
diff --git a/src/test/sync_tests.cpp b/src/test/sync_tests.cpp
index 55c2c5108d..e1270a362b 100644
--- a/src/test/sync_tests.cpp
+++ b/src/test/sync_tests.cpp
@@ -107,12 +107,12 @@ BOOST_AUTO_TEST_CASE(potential_deadlock_detected)
#ifdef DEBUG_LOCKORDER
BOOST_AUTO_TEST_CASE(double_lock_mutex)
{
- TestDoubleLock<Mutex>(true /* should throw */);
+ TestDoubleLock<Mutex>(/*should_throw=*/true);
}
BOOST_AUTO_TEST_CASE(double_lock_recursive_mutex)
{
- TestDoubleLock<RecursiveMutex>(false /* should not throw */);
+ TestDoubleLock<RecursiveMutex>(/*should_throw=*/false);
}
#endif /* DEBUG_LOCKORDER */
diff --git a/src/test/util/setup_common.cpp b/src/test/util/setup_common.cpp
index a7ca97222a..c97f400137 100644
--- a/src/test/util/setup_common.cpp
+++ b/src/test/util/setup_common.cpp
@@ -17,6 +17,7 @@
#include <init.h>
#include <init/common.h>
#include <interfaces/chain.h>
+#include <kernel/mempool_entry.h>
#include <net.h>
#include <net_processing.h>
#include <node/blockstorage.h>
@@ -41,7 +42,6 @@
#include <timedata.h>
#include <txdb.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <util/strencodings.h>
#include <util/string.h>
#include <util/thread.h>
diff --git a/src/txmempool.h b/src/txmempool.h
index d48327e5dc..dd28a84c23 100644
--- a/src/txmempool.h
+++ b/src/txmempool.h
@@ -20,12 +20,12 @@
#include <coins.h>
#include <consensus/amount.h>
#include <indirectmap.h>
+#include <kernel/mempool_entry.h>
#include <policy/feerate.h>
#include <policy/packages.h>
#include <primitives/transaction.h>
#include <random.h>
#include <sync.h>
-#include <txmempool_entry.h>
#include <util/epochguard.h>
#include <util/hasher.h>
diff --git a/src/validation.cpp b/src/validation.cpp
index 8fdb4d0b47..2380c5b925 100644
--- a/src/validation.cpp
+++ b/src/validation.cpp
@@ -22,6 +22,7 @@
#include <flatfile.h>
#include <fs.h>
#include <hash.h>
+#include <kernel/mempool_entry.h>
#include <logging.h>
#include <logging/timer.h>
#include <node/blockstorage.h>
@@ -42,7 +43,6 @@
#include <tinyformat.h>
#include <txdb.h>
#include <txmempool.h>
-#include <txmempool_entry.h>
#include <uint256.h>
#include <undo.h>
#include <util/check.h> // For NDEBUG compile time check
diff --git a/src/wallet/coinselection.cpp b/src/wallet/coinselection.cpp
index b889d31928..ba1d60fe44 100644
--- a/src/wallet/coinselection.cpp
+++ b/src/wallet/coinselection.cpp
@@ -5,6 +5,7 @@
#include <wallet/coinselection.h>
#include <consensus/amount.h>
+#include <consensus/consensus.h>
#include <policy/feerate.h>
#include <util/check.h>
#include <util/system.h>
@@ -354,6 +355,10 @@ void OutputGroup::Insert(const COutput& output, size_t ancestors, size_t descend
// descendants is the count as seen from the top ancestor, not the descendants as seen from the
// coin itself; thus, this value is counted as the max, not the sum
m_descendants = std::max(m_descendants, descendants);
+
+ if (output.input_bytes > 0) {
+ m_weight += output.input_bytes * WITNESS_SCALE_FACTOR;
+ }
}
bool OutputGroup::EligibleForSpending(const CoinEligibilityFilter& eligibility_filter) const
@@ -436,18 +441,25 @@ void SelectionResult::Clear()
{
m_selected_inputs.clear();
m_waste.reset();
+ m_weight = 0;
}
void SelectionResult::AddInput(const OutputGroup& group)
{
util::insert(m_selected_inputs, group.m_outputs);
m_use_effective = !group.m_subtract_fee_outputs;
+
+ m_weight += group.m_weight;
}
void SelectionResult::AddInputs(const std::set<COutput>& inputs, bool subtract_fee_outputs)
{
util::insert(m_selected_inputs, inputs);
m_use_effective = !subtract_fee_outputs;
+
+ m_weight += std::accumulate(inputs.cbegin(), inputs.cend(), 0, [](int sum, const auto& coin) {
+ return sum + std::max(coin.input_bytes, 0) * WITNESS_SCALE_FACTOR;
+ });
}
void SelectionResult::Merge(const SelectionResult& other)
@@ -462,6 +474,8 @@ void SelectionResult::Merge(const SelectionResult& other)
}
util::insert(m_selected_inputs, other.m_selected_inputs);
assert(m_selected_inputs.size() == expected_count);
+
+ m_weight += other.m_weight;
}
const std::set<COutput>& SelectionResult::GetInputSet() const
diff --git a/src/wallet/coinselection.h b/src/wallet/coinselection.h
index 2ab4061a9b..ecfc5bfd6b 100644
--- a/src/wallet/coinselection.h
+++ b/src/wallet/coinselection.h
@@ -6,6 +6,7 @@
#define BITCOIN_WALLET_COINSELECTION_H
#include <consensus/amount.h>
+#include <consensus/consensus.h>
#include <policy/feerate.h>
#include <primitives/transaction.h>
#include <random.h>
@@ -223,6 +224,8 @@ struct OutputGroup
/** Indicate that we are subtracting the fee from outputs.
* When true, the value that is used for coin selection is the UTXO's real value rather than effective value */
bool m_subtract_fee_outputs{false};
+ /** Total weight of the UTXOs in this group. */
+ int m_weight{0};
OutputGroup() {}
OutputGroup(const CoinSelectionParams& params) :
@@ -295,6 +298,8 @@ private:
bool m_use_effective{false};
/** The computed waste */
std::optional<CAmount> m_waste;
+ /** Total weight of the selected inputs */
+ int m_weight{0};
public:
explicit SelectionResult(const CAmount target, SelectionAlgorithm algo)
@@ -353,6 +358,8 @@ public:
CAmount GetTarget() const { return m_target; }
SelectionAlgorithm GetAlgo() const { return m_algo; }
+
+ int GetWeight() const { return m_weight; }
};
std::optional<SelectionResult> SelectCoinsBnB(std::vector<OutputGroup>& utxo_pool, const CAmount& selection_target, const CAmount& cost_of_change);
diff --git a/src/wallet/dump.cpp b/src/wallet/dump.cpp
index f7fee443d0..2e46cf5454 100644
--- a/src/wallet/dump.cpp
+++ b/src/wallet/dump.cpp
@@ -201,7 +201,7 @@ bool CreateFromDump(const ArgsManager& args, const std::string& name, const fs::
// dummy chain interface
bool ret = true;
- std::shared_ptr<CWallet> wallet(new CWallet(nullptr /* chain */, name, gArgs, std::move(database)), WalletToolReleaseWallet);
+ std::shared_ptr<CWallet> wallet(new CWallet(/*chain=*/nullptr, name, gArgs, std::move(database)), WalletToolReleaseWallet);
{
LOCK(wallet->cs_wallet);
DBErrors load_wallet_ret = wallet->LoadWallet();
diff --git a/src/wallet/fees.cpp b/src/wallet/fees.cpp
index 3514d018b7..3e442a3f5f 100644
--- a/src/wallet/fees.cpp
+++ b/src/wallet/fees.cpp
@@ -84,7 +84,7 @@ CFeeRate GetMinimumFeeRate(const CWallet& wallet, const CCoinControl& coin_contr
CFeeRate GetDiscardRate(const CWallet& wallet)
{
unsigned int highest_target = wallet.chain().estimateMaxBlocks();
- CFeeRate discard_rate = wallet.chain().estimateSmartFee(highest_target, false /* conservative */);
+ CFeeRate discard_rate = wallet.chain().estimateSmartFee(highest_target, /*conservative=*/false);
// Don't let discard_rate be greater than longest possible fee estimate if we get a valid fee estimate
discard_rate = (discard_rate == CFeeRate(0)) ? wallet.m_discard_rate : std::min(discard_rate, wallet.m_discard_rate);
// Discard rate must be at least dust relay feerate
diff --git a/src/wallet/interfaces.cpp b/src/wallet/interfaces.cpp
index 9cf2b677e6..557c85ab55 100644
--- a/src/wallet/interfaces.cpp
+++ b/src/wallet/interfaces.cpp
@@ -481,7 +481,7 @@ public:
CAmount getDefaultMaxTxFee() override { return m_wallet->m_default_max_tx_fee; }
void remove() override
{
- RemoveWallet(m_context, m_wallet, false /* load_on_start */);
+ RemoveWallet(m_context, m_wallet, /*load_on_start=*/false);
}
bool isLegacy() override { return m_wallet->IsLegacy(); }
std::unique_ptr<Handler> handleUnload(UnloadFn fn) override
diff --git a/src/wallet/rpc/backup.cpp b/src/wallet/rpc/backup.cpp
index 1d2d7d2a10..ddf10cae15 100644
--- a/src/wallet/rpc/backup.cpp
+++ b/src/wallet/rpc/backup.cpp
@@ -184,7 +184,7 @@ RPCHelpMan importprivkey()
// Add the wpkh script for this key if possible
if (pubkey.IsCompressed()) {
- pwallet->ImportScripts({GetScriptForDestination(WitnessV0KeyHash(vchAddress))}, 0 /* timestamp */);
+ pwallet->ImportScripts({GetScriptForDestination(WitnessV0KeyHash(vchAddress))}, /*timestamp=*/0);
}
}
}
@@ -273,19 +273,19 @@ RPCHelpMan importaddress()
pwallet->MarkDirty();
- pwallet->ImportScriptPubKeys(strLabel, {GetScriptForDestination(dest)}, false /* have_solving_data */, true /* apply_label */, 1 /* timestamp */);
+ pwallet->ImportScriptPubKeys(strLabel, {GetScriptForDestination(dest)}, /*have_solving_data=*/false, /*apply_label=*/true, /*timestamp=*/1);
} else if (IsHex(request.params[0].get_str())) {
std::vector<unsigned char> data(ParseHex(request.params[0].get_str()));
CScript redeem_script(data.begin(), data.end());
std::set<CScript> scripts = {redeem_script};
- pwallet->ImportScripts(scripts, 0 /* timestamp */);
+ pwallet->ImportScripts(scripts, /*timestamp=*/0);
if (fP2SH) {
scripts.insert(GetScriptForDestination(ScriptHash(redeem_script)));
}
- pwallet->ImportScriptPubKeys(strLabel, scripts, false /* have_solving_data */, true /* apply_label */, 1 /* timestamp */);
+ pwallet->ImportScriptPubKeys(strLabel, scripts, /*have_solving_data=*/false, /*apply_label=*/true, /*timestamp=*/1);
} else {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Invalid Bitcoin address or script");
}
@@ -464,9 +464,9 @@ RPCHelpMan importpubkey()
pwallet->MarkDirty();
- pwallet->ImportScriptPubKeys(strLabel, script_pub_keys, true /* have_solving_data */, true /* apply_label */, 1 /* timestamp */);
+ pwallet->ImportScriptPubKeys(strLabel, script_pub_keys, /*have_solving_data=*/true, /*apply_label=*/true, /*timestamp=*/1);
- pwallet->ImportPubKeys({pubKey.GetID()}, {{pubKey.GetID(), pubKey}} , {} /* key_origins */, false /* add_keypool */, false /* internal */, 1 /* timestamp */);
+ pwallet->ImportPubKeys({pubKey.GetID()}, {{pubKey.GetID(), pubKey}} , /*key_origins=*/{}, /*add_keypool=*/false, /*internal=*/false, /*timestamp=*/1);
}
if (fRescan)
{
@@ -625,7 +625,7 @@ RPCHelpMan importwallet()
pwallet->chain().showProgress("", 100, false); // hide progress dialog in GUI
}
pwallet->chain().showProgress("", 100, false); // hide progress dialog in GUI
- RescanWallet(*pwallet, reserver, nTimeBegin, false /* update */);
+ RescanWallet(*pwallet, reserver, nTimeBegin, /*update=*/false);
pwallet->MarkDirty();
if (!fGood)
@@ -1399,7 +1399,7 @@ RPCHelpMan importmulti()
}
}
if (fRescan && fRunScan && requests.size()) {
- int64_t scannedTime = pwallet->RescanFromTime(nLowestTimestamp, reserver, true /* update */);
+ int64_t scannedTime = pwallet->RescanFromTime(nLowestTimestamp, reserver, /*update=*/true);
pwallet->ResubmitWalletTransactions(/*relay=*/false, /*force=*/true);
if (pwallet->IsAbortingRescan()) {
@@ -1691,7 +1691,7 @@ RPCHelpMan importdescriptors()
// Rescan the blockchain using the lowest timestamp
if (rescan) {
- int64_t scanned_time = pwallet->RescanFromTime(lowest_timestamp, reserver, true /* update */);
+ int64_t scanned_time = pwallet->RescanFromTime(lowest_timestamp, reserver, /*update=*/true);
pwallet->ResubmitWalletTransactions(/*relay=*/false, /*force=*/true);
if (pwallet->IsAbortingRescan()) {
diff --git a/src/wallet/rpc/spend.cpp b/src/wallet/rpc/spend.cpp
index 0fa693e7e7..7ab4044bf5 100644
--- a/src/wallet/rpc/spend.cpp
+++ b/src/wallet/rpc/spend.cpp
@@ -161,7 +161,7 @@ UniValue SendMoney(CWallet& wallet, const CCoinControl &coin_control, std::vecto
throw JSONRPCError(RPC_WALLET_INSUFFICIENT_FUNDS, util::ErrorString(res).original);
}
const CTransactionRef& tx = res->tx;
- wallet.CommitTransaction(tx, std::move(map_value), {} /* orderForm */);
+ wallet.CommitTransaction(tx, std::move(map_value), /*orderForm=*/{});
if (verbose) {
UniValue entry(UniValue::VOBJ);
entry.pushKV("txid", tx->GetHash().GetHex());
@@ -1083,7 +1083,7 @@ static RPCHelpMan bumpfee_helper(std::string method_name)
} else {
PartiallySignedTransaction psbtx(mtx);
bool complete = false;
- const TransactionError err = pwallet->FillPSBT(psbtx, complete, SIGHASH_DEFAULT, false /* sign */, true /* bip32derivs */);
+ const TransactionError err = pwallet->FillPSBT(psbtx, complete, SIGHASH_DEFAULT, /*sign=*/false, /*bip32derivs=*/true);
CHECK_NONFATAL(err == TransactionError::OK);
CHECK_NONFATAL(!complete);
CDataStream ssTx(SER_NETWORK, PROTOCOL_VERSION);
diff --git a/src/wallet/rpc/transactions.cpp b/src/wallet/rpc/transactions.cpp
index 3c10b47082..667cd929d1 100644
--- a/src/wallet/rpc/transactions.cpp
+++ b/src/wallet/rpc/transactions.cpp
@@ -614,7 +614,7 @@ RPCHelpMan listsinceblock()
blockId = ParseHashV(request.params[0], "blockhash");
height = int{};
altheight = int{};
- if (!wallet.chain().findCommonAncestor(blockId, wallet.GetLastBlockHash(), /* ancestor out */ FoundBlock().height(*height), /* blockId out */ FoundBlock().height(*altheight))) {
+ if (!wallet.chain().findCommonAncestor(blockId, wallet.GetLastBlockHash(), /*ancestor_out=*/FoundBlock().height(*height), /*block1_out=*/FoundBlock().height(*altheight))) {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Block not found");
}
}
@@ -642,7 +642,7 @@ RPCHelpMan listsinceblock()
const CWalletTx& tx = pairWtx.second;
if (depth == -1 || abs(wallet.GetTxDepthInMainChain(tx)) < depth) {
- ListTransactions(wallet, tx, 0, true, transactions, filter, nullptr /* filter_label */, /*include_change=*/include_change);
+ ListTransactions(wallet, tx, 0, true, transactions, filter, /*filter_label=*/nullptr, /*include_change=*/include_change);
}
}
@@ -659,7 +659,7 @@ RPCHelpMan listsinceblock()
if (it != wallet.mapWallet.end()) {
// We want all transactions regardless of confirmation count to appear here,
// even negative confirmation ones, hence the big negative.
- ListTransactions(wallet, it->second, -100000000, true, removed, filter, nullptr /* filter_label */, /*include_change=*/include_change);
+ ListTransactions(wallet, it->second, -100000000, true, removed, filter, /*filter_label=*/nullptr, /*include_change=*/include_change);
}
}
blockId = block.hashPrevBlock;
@@ -777,7 +777,7 @@ RPCHelpMan gettransaction()
WalletTxToJSON(*pwallet, wtx, entry);
UniValue details(UniValue::VARR);
- ListTransactions(*pwallet, wtx, 0, false, details, filter, nullptr /* filter_label */);
+ ListTransactions(*pwallet, wtx, 0, false, details, filter, /*filter_label=*/nullptr);
entry.pushKV("details", details);
std::string strHex = EncodeHexTx(*wtx.tx, pwallet->chain().rpcSerializationFlags());
diff --git a/src/wallet/spend.cpp b/src/wallet/spend.cpp
index c6c6ec0b89..3ced3ebeb5 100644
--- a/src/wallet/spend.cpp
+++ b/src/wallet/spend.cpp
@@ -2,9 +2,11 @@
// Distributed under the MIT software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
+#include <algorithm>
#include <consensus/amount.h>
#include <consensus/validation.h>
#include <interfaces/chain.h>
+#include <numeric>
#include <policy/policy.h>
#include <script/signingprovider.h>
#include <util/check.h>
@@ -555,14 +557,24 @@ std::optional<SelectionResult> ChooseSelectionResult(const CWallet& wallet, cons
results.push_back(*srd_result);
}
- if (results.size() == 0) {
+ if (results.empty()) {
// No solution found
return std::nullopt;
}
+ std::vector<SelectionResult> eligible_results;
+ std::copy_if(results.begin(), results.end(), std::back_inserter(eligible_results), [coin_selection_params](const SelectionResult& result) {
+ const auto initWeight{coin_selection_params.tx_noinputs_size * WITNESS_SCALE_FACTOR};
+ return initWeight + result.GetWeight() <= static_cast<int>(MAX_STANDARD_TX_WEIGHT);
+ });
+
+ if (eligible_results.empty()) {
+ return std::nullopt;
+ }
+
// Choose the result with the least waste
// If the waste is the same, choose the one which spends more inputs.
- auto& best_result = *std::min_element(results.begin(), results.end());
+ auto& best_result = *std::min_element(eligible_results.begin(), eligible_results.end());
return best_result;
}
@@ -651,7 +663,7 @@ std::optional<SelectionResult> AutomaticCoinSelection(const CWallet& wallet, Coi
// If partial groups are allowed, relax the requirement of spending OutputGroups (groups
// of UTXOs sent to the same address, which are obviously controlled by a single wallet)
// in their entirety.
- if (auto r6{AttemptSelection(wallet, value_to_select, CoinEligibilityFilter(0, 1, max_ancestors-1, max_descendants-1, true /* include_partial_groups */),
+ if (auto r6{AttemptSelection(wallet, value_to_select, CoinEligibilityFilter(0, 1, max_ancestors-1, max_descendants-1, /*include_partial=*/true),
available_coins, coin_selection_params, /*allow_mixed_output_types=*/true)}) {
return r6;
}
@@ -659,7 +671,7 @@ std::optional<SelectionResult> AutomaticCoinSelection(const CWallet& wallet, Coi
// received from other wallets.
if (coin_control.m_include_unsafe_inputs) {
if (auto r7{AttemptSelection(wallet, value_to_select,
- CoinEligibilityFilter(0 /* conf_mine */, 0 /* conf_theirs */, max_ancestors-1, max_descendants-1, true /* include_partial_groups */),
+ CoinEligibilityFilter(/*conf_mine=*/0, /*conf_theirs=*/0, max_ancestors-1, max_descendants-1, /*include_partial=*/true),
available_coins, coin_selection_params, /*allow_mixed_output_types=*/true)}) {
return r7;
}
@@ -669,7 +681,7 @@ std::optional<SelectionResult> AutomaticCoinSelection(const CWallet& wallet, Coi
// OutputGroups use heuristics that may overestimate ancestor/descendant counts.
if (!fRejectLongChains) {
if (auto r8{AttemptSelection(wallet, value_to_select,
- CoinEligibilityFilter(0, 1, std::numeric_limits<uint64_t>::max(), std::numeric_limits<uint64_t>::max(), true /* include_partial_groups */),
+ CoinEligibilityFilter(0, 1, std::numeric_limits<uint64_t>::max(), std::numeric_limits<uint64_t>::max(), /*include_partial=*/true),
available_coins, coin_selection_params, /*allow_mixed_output_types=*/true)}) {
return r8;
}
@@ -867,19 +879,16 @@ static util::Result<CreatedTransactionResult> CreateTransactionInternal(
const auto change_spend_fee = coin_selection_params.m_discard_feerate.GetFee(coin_selection_params.change_spend_size);
coin_selection_params.min_viable_change = std::max(change_spend_fee + 1, dust);
+ // Static vsize overhead + outputs vsize. 4 nVersion, 4 nLocktime, 1 input count, 1 witness overhead (dummy, flag, stack size)
+ coin_selection_params.tx_noinputs_size = 10 + GetSizeOfCompactSize(vecSend.size()); // bytes for output count
+
// vouts to the payees
- if (!coin_selection_params.m_subtract_fee_outputs) {
- coin_selection_params.tx_noinputs_size = 10; // Static vsize overhead + outputs vsize. 4 nVersion, 4 nLocktime, 1 input count, 1 witness overhead (dummy, flag, stack size)
- coin_selection_params.tx_noinputs_size += GetSizeOfCompactSize(vecSend.size()); // bytes for output count
- }
for (const auto& recipient : vecSend)
{
CTxOut txout(recipient.nAmount, recipient.scriptPubKey);
// Include the fee cost for outputs.
- if (!coin_selection_params.m_subtract_fee_outputs) {
- coin_selection_params.tx_noinputs_size += ::GetSerializeSize(txout, PROTOCOL_VERSION);
- }
+ coin_selection_params.tx_noinputs_size += ::GetSerializeSize(txout, PROTOCOL_VERSION);
if (IsDust(txout, wallet.chain().relayDustFee())) {
return util::Error{_("Transaction amount too small")};
@@ -888,7 +897,7 @@ static util::Result<CreatedTransactionResult> CreateTransactionInternal(
}
// Include the fees for things that aren't inputs, excluding the change output
- const CAmount not_input_fees = coin_selection_params.m_effective_feerate.GetFee(coin_selection_params.tx_noinputs_size);
+ const CAmount not_input_fees = coin_selection_params.m_effective_feerate.GetFee(coin_selection_params.m_subtract_fee_outputs ? 0 : coin_selection_params.tx_noinputs_size);
CAmount selection_target = recipients_sum + not_input_fees;
// Fetch manually selected coins
diff --git a/src/wallet/test/coinselector_tests.cpp b/src/wallet/test/coinselector_tests.cpp
index c764264cd7..ce875d5442 100644
--- a/src/wallet/test/coinselector_tests.cpp
+++ b/src/wallet/test/coinselector_tests.cpp
@@ -4,6 +4,7 @@
#include <consensus/amount.h>
#include <node/context.h>
+#include <policy/policy.h>
#include <primitives/transaction.h>
#include <random.h>
#include <test/util/setup_common.h>
@@ -930,6 +931,124 @@ BOOST_AUTO_TEST_CASE(effective_value_test)
BOOST_CHECK_EQUAL(output5.GetEffectiveValue(), nValue); // The effective value should be equal to the absolute value if input_bytes is -1
}
+static std::optional<SelectionResult> select_coins(const CAmount& target, const CoinSelectionParams& cs_params, const CCoinControl& cc, std::function<CoinsResult(CWallet&)> coin_setup, interfaces::Chain* chain, const ArgsManager& args)
+{
+ std::unique_ptr<CWallet> wallet = std::make_unique<CWallet>(chain, "", args, CreateMockWalletDatabase());
+ wallet->LoadWallet();
+ LOCK(wallet->cs_wallet);
+ wallet->SetWalletFlag(WALLET_FLAG_DESCRIPTORS);
+ wallet->SetupDescriptorScriptPubKeyMans();
+
+ auto available_coins = coin_setup(*wallet);
+
+ const auto result = SelectCoins(*wallet, available_coins, /*pre_set_inputs=*/ {}, target, cc, cs_params);
+ if (result) {
+ const auto signedTxSize = 10 + 34 + 68 * result->GetInputSet().size(); // static header size + output size + inputs size (P2WPKH)
+ BOOST_CHECK_LE(signedTxSize * WITNESS_SCALE_FACTOR, MAX_STANDARD_TX_WEIGHT);
+
+ BOOST_CHECK_GE(result->GetSelectedValue(), target);
+ }
+ return result;
+}
+
+static bool has_coin(const CoinSet& set, CAmount amount)
+{
+ return std::any_of(set.begin(), set.end(), [&](const auto& coin) { return coin.GetEffectiveValue() == amount; });
+}
+
+BOOST_AUTO_TEST_CASE(check_max_weight)
+{
+ const CAmount target = 49.5L * COIN;
+ CCoinControl cc;
+
+ FastRandomContext rand;
+ CoinSelectionParams cs_params{
+ rand,
+ /*change_output_size=*/34,
+ /*change_spend_size=*/68,
+ /*min_change_target=*/CENT,
+ /*effective_feerate=*/CFeeRate(0),
+ /*long_term_feerate=*/CFeeRate(0),
+ /*discard_feerate=*/CFeeRate(0),
+ /*tx_noinputs_size=*/10 + 34, // static header size + output size
+ /*avoid_partial=*/false,
+ };
+
+ auto chain{m_node.chain.get()};
+
+ {
+ // Scenario 1:
+ // The actor starts with 1x 50.0 BTC and 1515x 0.033 BTC (~100.0 BTC total) unspent outputs
+ // Then tries to spend 49.5 BTC
+ // The 50.0 BTC output should be selected, because the transaction would otherwise be too large
+
+ // Perform selection
+
+ const auto result = select_coins(
+ target, cs_params, cc, [&](CWallet& wallet) {
+ CoinsResult available_coins;
+ for (int j = 0; j < 1515; ++j) {
+ add_coin(available_coins, wallet, CAmount(0.033 * COIN), CFeeRate(0), 144, false, 0, true);
+ }
+
+ add_coin(available_coins, wallet, CAmount(50 * COIN), CFeeRate(0), 144, false, 0, true);
+ return available_coins;
+ },
+ chain, m_args);
+
+ BOOST_CHECK(result);
+ BOOST_CHECK(has_coin(result->GetInputSet(), CAmount(50 * COIN)));
+ }
+
+ {
+ // Scenario 2:
+
+ // The actor starts with 400x 0.0625 BTC and 2000x 0.025 BTC (75.0 BTC total) unspent outputs
+ // Then tries to spend 49.5 BTC
+ // A combination of coins should be selected, such that the created transaction is not too large
+
+ // Perform selection
+ const auto result = select_coins(
+ target, cs_params, cc, [&](CWallet& wallet) {
+ CoinsResult available_coins;
+ for (int j = 0; j < 400; ++j) {
+ add_coin(available_coins, wallet, CAmount(0.0625 * COIN), CFeeRate(0), 144, false, 0, true);
+ }
+ for (int j = 0; j < 2000; ++j) {
+ add_coin(available_coins, wallet, CAmount(0.025 * COIN), CFeeRate(0), 144, false, 0, true);
+ }
+ return available_coins;
+ },
+ chain, m_args);
+
+ BOOST_CHECK(has_coin(result->GetInputSet(), CAmount(0.0625 * COIN)));
+ BOOST_CHECK(has_coin(result->GetInputSet(), CAmount(0.025 * COIN)));
+ }
+
+ {
+ // Scenario 3:
+
+ // The actor starts with 1515x 0.033 BTC (49.995 BTC total) unspent outputs
+ // No results should be returned, because the transaction would be too large
+
+ // Perform selection
+ const auto result = select_coins(
+ target, cs_params, cc, [&](CWallet& wallet) {
+ CoinsResult available_coins;
+ for (int j = 0; j < 1515; ++j) {
+ add_coin(available_coins, wallet, CAmount(0.033 * COIN), CFeeRate(0), 144, false, 0, true);
+ }
+ return available_coins;
+ },
+ chain, m_args);
+
+ // No results
+ // 1515 inputs * 68 bytes = 103,020 bytes
+ // 103,020 bytes * 4 = 412,080 weight, which is above the MAX_STANDARD_TX_WEIGHT of 400,000
+ BOOST_CHECK(!result);
+ }
+}
+
BOOST_AUTO_TEST_CASE(SelectCoins_effective_value_test)
{
// Test that the effective value is used to check whether preset inputs provide sufficient funds when subtract_fee_outputs is not used.
diff --git a/src/wallet/test/spend_tests.cpp b/src/wallet/test/spend_tests.cpp
index 81a8883f85..40756fedfb 100644
--- a/src/wallet/test/spend_tests.cpp
+++ b/src/wallet/test/spend_tests.cpp
@@ -26,7 +26,7 @@ BOOST_FIXTURE_TEST_CASE(SubtractFee, TestChain100Setup)
// leftover input amount which would have been change to the recipient
// instead of the miner.
auto check_tx = [&wallet](CAmount leftover_input_amount) {
- CRecipient recipient{GetScriptForRawPubKey({}), 50 * COIN - leftover_input_amount, true /* subtract fee */};
+ CRecipient recipient{GetScriptForRawPubKey({}), 50 * COIN - leftover_input_amount, /*subtract_fee=*/true};
constexpr int RANDOM_CHANGE_POSITION = -1;
CCoinControl coin_control;
coin_control.m_feerate.emplace(10000);
diff --git a/src/wallet/test/wallet_tests.cpp b/src/wallet/test/wallet_tests.cpp
index 60fdbde71b..0f703b7d00 100644
--- a/src/wallet/test/wallet_tests.cpp
+++ b/src/wallet/test/wallet_tests.cpp
@@ -587,7 +587,7 @@ BOOST_FIXTURE_TEST_CASE(ListCoinsTest, ListCoinsTestingSetup)
// returns the coin associated with the change address underneath the
// coinbaseKey pubkey, even though the change address has a different
// pubkey.
- AddTx(CRecipient{GetScriptForRawPubKey({}), 1 * COIN, false /* subtract fee */});
+ AddTx(CRecipient{GetScriptForRawPubKey({}), 1 * COIN, /*subtract_fee=*/false});
{
LOCK(wallet->cs_wallet);
list = ListCoins(*wallet);
diff --git a/src/wallet/wallet.cpp b/src/wallet/wallet.cpp
index 58ba378f4b..5e8c775b63 100644
--- a/src/wallet/wallet.cpp
+++ b/src/wallet/wallet.cpp
@@ -1411,7 +1411,7 @@ void CWallet::blockConnected(const interfaces::BlockInfo& block)
m_last_block_processed = block.hash;
for (size_t index = 0; index < block.data->vtx.size(); index++) {
SyncTransaction(block.data->vtx[index], TxStateConfirmed{block.hash, block.height, static_cast<int>(index)});
- transactionRemovedFromMempool(block.data->vtx[index], MemPoolRemovalReason::BLOCK, 0 /* mempool_sequence */);
+ transactionRemovedFromMempool(block.data->vtx[index], MemPoolRemovalReason::BLOCK, /*mempool_sequence=*/0);
}
}
@@ -2463,7 +2463,7 @@ bool CWallet::TopUpKeyPool(unsigned int kpSize)
util::Result<CTxDestination> CWallet::GetNewDestination(const OutputType type, const std::string label)
{
LOCK(cs_wallet);
- auto spk_man = GetScriptPubKeyMan(type, false /* internal */);
+ auto spk_man = GetScriptPubKeyMan(type, /*internal=*/false);
if (!spk_man) {
return util::Error{strprintf(_("Error: No %s addresses available."), FormatOutputType(type))};
}
diff --git a/src/wallet/wallettool.cpp b/src/wallet/wallettool.cpp
index e991bc0814..9ed2a7c18b 100644
--- a/src/wallet/wallettool.cpp
+++ b/src/wallet/wallettool.cpp
@@ -58,7 +58,7 @@ static const std::shared_ptr<CWallet> MakeWallet(const std::string& name, const
}
// dummy chain interface
- std::shared_ptr<CWallet> wallet_instance{new CWallet(nullptr /* chain */, name, args, std::move(database)), WalletToolReleaseWallet};
+ std::shared_ptr<CWallet> wallet_instance{new CWallet(/*chain=*/nullptr, name, args, std::move(database)), WalletToolReleaseWallet};
DBErrors load_wallet_ret;
try {
load_wallet_ret = wallet_instance->LoadWallet();
diff --git a/test/functional/rpc_fundrawtransaction.py b/test/functional/rpc_fundrawtransaction.py
index 6874154f35..bf218bfee9 100755
--- a/test/functional/rpc_fundrawtransaction.py
+++ b/test/functional/rpc_fundrawtransaction.py
@@ -987,7 +987,7 @@ class RawTransactionsTest(BitcoinTestFramework):
outputs[recipient.getnewaddress()] = 0.1
wallet.sendmany("", outputs)
self.generate(self.nodes[0], 10)
- assert_raises_rpc_error(-4, "Transaction too large", recipient.fundrawtransaction, rawtx)
+ assert_raises_rpc_error(-4, "Insufficient funds", recipient.fundrawtransaction, rawtx)
self.nodes[0].unloadwallet("large")
def test_external_inputs(self):