From 987c3139dce921c98b4a24bab52354102f21fb1e Mon Sep 17 00:00:00 2001 From: moneromooo-monero Date: Mon, 9 Dec 2019 14:56:44 +0000 Subject: [PATCH] print_coinbase_tx_sum now supports 128 bits sums The tail emission will bring the total above 64 bits --- .../cryptonote_format_utils.cpp | 18 ++++++++++++++++-- src/cryptonote_basic/cryptonote_format_utils.h | 2 ++ src/cryptonote_core/cryptonote_core.cpp | 8 ++++---- src/cryptonote_core/cryptonote_core.h | 2 +- src/daemon/rpc_command_executor.cpp | 6 +++--- src/rpc/core_rpc_server.cpp | 17 +++++++++++------ src/rpc/core_rpc_server_commands_defs.h | 8 ++++++++ tests/functional_tests/blockchain.py | 5 +++++ 8 files changed, 50 insertions(+), 16 deletions(-) diff --git a/src/cryptonote_basic/cryptonote_format_utils.cpp b/src/cryptonote_basic/cryptonote_format_utils.cpp index 138cf49f4..651d61b06 100644 --- a/src/cryptonote_basic/cryptonote_format_utils.cpp +++ b/src/cryptonote_basic/cryptonote_format_utils.cpp @@ -996,17 +996,31 @@ namespace cryptonote } } //--------------------------------------------------------------- - std::string print_money(uint64_t amount, unsigned int decimal_point) + static void insert_money_decimal_point(std::string &s, unsigned int decimal_point) { if (decimal_point == (unsigned int)-1) decimal_point = default_decimal_point; - std::string s = std::to_string(amount); if(s.size() < decimal_point+1) { s.insert(0, decimal_point+1 - s.size(), '0'); } if (decimal_point > 0) s.insert(s.size() - decimal_point, "."); + } + //--------------------------------------------------------------- + std::string print_money(uint64_t amount, unsigned int decimal_point) + { + std::string s = std::to_string(amount); + insert_money_decimal_point(s, decimal_point); + return s; + } + //--------------------------------------------------------------- + std::string print_money(const boost::multiprecision::uint128_t &amount, unsigned int decimal_point) + { + std::stringstream ss; + ss << amount; + std::string s = ss.str(); + insert_money_decimal_point(s, decimal_point); return s; } //--------------------------------------------------------------- diff --git a/src/cryptonote_basic/cryptonote_format_utils.h b/src/cryptonote_basic/cryptonote_format_utils.h index 29e4def64..8ed3b0b43 100644 --- a/src/cryptonote_basic/cryptonote_format_utils.h +++ b/src/cryptonote_basic/cryptonote_format_utils.h @@ -38,6 +38,7 @@ #include "crypto/crypto.h" #include "crypto/hash.h" #include +#include namespace epee { @@ -139,6 +140,7 @@ namespace cryptonote unsigned int get_default_decimal_point(); std::string get_unit(unsigned int decimal_point = -1); std::string print_money(uint64_t amount, unsigned int decimal_point = -1); + std::string print_money(const boost::multiprecision::uint128_t &amount, unsigned int decimal_point = -1); //--------------------------------------------------------------- template bool t_serializable_object_from_blob(t_object& to, const blobdata& b_blob) diff --git a/src/cryptonote_core/cryptonote_core.cpp b/src/cryptonote_core/cryptonote_core.cpp index 02620996e..460ff07d8 100644 --- a/src/cryptonote_core/cryptonote_core.cpp +++ b/src/cryptonote_core/cryptonote_core.cpp @@ -1178,10 +1178,10 @@ namespace cryptonote return m_mempool.check_for_key_images(key_im, spent); } //----------------------------------------------------------------------------------------------- - std::pair core::get_coinbase_tx_sum(const uint64_t start_offset, const size_t count) + std::pair core::get_coinbase_tx_sum(const uint64_t start_offset, const size_t count) { - uint64_t emission_amount = 0; - uint64_t total_fee_amount = 0; + boost::multiprecision::uint128_t emission_amount = 0; + boost::multiprecision::uint128_t total_fee_amount = 0; if (count) { const uint64_t end = start_offset + count - 1; @@ -1203,7 +1203,7 @@ namespace cryptonote }); } - return std::pair(emission_amount, total_fee_amount); + return std::pair(emission_amount, total_fee_amount); } //----------------------------------------------------------------------------------------------- bool core::check_tx_inputs_keyimages_diff(const transaction& tx) const diff --git a/src/cryptonote_core/cryptonote_core.h b/src/cryptonote_core/cryptonote_core.h index f69ac3509..01df86fd5 100644 --- a/src/cryptonote_core/cryptonote_core.h +++ b/src/cryptonote_core/cryptonote_core.h @@ -743,7 +743,7 @@ namespace cryptonote * * @return the number of blocks to sync in one go */ - std::pair get_coinbase_tx_sum(const uint64_t start_offset, const size_t count); + std::pair get_coinbase_tx_sum(const uint64_t start_offset, const size_t count); /** * @brief get the network type we're on diff --git a/src/daemon/rpc_command_executor.cpp b/src/daemon/rpc_command_executor.cpp index ed614a89b..94fb304e5 100644 --- a/src/daemon/rpc_command_executor.cpp +++ b/src/daemon/rpc_command_executor.cpp @@ -1851,9 +1851,9 @@ bool t_rpc_command_executor::print_coinbase_tx_sum(uint64_t height, uint64_t cou tools::msg_writer() << "Sum of coinbase transactions between block heights [" << height << ", " << (height + count) << ") is " - << cryptonote::print_money(res.emission_amount + res.fee_amount) << " " - << "consisting of " << cryptonote::print_money(res.emission_amount) - << " in emissions, and " << cryptonote::print_money(res.fee_amount) << " in fees"; + << cryptonote::print_money(boost::multiprecision::uint128_t(res.wide_emission_amount) + boost::multiprecision::uint128_t(res.wide_fee_amount)) << " " + << "consisting of " << cryptonote::print_money(boost::multiprecision::uint128_t(res.wide_emission_amount)) + << " in emissions, and " << cryptonote::print_money(boost::multiprecision::uint128_t(res.wide_fee_amount)) << " in fees"; return true; } diff --git a/src/rpc/core_rpc_server.cpp b/src/rpc/core_rpc_server.cpp index 9117b5b3a..0de667dd1 100644 --- a/src/rpc/core_rpc_server.cpp +++ b/src/rpc/core_rpc_server.cpp @@ -120,11 +120,16 @@ namespace return (value + quantum - 1) / quantum * quantum; } + void store_128(boost::multiprecision::uint128_t value, uint64_t &slow64, std::string &swide, uint64_t &stop64) + { + slow64 = (value & 0xffffffffffffffff).convert_to(); + swide = cryptonote::hex(value); + stop64 = ((value >> 64) & 0xffffffffffffffff).convert_to(); + } + void store_difficulty(cryptonote::difficulty_type difficulty, uint64_t &sdiff, std::string &swdiff, uint64_t &stop64) { - sdiff = (difficulty & 0xffffffffffffffff).convert_to(); - swdiff = cryptonote::hex(difficulty); - stop64 = ((difficulty >> 64) & 0xffffffffffffffff).convert_to(); + store_128(difficulty, sdiff, swdiff, stop64); } } @@ -2486,9 +2491,9 @@ namespace cryptonote return true; } CHECK_PAYMENT_MIN1(req, res, COST_PER_COINBASE_TX_SUM_BLOCK * req.count, false); - std::pair amounts = m_core.get_coinbase_tx_sum(req.height, req.count); - res.emission_amount = amounts.first; - res.fee_amount = amounts.second; + std::pair amounts = m_core.get_coinbase_tx_sum(req.height, req.count); + store_128(amounts.first, res.emission_amount, res.wide_emission_amount, res.emission_amount_top64); + store_128(amounts.second, res.fee_amount, res.wide_fee_amount, res.fee_amount_top64); res.status = CORE_RPC_STATUS_OK; return true; } diff --git a/src/rpc/core_rpc_server_commands_defs.h b/src/rpc/core_rpc_server_commands_defs.h index 855ea854c..5425e7f6c 100644 --- a/src/rpc/core_rpc_server_commands_defs.h +++ b/src/rpc/core_rpc_server_commands_defs.h @@ -2021,12 +2021,20 @@ namespace cryptonote struct response_t: public rpc_access_response_base { uint64_t emission_amount; + std::string wide_emission_amount; + uint64_t emission_amount_top64; uint64_t fee_amount; + std::string wide_fee_amount; + uint64_t fee_amount_top64; BEGIN_KV_SERIALIZE_MAP() KV_SERIALIZE_PARENT(rpc_access_response_base) KV_SERIALIZE(emission_amount) + KV_SERIALIZE(wide_emission_amount) + KV_SERIALIZE(emission_amount_top64) KV_SERIALIZE(fee_amount) + KV_SERIALIZE(wide_fee_amount) + KV_SERIALIZE(fee_amount_top64) END_KV_SERIALIZE_MAP() }; typedef epee::misc_utils::struct_init response; diff --git a/tests/functional_tests/blockchain.py b/tests/functional_tests/blockchain.py index 78e0d8952..b8f8bac1a 100755 --- a/tests/functional_tests/blockchain.py +++ b/tests/functional_tests/blockchain.py @@ -203,10 +203,15 @@ class BlockchainTest(): res_sum = daemon.get_coinbase_tx_sum(i, 1) res_header = daemon.getblockheaderbyheight(i) assert res_sum.emission_amount == res_header.block_header.reward + assert res_sum.emission_amount_top64 == 0 + assert res_sum.emission_amount == int(res_sum.wide_emission_amount, 16) + assert res_sum.fee_amount == int(res_sum.wide_fee_amount, 16) res = daemon.get_coinbase_tx_sum(0, 1) assert res.emission_amount == 17592186044415 + assert res.emission_amount_top64 == 0 assert res.fee_amount == 0 + assert res.fee_amount_top64 == 0 sum_blocks = height + nblocks - 1 res = daemon.get_coinbase_tx_sum(0, sum_blocks) extrapolated = 17592186044415 + 17592186044415 * 2 * (sum_blocks - 1)