diff --git a/src/amount.cpp b/src/amount.cpp index bde2f4d22..57ea8d0df 100644 --- a/src/amount.cpp +++ b/src/amount.cpp @@ -1,26 +1,36 @@ // Copyright (c) 2009-2010 Satoshi Nakamoto // Copyright (c) 2009-2016 The Bitcoin Core developers // Copyright (c) 2017-2019 The Bitcoin developers // Distributed under the MIT software license, see the accompanying // file COPYING or http://www.opensource.org/licenses/mit-license.php. #include #include #include #include +static constexpr Currency BCHA{COIN, SATOSHI, 8}; + +const Currency &Currency::get() { + return BCHA; +} + std::string Amount::ToString() const { - return strprintf("%d.%08d %s", *this / COIN, (*this % COIN) / SATOSHI, + const auto currency = Currency::get(); + return strprintf("%d.%0*d %s", *this / currency.baseunit, currency.decimals, + (*this % currency.baseunit) / currency.subunit, CURRENCY_UNIT); } Amount::operator UniValue() const { bool sign = *this < Amount::zero(); Amount n_abs(sign ? -amount : amount); - int64_t quotient = n_abs / COIN; - int64_t remainder = (n_abs % COIN) / SATOSHI; - return UniValue(UniValue::VNUM, strprintf("%s%d.%08d", sign ? "-" : "", - quotient, remainder)); + const auto currency = Currency::get(); + int64_t quotient = n_abs / currency.baseunit; + int64_t remainder = (n_abs % currency.baseunit) / currency.subunit; + return UniValue(UniValue::VNUM, + strprintf("%s%d.%0*d", sign ? "-" : "", quotient, + currency.decimals, remainder)); } diff --git a/src/amount.h b/src/amount.h index ec9451d0a..c0b287945 100644 --- a/src/amount.h +++ b/src/amount.h @@ -1,172 +1,180 @@ // Copyright (c) 2009-2010 Satoshi Nakamoto // Copyright (c) 2009-2016 The Bitcoin Core developers // Copyright (c) 2017-2019 The Bitcoin developers // Distributed under the MIT software license, see the accompanying // file COPYING or http://www.opensource.org/licenses/mit-license.php. #ifndef BITCOIN_AMOUNT_H #define BITCOIN_AMOUNT_H #include #include #include #include #include class UniValue; struct Amount { private: int64_t amount; explicit constexpr Amount(int64_t _amount) : amount(_amount) {} public: constexpr Amount() : amount(0) {} constexpr Amount(const Amount &other) : amount(other.amount) {} /** * Convenient implicit UniValue conversion operator */ operator UniValue() const; /** * Assignement operator. */ constexpr Amount &operator=(const Amount &other) { amount = other.amount; return *this; } static constexpr Amount zero() { return Amount(0); } static constexpr Amount satoshi() { return Amount(1); } /** * Implement standard operators */ Amount &operator+=(const Amount a) { amount += a.amount; return *this; } Amount &operator-=(const Amount a) { amount -= a.amount; return *this; } /** * Equality */ friend constexpr bool operator==(const Amount a, const Amount b) { return a.amount == b.amount; } friend constexpr bool operator!=(const Amount a, const Amount b) { return !(a == b); } /** * Comparison */ friend constexpr bool operator<(const Amount a, const Amount b) { return a.amount < b.amount; } friend constexpr bool operator>(const Amount a, const Amount b) { return b < a; } friend constexpr bool operator<=(const Amount a, const Amount b) { return !(a > b); } friend constexpr bool operator>=(const Amount a, const Amount b) { return !(a < b); } /** * Unary minus */ constexpr Amount operator-() const { return Amount(-amount); } /** * Addition and subtraction. */ friend constexpr Amount operator+(const Amount a, const Amount b) { return Amount(a.amount + b.amount); } friend constexpr Amount operator-(const Amount a, const Amount b) { return a + -b; } /** * Multiplication */ friend constexpr Amount operator*(const int64_t a, const Amount b) { return Amount(a * b.amount); } friend constexpr Amount operator*(const int a, const Amount b) { return Amount(a * b.amount); } /** * Division */ constexpr int64_t operator/(const Amount b) const { return amount / b.amount; } constexpr Amount operator/(const int64_t b) const { return Amount(amount / b); } constexpr Amount operator/(const int b) const { return Amount(amount / b); } Amount &operator/=(const int64_t n) { amount /= n; return *this; } /** * Modulus */ constexpr Amount operator%(const Amount b) const { return Amount(amount % b.amount); } constexpr Amount operator%(const int64_t b) const { return Amount(amount % b); } constexpr Amount operator%(const int b) const { return Amount(amount % b); } /** * Do not implement double ops to get an error with double and ensure * casting to integer is explicit. */ friend constexpr Amount operator*(const double a, const Amount b) = delete; constexpr Amount operator/(const double b) const = delete; constexpr Amount operator%(const double b) const = delete; // ostream support friend std::ostream &operator<<(std::ostream &stream, const Amount &ca) { return stream << ca.amount; } std::string ToString() const; // serialization support SERIALIZE_METHODS(Amount, obj) { READWRITE(obj.amount); } }; static constexpr Amount SATOSHI = Amount::satoshi(); static constexpr Amount CASH = 100 * SATOSHI; static constexpr Amount COIN = 100000000 * SATOSHI; +struct Currency { + Amount baseunit; + Amount subunit; + uint8_t decimals; + + static const Currency &get(); +}; + /** * No amount larger than this (in satoshi) is valid. * * Note that this constant is *not* the total money supply, which in Bitcoin * currently happens to be less than 21,000,000 BCH for various reasons, but * rather a sanity check. As this sanity check is used by consensus-critical * validation code, the exact value of the MAX_MONEY constant is consensus * critical; in unusual circumstances like a(nother) overflow bug that allowed * for the creation of coins out of thin air modification could lead to a fork. */ static const Amount MAX_MONEY = 21000000 * COIN; inline bool MoneyRange(const Amount nValue) { return nValue >= Amount::zero() && nValue <= MAX_MONEY; } #endif // BITCOIN_AMOUNT_H diff --git a/src/feerate.cpp b/src/feerate.cpp index 70690d64e..9dc7f0435 100644 --- a/src/feerate.cpp +++ b/src/feerate.cpp @@ -1,62 +1,64 @@ // Copyright (c) 2009-2010 Satoshi Nakamoto // Copyright (c) 2009-2016 The Bitcoin Core developers // Copyright (c) 2017-2019 The Bitcoin developers // Distributed under the MIT software license, see the accompanying // file COPYING or http://www.opensource.org/licenses/mit-license.php. #include #include #include CFeeRate::CFeeRate(const Amount nFeePaid, size_t nBytes_) { assert(nBytes_ <= uint64_t(std::numeric_limits::max())); int64_t nSize = int64_t(nBytes_); if (nSize > 0) { nSatoshisPerK = 1000 * nFeePaid / nSize; } else { nSatoshisPerK = Amount::zero(); } } template static Amount GetFee(size_t nBytes_, Amount nSatoshisPerK) { assert(nBytes_ <= uint64_t(std::numeric_limits::max())); int64_t nSize = int64_t(nBytes_); // Ensure fee is rounded up when truncated if ceil is true. Amount nFee = Amount::zero(); if (ceil) { nFee = Amount(nSize * nSatoshisPerK % 1000 > Amount::zero() ? nSize * nSatoshisPerK / 1000 + SATOSHI : nSize * nSatoshisPerK / 1000); } else { nFee = nSize * nSatoshisPerK / 1000; } if (nFee == Amount::zero() && nSize != 0) { if (nSatoshisPerK > Amount::zero()) { nFee = SATOSHI; } if (nSatoshisPerK < Amount::zero()) { nFee = -SATOSHI; } } return nFee; } Amount CFeeRate::GetFee(size_t nBytes) const { return ::GetFee(nBytes, nSatoshisPerK); } Amount CFeeRate::GetFeeCeiling(size_t nBytes) const { return ::GetFee(nBytes, nSatoshisPerK); } std::string CFeeRate::ToString() const { - return strprintf("%d.%08d %s/kB", nSatoshisPerK / COIN, - (nSatoshisPerK % COIN) / SATOSHI, CURRENCY_UNIT); + const auto currency = Currency::get(); + return strprintf( + "%d.%0*d %s/kB", nSatoshisPerK / currency.baseunit, currency.decimals, + (nSatoshisPerK % currency.baseunit) / currency.subunit, CURRENCY_UNIT); } diff --git a/src/rpc/util.cpp b/src/rpc/util.cpp index b27949c28..493506af8 100644 --- a/src/rpc/util.cpp +++ b/src/rpc/util.cpp @@ -1,904 +1,904 @@ // Copyright (c) 2017-2019 The Bitcoin Core developers // Distributed under the MIT software license, see the accompanying // file COPYING or http://www.opensource.org/licenses/mit-license.php. #include #include #include