Skip to content

Commit

Permalink
Merge bitcoin/bitcoin#27877: wallet: Add CoinGrinder coin selection a…
Browse files Browse the repository at this point in the history
…lgorithm

13161ec opt: Skip over barren combinations of tiny UTXOs (Murch)
b7672c7 opt: Skip checking max_weight separately (Murch)
1edd2ba opt: Cut if last addition was minimal weight (Murch)
5248e2a opt: Skip heavier UTXOs with same effective value (Murch)
9124c73 opt: Tiebreak UTXOs by weight for CoinGrinder (Murch)
451be19 opt: Skip evaluation of equivalent input sets (Murch)
407b1e3 opt: Track remaining effective_value in lookahead (Murch)
5f84f3c opt: Skip branches with worse weight (Murch)
d68bc74 fuzz: Test optimality of CoinGrinder (Murch)
67df6c6 fuzz: Add CoinGrinder fuzz target (Murch)
1502231 coinselection: Track whether CG completed (Murch)
7488acc test: Add coin_grinder_tests (Murch)
6cc9a46 coinselection: Add CoinGrinder algorithm (Murch)
89d0956 opt: Tie-break UTXO sort by waste for BnB (Murch)
aaee658 doc: Document max_weight on BnB (Murch)

Pull request description:

  ***Please refer to the [topic on Delving Bitcoin](https://delvingbitcoin.org/t/gutterguard-and-coingrinder-simulation-results/279) discussing Gutter Guard/Coingrinder simulation results.***

  Adds a coin selection algorithm that minimizes the weight of the input set while creating change.

  Motivations
  ---

  - At high feerates, using unnecessary inputs can significantly increase the fees
  - Users are upset when fees are relatively large compared to the amount sent
  - Some users struggle to maintain a sufficient count of UTXOs in their wallet

  Approach
  ---

  So far, Bitcoin Core has used a balanced approach to coin selection, where it will generate multiple input set candidates using various coin selection algorithms and pick the least wasteful among their results, but not explicitly minimize the input set weight. Under some circumstances, we _do_ want to minimize the weight of the input set. Sometimes changeless solutions require many or heavy inputs, and there is not always a changeless solution for Branch and Bound to find in the first place. This can cause expensive transactions unnecessarily. Given a wallet with sufficient funds, `CoinGrinder` will pick the minimal-waste input set for a transaction with a change output. The current implementation only runs `CoinGrinder` at feerates over 3×long-term-feerate-estimate (by default 30 ṩ/vB), which may be a decent compromise between our goal to reduce costs for the users, but still permit transactions at lower feerates to naturally reduce the wallet’s UTXO pool to curb bloat.

  Trade-offs
  ---

  Simulations for my thesis on coin selection ([see Section 6.3.2.1 [PDF]](https://murch.one/erhardt2016coinselection.pdf)) suggest that minimizing the input set for all transactions tends to grind a wallet’s UTXO pool to dust (pun intended): an approach selecting inputs per coin-age-priority (in effect similar to “largest first selection”) on average produced a UTXO pool with 15× the UTXO count as Bitcoin Core’s Knapsack-based Coin Selection then (in 2016). Therefore, I do not recommend running `CoinGrinder` under all circumstances, but only at extreme feerates or when we have another good reason to minimize the input set for other reasons. In the long-term, we should introduce additional metrics to score different input set candidates, e.g. on basis of their privacy and wallet health impact, to pick from all our coin selection results, but until then, we may want to limit use of `CoinGrinder` in other ways.

ACKs for top commit:
  achow101:
    ACK 13161ec
  sr-gi:
    ACK [13161ec](bitcoin/bitcoin@13161ec)
  sipa:
    ACK 13161ec

Tree-SHA512: 895b08b2ebfd0b71127949b7dba27146a6d10700bf8590402b14f261e7b937f4e2e1b24ca46de440c35f19349043ed2eba4159dc2aa3edae57721384186dae40
  • Loading branch information
achow101 committed Feb 9, 2024
2 parents b2b2b1e + 13161ec commit 1d334d8
Show file tree
Hide file tree
Showing 5 changed files with 745 additions and 4 deletions.
Loading

0 comments on commit 1d334d8

Please sign in to comment.