mirror of
https://github.com/dashpay/dash.git
synced 2024-12-26 04:22:55 +01:00
Merge #9279: Consensus: Move CFeeRate out of libconsensus
381a46e
Consensus: Policy: MOVEONLY: Move CFeeRate out of the consensus module (Jorge Timón)330bb5a
Consensus: Minimal way to move dust out of consensus (Jorge Timón) Tree-SHA512: 19a2ea8169afd5a9d3f940d8974e34cfaead153e3ff3068ac82fccdb8694d19d9b45938904ec9e8cd095bd5ca3a0080364da29372f6aaf56b11a6c2ccd6c7a4d
This commit is contained in:
parent
535d7d6a84
commit
39cfd61c07
@ -193,6 +193,7 @@ BITCOIN_CORE_H = \
|
|||||||
netfulfilledman.h \
|
netfulfilledman.h \
|
||||||
netmessagemaker.h \
|
netmessagemaker.h \
|
||||||
noui.h \
|
noui.h \
|
||||||
|
policy/feerate.h \
|
||||||
policy/fees.h \
|
policy/fees.h \
|
||||||
policy/policy.h \
|
policy/policy.h \
|
||||||
pow.h \
|
pow.h \
|
||||||
@ -456,7 +457,6 @@ libdash_consensus_a_SOURCES = \
|
|||||||
libdash_common_a_CPPFLAGS = $(AM_CPPFLAGS) $(BITCOIN_INCLUDES)
|
libdash_common_a_CPPFLAGS = $(AM_CPPFLAGS) $(BITCOIN_INCLUDES)
|
||||||
libdash_common_a_CXXFLAGS = $(AM_CXXFLAGS) $(PIE_FLAGS)
|
libdash_common_a_CXXFLAGS = $(AM_CXXFLAGS) $(PIE_FLAGS)
|
||||||
libdash_common_a_SOURCES = \
|
libdash_common_a_SOURCES = \
|
||||||
amount.cpp \
|
|
||||||
base58.cpp \
|
base58.cpp \
|
||||||
bip39.cpp \
|
bip39.cpp \
|
||||||
chainparams.cpp \
|
chainparams.cpp \
|
||||||
@ -469,6 +469,7 @@ libdash_common_a_SOURCES = \
|
|||||||
keystore.cpp \
|
keystore.cpp \
|
||||||
netaddress.cpp \
|
netaddress.cpp \
|
||||||
netbase.cpp \
|
netbase.cpp \
|
||||||
|
policy/feerate.cpp \
|
||||||
protocol.cpp \
|
protocol.cpp \
|
||||||
saltedhasher.cpp \
|
saltedhasher.cpp \
|
||||||
scheduler.cpp \
|
scheduler.cpp \
|
||||||
|
45
src/amount.h
45
src/amount.h
@ -6,10 +6,7 @@
|
|||||||
#ifndef BITCOIN_AMOUNT_H
|
#ifndef BITCOIN_AMOUNT_H
|
||||||
#define BITCOIN_AMOUNT_H
|
#define BITCOIN_AMOUNT_H
|
||||||
|
|
||||||
#include "serialize.h"
|
#include <stdint.h>
|
||||||
|
|
||||||
#include <stdlib.h>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
/** Amount in satoshis (Can be negative) */
|
/** Amount in satoshis (Can be negative) */
|
||||||
typedef int64_t CAmount;
|
typedef int64_t CAmount;
|
||||||
@ -17,8 +14,6 @@ typedef int64_t CAmount;
|
|||||||
static const CAmount COIN = 100000000;
|
static const CAmount COIN = 100000000;
|
||||||
static const CAmount CENT = 1000000;
|
static const CAmount CENT = 1000000;
|
||||||
|
|
||||||
extern const std::string CURRENCY_UNIT;
|
|
||||||
|
|
||||||
/** No amount larger than this (in satoshi) is valid.
|
/** No amount larger than this (in satoshi) is valid.
|
||||||
*
|
*
|
||||||
* Note that this constant is *not* the total money supply, which in Bitcoin
|
* Note that this constant is *not* the total money supply, which in Bitcoin
|
||||||
@ -31,42 +26,4 @@ extern const std::string CURRENCY_UNIT;
|
|||||||
static const CAmount MAX_MONEY = 21000000 * COIN;
|
static const CAmount MAX_MONEY = 21000000 * COIN;
|
||||||
inline bool MoneyRange(const CAmount& nValue) { return (nValue >= 0 && nValue <= MAX_MONEY); }
|
inline bool MoneyRange(const CAmount& nValue) { return (nValue >= 0 && nValue <= MAX_MONEY); }
|
||||||
|
|
||||||
/**
|
|
||||||
* Fee rate in satoshis per kilobyte: CAmount / kB
|
|
||||||
*/
|
|
||||||
class CFeeRate
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
CAmount nSatoshisPerK; // unit is satoshis-per-1,000-bytes
|
|
||||||
public:
|
|
||||||
/** Fee rate of 0 satoshis per kB */
|
|
||||||
CFeeRate() : nSatoshisPerK(0) { }
|
|
||||||
explicit CFeeRate(const CAmount& _nSatoshisPerK): nSatoshisPerK(_nSatoshisPerK) { }
|
|
||||||
/** Constructor for a fee rate in satoshis per kB. The size in bytes must not exceed (2^63 - 1)*/
|
|
||||||
CFeeRate(const CAmount& nFeePaid, size_t nBytes);
|
|
||||||
CFeeRate(const CFeeRate& other) { nSatoshisPerK = other.nSatoshisPerK; }
|
|
||||||
/**
|
|
||||||
* Return the fee in satoshis for the given size in bytes.
|
|
||||||
*/
|
|
||||||
CAmount GetFee(size_t nBytes) const;
|
|
||||||
/**
|
|
||||||
* Return the fee in satoshis for a size of 1000 bytes
|
|
||||||
*/
|
|
||||||
CAmount GetFeePerK() const { return GetFee(1000); }
|
|
||||||
friend bool operator<(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK < b.nSatoshisPerK; }
|
|
||||||
friend bool operator>(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK > b.nSatoshisPerK; }
|
|
||||||
friend bool operator==(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK == b.nSatoshisPerK; }
|
|
||||||
friend bool operator<=(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK <= b.nSatoshisPerK; }
|
|
||||||
friend bool operator>=(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK >= b.nSatoshisPerK; }
|
|
||||||
CFeeRate& operator+=(const CFeeRate& a) { nSatoshisPerK += a.nSatoshisPerK; return *this; }
|
|
||||||
std::string ToString() const;
|
|
||||||
|
|
||||||
ADD_SERIALIZE_METHODS;
|
|
||||||
|
|
||||||
template <typename Stream, typename Operation>
|
|
||||||
inline void SerializationOp(Stream& s, Operation ser_action) {
|
|
||||||
READWRITE(nSatoshisPerK);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // BITCOIN_AMOUNT_H
|
#endif // BITCOIN_AMOUNT_H
|
||||||
|
@ -27,6 +27,7 @@
|
|||||||
#include "netbase.h"
|
#include "netbase.h"
|
||||||
#include "net.h"
|
#include "net.h"
|
||||||
#include "net_processing.h"
|
#include "net_processing.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "policy/fees.h"
|
#include "policy/fees.h"
|
||||||
#include "policy/policy.h"
|
#include "policy/policy.h"
|
||||||
#include "rpc/server.h"
|
#include "rpc/server.h"
|
||||||
|
@ -16,6 +16,7 @@
|
|||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "validation.h"
|
#include "validation.h"
|
||||||
#include "net.h"
|
#include "net.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "policy/policy.h"
|
#include "policy/policy.h"
|
||||||
#include "pow.h"
|
#include "pow.h"
|
||||||
#include "primitives/transaction.h"
|
#include "primitives/transaction.h"
|
||||||
|
@ -14,6 +14,7 @@
|
|||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
#include "limitedmap.h"
|
#include "limitedmap.h"
|
||||||
#include "netaddress.h"
|
#include "netaddress.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "protocol.h"
|
#include "protocol.h"
|
||||||
#include "random.h"
|
#include "random.h"
|
||||||
#include "saltedhasher.h"
|
#include "saltedhasher.h"
|
||||||
|
@ -3,7 +3,7 @@
|
|||||||
// Distributed under the MIT software license, see the accompanying
|
// Distributed under the MIT software license, see the accompanying
|
||||||
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
|
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
|
||||||
|
|
||||||
#include "amount.h"
|
#include "feerate.h"
|
||||||
|
|
||||||
#include "tinyformat.h"
|
#include "tinyformat.h"
|
||||||
|
|
54
src/policy/feerate.h
Normal file
54
src/policy/feerate.h
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
// Copyright (c) 2009-2010 Satoshi Nakamoto
|
||||||
|
// Copyright (c) 2009-2015 The Bitcoin Core developers
|
||||||
|
// Distributed under the MIT software license, see the accompanying
|
||||||
|
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
|
||||||
|
|
||||||
|
#ifndef BITCOIN_POLICY_FEERATE_H
|
||||||
|
#define BITCOIN_POLICY_FEERATE_H
|
||||||
|
|
||||||
|
#include "amount.h"
|
||||||
|
#include "serialize.h"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
extern const std::string CURRENCY_UNIT;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Fee rate in satoshis per kilobyte: CAmount / kB
|
||||||
|
*/
|
||||||
|
class CFeeRate
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
CAmount nSatoshisPerK; // unit is satoshis-per-1,000-bytes
|
||||||
|
public:
|
||||||
|
/** Fee rate of 0 satoshis per kB */
|
||||||
|
CFeeRate() : nSatoshisPerK(0) { }
|
||||||
|
explicit CFeeRate(const CAmount& _nSatoshisPerK): nSatoshisPerK(_nSatoshisPerK) { }
|
||||||
|
/** Constructor for a fee rate in satoshis per kB. The size in bytes must not exceed (2^63 - 1)*/
|
||||||
|
CFeeRate(const CAmount& nFeePaid, size_t nBytes);
|
||||||
|
CFeeRate(const CFeeRate& other) { nSatoshisPerK = other.nSatoshisPerK; }
|
||||||
|
/**
|
||||||
|
* Return the fee in satoshis for the given size in bytes.
|
||||||
|
*/
|
||||||
|
CAmount GetFee(size_t nBytes) const;
|
||||||
|
/**
|
||||||
|
* Return the fee in satoshis for a size of 1000 bytes
|
||||||
|
*/
|
||||||
|
CAmount GetFeePerK() const { return GetFee(1000); }
|
||||||
|
friend bool operator<(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK < b.nSatoshisPerK; }
|
||||||
|
friend bool operator>(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK > b.nSatoshisPerK; }
|
||||||
|
friend bool operator==(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK == b.nSatoshisPerK; }
|
||||||
|
friend bool operator<=(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK <= b.nSatoshisPerK; }
|
||||||
|
friend bool operator>=(const CFeeRate& a, const CFeeRate& b) { return a.nSatoshisPerK >= b.nSatoshisPerK; }
|
||||||
|
CFeeRate& operator+=(const CFeeRate& a) { nSatoshisPerK += a.nSatoshisPerK; return *this; }
|
||||||
|
std::string ToString() const;
|
||||||
|
|
||||||
|
ADD_SERIALIZE_METHODS;
|
||||||
|
|
||||||
|
template <typename Stream, typename Operation>
|
||||||
|
inline void SerializationOp(Stream& s, Operation ser_action) {
|
||||||
|
READWRITE(nSatoshisPerK);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // BITCOIN_POLICY_FEERATE_H
|
@ -6,6 +6,7 @@
|
|||||||
#define BITCOIN_POLICYESTIMATOR_H
|
#define BITCOIN_POLICYESTIMATOR_H
|
||||||
|
|
||||||
#include "amount.h"
|
#include "amount.h"
|
||||||
|
#include "feerate.h"
|
||||||
#include "uint256.h"
|
#include "uint256.h"
|
||||||
#include "random.h"
|
#include "random.h"
|
||||||
#include "sync.h"
|
#include "sync.h"
|
||||||
|
@ -15,6 +15,27 @@
|
|||||||
|
|
||||||
#include <boost/foreach.hpp>
|
#include <boost/foreach.hpp>
|
||||||
|
|
||||||
|
CAmount GetDustThreshold(const CTxOut& txout, const CFeeRate& dustRelayFee)
|
||||||
|
{
|
||||||
|
// "Dust" is defined in terms of CTransaction::minRelayTxFee, which has units duffs-per-kilobyte.
|
||||||
|
// If you'd pay more than 1/3 in fees to spend something, then we consider it dust.
|
||||||
|
// A typical spendable txout is 34 bytes big, and will need a CTxIn of at least 148 bytes to spend
|
||||||
|
// i.e. total is 148 + 34 = 182 bytes. Default -minrelaytxfee is 1000 duffs per kB
|
||||||
|
// and that means that fee per spendable txout is 182 * 1000 / 1000 = 182 duffs.
|
||||||
|
// So dust is a spendable txout less than 546 * minRelayTxFee / 1000 (in duffs)
|
||||||
|
// i.e. 182 * 3 = 546 duffs with default -minrelaytxfee = minRelayTxFee = 1000 duffs per kB.
|
||||||
|
if (txout.scriptPubKey.IsUnspendable())
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
size_t nSize = GetSerializeSize(txout, SER_DISK, 0)+148u;
|
||||||
|
return 3 * dustRelayFee.GetFee(nSize);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool IsDust(const CTxOut& txout, const CFeeRate& dustRelayFee)
|
||||||
|
{
|
||||||
|
return (txout.nValue < GetDustThreshold(txout, dustRelayFee));
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check transaction inputs to mitigate two
|
* Check transaction inputs to mitigate two
|
||||||
* potential denial-of-service attacks:
|
* potential denial-of-service attacks:
|
||||||
@ -103,7 +124,7 @@ bool IsStandardTx(const CTransaction& tx, std::string& reason)
|
|||||||
else if ((whichType == TX_MULTISIG) && (!fIsBareMultisigStd)) {
|
else if ((whichType == TX_MULTISIG) && (!fIsBareMultisigStd)) {
|
||||||
reason = "bare-multisig";
|
reason = "bare-multisig";
|
||||||
return false;
|
return false;
|
||||||
} else if (txout.IsDust(dustRelayFee)) {
|
} else if (IsDust(txout, ::dustRelayFee)) {
|
||||||
reason = "dust";
|
reason = "dust";
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -7,12 +7,14 @@
|
|||||||
#define BITCOIN_POLICY_POLICY_H
|
#define BITCOIN_POLICY_POLICY_H
|
||||||
|
|
||||||
#include "consensus/consensus.h"
|
#include "consensus/consensus.h"
|
||||||
|
#include "feerate.h"
|
||||||
#include "script/interpreter.h"
|
#include "script/interpreter.h"
|
||||||
#include "script/standard.h"
|
#include "script/standard.h"
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
class CCoinsViewCache;
|
class CCoinsViewCache;
|
||||||
|
class CTxOut;
|
||||||
|
|
||||||
/** Default for -blockmaxsize, which controls the maximum size of block the mining code will create **/
|
/** Default for -blockmaxsize, which controls the maximum size of block the mining code will create **/
|
||||||
static const unsigned int DEFAULT_BLOCK_MAX_SIZE = 2000000;
|
static const unsigned int DEFAULT_BLOCK_MAX_SIZE = 2000000;
|
||||||
@ -58,6 +60,10 @@ static const unsigned int STANDARD_NOT_MANDATORY_VERIFY_FLAGS = STANDARD_SCRIPT_
|
|||||||
static const unsigned int STANDARD_LOCKTIME_VERIFY_FLAGS = LOCKTIME_VERIFY_SEQUENCE |
|
static const unsigned int STANDARD_LOCKTIME_VERIFY_FLAGS = LOCKTIME_VERIFY_SEQUENCE |
|
||||||
LOCKTIME_MEDIAN_TIME_PAST;
|
LOCKTIME_MEDIAN_TIME_PAST;
|
||||||
|
|
||||||
|
CAmount GetDustThreshold(const CTxOut& txout, const CFeeRate& dustRelayFee);
|
||||||
|
|
||||||
|
bool IsDust(const CTxOut& txout, const CFeeRate& dustRelayFee);
|
||||||
|
|
||||||
bool IsStandard(const CScript& scriptPubKey, txnouttype& whichType);
|
bool IsStandard(const CScript& scriptPubKey, txnouttype& whichType);
|
||||||
/**
|
/**
|
||||||
* Check for standard transaction types
|
* Check for standard transaction types
|
||||||
|
@ -175,27 +175,6 @@ public:
|
|||||||
return (nValue == -1);
|
return (nValue == -1);
|
||||||
}
|
}
|
||||||
|
|
||||||
CAmount GetDustThreshold(const CFeeRate &minRelayTxFee) const
|
|
||||||
{
|
|
||||||
// "Dust" is defined in terms of CTransaction::minRelayTxFee, which has units duffs-per-kilobyte.
|
|
||||||
// If you'd pay more than 1/3 in fees to spend something, then we consider it dust.
|
|
||||||
// A typical spendable txout is 34 bytes big, and will need a CTxIn of at least 148 bytes to spend
|
|
||||||
// i.e. total is 148 + 34 = 182 bytes. Default -minrelaytxfee is 1000 duffs per kB
|
|
||||||
// and that means that fee per spendable txout is 182 * 1000 / 1000 = 182 duffs.
|
|
||||||
// So dust is a spendable txout less than 546 * minRelayTxFee / 1000 (in duffs)
|
|
||||||
// i.e. 182 * 3 = 546 duffs with default -minrelaytxfee = minRelayTxFee = 1000 duffs per kB.
|
|
||||||
if (scriptPubKey.IsUnspendable())
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
size_t nSize = GetSerializeSize(*this, SER_DISK, 0)+148u;
|
|
||||||
return 3*minRelayTxFee.GetFee(nSize);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool IsDust(const CFeeRate &minRelayTxFee) const
|
|
||||||
{
|
|
||||||
return (nValue < GetDustThreshold(minRelayTxFee));
|
|
||||||
}
|
|
||||||
|
|
||||||
friend bool operator==(const CTxOut& a, const CTxOut& b)
|
friend bool operator==(const CTxOut& a, const CTxOut& b)
|
||||||
{
|
{
|
||||||
return (a.nValue == b.nValue &&
|
return (a.nValue == b.nValue &&
|
||||||
|
@ -489,8 +489,7 @@ void CoinControlDialog::updateLabels(WalletModel *model, QDialog* dialog)
|
|||||||
{
|
{
|
||||||
CTxOut txout(amount, (CScript)std::vector<unsigned char>(24, 0));
|
CTxOut txout(amount, (CScript)std::vector<unsigned char>(24, 0));
|
||||||
txDummy.vout.push_back(txout);
|
txDummy.vout.push_back(txout);
|
||||||
if (txout.IsDust(dustRelayFee))
|
fDust |= IsDust(txout, ::dustRelayFee);
|
||||||
fDust = true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -578,10 +577,10 @@ void CoinControlDialog::updateLabels(WalletModel *model, QDialog* dialog)
|
|||||||
if (nChange > 0 && nChange < MIN_CHANGE)
|
if (nChange > 0 && nChange < MIN_CHANGE)
|
||||||
{
|
{
|
||||||
CTxOut txout(nChange, (CScript)std::vector<unsigned char>(24, 0));
|
CTxOut txout(nChange, (CScript)std::vector<unsigned char>(24, 0));
|
||||||
if (txout.IsDust(dustRelayFee))
|
if (IsDust(txout, ::dustRelayFee))
|
||||||
{
|
{
|
||||||
if (CoinControlDialog::fSubtractFeeFromAmount) // dust-change will be raised until no dust
|
if (CoinControlDialog::fSubtractFeeFromAmount) // dust-change will be raised until no dust
|
||||||
nChange = txout.GetDustThreshold(dustRelayFee);
|
nChange = GetDustThreshold(txout, ::dustRelayFee);
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
nPayFee += nChange;
|
nPayFee += nChange;
|
||||||
|
@ -267,7 +267,7 @@ bool isDust(const QString& address, const CAmount& amount)
|
|||||||
CTxDestination dest = CBitcoinAddress(address.toStdString()).Get();
|
CTxDestination dest = CBitcoinAddress(address.toStdString()).Get();
|
||||||
CScript script = GetScriptForDestination(dest);
|
CScript script = GetScriptForDestination(dest);
|
||||||
CTxOut txOut(amount, script);
|
CTxOut txOut(amount, script);
|
||||||
return txOut.IsDust(dustRelayFee);
|
return IsDust(txOut, ::dustRelayFee);
|
||||||
}
|
}
|
||||||
|
|
||||||
QString HtmlEscape(const QString& str, bool fMultiLine)
|
QString HtmlEscape(const QString& str, bool fMultiLine)
|
||||||
|
@ -583,7 +583,7 @@ bool PaymentServer::processPaymentRequest(const PaymentRequestPlus& request, Sen
|
|||||||
|
|
||||||
// Extract and check amounts
|
// Extract and check amounts
|
||||||
CTxOut txOut(sendingTo.second, sendingTo.first);
|
CTxOut txOut(sendingTo.second, sendingTo.first);
|
||||||
if (txOut.IsDust(dustRelayFee)) {
|
if (IsDust(txOut, ::dustRelayFee)) {
|
||||||
Q_EMIT message(tr("Payment request error"), tr("Requested payment amount of %1 is too small (considered dust).")
|
Q_EMIT message(tr("Payment request error"), tr("Requested payment amount of %1 is too small (considered dust).")
|
||||||
.arg(BitcoinUnits::formatWithUnit(optionsModel->getDisplayUnit(), sendingTo.second)),
|
.arg(BitcoinUnits::formatWithUnit(optionsModel->getDisplayUnit(), sendingTo.second)),
|
||||||
CClientUIInterface::MSG_ERROR);
|
CClientUIInterface::MSG_ERROR);
|
||||||
|
@ -16,6 +16,7 @@
|
|||||||
#include "instantsend.h"
|
#include "instantsend.h"
|
||||||
#include "validation.h"
|
#include "validation.h"
|
||||||
#include "core_io.h"
|
#include "core_io.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "policy/policy.h"
|
#include "policy/policy.h"
|
||||||
#include "primitives/transaction.h"
|
#include "primitives/transaction.h"
|
||||||
#include "rpc/server.h"
|
#include "rpc/server.h"
|
||||||
|
@ -3,6 +3,7 @@
|
|||||||
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
|
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
|
||||||
|
|
||||||
#include "amount.h"
|
#include "amount.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "test/test_dash.h"
|
#include "test/test_dash.h"
|
||||||
|
|
||||||
#include <boost/test/unit_test.hpp>
|
#include <boost/test/unit_test.hpp>
|
||||||
|
@ -18,6 +18,7 @@
|
|||||||
#include "amount.h"
|
#include "amount.h"
|
||||||
#include "coins.h"
|
#include "coins.h"
|
||||||
#include "indirectmap.h"
|
#include "indirectmap.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "primitives/transaction.h"
|
#include "primitives/transaction.h"
|
||||||
#include "sync.h"
|
#include "sync.h"
|
||||||
#include "random.h"
|
#include "random.h"
|
||||||
|
@ -15,6 +15,7 @@
|
|||||||
#include "coins.h"
|
#include "coins.h"
|
||||||
#include "fs.h"
|
#include "fs.h"
|
||||||
#include "protocol.h" // For CMessageHeader::MessageStartChars
|
#include "protocol.h" // For CMessageHeader::MessageStartChars
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "script/script_error.h"
|
#include "script/script_error.h"
|
||||||
#include "sync.h"
|
#include "sync.h"
|
||||||
#include "versionbits.h"
|
#include "versionbits.h"
|
||||||
|
@ -5,6 +5,7 @@
|
|||||||
#ifndef BITCOIN_WALLET_COINCONTROL_H
|
#ifndef BITCOIN_WALLET_COINCONTROL_H
|
||||||
#define BITCOIN_WALLET_COINCONTROL_H
|
#define BITCOIN_WALLET_COINCONTROL_H
|
||||||
|
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "primitives/transaction.h"
|
#include "primitives/transaction.h"
|
||||||
|
|
||||||
/** Coin Control Features. */
|
/** Coin Control Features. */
|
||||||
|
@ -13,6 +13,7 @@
|
|||||||
#include "wallet/coincontrol.h"
|
#include "wallet/coincontrol.h"
|
||||||
#include "instantsend.h"
|
#include "instantsend.h"
|
||||||
#include "net.h"
|
#include "net.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "policy/fees.h"
|
#include "policy/fees.h"
|
||||||
#include "rpc/server.h"
|
#include "rpc/server.h"
|
||||||
#include "timedata.h"
|
#include "timedata.h"
|
||||||
|
@ -3509,7 +3509,7 @@ bool CWallet::CreateTransaction(const std::vector<CRecipient>& vecSend, CWalletT
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (txout.IsDust(dustRelayFee))
|
if (IsDust(txout, ::dustRelayFee))
|
||||||
{
|
{
|
||||||
if (recipient.fSubtractFeeFromAmount && nFeeRet > 0)
|
if (recipient.fSubtractFeeFromAmount && nFeeRet > 0)
|
||||||
{
|
{
|
||||||
@ -3596,16 +3596,16 @@ bool CWallet::CreateTransaction(const std::vector<CRecipient>& vecSend, CWalletT
|
|||||||
// We do not move dust-change to fees, because the sender would end up paying more than requested.
|
// We do not move dust-change to fees, because the sender would end up paying more than requested.
|
||||||
// This would be against the purpose of the all-inclusive feature.
|
// This would be against the purpose of the all-inclusive feature.
|
||||||
// So instead we raise the change and deduct from the recipient.
|
// So instead we raise the change and deduct from the recipient.
|
||||||
if (nSubtractFeeFromAmount > 0 && newTxOut.IsDust(dustRelayFee))
|
if (nSubtractFeeFromAmount > 0 && IsDust(newTxOut, ::dustRelayFee))
|
||||||
{
|
{
|
||||||
CAmount nDust = newTxOut.GetDustThreshold(dustRelayFee) - newTxOut.nValue;
|
CAmount nDust = GetDustThreshold(newTxOut, ::dustRelayFee) - newTxOut.nValue;
|
||||||
newTxOut.nValue += nDust; // raise change until no more dust
|
newTxOut.nValue += nDust; // raise change until no more dust
|
||||||
for (unsigned int i = 0; i < vecSend.size(); i++) // subtract from first recipient
|
for (unsigned int i = 0; i < vecSend.size(); i++) // subtract from first recipient
|
||||||
{
|
{
|
||||||
if (vecSend[i].fSubtractFeeFromAmount)
|
if (vecSend[i].fSubtractFeeFromAmount)
|
||||||
{
|
{
|
||||||
txNew.vout[i].nValue -= nDust;
|
txNew.vout[i].nValue -= nDust;
|
||||||
if (txNew.vout[i].IsDust(dustRelayFee))
|
if (IsDust(txNew.vout[i], ::dustRelayFee))
|
||||||
{
|
{
|
||||||
strFailReason = _("The transaction amount is too small to send after the fee has been deducted");
|
strFailReason = _("The transaction amount is too small to send after the fee has been deducted");
|
||||||
return false;
|
return false;
|
||||||
@ -3617,7 +3617,7 @@ bool CWallet::CreateTransaction(const std::vector<CRecipient>& vecSend, CWalletT
|
|||||||
|
|
||||||
// Never create dust outputs; if we would, just
|
// Never create dust outputs; if we would, just
|
||||||
// add the dust to the fee.
|
// add the dust to the fee.
|
||||||
if (newTxOut.IsDust(dustRelayFee))
|
if (IsDust(newTxOut, ::dustRelayFee))
|
||||||
{
|
{
|
||||||
nChangePosInOut = -1;
|
nChangePosInOut = -1;
|
||||||
nFeeRet += nChange;
|
nFeeRet += nChange;
|
||||||
|
@ -9,6 +9,7 @@
|
|||||||
|
|
||||||
#include "amount.h"
|
#include "amount.h"
|
||||||
#include "base58.h"
|
#include "base58.h"
|
||||||
|
#include "policy/feerate.h"
|
||||||
#include "streams.h"
|
#include "streams.h"
|
||||||
#include "tinyformat.h"
|
#include "tinyformat.h"
|
||||||
#include "ui_interface.h"
|
#include "ui_interface.h"
|
||||||
|
Loading…
Reference in New Issue
Block a user