aboutsummaryrefslogtreecommitdiff
path: root/src/policy
diff options
context:
space:
mode:
Diffstat (limited to 'src/policy')
-rw-r--r--src/policy/feerate.cpp21
-rw-r--r--src/policy/feerate.h11
-rw-r--r--src/policy/fees.cpp48
3 files changed, 47 insertions, 33 deletions
diff --git a/src/policy/feerate.cpp b/src/policy/feerate.cpp
index 3da85fedf9..25b9282b4e 100644
--- a/src/policy/feerate.cpp
+++ b/src/policy/feerate.cpp
@@ -7,29 +7,26 @@
#include <tinyformat.h>
-CFeeRate::CFeeRate(const CAmount& nFeePaid, size_t nBytes_)
+CFeeRate::CFeeRate(const CAmount& nFeePaid, uint32_t num_bytes)
{
- assert(nBytes_ <= uint64_t(std::numeric_limits<int64_t>::max()));
- int64_t nSize = int64_t(nBytes_);
+ const int64_t nSize{num_bytes};
- if (nSize > 0)
+ if (nSize > 0) {
nSatoshisPerK = nFeePaid * 1000 / nSize;
- else
+ } else {
nSatoshisPerK = 0;
+ }
}
-CAmount CFeeRate::GetFee(size_t nBytes_) const
+CAmount CFeeRate::GetFee(uint32_t num_bytes) const
{
- assert(nBytes_ <= uint64_t(std::numeric_limits<int64_t>::max()));
- int64_t nSize = int64_t(nBytes_);
+ const int64_t nSize{num_bytes};
CAmount nFee = nSatoshisPerK * nSize / 1000;
if (nFee == 0 && nSize != 0) {
- if (nSatoshisPerK > 0)
- nFee = CAmount(1);
- if (nSatoshisPerK < 0)
- nFee = CAmount(-1);
+ if (nSatoshisPerK > 0) nFee = CAmount(1);
+ if (nSatoshisPerK < 0) nFee = CAmount(-1);
}
return nFee;
diff --git a/src/policy/feerate.h b/src/policy/feerate.h
index 0e4f9914b8..d296d32774 100644
--- a/src/policy/feerate.h
+++ b/src/policy/feerate.h
@@ -39,20 +39,17 @@ public:
// We've previously had bugs creep in from silent double->int conversion...
static_assert(std::is_integral<I>::value, "CFeeRate should be used without floats");
}
- /** Constructor for a fee rate in satoshis per kvB (sat/kvB). The size in bytes must not exceed (2^63 - 1).
+ /** Constructor for a fee rate in satoshis per kvB (sat/kvB).
*
- * Passing an nBytes value of COIN (1e8) returns a fee rate in satoshis per vB (sat/vB),
+ * Passing a num_bytes value of COIN (1e8) returns a fee rate in satoshis per vB (sat/vB),
* e.g. (nFeePaid * 1e8 / 1e3) == (nFeePaid / 1e5),
* where 1e5 is the ratio to convert from BTC/kvB to sat/vB.
- *
- * @param[in] nFeePaid CAmount fee rate to construct with
- * @param[in] nBytes size_t bytes (units) to construct with
*/
- CFeeRate(const CAmount& nFeePaid, size_t nBytes);
+ CFeeRate(const CAmount& nFeePaid, uint32_t num_bytes);
/**
* Return the fee in satoshis for the given size in bytes.
*/
- CAmount GetFee(size_t nBytes) const;
+ CAmount GetFee(uint32_t num_bytes) const;
/**
* Return the fee in satoshis for a size of 1000 bytes
*/
diff --git a/src/policy/fees.cpp b/src/policy/fees.cpp
index 7da171d2e1..2ae5798ebe 100644
--- a/src/policy/fees.cpp
+++ b/src/policy/fees.cpp
@@ -10,6 +10,7 @@
#include <logging.h>
#include <streams.h>
#include <txmempool.h>
+#include <util/serfloat.h>
#include <util/system.h>
static const char* FEE_ESTIMATES_FILENAME = "fee_estimates.dat";
@@ -26,6 +27,25 @@ std::string StringForFeeEstimateHorizon(FeeEstimateHorizon horizon)
assert(false);
}
+namespace {
+
+struct EncodedDoubleFormatter
+{
+ template<typename Stream> void Ser(Stream &s, double v)
+ {
+ s << EncodeDouble(v);
+ }
+
+ template<typename Stream> void Unser(Stream& s, double& v)
+ {
+ uint64_t encoded;
+ s >> encoded;
+ v = DecodeDouble(encoded);
+ }
+};
+
+} // namespace
+
/**
* We will instantiate an instance of this class to track transactions that were
* included in a block. We will lump transactions into a bucket according to their
@@ -356,12 +376,12 @@ double TxConfirmStats::EstimateMedianVal(int confTarget, double sufficientTxVal,
void TxConfirmStats::Write(CAutoFile& fileout) const
{
- fileout << decay;
+ fileout << Using<EncodedDoubleFormatter>(decay);
fileout << scale;
- fileout << m_feerate_avg;
- fileout << txCtAvg;
- fileout << confAvg;
- fileout << failAvg;
+ fileout << Using<VectorFormatter<EncodedDoubleFormatter>>(m_feerate_avg);
+ fileout << Using<VectorFormatter<EncodedDoubleFormatter>>(txCtAvg);
+ fileout << Using<VectorFormatter<VectorFormatter<EncodedDoubleFormatter>>>(confAvg);
+ fileout << Using<VectorFormatter<VectorFormatter<EncodedDoubleFormatter>>>(failAvg);
}
void TxConfirmStats::Read(CAutoFile& filein, int nFileVersion, size_t numBuckets)
@@ -372,7 +392,7 @@ void TxConfirmStats::Read(CAutoFile& filein, int nFileVersion, size_t numBuckets
size_t maxConfirms, maxPeriods;
// The current version will store the decay with each individual TxConfirmStats and also keep a scale factor
- filein >> decay;
+ filein >> Using<EncodedDoubleFormatter>(decay);
if (decay <= 0 || decay >= 1) {
throw std::runtime_error("Corrupt estimates file. Decay must be between 0 and 1 (non-inclusive)");
}
@@ -381,15 +401,15 @@ void TxConfirmStats::Read(CAutoFile& filein, int nFileVersion, size_t numBuckets
throw std::runtime_error("Corrupt estimates file. Scale must be non-zero");
}
- filein >> m_feerate_avg;
+ filein >> Using<VectorFormatter<EncodedDoubleFormatter>>(m_feerate_avg);
if (m_feerate_avg.size() != numBuckets) {
throw std::runtime_error("Corrupt estimates file. Mismatch in feerate average bucket count");
}
- filein >> txCtAvg;
+ filein >> Using<VectorFormatter<EncodedDoubleFormatter>>(txCtAvg);
if (txCtAvg.size() != numBuckets) {
throw std::runtime_error("Corrupt estimates file. Mismatch in tx count bucket count");
}
- filein >> confAvg;
+ filein >> Using<VectorFormatter<VectorFormatter<EncodedDoubleFormatter>>>(confAvg);
maxPeriods = confAvg.size();
maxConfirms = scale * maxPeriods;
@@ -402,7 +422,7 @@ void TxConfirmStats::Read(CAutoFile& filein, int nFileVersion, size_t numBuckets
}
}
- filein >> failAvg;
+ filein >> Using<VectorFormatter<VectorFormatter<EncodedDoubleFormatter>>>(failAvg);
if (maxPeriods != failAvg.size()) {
throw std::runtime_error("Corrupt estimates file. Mismatch in confirms tracked for failures");
}
@@ -504,7 +524,7 @@ CBlockPolicyEstimator::CBlockPolicyEstimator()
longStats = std::unique_ptr<TxConfirmStats>(new TxConfirmStats(buckets, bucketMap, LONG_BLOCK_PERIODS, LONG_DECAY, LONG_SCALE));
// If the fee estimation file is present, read recorded estimations
- fs::path est_filepath = GetDataDir() / FEE_ESTIMATES_FILENAME;
+ fs::path est_filepath = gArgs.GetDataDirNet() / FEE_ESTIMATES_FILENAME;
CAutoFile est_file(fsbridge::fopen(est_filepath, "rb"), SER_DISK, CLIENT_VERSION);
if (est_file.IsNull() || !Read(est_file)) {
LogPrintf("Failed to read fee estimates from %s. Continue anyway.\n", est_filepath.string());
@@ -864,7 +884,7 @@ CFeeRate CBlockPolicyEstimator::estimateSmartFee(int confTarget, FeeCalculation
void CBlockPolicyEstimator::Flush() {
FlushUnconfirmed();
- fs::path est_filepath = GetDataDir() / FEE_ESTIMATES_FILENAME;
+ fs::path est_filepath = gArgs.GetDataDirNet() / FEE_ESTIMATES_FILENAME;
CAutoFile est_file(fsbridge::fopen(est_filepath, "wb"), SER_DISK, CLIENT_VERSION);
if (est_file.IsNull() || !Write(est_file)) {
LogPrintf("Failed to write fee estimates to %s. Continue anyway.\n", est_filepath.string());
@@ -884,7 +904,7 @@ bool CBlockPolicyEstimator::Write(CAutoFile& fileout) const
else {
fileout << historicalFirst << historicalBest;
}
- fileout << buckets;
+ fileout << Using<VectorFormatter<EncodedDoubleFormatter>>(buckets);
feeStats->Write(fileout);
shortStats->Write(fileout);
longStats->Write(fileout);
@@ -920,7 +940,7 @@ bool CBlockPolicyEstimator::Read(CAutoFile& filein)
throw std::runtime_error("Corrupt estimates file. Historical block range for estimates is invalid");
}
std::vector<double> fileBuckets;
- filein >> fileBuckets;
+ filein >> Using<VectorFormatter<EncodedDoubleFormatter>>(fileBuckets);
size_t numBuckets = fileBuckets.size();
if (numBuckets <= 1 || numBuckets > 1000) {
throw std::runtime_error("Corrupt estimates file. Must have between 2 and 1000 feerate buckets");