Skip to content

Commit

Permalink
Implement GetMaxInputsForConsolidationTxn()
Browse files Browse the repository at this point in the history
This implements a chain parameter function to get the maximum number of
inputs allowable for a UTXO consolidation transaction with either
the RPC consolidateunspent or the GUI "consolidate" button in coin
control.

The defalt value for the RPC consolidateunspent function has been
changed to be the same as the upper clamp at the value returned
by GetMaxInputsForConsolidationTxn(). The help returned for
consolidateunspent uses that value as well.
  • Loading branch information
jamescowens committed May 1, 2021
1 parent 2d8f583 commit 51b29dd
Show file tree
Hide file tree
Showing 3 changed files with 46 additions and 39 deletions.
5 changes: 5 additions & 0 deletions src/chainparams.h
Original file line number Diff line number Diff line change
Expand Up @@ -150,3 +150,8 @@ inline unsigned int GetMinimumConnectionsRequiredForStaking()
{
return fTestNet ? 1 : 3;
}

inline unsigned int GetMaxInputsForConsolidationTxn()
{
return (unsigned int) 600;
}
2 changes: 1 addition & 1 deletion src/qt/coincontroldialog.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ CCoinControl* CoinControlDialog::coinControl = new CCoinControl();

CoinControlDialog::CoinControlDialog(QWidget *parent) :
QDialog(parent),
m_inputSelectionLimit(600),
m_inputSelectionLimit(GetMaxInputsForConsolidationTxn()),
ui(new Ui::CoinControlDialog),
model(0)
{
Expand Down
78 changes: 40 additions & 38 deletions src/rpc/rawtransaction.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -493,50 +493,51 @@ UniValue listunspent(const UniValue& params, bool fHelp)

UniValue consolidateunspent(const UniValue& params, bool fHelp)
{
std::stringstream error_strm;

error_strm << "consolidateunspent <address> [UTXO size] [maximum number of inputs] [sweep all addresses] [sweep change]\n"
"\n"
"<address>: The Gridcoin address target for consolidation.\n"
"\n"
"[UTXO size]: Optional parameter for target consolidation output size.\n"
"\n"
"[maximum number of inputs]: Defaults and clamped to "
<< std::to_string(GetMaxInputsForConsolidationTxn())
<< " maximum to prevent transaction failures.\n"
"\n"
"[sweep all addresses]: Boolean to indicate whether all addresses should be used for inputs to the\n"
" consolidation. If true, the source of the consolidation is all addresses and\n"
" the output will be to the specified address, otherwise inputs will only be\n"
" sourced from the same address.\n"
"\n"
"[sweep change]: Boolean to indicate whether change associated with the address should be\n"
" consolidated. If [sweep all addresses] is true then this is also forced true.\n"
"\n"
"consolidateunspent performs a single transaction to consolidate UTXOs to/on a given address. The optional\n"
"parameter of UTXO size will result in consolidating UTXOs to generate the largest output possible less\n"
"than that size or the total value of the specified maximum number of smallest inputs, whichever is less.\n"
"\n"
"The script is designed to be run repeatedly and will become a no-op if the UTXO's are consolidated such\n"
"that no more meet the specified criteria. This is ideal for automated periodic scripting.\n"
"\n"
"To consolidate the entire wallet to one address do something like:\n"
"\n"
"consolidateunspent <address> <amount equal or larger than balance> 200 true repeatedly until there are\n"
"no more UTXOs to consolidate.\n"
"\n"
"In all cases the address MUST exist in your wallet beforehand. If doing this for the purpose of creating\n"
"a new smaller wallet, create a new address beforehand to serve as the target of the consolidation.\n";

if (fHelp || params.size() < 1 || params.size() > 5)
throw runtime_error(
"consolidateunspent <address> [UTXO size] [maximum number of inputs] [sweep all addresses] [sweep change]\n"
"\n"
"<address>: The Gridcoin address target for consolidation.\n"
"\n"
"[UTXO size]: Optional parameter for target consolidation output size.\n"
"\n"
"[maximum number of inputs]: Defaults to 50, clamped to 200 maximum to prevent transaction failures.\n"
"\n"
"[sweep all addresses]: Boolean to indicate whether all addresses should be used for inputs to the\n"
" consolidation. If true, the source of the consolidation is all addresses and\n"
" the output will be to the specified address, otherwise inputs will only be\n"
" sourced from the same address.\n"
"\n"
"[sweep change]: Boolean to indicate whether change associated with the address should be\n"
" consolidated. If [sweep all addresses] is true then this is also forced true.\n"
"\n"
"consolidateunspent performs a single transaction to consolidate UTXOs to/on a given address. The optional\n"
"parameter of UTXO size will result in consolidating UTXOs to generate the largest output possible less\n"
"than that size or the total value of the specified maximum number of smallest inputs, whichever is less.\n"
"\n"
"The script is designed to be run repeatedly and will become a no-op if the UTXO's are consolidated such\n"
"that no more meet the specified criteria. This is ideal for automated periodic scripting.\n"
"\n"
"To consolidate the entire wallet to one address do something like:\n"
"\n"
"consolidateunspent <address> <amount equal or larger than balance> 200 true repeatedly until there are\n"
"no more UTXOs to consolidate.\n"
"\n"
"In all cases the address MUST exist in your wallet beforehand. If doing this for the purpose of creating\n"
"a new smaller wallet, create a new address beforehand to serve as the target of the consolidation.\n");
throw runtime_error(error_strm.str());

UniValue result(UniValue::VOBJ);

std::string sAddress = params[0].get_str();
CBitcoinAddress OptimizeAddress(sAddress);

int64_t nConsolidateLimit = 0;
// Set default maximum consolidation to 50 inputs if it is not specified. This is based
// on performance tests on the Pi to ensure the transaction returns within a reasonable time.
// The performance tests on the Pi show about 3 UTXOs/second. Intel machines should do
// about 3x that. The GUI will not be responsive during the transaction due to locking.
unsigned int nInputNumberLimit = 50;
unsigned int nInputNumberLimit = GetMaxInputsForConsolidationTxn();

bool sweep_all_addresses = false;

Expand All @@ -551,8 +552,9 @@ UniValue consolidateunspent(const UniValue& params, bool fHelp)

if (params.size() > 4 && !sweep_all_addresses) sweep_change = params[4].get_bool();

// Clamp InputNumberLimit to 200. Above 200 risks an invalid transaction due to the size.
nInputNumberLimit = std::min<unsigned int>(nInputNumberLimit, 200);
// Clamp InputNumberLimit to GetMaxInputsForConsolidationTxn(). Above that number of inputs risks an invalid transaction
// due to the size.
nInputNumberLimit = std::min<unsigned int>(nInputNumberLimit, GetMaxInputsForConsolidationTxn());

if (!OptimizeAddress.IsValid())
{
Expand Down

0 comments on commit 51b29dd

Please sign in to comment.