LCOV - code coverage report
Current view: top level - src/wallet - fees.cpp (source / functions) Hit Total Coverage
Test: fuzz_coverage.info Lines: 15 59 25.4 %
Date: 2023-09-26 12:08:55 Functions: 8 14 57.1 %

          Line data    Source code
       1             : // Copyright (c) 2009-2010 Satoshi Nakamoto
       2             : // Copyright (c) 2009-2022 The Bitcoin Core developers
       3             : // Distributed under the MIT software license, see the accompanying
       4             : // file COPYING or http://www.opensource.org/licenses/mit-license.php.
       5             : 
       6             : #include <wallet/fees.h>
       7             : 
       8             : #include <wallet/coincontrol.h>
       9             : #include <wallet/wallet.h>
      10             : 
      11             : 
      12             : namespace wallet {
      13           0 : CAmount GetRequiredFee(const CWallet& wallet, unsigned int nTxBytes)
      14             : {
      15           0 :     return GetRequiredFeeRate(wallet).GetFee(nTxBytes);
      16             : }
      17           2 : 
      18           2 : 
      19           0 : CAmount GetMinimumFee(const CWallet& wallet, unsigned int nTxBytes, const CCoinControl& coin_control, FeeCalculation* feeCalc)
      20             : {
      21           0 :     return GetMinimumFeeRate(wallet, coin_control, feeCalc).GetFee(nTxBytes);
      22             : }
      23             : 
      24           0 : CFeeRate GetRequiredFeeRate(const CWallet& wallet)
      25             : {
      26           0 :     return std::max(wallet.m_min_fee, wallet.chain().relayMinFee());
      27           2 : }
      28             : 
      29           0 : CFeeRate GetMinimumFeeRate(const CWallet& wallet, const CCoinControl& coin_control, FeeCalculation* feeCalc)
      30             : {
      31             :     /* User control of how to calculate fee uses the following parameter precedence:
      32             :        1. coin_control.m_feerate
      33             :        2. coin_control.m_confirm_target
      34             :        3. m_pay_tx_fee (user-set member variable of wallet)
      35             :        4. m_confirm_target (user-set member variable of wallet)
      36             :        The first parameter that is set is used.
      37             :     */
      38           0 :     CFeeRate feerate_needed;
      39           0 :     if (coin_control.m_feerate) { // 1.
      40           0 :         feerate_needed = *(coin_control.m_feerate);
      41           0 :         if (feeCalc) feeCalc->reason = FeeReason::PAYTXFEE;
      42             :         // Allow to override automatic min/max check over coin control instance
      43           0 :         if (coin_control.fOverrideFeeRate) return feerate_needed;
      44           0 :     }
      45           0 :     else if (!coin_control.m_confirm_target && wallet.m_pay_tx_fee != CFeeRate(0)) { // 3. TODO: remove magic value of 0 for wallet member m_pay_tx_fee
      46           0 :         feerate_needed = wallet.m_pay_tx_fee;
      47           0 :         if (feeCalc) feeCalc->reason = FeeReason::PAYTXFEE;
      48           0 :     }
      49             :     else { // 2. or 4.
      50             :         // We will use smart fee estimation
      51           0 :         unsigned int target = coin_control.m_confirm_target ? *coin_control.m_confirm_target : wallet.m_confirm_target;
      52             :         // By default estimates are economical iff we are signaling opt-in-RBF
      53           0 :         bool conservative_estimate = !coin_control.m_signal_bip125_rbf.value_or(wallet.m_signal_rbf);
      54             :         // Allow to override the default fee estimate mode over the CoinControl instance
      55           0 :         if (coin_control.m_fee_mode == FeeEstimateMode::CONSERVATIVE) conservative_estimate = true;
      56           0 :         else if (coin_control.m_fee_mode == FeeEstimateMode::ECONOMICAL) conservative_estimate = false;
      57             : 
      58           0 :         feerate_needed = wallet.chain().estimateSmartFee(target, conservative_estimate, feeCalc);
      59           0 :         if (feerate_needed == CFeeRate(0)) {
      60             :             // if we don't have enough data for estimateSmartFee, then use fallback fee
      61           0 :             feerate_needed = wallet.m_fallback_fee;
      62           0 :             if (feeCalc) feeCalc->reason = FeeReason::FALLBACK;
      63             : 
      64             :             // directly return if fallback fee is disabled (feerate 0 == disabled)
      65           0 :             if (wallet.m_fallback_fee == CFeeRate(0)) return feerate_needed;
      66           0 :         }
      67             :         // Obey mempool min fee when using smart fee estimation
      68           0 :         CFeeRate min_mempool_feerate = wallet.chain().mempoolMinFee();
      69           0 :         if (feerate_needed < min_mempool_feerate) {
      70           0 :             feerate_needed = min_mempool_feerate;
      71           0 :             if (feeCalc) feeCalc->reason = FeeReason::MEMPOOL_MIN;
      72           0 :         }
      73             :     }
      74           2 : 
      75             :     // prevent user from paying a fee below the required fee rate
      76           0 :     CFeeRate required_feerate = GetRequiredFeeRate(wallet);
      77           0 :     if (required_feerate > feerate_needed) {
      78           0 :         feerate_needed = required_feerate;
      79           0 :         if (feeCalc) feeCalc->reason = FeeReason::REQUIRED;
      80           0 :     }
      81           0 :     return feerate_needed;
      82           0 : }
      83             : 
      84           0 : CFeeRate GetDiscardRate(const CWallet& wallet)
      85             : {
      86           0 :     unsigned int highest_target = wallet.chain().estimateMaxBlocks();
      87           0 :     CFeeRate discard_rate = wallet.chain().estimateSmartFee(highest_target, /*conservative=*/false);
      88             :     // Don't let discard_rate be greater than longest possible fee estimate if we get a valid fee estimate
      89           0 :     discard_rate = (discard_rate == CFeeRate(0)) ? wallet.m_discard_rate : std::min(discard_rate, wallet.m_discard_rate);
      90             :     // Discard rate must be at least dust relay feerate
      91           2 :     discard_rate = std::max(discard_rate, wallet.chain().relayDustFee());
      92           0 :     return discard_rate;
      93             : }
      94             : } // namespace wallet

Generated by: LCOV version 1.14