diff options
Diffstat (limited to 'src/rpc')
-rw-r--r-- | src/rpc/core_rpc_server.cpp | 56 | ||||
-rw-r--r-- | src/rpc/core_rpc_server.h | 2 | ||||
-rw-r--r-- | src/rpc/core_rpc_server_commands_defs.h | 4 |
3 files changed, 52 insertions, 10 deletions
diff --git a/src/rpc/core_rpc_server.cpp b/src/rpc/core_rpc_server.cpp index c3d1a9d11..aa5728fc3 100644 --- a/src/rpc/core_rpc_server.cpp +++ b/src/rpc/core_rpc_server.cpp @@ -209,6 +209,15 @@ namespace cryptonote return true; } //------------------------------------------------------------------------------------------------------------------------------ + static cryptonote::blobdata get_pruned_tx_blob(cryptonote::transaction &tx) + { + std::stringstream ss; + binary_archive<true> ba(ss); + bool r = tx.serialize_base(ba); + CHECK_AND_ASSERT_MES(r, cryptonote::blobdata(), "Failed to serialize rct signatures base"); + return ss.str(); + } + //------------------------------------------------------------------------------------------------------------------------------ static cryptonote::blobdata get_pruned_tx_blob(const cryptonote::blobdata &blobdata) { cryptonote::transaction tx; @@ -216,14 +225,9 @@ namespace cryptonote if (!cryptonote::parse_and_validate_tx_from_blob(blobdata, tx)) { MERROR("Failed to parse and validate tx from blob"); - return blobdata; + return cryptonote::blobdata(); } - - std::stringstream ss; - binary_archive<true> ba(ss); - bool r = tx.serialize_base(ba); - CHECK_AND_ASSERT_MES(r, blobdata, "Failed to serialize rct signatures base"); - return ss.str(); + return get_pruned_tx_blob(tx); } //------------------------------------------------------------------------------------------------------------------------------ bool core_rpc_server::on_get_blocks(const COMMAND_RPC_GET_BLOCKS_FAST::request& req, COMMAND_RPC_GET_BLOCKS_FAST::response& res) @@ -633,7 +637,7 @@ namespace cryptonote crypto::hash tx_hash = *vhi++; e.tx_hash = *txhi++; - blobdata blob = t_serializable_object_to_blob(tx); + blobdata blob = req.prune ? get_pruned_tx_blob(tx) : t_serializable_object_to_blob(tx); e.as_hex = string_tools::buff_to_hex_nodelimer(blob); if (req.decode_as_json) e.as_json = obj_to_json_str(tx); @@ -2078,10 +2082,27 @@ namespace cryptonote //------------------------------------------------------------------------------------------------------------------------------ bool core_rpc_server::on_get_output_distribution(const COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::request& req, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::response& res, epee::json_rpc::error& error_resp) { + PERF_TIMER(on_get_output_distribution); try { for (uint64_t amount: req.amounts) { + static struct D + { + boost::mutex mutex; + std::vector<uint64_t> cached_distribution; + uint64_t cached_from, cached_to, cached_start_height, cached_base; + bool cached; + D(): cached_from(0), cached_to(0), cached_start_height(0), cached_base(0), cached(false) {} + } d; + boost::unique_lock<boost::mutex> lock(d.mutex); + + if (d.cached && amount == 0 && d.cached_from == req.from_height && d.cached_to == req.to_height) + { + res.distributions.push_back({amount, d.cached_start_height, d.cached_distribution, d.cached_base}); + continue; + } + std::vector<uint64_t> distribution; uint64_t start_height, base; if (!m_core.get_output_distribution(amount, req.from_height, start_height, distribution, base)) @@ -2090,12 +2111,29 @@ namespace cryptonote error_resp.message = "Failed to get rct distribution"; return false; } + if (req.to_height > 0 && req.to_height >= req.from_height) + { + uint64_t offset = std::max(req.from_height, start_height); + if (offset <= req.to_height && req.to_height - offset + 1 < distribution.size()) + distribution.resize(req.to_height - offset + 1); + } if (req.cumulative) { distribution[0] += base; for (size_t n = 1; n < distribution.size(); ++n) distribution[n] += distribution[n-1]; } + + if (amount == 0) + { + d.cached_from = req.from_height; + d.cached_to = req.to_height; + d.cached_distribution = distribution; + d.cached_start_height = start_height; + d.cached_base = base; + d.cached = true; + } + res.distributions.push_back({amount, start_height, std::move(distribution), base}); } } @@ -2117,7 +2155,7 @@ namespace cryptonote , "Port for RPC server" , std::to_string(config::RPC_DEFAULT_PORT) , {{ &cryptonote::arg_testnet_on, &cryptonote::arg_stagenet_on }} - , [](std::array<bool, 2> testnet_stagenet, bool defaulted, std::string val) { + , [](std::array<bool, 2> testnet_stagenet, bool defaulted, std::string val)->std::string { if (testnet_stagenet[0] && defaulted) return std::to_string(config::testnet::RPC_DEFAULT_PORT); else if (testnet_stagenet[1] && defaulted) diff --git a/src/rpc/core_rpc_server.h b/src/rpc/core_rpc_server.h index a5755e062..86e41e047 100644 --- a/src/rpc/core_rpc_server.h +++ b/src/rpc/core_rpc_server.h @@ -153,7 +153,7 @@ namespace cryptonote MAP_JON_RPC_WE_IF("relay_tx", on_relay_tx, COMMAND_RPC_RELAY_TX, !m_restricted) MAP_JON_RPC_WE_IF("sync_info", on_sync_info, COMMAND_RPC_SYNC_INFO, !m_restricted) MAP_JON_RPC_WE("get_txpool_backlog", on_get_txpool_backlog, COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG) - MAP_JON_RPC_WE_IF("get_output_distribution", on_get_output_distribution, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION, !m_restricted) + MAP_JON_RPC_WE("get_output_distribution", on_get_output_distribution, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION) END_JSON_RPC_MAP() END_URI_MAP2() diff --git a/src/rpc/core_rpc_server_commands_defs.h b/src/rpc/core_rpc_server_commands_defs.h index 660fb7889..a97277c0e 100644 --- a/src/rpc/core_rpc_server_commands_defs.h +++ b/src/rpc/core_rpc_server_commands_defs.h @@ -563,10 +563,12 @@ namespace cryptonote { std::list<std::string> txs_hashes; bool decode_as_json; + bool prune; BEGIN_KV_SERIALIZE_MAP() KV_SERIALIZE(txs_hashes) KV_SERIALIZE(decode_as_json) + KV_SERIALIZE_OPT(prune, false) END_KV_SERIALIZE_MAP() }; @@ -2210,11 +2212,13 @@ namespace cryptonote { std::vector<uint64_t> amounts; uint64_t from_height; + uint64_t to_height; bool cumulative; BEGIN_KV_SERIALIZE_MAP() KV_SERIALIZE(amounts) KV_SERIALIZE_OPT(from_height, (uint64_t)0) + KV_SERIALIZE_OPT(to_height, (uint64_t)0) KV_SERIALIZE_OPT(cumulative, false) END_KV_SERIALIZE_MAP() }; |