mirror of
https://github.com/bitcoin/bitcoin.git
synced 2025-02-08 10:31:50 -05:00
[wallet]: add maxfeerate
wallet startup option
- The commits adds a new wallet startup option `-maxfeerate` - The value will be used as the upper limit of wallet transaction fee rate. - The commit updates all instances where `-maxtxfee` value is utilized to check wallet transactions fee rate upper limit to now use `-maxfeerate` value. - `settxfee` RPC now only check if the fee rate user set is less `minrelaytxfee`, less than wallet min fee, or whether it exceed `maxfeerate`. We should not check whether `settxfee` RPC respects `maxtxfee` limit in in the functional test because its not enforced. We now only check if `settxfee` respects `maxfeerate` limit.
This commit is contained in:
parent
d3600accf9
commit
832d468c34
6 changed files with 23 additions and 9 deletions
|
@ -37,6 +37,7 @@ void DummyWalletInit::AddWalletOptions(ArgsManager& argsman) const
|
|||
"-keypool=<n>",
|
||||
"-maxapsfee=<n>",
|
||||
"-maxtxfee=<amt>",
|
||||
"-maxfeerate=<amt>",
|
||||
"-mintxfee=<amt>",
|
||||
"-paytxfee=<amt>",
|
||||
"-signer=<cmd>",
|
||||
|
|
|
@ -64,6 +64,7 @@ void WalletInit::AddWalletOptions(ArgsManager& argsman) const
|
|||
argsman.AddArg("-maxapsfee=<n>", strprintf("Spend up to this amount in additional (absolute) fees (in %s) if it allows the use of partial spend avoidance (default: %s)", CURRENCY_UNIT, FormatMoney(DEFAULT_MAX_AVOIDPARTIALSPEND_FEE)), ArgsManager::ALLOW_ANY, OptionsCategory::WALLET);
|
||||
argsman.AddArg("-maxtxfee=<amt>", strprintf("Maximum total fees (in %s) to use in a single wallet transaction; setting this too low may abort large transactions (default: %s)",
|
||||
CURRENCY_UNIT, FormatMoney(DEFAULT_TRANSACTION_MAXFEE)), ArgsManager::ALLOW_ANY, OptionsCategory::DEBUG_TEST);
|
||||
argsman.AddArg("-maxfeerate=<amt>", strprintf("Maximum fee rate (in %s/kvB) for a wallet transactions (default: %s %s/kvB)", CURRENCY_UNIT, FormatMoney(DEFAULT_MAX_TRANSACTION_FEERATE.GetFeePerK()), CURRENCY_UNIT), ArgsManager::ALLOW_ANY, OptionsCategory::WALLET);
|
||||
argsman.AddArg("-mintxfee=<amt>", strprintf("Fee rates (in %s/kvB) smaller than this are considered zero fee for transaction creation (default: %s)",
|
||||
CURRENCY_UNIT, FormatMoney(DEFAULT_TRANSACTION_MINFEE)), ArgsManager::ALLOW_ANY, OptionsCategory::WALLET);
|
||||
argsman.AddArg("-paytxfee=<amt>", strprintf("Fee rate (in %s/kvB) to add to transactions you send (default: %s)",
|
||||
|
|
|
@ -439,15 +439,14 @@ RPCHelpMan settxfee()
|
|||
|
||||
CAmount nAmount = AmountFromValue(request.params[0]);
|
||||
CFeeRate tx_fee_rate(nAmount, 1000);
|
||||
CFeeRate max_tx_fee_rate(pwallet->m_max_tx_fee, 1000);
|
||||
if (tx_fee_rate == CFeeRate(0)) {
|
||||
// automatic selection
|
||||
} else if (tx_fee_rate < pwallet->chain().relayMinFee()) {
|
||||
throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("txfee cannot be less than min relay tx fee (%s)", pwallet->chain().relayMinFee().ToString()));
|
||||
} else if (tx_fee_rate < pwallet->m_min_fee) {
|
||||
throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("txfee cannot be less than wallet min fee (%s)", pwallet->m_min_fee.ToString()));
|
||||
} else if (tx_fee_rate > max_tx_fee_rate) {
|
||||
throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("txfee cannot be more than wallet max tx fee (%s)", max_tx_fee_rate.ToString()));
|
||||
} else if (tx_fee_rate > pwallet->m_max_tx_fee_rate) {
|
||||
throw JSONRPCError(RPC_INVALID_PARAMETER, strprintf("fee rate cannot be more than wallet max tx fee rate (%s)", pwallet->m_max_tx_fee_rate.ToString()));
|
||||
}
|
||||
|
||||
pwallet->m_pay_tx_fee = tx_fee_rate;
|
||||
|
|
|
@ -3194,13 +3194,22 @@ std::shared_ptr<CWallet> CWallet::Create(WalletContext& context, const std::stri
|
|||
warnings.push_back(strprintf(_("%s is set very high! Fees this large could be paid on a single transaction."), "-maxtxfee"));
|
||||
}
|
||||
|
||||
if (chain && CFeeRate{max_tx_fee.value(), 1000} < chain->relayMinFee()) {
|
||||
walletInstance->m_max_tx_fee = max_tx_fee.value();
|
||||
}
|
||||
|
||||
if (args.IsArgSet("-maxfeerate")) {
|
||||
std::optional<CAmount> max_tx_fee_rate = ParseMoney(args.GetArg("-maxfeerate", ""));
|
||||
if (!max_tx_fee_rate) {
|
||||
error = AmountErrMsg("maxfeerate", args.GetArg("-maxfeerate", ""));
|
||||
return nullptr;
|
||||
}
|
||||
if (chain && CFeeRate(max_tx_fee_rate.value()) < chain->relayMinFee()) {
|
||||
error = strprintf(_("Invalid amount for %s=<amount>: '%s' (must be at least the minrelay fee of %s to prevent stuck transactions)"),
|
||||
"-maxtxfee", args.GetArg("-maxtxfee", ""), chain->relayMinFee().ToString());
|
||||
"-maxfeerate", args.GetArg("-maxfeerate", ""), chain->relayMinFee().ToString());
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
walletInstance->m_max_tx_fee = max_tx_fee.value();
|
||||
walletInstance->m_max_tx_fee_rate = CFeeRate(max_tx_fee_rate.value());
|
||||
}
|
||||
|
||||
if (args.IsArgSet("-consolidatefeerate")) {
|
||||
|
|
|
@ -135,6 +135,8 @@ static const bool DEFAULT_DISABLE_WALLET = false;
|
|||
static const bool DEFAULT_WALLETCROSSCHAIN = false;
|
||||
//! -maxtxfee default
|
||||
constexpr CAmount DEFAULT_TRANSACTION_MAXFEE{COIN / 10};
|
||||
//! maxfeerate default
|
||||
const CFeeRate DEFAULT_MAX_TRANSACTION_FEERATE(CFeeRate(COIN / 10));
|
||||
//! Discourage users to set fees higher than this amount (in satoshis) per kB
|
||||
constexpr CAmount HIGH_TX_FEE_PER_KB{COIN / 100};
|
||||
//! -maxtxfee will warn if called with a higher fee than this amount (in satoshis)
|
||||
|
@ -730,6 +732,8 @@ public:
|
|||
/** Absolute maximum transaction fee (in satoshis) used by default for the wallet */
|
||||
CAmount m_max_tx_fee{DEFAULT_TRANSACTION_MAXFEE};
|
||||
|
||||
/** Maximum transaction fee rate used for the wallet */
|
||||
CFeeRate m_max_tx_fee_rate{DEFAULT_MAX_TRANSACTION_FEERATE};
|
||||
/** Number of pre-generated keys/scripts by each spkm (part of the look-ahead process, used to detect payments) */
|
||||
int64_t m_keypool_size{DEFAULT_KEYPOOL_SIZE};
|
||||
|
||||
|
|
|
@ -547,9 +547,9 @@ def test_settxfee(self, rbf_node, dest_address):
|
|||
assert_greater_than(Decimal("0.00001000"), abs(requested_feerate - actual_feerate))
|
||||
rbf_node.settxfee(Decimal("0.00000000")) # unset paytxfee
|
||||
|
||||
# check that settxfee respects -maxtxfee
|
||||
self.restart_node(1, ['-maxtxfee=0.000025'] + self.extra_args[1])
|
||||
assert_raises_rpc_error(-8, "txfee cannot be more than wallet max tx fee", rbf_node.settxfee, Decimal('0.00003'))
|
||||
# check that settxfee respects -maxfeerate
|
||||
self.restart_node(1, ['-maxfeerate=0.000025'] + self.extra_args[1])
|
||||
assert_raises_rpc_error(-8, "fee rate cannot be more than wallet max tx fee rate", rbf_node.settxfee, Decimal('0.00003'))
|
||||
self.restart_node(1, self.extra_args[1])
|
||||
rbf_node.walletpassphrase(WALLET_PASSPHRASE, WALLET_PASSPHRASE_TIMEOUT)
|
||||
self.connect_nodes(1, 0)
|
||||
|
|
Loading…
Add table
Reference in a new issue