Electroneum
Loading...
Searching...
No Matches
cryptonote::core_rpc_server Class Reference

#include <core_rpc_server.h>

Inheritance diagram for cryptonote::core_rpc_server:
Collaboration diagram for cryptonote::core_rpc_server:

Public Types

typedef epee::net_utils::connection_context_base connection_context

Public Member Functions

 core_rpc_server (core &cr, nodetool::node_server< cryptonote::t_cryptonote_protocol_handler< cryptonote::core > > &p2p)
bool init (const boost::program_options::variables_map &vm, const bool restricted, const std::string &port)
network_type nettype () const
 CHAIN_HTTP_TO_MAP2 (connection_context)
bool on_get_height (const COMMAND_RPC_GET_HEIGHT::request &req, COMMAND_RPC_GET_HEIGHT::response &res, const connection_context *ctx=NULL)
bool on_get_blocks (const COMMAND_RPC_GET_BLOCKS_FAST::request &req, COMMAND_RPC_GET_BLOCKS_FAST::response &res, const connection_context *ctx=NULL)
bool on_get_alt_blocks_hashes (const COMMAND_RPC_GET_ALT_BLOCKS_HASHES::request &req, COMMAND_RPC_GET_ALT_BLOCKS_HASHES::response &res, const connection_context *ctx=NULL)
bool on_get_blocks_by_height (const COMMAND_RPC_GET_BLOCKS_BY_HEIGHT::request &req, COMMAND_RPC_GET_BLOCKS_BY_HEIGHT::response &res, const connection_context *ctx=NULL)
bool on_get_hashes (const COMMAND_RPC_GET_HASHES_FAST::request &req, COMMAND_RPC_GET_HASHES_FAST::response &res, const connection_context *ctx=NULL)
bool on_get_transactions (const COMMAND_RPC_GET_TRANSACTIONS::request &req, COMMAND_RPC_GET_TRANSACTIONS::response &res, const connection_context *ctx=NULL)
bool on_is_key_image_spent (const COMMAND_RPC_IS_KEY_IMAGE_SPENT::request &req, COMMAND_RPC_IS_KEY_IMAGE_SPENT::response &res, const connection_context *ctx=NULL)
bool on_is_public_output_spent (const COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT::request &req, COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT::response &res, const connection_context *ctx=NULL)
bool on_get_indexes (const COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES::request &req, COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES::response &res, const connection_context *ctx=NULL)
bool on_send_raw_tx (const COMMAND_RPC_SEND_RAW_TX::request &req, COMMAND_RPC_SEND_RAW_TX::response &res, const connection_context *ctx=NULL)
bool on_start_mining (const COMMAND_RPC_START_MINING::request &req, COMMAND_RPC_START_MINING::response &res, const connection_context *ctx=NULL)
bool on_stop_mining (const COMMAND_RPC_STOP_MINING::request &req, COMMAND_RPC_STOP_MINING::response &res, const connection_context *ctx=NULL)
bool on_mining_status (const COMMAND_RPC_MINING_STATUS::request &req, COMMAND_RPC_MINING_STATUS::response &res, const connection_context *ctx=NULL)
bool on_get_outs_bin (const COMMAND_RPC_GET_OUTPUTS_BIN::request &req, COMMAND_RPC_GET_OUTPUTS_BIN::response &res, const connection_context *ctx=NULL)
bool on_get_outs (const COMMAND_RPC_GET_OUTPUTS::request &req, COMMAND_RPC_GET_OUTPUTS::response &res, const connection_context *ctx=NULL)
bool on_get_info (const COMMAND_RPC_GET_INFO::request &req, COMMAND_RPC_GET_INFO::response &res, const connection_context *ctx=NULL)
bool on_get_net_stats (const COMMAND_RPC_GET_NET_STATS::request &req, COMMAND_RPC_GET_NET_STATS::response &res, const connection_context *ctx=NULL)
bool on_save_bc (const COMMAND_RPC_SAVE_BC::request &req, COMMAND_RPC_SAVE_BC::response &res, const connection_context *ctx=NULL)
bool on_get_peer_list (const COMMAND_RPC_GET_PEER_LIST::request &req, COMMAND_RPC_GET_PEER_LIST::response &res, const connection_context *ctx=NULL)
bool on_set_log_hash_rate (const COMMAND_RPC_SET_LOG_HASH_RATE::request &req, COMMAND_RPC_SET_LOG_HASH_RATE::response &res, const connection_context *ctx=NULL)
bool on_set_log_level (const COMMAND_RPC_SET_LOG_LEVEL::request &req, COMMAND_RPC_SET_LOG_LEVEL::response &res, const connection_context *ctx=NULL)
bool on_set_log_categories (const COMMAND_RPC_SET_LOG_CATEGORIES::request &req, COMMAND_RPC_SET_LOG_CATEGORIES::response &res, const connection_context *ctx=NULL)
bool on_get_transaction_pool (const COMMAND_RPC_GET_TRANSACTION_POOL::request &req, COMMAND_RPC_GET_TRANSACTION_POOL::response &res, const connection_context *ctx=NULL)
bool on_get_transaction_pool_hashes_bin (const COMMAND_RPC_GET_TRANSACTION_POOL_HASHES_BIN::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_HASHES_BIN::response &res, const connection_context *ctx=NULL)
bool on_get_transaction_pool_hashes (const COMMAND_RPC_GET_TRANSACTION_POOL_HASHES::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_HASHES::response &res, const connection_context *ctx=NULL)
bool on_get_transaction_pool_stats (const COMMAND_RPC_GET_TRANSACTION_POOL_STATS::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_STATS::response &res, const connection_context *ctx=NULL)
bool on_stop_daemon (const COMMAND_RPC_STOP_DAEMON::request &req, COMMAND_RPC_STOP_DAEMON::response &res, const connection_context *ctx=NULL)
bool on_get_limit (const COMMAND_RPC_GET_LIMIT::request &req, COMMAND_RPC_GET_LIMIT::response &res, const connection_context *ctx=NULL)
bool on_set_limit (const COMMAND_RPC_SET_LIMIT::request &req, COMMAND_RPC_SET_LIMIT::response &res, const connection_context *ctx=NULL)
bool on_out_peers (const COMMAND_RPC_OUT_PEERS::request &req, COMMAND_RPC_OUT_PEERS::response &res, const connection_context *ctx=NULL)
bool on_in_peers (const COMMAND_RPC_IN_PEERS::request &req, COMMAND_RPC_IN_PEERS::response &res, const connection_context *ctx=NULL)
bool on_start_save_graph (const COMMAND_RPC_START_SAVE_GRAPH::request &req, COMMAND_RPC_START_SAVE_GRAPH::response &res, const connection_context *ctx=NULL)
bool on_stop_save_graph (const COMMAND_RPC_STOP_SAVE_GRAPH::request &req, COMMAND_RPC_STOP_SAVE_GRAPH::response &res, const connection_context *ctx=NULL)
bool on_update (const COMMAND_RPC_UPDATE::request &req, COMMAND_RPC_UPDATE::response &res, const connection_context *ctx=NULL)
bool on_get_output_distribution_bin (const COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::request &req, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::response &res, const connection_context *ctx=NULL)
bool on_pop_blocks (const COMMAND_RPC_POP_BLOCKS::request &req, COMMAND_RPC_POP_BLOCKS::response &res, const connection_context *ctx=NULL)
bool on_get_balance (const COMMAND_RPC_GET_BALANCE::request &req, COMMAND_RPC_GET_BALANCE::response &res, const connection_context *ctx=NULL)
bool on_get_address_batch_history (const COMMAND_RPC_GET_ADDRESS_BATCH_HISTORY::request &req, COMMAND_RPC_GET_ADDRESS_BATCH_HISTORY::response &res, const connection_context *ctx=NULL)
bool on_get_addr_tx_batch_history (const COMMAND_RPC_GET_ADDR_TX_BATCH_HISTORY::request &req, COMMAND_RPC_GET_ADDR_TX_BATCH_HISTORY::response &res, const connection_context *ctx=NULL)
bool on_get_tax_data (const COMMAND_RPC_GET_TAX_DATA::request &req, COMMAND_RPC_GET_TAX_DATA::response &res, const connection_context *ctx=NULL)
bool on_getblockcount (const COMMAND_RPC_GETBLOCKCOUNT::request &req, COMMAND_RPC_GETBLOCKCOUNT::response &res, const connection_context *ctx=NULL)
bool on_getblockhash (const COMMAND_RPC_GETBLOCKHASH::request &req, COMMAND_RPC_GETBLOCKHASH::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_getblocktemplate (const COMMAND_RPC_GETBLOCKTEMPLATE::request &req, COMMAND_RPC_GETBLOCKTEMPLATE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_submitblock (const COMMAND_RPC_SUBMITBLOCK::request &req, COMMAND_RPC_SUBMITBLOCK::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_generateblocks (const COMMAND_RPC_GENERATEBLOCKS::request &req, COMMAND_RPC_GENERATEBLOCKS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_last_block_header (const COMMAND_RPC_GET_LAST_BLOCK_HEADER::request &req, COMMAND_RPC_GET_LAST_BLOCK_HEADER::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_block_header_by_hash (const COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH::request &req, COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_block_header_by_height (const COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT::request &req, COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_block_headers_range (const COMMAND_RPC_GET_BLOCK_HEADERS_RANGE::request &req, COMMAND_RPC_GET_BLOCK_HEADERS_RANGE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_block (const COMMAND_RPC_GET_BLOCK::request &req, COMMAND_RPC_GET_BLOCK::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_connections (const COMMAND_RPC_GET_CONNECTIONS::request &req, COMMAND_RPC_GET_CONNECTIONS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_info_json (const COMMAND_RPC_GET_INFO::request &req, COMMAND_RPC_GET_INFO::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_hard_fork_info (const COMMAND_RPC_HARD_FORK_INFO::request &req, COMMAND_RPC_HARD_FORK_INFO::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_set_bans (const COMMAND_RPC_SETBANS::request &req, COMMAND_RPC_SETBANS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_bans (const COMMAND_RPC_GETBANS::request &req, COMMAND_RPC_GETBANS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_flush_txpool (const COMMAND_RPC_FLUSH_TRANSACTION_POOL::request &req, COMMAND_RPC_FLUSH_TRANSACTION_POOL::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_output_histogram (const COMMAND_RPC_GET_OUTPUT_HISTOGRAM::request &req, COMMAND_RPC_GET_OUTPUT_HISTOGRAM::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_version (const COMMAND_RPC_GET_VERSION::request &req, COMMAND_RPC_GET_VERSION::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_coinbase_tx_sum (const COMMAND_RPC_GET_COINBASE_TX_SUM::request &req, COMMAND_RPC_GET_COINBASE_TX_SUM::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_base_fee_estimate (const COMMAND_RPC_GET_BASE_FEE_ESTIMATE::request &req, COMMAND_RPC_GET_BASE_FEE_ESTIMATE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_alternate_chains (const COMMAND_RPC_GET_ALTERNATE_CHAINS::request &req, COMMAND_RPC_GET_ALTERNATE_CHAINS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_relay_tx (const COMMAND_RPC_RELAY_TX::request &req, COMMAND_RPC_RELAY_TX::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_sync_info (const COMMAND_RPC_SYNC_INFO::request &req, COMMAND_RPC_SYNC_INFO::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_get_txpool_backlog (const COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool 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, const connection_context *ctx=NULL)
bool on_prune_blockchain (const COMMAND_RPC_PRUNE_BLOCKCHAIN::request &req, COMMAND_RPC_PRUNE_BLOCKCHAIN::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_set_validator_key (const COMMAND_RPC_SET_VALIDATOR_KEY::request &req, COMMAND_RPC_SET_VALIDATOR_KEY::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_generate_ed25519_keypair (const COMMAND_RPC_GENERATE_ED25519_KEYPAIR::request &req, COMMAND_RPC_GENERATE_ED25519_KEYPAIR::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_sign_message (const COMMAND_RPC_SIGN_MESSAGE::request &req, COMMAND_RPC_SIGN_MESSAGE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_inject_emergency_vlist (const COMMAND_RPC_INJECT_EMERGENCY_VLIST::request &req, COMMAND_RPC_INJECT_EMERGENCY_VLIST::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Public Member Functions inherited from epee::http_server_impl_base< core_rpc_server >
 http_server_impl_base ()
bool init (std::function< void(size_t, uint8_t *)> rng, const std::string &bind_port="0", const std::string &bind_ip="0.0.0.0", std::vector< std::string > access_control_origins=std::vector< std::string >(), boost::optional< net_utils::http::login > user=boost::none, net_utils::ssl_options_t ssl_options=net_utils::ssl_support_t::e_ssl_support_autodetect)
bool run (size_t threads_count, bool wait=true)
bool deinit ()
bool timed_wait_server_stop (uint64_t ms)
bool send_stop_signal ()
int get_binded_port ()
long get_connections_count () const
Public Member Functions inherited from epee::net_utils::http::i_http_server_handler< epee::net_utils::connection_context_base >
virtual ~i_http_server_handler ()
virtual bool handle_http_request (const http_request_info &query_info, http_response_info &response, epee::net_utils::connection_context_base &m_conn_context)=0
virtual bool init_server_thread ()
virtual bool deinit_server_thread ()

Static Public Member Functions

static void init_options (boost::program_options::options_description &desc)

Static Public Attributes

static const command_line::arg_descriptor< bool > arg_public_node
static const command_line::arg_descriptor< std::string, false, true, 2 > arg_rpc_bind_port
static const command_line::arg_descriptor< std::string > arg_rpc_restricted_bind_port
static const command_line::arg_descriptor< bool > arg_restricted_rpc
static const command_line::arg_descriptor< std::string > arg_rpc_ssl
static const command_line::arg_descriptor< std::string > arg_rpc_ssl_private_key
static const command_line::arg_descriptor< std::string > arg_rpc_ssl_certificate
static const command_line::arg_descriptor< std::string > arg_rpc_ssl_ca_certificates
static const command_line::arg_descriptor< std::vector< std::string > > arg_rpc_ssl_allowed_fingerprints
static const command_line::arg_descriptor< bool > arg_rpc_ssl_allow_any_cert
static const command_line::arg_descriptor< std::string > arg_bootstrap_daemon_address
static const command_line::arg_descriptor< std::string > arg_bootstrap_daemon_login

Additional Inherited Members

Protected Attributes inherited from epee::http_server_impl_base< core_rpc_server >
net_utils::boosted_tcp_server< net_utils::http::http_custom_handler< epee::net_utils::connection_context_base > > m_net_server

Detailed Description

Definition at line 58 of file core_rpc_server.h.

Member Typedef Documentation

◆ connection_context

Constructor & Destructor Documentation

◆ core_rpc_server()

cryptonote::core_rpc_server::core_rpc_server ( core & cr,
nodetool::node_server< cryptonote::t_cryptonote_protocol_handler< cryptonote::core > > & p2p )

Definition at line 107 of file core_rpc_server.cpp.

111 : m_core(cr)
112 , m_p2p(p2p)
113 {}
Here is the caller graph for this function:

Member Function Documentation

◆ CHAIN_HTTP_TO_MAP2()

cryptonote::core_rpc_server::CHAIN_HTTP_TO_MAP2 ( connection_context )

◆ init()

bool cryptonote::core_rpc_server::init ( const boost::program_options::variables_map & vm,
const bool restricted,
const std::string & port )

Definition at line 115 of file core_rpc_server.cpp.

120 {
121 m_restricted = restricted;
122 m_net_server.set_threads_prefix("RPC");
123
124 auto rpc_config = cryptonote::rpc_args::process(vm, true);
125 if (!rpc_config)
126 return false;
127
128 m_bootstrap_daemon_address = command_line::get_arg(vm, arg_bootstrap_daemon_address);
129 if (!m_bootstrap_daemon_address.empty())
130 {
131 const std::string &bootstrap_daemon_login = command_line::get_arg(vm, arg_bootstrap_daemon_login);
132 const auto loc = bootstrap_daemon_login.find(':');
133 if (!bootstrap_daemon_login.empty() && loc != std::string::npos)
134 {
135 epee::net_utils::http::login login;
136 login.username = bootstrap_daemon_login.substr(0, loc);
137 login.password = bootstrap_daemon_login.substr(loc + 1);
138 m_http_client.set_server(m_bootstrap_daemon_address, login, epee::net_utils::ssl_support_t::e_ssl_support_autodetect);
139 }
140 else
141 {
142 m_http_client.set_server(m_bootstrap_daemon_address, boost::none, epee::net_utils::ssl_support_t::e_ssl_support_autodetect);
143 }
144 m_should_use_bootstrap_daemon = true;
145 }
146 else
147 {
148 m_should_use_bootstrap_daemon = false;
149 }
150 m_was_bootstrap_ever_used = false;
151
152 boost::optional<epee::net_utils::http::login> http_login{};
153
154 if (rpc_config->login)
155 http_login.emplace(std::move(rpc_config->login->username), std::move(rpc_config->login->password).password());
156
157 auto rng = [](size_t len, uint8_t *ptr){ return crypto::rand(len, ptr); };
159 rng, std::move(port), std::move(rpc_config->bind_ip), std::move(rpc_config->access_control_origins), std::move(http_login), std::move(rpc_config->ssl_options)
160 );
161 }
static const command_line::arg_descriptor< std::string > arg_bootstrap_daemon_address
static const command_line::arg_descriptor< std::string > arg_bootstrap_daemon_login
bool init(std::function< void(size_t, uint8_t *)> rng, const std::string &bind_port="0", const std::string &bind_ip="0.0.0.0", std::vector< std::string > access_control_origins=std::vector< std::string >(), boost::optional< net_utils::http::login > user=boost::none, net_utils::ssl_options_t ssl_options=net_utils::ssl_support_t::e_ssl_support_autodetect)
net_utils::boosted_tcp_server< net_utils::http::http_custom_handler< epee::net_utils::connection_context_base > > m_net_server
T get_arg(const boost::program_options::variables_map &vm, const arg_descriptor< T, false, true > &arg)
std::enable_if< std::is_pod< T >::value, T >::type rand()
Definition crypto.h:216
unsigned char uint8_t
Definition stdint.h:124
static boost::optional< rpc_args > process(const boost::program_options::variables_map &vm, const bool any_cert_option=false)
Definition rpc_args.cpp:125
wipeable_string password
Definition http_auth.h:57
Here is the call graph for this function:

◆ init_options()

void cryptonote::core_rpc_server::init_options ( boost::program_options::options_description & desc)
static

Definition at line 97 of file core_rpc_server.cpp.

98 {
105 }
static const command_line::arg_descriptor< std::string, false, true, 2 > arg_rpc_bind_port
static const command_line::arg_descriptor< std::string > arg_rpc_restricted_bind_port
static const command_line::arg_descriptor< bool > arg_restricted_rpc
void add_arg(boost::program_options::options_description &description, const arg_descriptor< T, required, dependent, NUM_DEPS > &arg, bool unique=true)
static void init_options(boost::program_options::options_description &desc, const bool any_cert_option=false)
Definition rpc_args.cpp:108
Here is the call graph for this function:
Here is the caller graph for this function:

◆ nettype()

network_type cryptonote::core_rpc_server::nettype ( ) const
inline

Definition at line 88 of file core_rpc_server.h.

88{ return m_core.get_nettype(); }
Here is the caller graph for this function:

◆ on_flush_txpool()

bool cryptonote::core_rpc_server::on_flush_txpool ( const COMMAND_RPC_FLUSH_TRANSACTION_POOL::request & req,
COMMAND_RPC_FLUSH_TRANSACTION_POOL::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2091 of file core_rpc_server.cpp.

2092 {
2094
2095 bool failed = false;
2096 std::vector<crypto::hash> txids;
2097 if (req.txids.empty())
2098 {
2099 std::vector<transaction> pool_txs;
2100 bool r = m_core.get_pool_transactions(pool_txs);
2101 if (!r)
2102 {
2103 res.status = "Failed to get txpool contents";
2104 return true;
2105 }
2106 for (const auto &tx: pool_txs)
2107 {
2108 txids.push_back(cryptonote::get_transaction_hash(tx));
2109 }
2110 }
2111 else
2112 {
2113 for (const auto &str: req.txids)
2114 {
2115 cryptonote::blobdata txid_data;
2117 {
2118 failed = true;
2119 }
2120 else
2121 {
2122 crypto::hash txid = *reinterpret_cast<const crypto::hash*>(txid_data.data());
2123 txids.push_back(txid);
2124 }
2125 }
2126 }
2127 if (!m_core.get_blockchain_storage().flush_txes_from_pool(txids))
2128 {
2129 res.status = "Failed to remove one or more tx(es)";
2130 return false;
2131 }
2132
2133 if (failed)
2134 {
2135 if (txids.empty())
2136 res.status = "Failed to parse txid";
2137 else
2138 res.status = "Failed to parse some of the txids";
2139 return false;
2140 }
2141
2142 res.status = CORE_RPC_STATUS_OK;
2143 return true;
2144 }
bool on_flush_txpool(const COMMAND_RPC_FLUSH_TRANSACTION_POOL::request &req, COMMAND_RPC_FLUSH_TRANSACTION_POOL::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
#define CORE_RPC_STATUS_OK
const char * res
POD_CLASS hash
Definition hash.h:50
crypto::hash get_transaction_hash(const transaction &t)
std::string blobdata
bool parse_hexstr_to_binbuff(const epee::span< const char > s, epee::span< char > &res)
#define PERF_TIMER(name)
Definition perf_timer.h:82
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_generate_ed25519_keypair()

bool cryptonote::core_rpc_server::on_generate_ed25519_keypair ( const COMMAND_RPC_GENERATE_ED25519_KEYPAIR::request & req,
COMMAND_RPC_GENERATE_ED25519_KEYPAIR::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2624 of file core_rpc_server.cpp.

2625 {
2626 std::vector<std::string> v = m_core.generate_ed25519_keypair();
2627 if(v.size() == 0) {
2629 error_resp.message = "Failed to generate ED25519-Donna keypair.";
2630 return false;
2631 }
2632
2633 res.privateKey = v[0];
2634 res.publicKey = v[1];
2635
2636 res.status = CORE_RPC_STATUS_OK;
2637 return true;
2638 }
#define CORE_RPC_ERROR_CODE_INTERNAL_ERROR
Here is the caller graph for this function:

◆ on_generateblocks()

bool cryptonote::core_rpc_server::on_generateblocks ( const COMMAND_RPC_GENERATEBLOCKS::request & req,
COMMAND_RPC_GENERATEBLOCKS::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1480 of file core_rpc_server.cpp.

1481 {
1483
1485
1486 res.status = CORE_RPC_STATUS_OK;
1487
1488 if(m_core.get_nettype() != FAKECHAIN)
1489 {
1491 error_resp.message = "Regtest required when generating blocks";
1492 return false;
1493 }
1494
1499
1500 template_req.reserve_size = 1;
1501 template_req.wallet_address = req.wallet_address;
1502 template_req.prev_block = req.prev_block;
1503 submit_req.push_back(boost::value_initialized<std::string>());
1504 res.height = m_core.get_blockchain_storage().get_current_blockchain_height();
1505
1506 for(size_t i = 0; i < req.amount_of_blocks; i++)
1507 {
1508 bool r = on_getblocktemplate(template_req, template_res, error_resp, ctx);
1509 res.status = template_res.status;
1510 template_req.prev_block.clear();
1511
1512 if (!r) return false;
1513
1514 blobdata blockblob;
1515 if(!string_tools::parse_hexstr_to_binbuff(template_res.blocktemplate_blob, blockblob))
1516 {
1518 error_resp.message = "Wrong block blob";
1519 return false;
1520 }
1521 block b;
1522 if(!parse_and_validate_block_from_blob(blockblob, b))
1523 {
1525 error_resp.message = "Wrong block blob";
1526 return false;
1527 }
1528 b.nonce = req.starting_nonce;
1529 miner::find_nonce_for_given_block(b, template_res.difficulty, template_res.height);
1530
1531 submit_req.front() = string_tools::buff_to_hex_nodelimer(block_to_blob(b));
1532 r = on_submitblock(submit_req, submit_res, error_resp, ctx);
1533 res.status = submit_res.status;
1534
1535 if (!r) return false;
1536
1538 template_req.prev_block = res.blocks.back();
1539 res.height = template_res.height;
1540 }
1541
1542 return true;
1543 }
bool on_submitblock(const COMMAND_RPC_SUBMITBLOCK::request &req, COMMAND_RPC_SUBMITBLOCK::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_getblocktemplate(const COMMAND_RPC_GETBLOCKTEMPLATE::request &req, COMMAND_RPC_GETBLOCKTEMPLATE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool on_generateblocks(const COMMAND_RPC_GENERATEBLOCKS::request &req, COMMAND_RPC_GENERATEBLOCKS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
static bool find_nonce_for_given_block(block &bl, const difficulty_type &diffic, uint64_t height)
Definition miner.cpp:478
#define CHECK_CORE_READY()
#define CORE_RPC_ERROR_CODE_WRONG_BLOCKBLOB
#define CORE_RPC_ERROR_CODE_REGTEST_REQUIRED
bool get_block_hash(const block &b, crypto::hash &res)
bool parse_and_validate_block_from_blob(const blobdata &b_blob, block &b, crypto::hash *block_hash)
blobdata block_to_blob(const block &b)
std::string pod_to_hex(const t_pod_type &s)
std::string buff_to_hex_nodelimer(const std::string &src)
epee::misc_utils::struct_init< response_t > response
epee::misc_utils::struct_init< request_t > request
epee::misc_utils::struct_init< response_t > response
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_addr_tx_batch_history()

bool cryptonote::core_rpc_server::on_get_addr_tx_batch_history ( const COMMAND_RPC_GET_ADDR_TX_BATCH_HISTORY::request & req,
COMMAND_RPC_GET_ADDR_TX_BATCH_HISTORY::response & res,
const connection_context * ctx = NULL )

Definition at line 1944 of file core_rpc_server.cpp.

1945 {
1948
1949 if (req.etn_address.empty())
1950 {
1951 res.status = "Failed: Request attribute <etn_address> is mandatory.";
1952 return true;
1953 }
1954
1955 address_parse_info addr_info;
1956 if(!get_account_address_from_str(addr_info, nettype(), req.etn_address))
1957 {
1958 res.status = "Failed: can't parse address from <etn_address> = " + req.etn_address;
1959 return true;
1960 }
1961
1962 try
1963 {
1964 std::vector<address_txs> addr_txs = m_core.get_addr_tx_batch_history(addr_info, req.start_addr_tx_id, req.batch_size, req.desc);
1965 if(!addr_txs.empty() && addr_txs.size() > req.batch_size)
1966 {
1967 res.next_addr_tx_id = addr_txs.at(addr_txs.size() - 1).addr_tx_id;
1968 res.last_page = false;
1969 addr_txs.pop_back();
1970 }
1971 else
1972 {
1973 res.last_page = true;
1974 }
1975
1976 for(auto addr_tx: addr_txs)
1977 {
1978 res.txs.push_back(epee::string_tools::pod_to_hex(addr_tx.tx_hash));
1979 }
1980
1981 res.status = "OK";
1982 }
1983 catch(const std::exception& e)
1984 {
1985 res.status = "Failed: " + std::string(e.what());
1986 return true;
1987 }
1988
1989 return true;
1990 }
bool on_get_addr_tx_batch_history(const COMMAND_RPC_GET_ADDR_TX_BATCH_HISTORY::request &req, COMMAND_RPC_GET_ADDR_TX_BATCH_HISTORY::response &res, const connection_context *ctx=NULL)
network_type nettype() const
bool get_account_address_from_str(address_parse_info &info, network_type nettype, std::string const &str)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_address_batch_history()

bool cryptonote::core_rpc_server::on_get_address_batch_history ( const COMMAND_RPC_GET_ADDRESS_BATCH_HISTORY::request & req,
COMMAND_RPC_GET_ADDRESS_BATCH_HISTORY::response & res,
const connection_context * ctx = NULL )

Definition at line 1896 of file core_rpc_server.cpp.

1897 {
1900
1901 if (req.etn_address.empty())
1902 {
1903 res.status = "Failed: Request attribute <etn_address> is mandatory.";
1904 return true;
1905 }
1906
1907 address_parse_info addr_info;
1908 if(!get_account_address_from_str(addr_info, nettype(), req.etn_address))
1909 {
1910 res.status = "Failed: can't parse address from <etn_address> = " + req.etn_address;
1911 return true;
1912 }
1913
1914 try
1915 {
1916 std::vector<address_outputs> outs = m_core.get_address_batch_history(addr_info, req.start_out_id, req.batch_size, req.desc);
1917 if(!outs.empty() && outs.size() > req.batch_size)
1918 {
1919 res.next_out_id = outs.at(outs.size() - 1).out_id;
1920 res.last_page = false;
1921 outs.pop_back();
1922 }
1923 else
1924 {
1925 res.last_page = true;
1926 }
1927
1928 for(auto out: outs)
1929 {
1930 res.txs.push_back(epee::string_tools::pod_to_hex(out.tx_hash));
1931 }
1932
1933 res.status = "OK";
1934 }
1935 catch(const std::exception& e)
1936 {
1937 res.status = "Failed: " + std::string(e.what());
1938 return true;
1939 }
1940
1941 return true;
1942 }
bool on_get_address_batch_history(const COMMAND_RPC_GET_ADDRESS_BATCH_HISTORY::request &req, COMMAND_RPC_GET_ADDRESS_BATCH_HISTORY::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_alt_blocks_hashes()

bool cryptonote::core_rpc_server::on_get_alt_blocks_hashes ( const COMMAND_RPC_GET_ALT_BLOCKS_HASHES::request & req,
COMMAND_RPC_GET_ALT_BLOCKS_HASHES::response & res,
const connection_context * ctx = NULL )

Definition at line 364 of file core_rpc_server.cpp.

365 {
367 bool r;
368 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_ALT_BLOCKS_HASHES>(invoke_http_mode::JON, "/get_alt_blocks_hashes", req, res, r))
369 return r;
370
371 std::vector<block> blks;
372
373 if(!m_core.get_alternative_blocks(blks))
374 {
375 res.status = "Failed";
376 return false;
377 }
378
379 res.blks_hashes.reserve(blks.size());
380
381 for (auto const& blk: blks)
382 {
383 res.blks_hashes.push_back(epee::string_tools::pod_to_hex(get_block_hash(blk)));
384 }
385
386 MDEBUG("on_get_alt_blocks_hashes: " << blks.size() << " blocks " );
387 res.status = CORE_RPC_STATUS_OK;
388 return true;
389 }
bool on_get_alt_blocks_hashes(const COMMAND_RPC_GET_ALT_BLOCKS_HASHES::request &req, COMMAND_RPC_GET_ALT_BLOCKS_HASHES::response &res, const connection_context *ctx=NULL)
#define MDEBUG(x)
Definition misc_log_ex.h:76
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_alternate_chains()

bool cryptonote::core_rpc_server::on_get_alternate_chains ( const COMMAND_RPC_GET_ALTERNATE_CHAINS::request & req,
COMMAND_RPC_GET_ALTERNATE_CHAINS::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2218 of file core_rpc_server.cpp.

2219 {
2221 try
2222 {
2223 std::list<std::pair<Blockchain::block_extended_info, std::vector<crypto::hash>>> chains = m_core.get_blockchain_storage().get_alternative_chains();
2224 for (const auto &i: chains)
2225 {
2226 difficulty_type wdiff = i.first.cumulative_difficulty;
2227 res.chains.push_back(COMMAND_RPC_GET_ALTERNATE_CHAINS::chain_info{epee::string_tools::pod_to_hex(get_block_hash(i.first.bl)), i.first.height, i.second.size(), 0, "", 0, {}, std::string()});
2228 store_difficulty(wdiff, res.chains.back().difficulty, res.chains.back().wide_difficulty, res.chains.back().difficulty_top64);
2229 res.chains.back().block_hashes.reserve(i.second.size());
2230 for (const crypto::hash &block_id: i.second)
2231 res.chains.back().block_hashes.push_back(epee::string_tools::pod_to_hex(block_id));
2232 if (i.first.height < i.second.size())
2233 {
2234 res.status = "Error finding alternate chain attachment point";
2235 return true;
2236 }
2237 cryptonote::block main_chain_parent_block;
2238 try { main_chain_parent_block = m_core.get_blockchain_storage().get_db().get_block_from_height(i.first.height - i.second.size()); }
2239 catch (const std::exception &e) { res.status = "Error finding alternate chain attachment point"; return true; }
2240 res.chains.back().main_chain_parent_block = epee::string_tools::pod_to_hex(get_block_hash(main_chain_parent_block));
2241 }
2242 res.status = CORE_RPC_STATUS_OK;
2243 }
2244 catch (...)
2245 {
2246 res.status = "Error retrieving alternate chains";
2247 }
2248 return true;
2249 }
bool on_get_alternate_chains(const COMMAND_RPC_GET_ALTERNATE_CHAINS::request &req, COMMAND_RPC_GET_ALTERNATE_CHAINS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
boost::multiprecision::uint128_t difficulty_type
Definition difficulty.h:43
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_balance()

bool cryptonote::core_rpc_server::on_get_balance ( const COMMAND_RPC_GET_BALANCE::request & req,
COMMAND_RPC_GET_BALANCE::response & res,
const connection_context * ctx = NULL )

Definition at line 1871 of file core_rpc_server.cpp.

1872 {
1874
1876
1877 if (req.etn_address.empty())
1878 {
1879 res.status = "Failed: Request attribute <etn_address> is mandatory.";
1880 return true;
1881 }
1882
1883 address_parse_info addr_info;
1884 if(!get_account_address_from_str(addr_info, nettype(), req.etn_address))
1885 {
1886 res.status = "Failed: can't parse address from <etn_address> = " + req.etn_address;
1887 return true;
1888 }
1889
1890 res.balance = m_core.get_balance(addr_info);
1891 res.status = "OK";
1892
1893 return true;
1894 }
bool on_get_balance(const COMMAND_RPC_GET_BALANCE::request &req, COMMAND_RPC_GET_BALANCE::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_bans()

bool cryptonote::core_rpc_server::on_get_bans ( const COMMAND_RPC_GETBANS::request & req,
COMMAND_RPC_GETBANS::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2024 of file core_rpc_server.cpp.

2025 {
2027
2028 auto now = time(nullptr);
2029 std::map<std::string, time_t> blocked_hosts = m_p2p.get_blocked_hosts();
2030 for (std::map<std::string, time_t>::const_iterator i = blocked_hosts.begin(); i != blocked_hosts.end(); ++i)
2031 {
2032 if (i->second > now) {
2033 COMMAND_RPC_GETBANS::ban b;
2034 b.host = i->first;
2035 b.ip = 0;
2036 uint32_t ip;
2038 b.ip = ip;
2039 b.seconds = i->second - now;
2040 res.bans.push_back(b);
2041 }
2042 }
2043
2044 res.status = CORE_RPC_STATUS_OK;
2045 return true;
2046 }
time_t time
bool on_get_bans(const COMMAND_RPC_GETBANS::request &req, COMMAND_RPC_GETBANS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
bool get_ip_int32_from_string(uint32_t &ip, const std::string &ip_str)
unsigned int uint32_t
Definition stdint.h:126
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_base_fee_estimate()

bool cryptonote::core_rpc_server::on_get_base_fee_estimate ( const COMMAND_RPC_GET_BASE_FEE_ESTIMATE::request & req,
COMMAND_RPC_GET_BASE_FEE_ESTIMATE::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2205 of file core_rpc_server.cpp.

2206 {
2208 bool r;
2209 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BASE_FEE_ESTIMATE>(invoke_http_mode::JON_RPC, "get_fee_estimate", req, res, r))
2210 return r;
2211
2212 res.fee = m_core.get_blockchain_storage().get_dynamic_base_fee_estimate(req.grace_blocks);
2213 res.quantization_mask = Blockchain::get_fee_quantization_mask();
2214 res.status = CORE_RPC_STATUS_OK;
2215 return true;
2216 }
static uint64_t get_fee_quantization_mask()
get fee quantization mask
bool on_get_base_fee_estimate(const COMMAND_RPC_GET_BASE_FEE_ESTIMATE::request &req, COMMAND_RPC_GET_BASE_FEE_ESTIMATE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_block()

bool cryptonote::core_rpc_server::on_get_block ( const COMMAND_RPC_GET_BLOCK::request & req,
COMMAND_RPC_GET_BLOCK::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1807 of file core_rpc_server.cpp.

1808 {
1810 bool r;
1811 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BLOCK>(invoke_http_mode::JON_RPC, "getblock", req, res, r))
1812 return r;
1813
1814 crypto::hash block_hash;
1815 if (!req.hash.empty())
1816 {
1817 bool hash_parsed = parse_hash256(req.hash, block_hash);
1818 if(!hash_parsed)
1819 {
1821 error_resp.message = "Failed to parse hex representation of block hash. Hex = " + req.hash + '.';
1822 return false;
1823 }
1824 }
1825 else
1826 {
1827 if(m_core.get_current_blockchain_height() <= req.height)
1828 {
1830 error_resp.message = std::string("Requested block height: ") + std::to_string(req.height) + " greater than current top block height: " + std::to_string(m_core.get_current_blockchain_height() - 1);
1831 return false;
1832 }
1833 block_hash = m_core.get_block_id_by_height(req.height);
1834 }
1835 block blk;
1836 bool orphan = false;
1837 bool have_block = m_core.get_block_by_hash(block_hash, blk, &orphan);
1838 if (!have_block)
1839 {
1841 error_resp.message = "Internal error: can't get block by hash. Hash = " + req.hash + '.';
1842 return false;
1843 }
1844 if (blk.miner_tx.vin.size() != 1 || blk.miner_tx.vin.front().type() != typeid(txin_gen))
1845 {
1847 error_resp.message = "Internal error: coinbase transaction in the block has the wrong type";
1848 return false;
1849 }
1850 uint64_t block_height = boost::get<txin_gen>(blk.miner_tx.vin.front()).height;
1851 const bool restricted = m_restricted && ctx;
1852 bool response_filled = fill_block_header_response(blk, orphan, block_height, block_hash, res.block_header, req.fill_pow_hash && !restricted);
1853 if (!response_filled)
1854 {
1856 error_resp.message = "Internal error: can't produce valid response.";
1857 return false;
1858 }
1860 for (size_t n = 0; n < blk.tx_hashes.size(); ++n)
1861 {
1862 res.tx_hashes.push_back(epee::string_tools::pod_to_hex(blk.tx_hashes[n]));
1863 }
1865 res.json = obj_to_json_str(blk);
1866 res.status = CORE_RPC_STATUS_OK;
1867
1868 return true;
1869 }
bool on_get_block(const COMMAND_RPC_GET_BLOCK::request &req, COMMAND_RPC_GET_BLOCK::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
#define CORE_RPC_ERROR_CODE_TOO_BIG_HEIGHT
#define CORE_RPC_ERROR_CODE_WRONG_PARAM
bool parse_hash256(const std::string &str_hash, crypto::hash &hash)
std::string obj_to_json_str(T &obj)
bool t_serializable_object_to_blob(const t_object &to, blobdata &b_blob)
unsigned __int64 uint64_t
Definition stdint.h:136
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_block_header_by_hash()

bool cryptonote::core_rpc_server::on_get_block_header_by_hash ( const COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH::request & req,
COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1678 of file core_rpc_server.cpp.

1679 {
1681 bool r;
1682 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH>(invoke_http_mode::JON_RPC, "getblockheaderbyhash", req, res, r))
1683 return r;
1684
1685 crypto::hash block_hash;
1686 bool hash_parsed = parse_hash256(req.hash, block_hash);
1687 if(!hash_parsed)
1688 {
1690 error_resp.message = "Failed to parse hex representation of block hash. Hex = " + req.hash + '.';
1691 return false;
1692 }
1693 block blk;
1694 bool orphan = false;
1695 bool have_block = m_core.get_block_by_hash(block_hash, blk, &orphan);
1696 if (!have_block)
1697 {
1699 error_resp.message = "Internal error: can't get block by hash. Hash = " + req.hash + '.';
1700 return false;
1701 }
1702 if (blk.miner_tx.vin.size() != 1 || blk.miner_tx.vin.front().type() != typeid(txin_gen))
1703 {
1705 error_resp.message = "Internal error: coinbase transaction in the block has the wrong type";
1706 return false;
1707 }
1708 uint64_t block_height = boost::get<txin_gen>(blk.miner_tx.vin.front()).height;
1709 const bool restricted = m_restricted && ctx;
1710 bool response_filled = fill_block_header_response(blk, orphan, block_height, block_hash, res.block_header, req.fill_pow_hash && !restricted);
1711 if (!response_filled)
1712 {
1714 error_resp.message = "Internal error: can't produce valid response.";
1715 return false;
1716 }
1717 res.status = CORE_RPC_STATUS_OK;
1718 return true;
1719 }
bool on_get_block_header_by_hash(const COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH::request &req, COMMAND_RPC_GET_BLOCK_HEADER_BY_HASH::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_block_header_by_height()

bool cryptonote::core_rpc_server::on_get_block_header_by_height ( const COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT::request & req,
COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1773 of file core_rpc_server.cpp.

1774 {
1776 bool r;
1777 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT>(invoke_http_mode::JON_RPC, "getblockheaderbyheight", req, res, r))
1778 return r;
1779
1780 if(m_core.get_current_blockchain_height() <= req.height)
1781 {
1783 error_resp.message = std::string("Requested block height: ") + std::to_string(req.height) + " greater than current top block height: " + std::to_string(m_core.get_current_blockchain_height() - 1);
1784 return false;
1785 }
1786 crypto::hash block_hash = m_core.get_block_id_by_height(req.height);
1787 block blk;
1788 bool have_block = m_core.get_block_by_hash(block_hash, blk);
1789 if (!have_block)
1790 {
1792 error_resp.message = "Internal error: can't get block by height. Height = " + std::to_string(req.height) + '.';
1793 return false;
1794 }
1795 const bool restricted = m_restricted && ctx;
1796 bool response_filled = fill_block_header_response(blk, false, req.height, block_hash, res.block_header, req.fill_pow_hash && !restricted);
1797 if (!response_filled)
1798 {
1800 error_resp.message = "Internal error: can't produce valid response.";
1801 return false;
1802 }
1803 res.status = CORE_RPC_STATUS_OK;
1804 return true;
1805 }
bool on_get_block_header_by_height(const COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT::request &req, COMMAND_RPC_GET_BLOCK_HEADER_BY_HEIGHT::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_block_headers_range()

bool cryptonote::core_rpc_server::on_get_block_headers_range ( const COMMAND_RPC_GET_BLOCK_HEADERS_RANGE::request & req,
COMMAND_RPC_GET_BLOCK_HEADERS_RANGE::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1721 of file core_rpc_server.cpp.

1722 {
1724 bool r;
1725 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BLOCK_HEADERS_RANGE>(invoke_http_mode::JON_RPC, "getblockheadersrange", req, res, r))
1726 return r;
1727
1728 const uint64_t bc_height = m_core.get_current_blockchain_height();
1729 if (req.start_height >= bc_height || req.end_height >= bc_height || req.start_height > req.end_height)
1730 {
1732 error_resp.message = "Invalid start/end heights.";
1733 return false;
1734 }
1735 for (uint64_t h = req.start_height; h <= req.end_height; ++h)
1736 {
1737 crypto::hash block_hash = m_core.get_block_id_by_height(h);
1738 block blk;
1739 bool have_block = m_core.get_block_by_hash(block_hash, blk);
1740 if (!have_block)
1741 {
1743 error_resp.message = "Internal error: can't get block by height. Height = " + boost::lexical_cast<std::string>(h) + ". Hash = " + epee::string_tools::pod_to_hex(block_hash) + '.';
1744 return false;
1745 }
1746 if (blk.miner_tx.vin.size() != 1 || blk.miner_tx.vin.front().type() != typeid(txin_gen))
1747 {
1749 error_resp.message = "Internal error: coinbase transaction in the block has the wrong type";
1750 return false;
1751 }
1752 uint64_t block_height = boost::get<txin_gen>(blk.miner_tx.vin.front()).height;
1753 if (block_height != h)
1754 {
1756 error_resp.message = "Internal error: coinbase transaction in the block has the wrong height";
1757 return false;
1758 }
1759 res.headers.push_back(block_header_response());
1760 const bool restricted = m_restricted && ctx;
1761 bool response_filled = fill_block_header_response(blk, false, block_height, block_hash, res.headers.back(), req.fill_pow_hash && !restricted);
1762 if (!response_filled)
1763 {
1765 error_resp.message = "Internal error: can't produce valid response.";
1766 return false;
1767 }
1768 }
1769 res.status = CORE_RPC_STATUS_OK;
1770 return true;
1771 }
bool on_get_block_headers_range(const COMMAND_RPC_GET_BLOCK_HEADERS_RANGE::request &req, COMMAND_RPC_GET_BLOCK_HEADERS_RANGE::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_blocks()

bool cryptonote::core_rpc_server::on_get_blocks ( const COMMAND_RPC_GET_BLOCKS_FAST::request & req,
COMMAND_RPC_GET_BLOCKS_FAST::response & res,
const connection_context * ctx = NULL )

Definition at line 285 of file core_rpc_server.cpp.

286 {
288 bool r;
289 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BLOCKS_FAST>(invoke_http_mode::BIN, "/getblocks.bin", req, res, r))
290 return r;
291
292 //Vector of pairs where each pair is: item#1) pair<block blob, hash> item#2)vector of pairs of <tx hash, tx blob>
293 std::vector<
294 std::pair<
295 std::pair<cryptonote::blobdata, crypto::hash>, std::vector<std::pair<crypto::hash, cryptonote::blobdata> >
296 >
297 > bs;
298
299 if(!m_core.find_blockchain_supplement(req.start_height, req.block_ids, bs, res.current_height, res.start_height, req.prune, !req.no_miner_tx, COMMAND_RPC_GET_BLOCKS_FAST_MAX_COUNT))
300 {
301 res.status = "Failed";
302 return false;
303 }
304
305 size_t pruned_size = 0, unpruned_size = 0, ntxes = 0;
306
307 // Preallocate space in the RPC result
308 res.blocks.reserve(bs.size());
309 res.output_indices.reserve(bs.size());
310
311 // Loop over all of the block data and populate the rpc response
312 uint64_t height_counter = res.start_height;
313 for(auto& bd: bs)
314 {
315 res.blocks.resize(res.blocks.size()+1);
316 res.blocks.back().block = bd.first.first; // add block hash to response
317 pruned_size += bd.first.first.size();
318 unpruned_size += bd.first.first.size();
319 res.output_indices.push_back(COMMAND_RPC_GET_BLOCKS_FAST::block_output_indices());
320 ntxes += bd.second.size();
321 res.output_indices.back().indices.reserve(1 + bd.second.size());
322 if (req.no_miner_tx)
323 res.output_indices.back().indices.push_back(COMMAND_RPC_GET_BLOCKS_FAST::tx_output_indices());
324 res.blocks.back().txs.reserve(bd.second.size());
325
326 //go over the transactions in bs first
327 for (std::vector<std::pair<crypto::hash, cryptonote::blobdata>>::iterator i = bd.second.begin(); i != bd.second.end(); ++i)
328 {
329 unpruned_size += i->second.size();
330 res.blocks.back().txs.push_back(std::move(i->second)); //add a tx blob to rpc response
331 i->second.clear();
332 i->second.shrink_to_fit();
333 pruned_size += res.blocks.back().txs.back().size();
334 }
335
336 //no need to look up indexes for v2+ txes
337 auto v10_height = nettype() == cryptonote::network_type::MAINNET ? 1175315 : 1086402;
338 const size_t n_txes_to_lookup = height_counter >= v10_height ? 0 : (bd.second.size() + (req.no_miner_tx ? 0 : 1));
339 if (n_txes_to_lookup > 0)
340 {
341 std::vector<std::vector<uint64_t>> indices;
342 //either pass the first tx hash or the block hash depending on whether it was a miner tx or not
343 bool r = m_core.get_tx_outputs_gindexs(req.no_miner_tx ? bd.second.front().first : bd.first.second, n_txes_to_lookup, indices);
344 if (!r)
345 {
346 res.status = "Failed";
347 return false;
348 }
349 if (indices.size() != n_txes_to_lookup || res.output_indices.back().indices.size() != (req.no_miner_tx ? 1 : 0))
350 {
351 res.status = "Failed";
352 return false;
353 }
354 for (size_t i = 0; i < indices.size(); ++i)
355 res.output_indices.back().indices.push_back({std::move(indices[i])});
356 }
357 ++height_counter;
358 }
359
360 MDEBUG("on_get_blocks: " << bs.size() << " blocks, " << ntxes << " txes, pruned size " << pruned_size << ", unpruned size " << unpruned_size);
361 res.status = CORE_RPC_STATUS_OK;
362 return true;
363 }
bool on_get_blocks(const COMMAND_RPC_GET_BLOCKS_FAST::request &req, COMMAND_RPC_GET_BLOCKS_FAST::response &res, const connection_context *ctx=NULL)
#define COMMAND_RPC_GET_BLOCKS_FAST_MAX_COUNT
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_blocks_by_height()

bool cryptonote::core_rpc_server::on_get_blocks_by_height ( const COMMAND_RPC_GET_BLOCKS_BY_HEIGHT::request & req,
COMMAND_RPC_GET_BLOCKS_BY_HEIGHT::response & res,
const connection_context * ctx = NULL )

Definition at line 391 of file core_rpc_server.cpp.

392 {
394 bool r;
395 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_BLOCKS_BY_HEIGHT>(invoke_http_mode::BIN, "/getblocks_by_height.bin", req, res, r))
396 return r;
397
398 res.status = "Failed";
399 res.blocks.clear();
400 res.blocks.reserve(req.heights.size());
401 for (uint64_t height : req.heights)
402 {
403 block blk;
404 try
405 {
406 blk = m_core.get_blockchain_storage().get_db().get_block_from_height(height);
407 }
408 catch (...)
409 {
410 res.status = "Error retrieving block at height " + std::to_string(height);
411 return true;
412 }
413 std::vector<transaction> txs;
414 std::vector<crypto::hash> missed_txs;
415 m_core.get_transactions(blk.tx_hashes, txs, missed_txs);
416 res.blocks.resize(res.blocks.size() + 1);
417 res.blocks.back().block = block_to_blob(blk);
418 for (auto& tx : txs)
419 res.blocks.back().txs.push_back(tx_to_blob(tx));
420 }
421 res.status = CORE_RPC_STATUS_OK;
422 return true;
423 }
uint64_t height
bool on_get_blocks_by_height(const COMMAND_RPC_GET_BLOCKS_BY_HEIGHT::request &req, COMMAND_RPC_GET_BLOCKS_BY_HEIGHT::response &res, const connection_context *ctx=NULL)
blobdata tx_to_blob(const transaction &tx)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_coinbase_tx_sum()

bool cryptonote::core_rpc_server::on_get_coinbase_tx_sum ( const COMMAND_RPC_GET_COINBASE_TX_SUM::request & req,
COMMAND_RPC_GET_COINBASE_TX_SUM::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2195 of file core_rpc_server.cpp.

2196 {
2198 std::pair<uint64_t, uint64_t> amounts = m_core.get_coinbase_tx_sum(req.height, req.count);
2199 res.emission_amount = amounts.first;
2200 res.fee_amount = amounts.second;
2201 res.status = CORE_RPC_STATUS_OK;
2202 return true;
2203 }
bool on_get_coinbase_tx_sum(const COMMAND_RPC_GET_COINBASE_TX_SUM::request &req, COMMAND_RPC_GET_COINBASE_TX_SUM::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_connections()

bool cryptonote::core_rpc_server::on_get_connections ( const COMMAND_RPC_GET_CONNECTIONS::request & req,
COMMAND_RPC_GET_CONNECTIONS::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1992 of file core_rpc_server.cpp.

1993 {
1995
1996 res.connections = m_p2p.get_payload_object().get_connections();
1997
1998 res.status = CORE_RPC_STATUS_OK;
1999
2000 return true;
2001 }
bool on_get_connections(const COMMAND_RPC_GET_CONNECTIONS::request &req, COMMAND_RPC_GET_CONNECTIONS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_hashes()

bool cryptonote::core_rpc_server::on_get_hashes ( const COMMAND_RPC_GET_HASHES_FAST::request & req,
COMMAND_RPC_GET_HASHES_FAST::response & res,
const connection_context * ctx = NULL )

Definition at line 425 of file core_rpc_server.cpp.

426 {
428 bool r;
429 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_HASHES_FAST>(invoke_http_mode::BIN, "/gethashes.bin", req, res, r))
430 return r;
431
432 res.start_height = req.start_height;
433 if(!m_core.get_blockchain_storage().find_blockchain_supplement(req.block_ids, res.m_block_ids, res.start_height, res.current_height, false))
434 {
435 res.status = "Failed";
436 return false;
437 }
438
439 res.status = CORE_RPC_STATUS_OK;
440 return true;
441 }
bool on_get_hashes(const COMMAND_RPC_GET_HASHES_FAST::request &req, COMMAND_RPC_GET_HASHES_FAST::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_height()

bool cryptonote::core_rpc_server::on_get_height ( const COMMAND_RPC_GET_HEIGHT::request & req,
COMMAND_RPC_GET_HEIGHT::response & res,
const connection_context * ctx = NULL )

Definition at line 174 of file core_rpc_server.cpp.

175 {
177 bool r;
178 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_HEIGHT>(invoke_http_mode::JON, "/getheight", req, res, r))
179 return r;
180
182 m_core.get_blockchain_top(res.height, hash);
183 ++res.height; // block height to chain height
184 res.hash = string_tools::pod_to_hex(hash);
185 res.status = CORE_RPC_STATUS_OK;
186 return true;
187 }
bool on_get_height(const COMMAND_RPC_GET_HEIGHT::request &req, COMMAND_RPC_GET_HEIGHT::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_indexes()

bool cryptonote::core_rpc_server::on_get_indexes ( const COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES::request & req,
COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES::response & res,
const connection_context * ctx = NULL )

Definition at line 515 of file core_rpc_server.cpp.

516 {
518 bool ok;
519 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES>(invoke_http_mode::BIN, "/get_o_indexes.bin", req, res, ok))
520 return ok;
521
522 bool r = m_core.get_tx_outputs_gindexs(req.txid, res.o_indexes);
523 if(!r)
524 {
525 res.status = "Failed";
526 return true;
527 }
528 res.status = CORE_RPC_STATUS_OK;
529 LOG_PRINT_L2("COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES: [" << res.o_indexes.size() << "]");
530 return true;
531 }
bool on_get_indexes(const COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES::request &req, COMMAND_RPC_GET_TX_GLOBAL_OUTPUTS_INDEXES::response &res, const connection_context *ctx=NULL)
#define LOG_PRINT_L2(x)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_info()

bool cryptonote::core_rpc_server::on_get_info ( const COMMAND_RPC_GET_INFO::request & req,
COMMAND_RPC_GET_INFO::response & res,
const connection_context * ctx = NULL )

Definition at line 189 of file core_rpc_server.cpp.

190 {
192 bool r;
193 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_INFO>(invoke_http_mode::JON, "/getinfo", req, res, r))
194 {
195 res.bootstrap_daemon_address = m_bootstrap_daemon_address;
196 crypto::hash top_hash;
197 m_core.get_blockchain_top(res.height_without_bootstrap, top_hash);
198 ++res.height_without_bootstrap; // turn top block height into blockchain height
199 res.was_bootstrap_ever_used = true;
200 return r;
201 }
202
203 const bool restricted = m_restricted && ctx;
204
205 crypto::hash top_hash;
206 m_core.get_blockchain_top(res.height, top_hash);
207 ++res.height; // turn top block height into blockchain height
208 res.top_block_hash = string_tools::pod_to_hex(top_hash);
209 res.target_height = m_core.get_target_blockchain_height();
210 store_difficulty(m_core.get_blockchain_storage().get_difficulty_for_next_block(), res.difficulty, res.wide_difficulty, res.difficulty_top64);
211 res.target = m_core.get_blockchain_storage().get_difficulty_target();
212 res.tx_count = m_core.get_blockchain_storage().get_total_transactions() - res.height; //without coinbase
213 res.tx_pool_size = m_core.get_pool_transactions_count();
214 res.alt_blocks_count = restricted ? 0 : m_core.get_blockchain_storage().get_alternative_blocks_count();
215 uint64_t total_conn = restricted ? 0 : m_p2p.get_public_connections_count();
216 res.outgoing_connections_count = restricted ? 0 : m_p2p.get_public_outgoing_connections_count();
217 res.incoming_connections_count = restricted ? 0 : (total_conn - res.outgoing_connections_count);
218 res.rpc_connections_count = restricted ? 0 : get_connections_count();
219 res.white_peerlist_size = restricted ? 0 : m_p2p.get_public_white_peers_count();
220 res.grey_peerlist_size = restricted ? 0 : m_p2p.get_public_gray_peers_count();
221
223 res.mainnet = net_type == MAINNET;
224 res.testnet = net_type == TESTNET;
225 res.stagenet = net_type == STAGENET;
226 res.nettype = net_type == MAINNET ? "mainnet" : net_type == TESTNET ? "testnet" : net_type == STAGENET ? "stagenet" : "fakechain";
227 store_difficulty(m_core.get_blockchain_storage().get_db().get_block_cumulative_difficulty(res.height - 1),
228 res.cumulative_difficulty, res.wide_cumulative_difficulty, res.cumulative_difficulty_top64);
229 res.block_size_limit = res.block_weight_limit = m_core.get_blockchain_storage().get_current_cumulative_block_weight_limit();
230 res.block_size_median = res.block_weight_median = m_core.get_blockchain_storage().get_current_cumulative_block_weight_median();
231 res.start_time = restricted ? 0 : (uint64_t)m_core.get_start_time();
232 res.free_space = restricted ? std::numeric_limits<uint64_t>::max() : m_core.get_free_space();
233 res.offline = m_core.offline();
234 res.bootstrap_daemon_address = restricted ? "" : m_bootstrap_daemon_address;
235 res.height_without_bootstrap = restricted ? 0 : res.height;
236 if (restricted)
237 res.was_bootstrap_ever_used = false;
238 else
239 {
240 boost::shared_lock<boost::shared_mutex> lock(m_bootstrap_daemon_mutex);
241 res.was_bootstrap_ever_used = m_was_bootstrap_ever_used;
242 }
243 res.database_size = m_core.get_blockchain_storage().get_db().get_database_size();
244 if (restricted)
245 res.database_size = round_up(res.database_size, 5ull* 1024 * 1024 * 1024);
246 res.update_available = restricted ? false : m_core.is_update_available();
247 res.version = restricted ? "" : ELECTRONEUM_VERSION;
248
249 res.status = CORE_RPC_STATUS_OK;
250
251 res.daemon_release_name = ELECTRONEUM_RELEASE_NAME;
252 res.daemon_version = ELECTRONEUM_VERSION;
253 res.daemon_version_full = ELECTRONEUM_VERSION_FULL;
254 res.daemon_version_tag = ELECTRONEUM_VERSION_TAG;
255 return true;
256 }
else if(0==res)
bool on_get_info(const COMMAND_RPC_GET_INFO::request &req, COMMAND_RPC_GET_INFO::response &res, const connection_context *ctx=NULL)
const char *const ELECTRONEUM_VERSION
const char *const ELECTRONEUM_RELEASE_NAME
const char *const ELECTRONEUM_VERSION_FULL
const char *const ELECTRONEUM_VERSION_TAG
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_info_json()

bool cryptonote::core_rpc_server::on_get_info_json ( const COMMAND_RPC_GET_INFO::request & req,
COMMAND_RPC_GET_INFO::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2003 of file core_rpc_server.cpp.

2004 {
2005 return on_get_info(req, res, ctx);
2006 }
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_last_block_header()

bool cryptonote::core_rpc_server::on_get_last_block_header ( const COMMAND_RPC_GET_LAST_BLOCK_HEADER::request & req,
COMMAND_RPC_GET_LAST_BLOCK_HEADER::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1647 of file core_rpc_server.cpp.

1648 {
1650 bool r;
1651 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_LAST_BLOCK_HEADER>(invoke_http_mode::JON_RPC, "getlastblockheader", req, res, r))
1652 return r;
1653
1655 uint64_t last_block_height;
1656 crypto::hash last_block_hash;
1657 m_core.get_blockchain_top(last_block_height, last_block_hash);
1658 block last_block;
1659 bool have_last_block = m_core.get_block_by_hash(last_block_hash, last_block);
1660 if (!have_last_block)
1661 {
1663 error_resp.message = "Internal error: can't get last block.";
1664 return false;
1665 }
1666 const bool restricted = m_restricted && ctx;
1667 bool response_filled = fill_block_header_response(last_block, false, last_block_height, last_block_hash, res.block_header, req.fill_pow_hash && !restricted);
1668 if (!response_filled)
1669 {
1671 error_resp.message = "Internal error: can't produce valid response.";
1672 return false;
1673 }
1674 res.status = CORE_RPC_STATUS_OK;
1675 return true;
1676 }
bool on_get_last_block_header(const COMMAND_RPC_GET_LAST_BLOCK_HEADER::request &req, COMMAND_RPC_GET_LAST_BLOCK_HEADER::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_limit()

bool cryptonote::core_rpc_server::on_get_limit ( const COMMAND_RPC_GET_LIMIT::request & req,
COMMAND_RPC_GET_LIMIT::response & res,
const connection_context * ctx = NULL )

Definition at line 2251 of file core_rpc_server.cpp.

2252 {
2254 bool r;
2255 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_LIMIT>(invoke_http_mode::JON, "/get_limit", req, res, r))
2256 return r;
2257
2260 res.status = CORE_RPC_STATUS_OK;
2261 return true;
2262 }
bool on_get_limit(const COMMAND_RPC_GET_LIMIT::request &req, COMMAND_RPC_GET_LIMIT::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_net_stats()

bool cryptonote::core_rpc_server::on_get_net_stats ( const COMMAND_RPC_GET_NET_STATS::request & req,
COMMAND_RPC_GET_NET_STATS::response & res,
const connection_context * ctx = NULL )

Definition at line 258 of file core_rpc_server.cpp.

259 {
261 // No bootstrap daemon check: Only ever get stats about local server
262 res.start_time = (uint64_t)m_core.get_start_time();
263 {
266 }
267 {
270 }
271 res.status = CORE_RPC_STATUS_OK;
272 return true;
273 }
bool on_get_net_stats(const COMMAND_RPC_GET_NET_STATS::request &req, COMMAND_RPC_GET_NET_STATS::response &res, const connection_context *ctx=NULL)
virtual void get_stats(uint64_t &total_packets, uint64_t &total_bytes) const =0
static i_network_throttle & get_global_throttle_in()
singleton ; for friend class ; caller MUST use proper locks! like m_lock_get_global_throttle_in
static i_network_throttle & get_global_throttle_out()
ditto ; use lock ... use m_lock_get_global_throttle_out obviously
#define CRITICAL_REGION_LOCAL(x)
Definition syncobj.h:228
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_output_distribution()

bool cryptonote::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,
const connection_context * ctx = NULL )

Definition at line 2695 of file core_rpc_server.cpp.

2696 {
2698 bool r;
2699 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_OUTPUT_DISTRIBUTION>(invoke_http_mode::JON_RPC, "get_output_distribution", req, res, r))
2700 return r;
2701
2702 try
2703 {
2704 // 0 is placeholder for the whole chain
2705 const uint64_t req_to_height = req.to_height ? req.to_height : (m_core.get_current_blockchain_height() - 1);
2706 for (uint64_t amount: req.amounts)
2707 {
2708 auto data = rpc::RpcHandler::get_output_distribution([this](uint64_t amount, uint64_t from, uint64_t to, uint64_t &start_height, std::vector<uint64_t> &distribution, uint64_t &base) { return m_core.get_output_distribution(amount, from, to, start_height, distribution, base); }, amount, req.from_height, req_to_height, [this](uint64_t height) { return m_core.get_blockchain_storage().get_db().get_block_hash_from_height(height); }, req.cumulative, m_core.get_current_blockchain_height());
2709 if (!data)
2710 {
2712 error_resp.message = "Failed to get output distribution";
2713 return false;
2714 }
2715
2716 res.distributions.push_back({std::move(*data), amount, "", req.binary, req.compress});
2717 }
2718 }
2719 catch (const std::exception &e)
2720 {
2722 error_resp.message = "Failed to get output distribution";
2723 return false;
2724 }
2725
2726 res.status = CORE_RPC_STATUS_OK;
2727 return true;
2728 }
bool 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, const connection_context *ctx=NULL)
static boost::optional< output_distribution_data > get_output_distribution(const std::function< bool(uint64_t, uint64_t, uint64_t, uint64_t &, std::vector< uint64_t > &, uint64_t &)> &f, uint64_t amount, uint64_t from_height, uint64_t to_height, const std::function< crypto::hash(uint64_t)> &get_hash, bool cumulative, uint64_t blockchain_height)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_output_distribution_bin()

bool cryptonote::core_rpc_server::on_get_output_distribution_bin ( const COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::request & req,
COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::response & res,
const connection_context * ctx = NULL )

Definition at line 2730 of file core_rpc_server.cpp.

2731 {
2733
2734 bool r;
2735 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_OUTPUT_DISTRIBUTION>(invoke_http_mode::BIN, "/get_output_distribution.bin", req, res, r))
2736 return r;
2737
2738 res.status = "Failed";
2739
2740 if (!req.binary)
2741 {
2742 res.status = "Binary only call";
2743 return false;
2744 }
2745 try
2746 {
2747 // 0 is placeholder for the whole chain
2748 const uint64_t req_to_height = req.to_height ? req.to_height : (m_core.get_current_blockchain_height() - 1);
2749 for (uint64_t amount: req.amounts)
2750 {
2751 auto data = rpc::RpcHandler::get_output_distribution([this](uint64_t amount, uint64_t from, uint64_t to, uint64_t &start_height, std::vector<uint64_t> &distribution, uint64_t &base) { return m_core.get_output_distribution(amount, from, to, start_height, distribution, base); }, amount, req.from_height, req_to_height, [this](uint64_t height) { return m_core.get_blockchain_storage().get_db().get_block_hash_from_height(height); }, req.cumulative, m_core.get_current_blockchain_height());
2752 if (!data)
2753 {
2754 res.status = "Failed to get output distribution";
2755 return false;
2756 }
2757
2758 res.distributions.push_back({std::move(*data), amount, "", req.binary, req.compress});
2759 }
2760 }
2761 catch (const std::exception &e)
2762 {
2763 res.status = "Failed to get output distribution";
2764 return false;
2765 }
2766
2767 res.status = CORE_RPC_STATUS_OK;
2768 return true;
2769 }
bool on_get_output_distribution_bin(const COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::request &req, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_output_histogram()

bool cryptonote::core_rpc_server::on_get_output_histogram ( const COMMAND_RPC_GET_OUTPUT_HISTOGRAM::request & req,
COMMAND_RPC_GET_OUTPUT_HISTOGRAM::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2146 of file core_rpc_server.cpp.

2147 {
2149 bool r;
2150 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_OUTPUT_HISTOGRAM>(invoke_http_mode::JON_RPC, "get_output_histogram", req, res, r))
2151 return r;
2152
2153 const bool restricted = m_restricted && ctx;
2154 if (restricted && req.recent_cutoff > 0 && req.recent_cutoff < (uint64_t)time(NULL) - OUTPUT_HISTOGRAM_RECENT_CUTOFF_RESTRICTION)
2155 {
2156 res.status = "Recent cutoff is too old";
2157 return true;
2158 }
2159
2160 std::map<uint64_t, std::tuple<uint64_t, uint64_t, uint64_t>> histogram;
2161 try
2162 {
2163 histogram = m_core.get_blockchain_storage().get_output_histogram(req.amounts, req.unlocked, req.recent_cutoff, req.min_count);
2164 }
2165 catch (const std::exception &e)
2166 {
2167 res.status = "Failed to get output histogram";
2168 return true;
2169 }
2170
2171 res.histogram.clear();
2172 res.histogram.reserve(histogram.size());
2173 for (const auto &i: histogram)
2174 {
2175 if (std::get<0>(i.second) >= req.min_count && (std::get<0>(i.second) <= req.max_count || req.max_count == 0))
2176 res.histogram.push_back(COMMAND_RPC_GET_OUTPUT_HISTOGRAM::entry(i.first, std::get<0>(i.second), std::get<1>(i.second), std::get<2>(i.second)));
2177 }
2178
2179 res.status = CORE_RPC_STATUS_OK;
2180 return true;
2181 }
bool on_get_output_histogram(const COMMAND_RPC_GET_OUTPUT_HISTOGRAM::request &req, COMMAND_RPC_GET_OUTPUT_HISTOGRAM::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
#define OUTPUT_HISTOGRAM_RECENT_CUTOFF_RESTRICTION
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_outs()

bool cryptonote::core_rpc_server::on_get_outs ( const COMMAND_RPC_GET_OUTPUTS::request & req,
COMMAND_RPC_GET_OUTPUTS::response & res,
const connection_context * ctx = NULL )

Definition at line 471 of file core_rpc_server.cpp.

472 {
474 bool r;
475 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_OUTPUTS>(invoke_http_mode::JON, "/get_outs", req, res, r))
476 return r;
477
478 res.status = "Failed";
479
480 const bool restricted = m_restricted && ctx;
481 if (restricted)
482 {
483 if (req.outputs.size() > MAX_RESTRICTED_GLOBAL_FAKE_OUTS_COUNT)
484 {
485 res.status = "Too many outs requested";
486 return true;
487 }
488 }
489
491 req_bin.outputs = req.outputs;
492 req_bin.get_txid = req.get_txid;
494 if(!m_core.get_outs(req_bin, res_bin))
495 {
496 return true;
497 }
498
499 // convert to text
500 for (const auto &i: res_bin.outs)
501 {
502 res.outs.push_back(cryptonote::COMMAND_RPC_GET_OUTPUTS::outkey());
503 cryptonote::COMMAND_RPC_GET_OUTPUTS::outkey &outkey = res.outs.back();
506 outkey.unlocked = i.unlocked;
507 outkey.height = i.height;
509 }
510
511 res.status = CORE_RPC_STATUS_OK;
512 return true;
513 }
bool on_get_outs(const COMMAND_RPC_GET_OUTPUTS::request &req, COMMAND_RPC_GET_OUTPUTS::response &res, const connection_context *ctx=NULL)
#define MAX_RESTRICTED_GLOBAL_FAKE_OUTS_COUNT
struct cryptonote::outkey outkey
epee::misc_utils::struct_init< request_t > request
epee::misc_utils::struct_init< response_t > response
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_outs_bin()

bool cryptonote::core_rpc_server::on_get_outs_bin ( const COMMAND_RPC_GET_OUTPUTS_BIN::request & req,
COMMAND_RPC_GET_OUTPUTS_BIN::response & res,
const connection_context * ctx = NULL )

Definition at line 443 of file core_rpc_server.cpp.

444 {
446 bool r;
447 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_OUTPUTS_BIN>(invoke_http_mode::BIN, "/get_outs.bin", req, res, r))
448 return r;
449
450 res.status = "Failed";
451
452 const bool restricted = m_restricted && ctx;
453 if (restricted)
454 {
455 if (req.outputs.size() > MAX_RESTRICTED_GLOBAL_FAKE_OUTS_COUNT)
456 {
457 res.status = "Too many outs requested";
458 return true;
459 }
460 }
461
462 if(!m_core.get_outs(req, res))
463 {
464 return true;
465 }
466
467 res.status = CORE_RPC_STATUS_OK;
468 return true;
469 }
bool on_get_outs_bin(const COMMAND_RPC_GET_OUTPUTS_BIN::request &req, COMMAND_RPC_GET_OUTPUTS_BIN::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_peer_list()

bool cryptonote::core_rpc_server::on_get_peer_list ( const COMMAND_RPC_GET_PEER_LIST::request & req,
COMMAND_RPC_GET_PEER_LIST::response & res,
const connection_context * ctx = NULL )

Definition at line 1130 of file core_rpc_server.cpp.

1131 {
1133 std::vector<nodetool::peerlist_entry> white_list;
1134 std::vector<nodetool::peerlist_entry> gray_list;
1135 m_p2p.get_public_peerlist(gray_list, white_list);
1136
1137 res.white_list.reserve(white_list.size());
1138 for (auto & entry : white_list)
1139 {
1140 if (entry.adr.get_type_id() == epee::net_utils::ipv4_network_address::get_type_id())
1141 res.white_list.emplace_back(entry.id, entry.adr.as<epee::net_utils::ipv4_network_address>().ip(),
1142 entry.adr.as<epee::net_utils::ipv4_network_address>().port(), entry.last_seen, entry.pruning_seed, entry.rpc_port);
1143 else
1144 res.white_list.emplace_back(entry.id, entry.adr.str(), entry.last_seen, entry.pruning_seed, entry.rpc_port);
1145 }
1146
1147 res.gray_list.reserve(gray_list.size());
1148 for (auto & entry : gray_list)
1149 {
1150 if (entry.adr.get_type_id() == epee::net_utils::ipv4_network_address::get_type_id())
1151 res.gray_list.emplace_back(entry.id, entry.adr.as<epee::net_utils::ipv4_network_address>().ip(),
1152 entry.adr.as<epee::net_utils::ipv4_network_address>().port(), entry.last_seen, entry.pruning_seed, entry.rpc_port);
1153 else
1154 res.gray_list.emplace_back(entry.id, entry.adr.str(), entry.last_seen, entry.pruning_seed, entry.rpc_port);
1155 }
1156
1157 res.status = CORE_RPC_STATUS_OK;
1158 return true;
1159 }
bool on_get_peer_list(const COMMAND_RPC_GET_PEER_LIST::request &req, COMMAND_RPC_GET_PEER_LIST::response &res, const connection_context *ctx=NULL)
static constexpr address_type get_type_id() noexcept
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_tax_data()

bool cryptonote::core_rpc_server::on_get_tax_data ( const COMMAND_RPC_GET_TAX_DATA::request & req,
COMMAND_RPC_GET_TAX_DATA::response & res,
const connection_context * ctx = NULL )

Definition at line 2450 of file core_rpc_server.cpp.

2451 {
2452 if (m_restricted && ctx)
2453 {
2454 res.status = "Method disabled on restricted RPC";
2455 return true;
2456 }
2458 std::string filename =
2459 "taxes-" + std::to_string(req.start_height) + "-" + std::to_string(req.end_height) + ".csv";
2460 std::ofstream file(filename);
2461 // header
2462 file <<
2463 boost::format("%64.64s,%64.64s,%64.64s,%64.64s,%64.64s") %
2464 tr("height") % tr("timestamp") % tr("txid") % tr("fee") % tr("amount")
2465 << std::endl;
2466
2467 auto formatter = boost::format("%64.64s,%64.64s,%64.64s,%64.64s,%64.64s");
2468
2469 std::vector<std::pair<cryptonote::blobdata, block>> blocks;
2470 size_t num_blocks = req.end_height - req.start_height;
2471 m_core.get_blocks(req.start_height, num_blocks, blocks);
2472
2473 uint64_t current_height = req.start_height;
2474 for (auto block: blocks) {
2475 std::vector<cryptonote::transaction> found_txs_vec;
2476 std::vector<crypto::hash> missed_vec;
2477 uint64_t tx_hash_counter = 0; //needed because of some weird compiler bug
2478 for(auto hash : block.second.tx_hashes){
2479 found_txs_vec.push_back(m_core.get_blockchain_storage().get_db().get_tx(hash));
2480 }
2481 // m_core.get_transactions(block.second.tx_hashes, found_txs_vec, missed_vec);
2482 for (transaction tx: found_txs_vec) {
2483 uint64_t fee = 0;
2484 if(tx.vin[0].type() == typeid(txin_to_key)){continue;}
2485 get_tx_fee(tx, fee);
2486 time_t time_date_stamp = time_t(block.second.timestamp);
2487 std::stringstream transTime;
2488 transTime << std::put_time(localtime(&time_date_stamp), "%D - %T");
2489 std::string myTime = transTime.str();
2490
2491 unsigned char *byteData = reinterpret_cast<unsigned char*>(tx.hash.data);
2492 std::string dest;
2493 std::stringstream hexStringStream;
2494
2495 hexStringStream << std::hex << std::setfill('0');
2496 for(size_t index = 0; index < 32; ++index)
2497 hexStringStream << std::setw(2) << static_cast<int>(byteData[index]);
2498 dest = hexStringStream.str();
2499
2500 file << formatter
2501 % current_height
2502 % myTime
2503 % epee::string_tools::pod_to_hex(block.second.tx_hashes[tx_hash_counter])
2504 % std::to_string(((double)fee / 100))
2505 % std::to_string((double)(size_t((accumulate(tx.vin.begin(), tx.vin.end(), 0, [](size_t sum, const txin_v& input){ return sum + boost::get<txin_to_key_public>(input).amount; })) - fee)) / 100)
2506 << std::endl;
2507 tx_hash_counter++;
2508 }
2509 current_height++;
2510 }
2511 file.close();
2512 res.status = CORE_RPC_STATUS_OK;
2513 return true;
2514 }
uint64_t num_blocks(const std::vector< test_event_entry > &events)
bool on_get_tax_data(const COMMAND_RPC_GET_TAX_DATA::request &req, COMMAND_RPC_GET_TAX_DATA::response &res, const connection_context *ctx=NULL)
#define tr(x)
boost::variant< txin_gen, txin_to_script, txin_to_scripthash, txin_to_key, txin_to_key_public > txin_v
bool get_tx_fee(const transaction &tx, uint64_t &fee)
CXA_THROW_INFO_T void(* dest)(void *))
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_transaction_pool()

bool cryptonote::core_rpc_server::on_get_transaction_pool ( const COMMAND_RPC_GET_TRANSACTION_POOL::request & req,
COMMAND_RPC_GET_TRANSACTION_POOL::response & res,
const connection_context * ctx = NULL )

Definition at line 1198 of file core_rpc_server.cpp.

1199 {
1201 bool r;
1202 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TRANSACTION_POOL>(invoke_http_mode::JON, "/get_transaction_pool", req, res, r))
1203 return r;
1204
1205 const bool restricted = m_restricted && ctx;
1206 const bool request_has_rpc_origin = ctx != NULL;
1207 m_core.get_pool_transactions_and_spent_keys_info(res.transactions, res.spent_key_images, !request_has_rpc_origin || !restricted);
1208 for (tx_info& txi : res.transactions)
1209 txi.tx_blob = epee::string_tools::buff_to_hex_nodelimer(txi.tx_blob);
1210 res.status = CORE_RPC_STATUS_OK;
1211 return true;
1212 }
bool on_get_transaction_pool(const COMMAND_RPC_GET_TRANSACTION_POOL::request &req, COMMAND_RPC_GET_TRANSACTION_POOL::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_transaction_pool_hashes()

bool cryptonote::core_rpc_server::on_get_transaction_pool_hashes ( const COMMAND_RPC_GET_TRANSACTION_POOL_HASHES::request & req,
COMMAND_RPC_GET_TRANSACTION_POOL_HASHES::response & res,
const connection_context * ctx = NULL )

Definition at line 1228 of file core_rpc_server.cpp.

1229 {
1231 bool r;
1232 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TRANSACTION_POOL_HASHES>(invoke_http_mode::JON, "/get_transaction_pool_hashes", req, res, r))
1233 return r;
1234
1235 const bool restricted = m_restricted && ctx;
1236 const bool request_has_rpc_origin = ctx != NULL;
1237 std::vector<crypto::hash> tx_hashes;
1238 m_core.get_pool_transaction_hashes(tx_hashes, !request_has_rpc_origin || !restricted);
1239 res.tx_hashes.reserve(tx_hashes.size());
1240 for (const crypto::hash &tx_hash: tx_hashes)
1241 res.tx_hashes.push_back(epee::string_tools::pod_to_hex(tx_hash));
1242 res.status = CORE_RPC_STATUS_OK;
1243 return true;
1244 }
bool on_get_transaction_pool_hashes(const COMMAND_RPC_GET_TRANSACTION_POOL_HASHES::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_HASHES::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_transaction_pool_hashes_bin()

bool cryptonote::core_rpc_server::on_get_transaction_pool_hashes_bin ( const COMMAND_RPC_GET_TRANSACTION_POOL_HASHES_BIN::request & req,
COMMAND_RPC_GET_TRANSACTION_POOL_HASHES_BIN::response & res,
const connection_context * ctx = NULL )

Definition at line 1214 of file core_rpc_server.cpp.

1215 {
1217 bool r;
1218 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TRANSACTION_POOL_HASHES_BIN>(invoke_http_mode::JON, "/get_transaction_pool_hashes.bin", req, res, r))
1219 return r;
1220
1221 const bool restricted = m_restricted && ctx;
1222 const bool request_has_rpc_origin = ctx != NULL;
1223 m_core.get_pool_transaction_hashes(res.tx_hashes, !request_has_rpc_origin || !restricted);
1224 res.status = CORE_RPC_STATUS_OK;
1225 return true;
1226 }
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_transaction_pool_stats()

bool cryptonote::core_rpc_server::on_get_transaction_pool_stats ( const COMMAND_RPC_GET_TRANSACTION_POOL_STATS::request & req,
COMMAND_RPC_GET_TRANSACTION_POOL_STATS::response & res,
const connection_context * ctx = NULL )

Definition at line 1246 of file core_rpc_server.cpp.

1247 {
1249 bool r;
1250 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TRANSACTION_POOL_STATS>(invoke_http_mode::JON, "/get_transaction_pool_stats", req, res, r))
1251 return r;
1252
1253 const bool restricted = m_restricted && ctx;
1254 const bool request_has_rpc_origin = ctx != NULL;
1255 m_core.get_pool_transaction_stats(res.pool_stats, !request_has_rpc_origin || !restricted);
1256 res.status = CORE_RPC_STATUS_OK;
1257 return true;
1258 }
bool on_get_transaction_pool_stats(const COMMAND_RPC_GET_TRANSACTION_POOL_STATS::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_STATS::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_transactions()

bool cryptonote::core_rpc_server::on_get_transactions ( const COMMAND_RPC_GET_TRANSACTIONS::request & req,
COMMAND_RPC_GET_TRANSACTIONS::response & res,
const connection_context * ctx = NULL )

Definition at line 533 of file core_rpc_server.cpp.

534 {
536 bool ok;
537 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TRANSACTIONS>(invoke_http_mode::JON, "/gettransactions", req, res, ok))
538 return ok;
539
540 std::vector<crypto::hash> vh;
541 for(const auto& tx_hex_str: req.txs_hashes)
542 {
543 blobdata b;
544 if(!string_tools::parse_hexstr_to_binbuff(tx_hex_str, b))
545 {
546 res.status = "Failed to parse hex representation of transaction hash";
547 return true;
548 }
549 if(b.size() != sizeof(crypto::hash))
550 {
551 res.status = "Failed, size of data mismatch";
552 return true;
553 }
554 vh.push_back(*reinterpret_cast<const crypto::hash*>(b.data()));
555 }
556 std::vector<crypto::hash> missed_txs;
557 std::vector<std::tuple<crypto::hash, cryptonote::blobdata, crypto::hash, cryptonote::blobdata>> txs;
558 bool r = m_core.get_split_transactions_blobs(vh, txs, missed_txs);
559 if(!r)
560 {
561 res.status = "Failed";
562 return true;
563 }
564 LOG_PRINT_L2("Found " << txs.size() << "/" << vh.size() << " transactions on the blockchain");
565
566 // try the pool for any missing txes
567 size_t found_in_pool = 0;
568 std::unordered_set<crypto::hash> pool_tx_hashes;
569 std::unordered_map<crypto::hash, tx_info> per_tx_pool_tx_info;
570 if (!missed_txs.empty())
571 {
572 std::vector<tx_info> pool_tx_info;
573 std::vector<spent_key_image_info> pool_key_image_info;
574 bool r = m_core.get_pool_transactions_and_spent_keys_info(pool_tx_info, pool_key_image_info);
575 if(r)
576 {
577 // sort to match original request
578 std::vector<std::tuple<crypto::hash, cryptonote::blobdata, crypto::hash, cryptonote::blobdata>> sorted_txs;
579 std::vector<tx_info>::const_iterator i;
580 unsigned txs_processed = 0;
581 for (const crypto::hash &h: vh)
582 {
583 if (std::find(missed_txs.begin(), missed_txs.end(), h) == missed_txs.end())
584 {
585 if (txs.size() == txs_processed)
586 {
587 res.status = "Failed: internal error - txs is empty";
588 return true;
589 }
590 // core returns the ones it finds in the right order
591 if (std::get<0>(txs[txs_processed]) != h)
592 {
593 res.status = "Failed: tx hash mismatch";
594 return true;
595 }
596 sorted_txs.push_back(std::move(txs[txs_processed]));
597 ++txs_processed;
598 }
599 else if ((i = std::find_if(pool_tx_info.begin(), pool_tx_info.end(), [h](const tx_info &txi) { return epee::string_tools::pod_to_hex(h) == txi.id_hash; })) != pool_tx_info.end())
600 {
601 cryptonote::transaction tx;
603 {
604 res.status = "Failed to parse and validate tx from blob";
605 return true;
606 }
607 std::stringstream ss;
608 binary_archive<true> ba(ss);
609 bool r = const_cast<cryptonote::transaction&>(tx).serialize_base(ba);
610 if (!r)
611 {
612 res.status = "Failed to serialize transaction base";
613 return true;
614 }
615 //TODO: Public
616 const cryptonote::blobdata pruned = ss.str();
617 sorted_txs.push_back(std::make_tuple(h, pruned, crypto::null_hash, std::string(i->tx_blob, pruned.size())));
618 missed_txs.erase(std::find(missed_txs.begin(), missed_txs.end(), h));
619 pool_tx_hashes.insert(h);
620 const std::string hash_string = epee::string_tools::pod_to_hex(h);
621 for (const auto &ti: pool_tx_info)
622 {
623 if (ti.id_hash == hash_string)
624 {
625 per_tx_pool_tx_info.insert(std::make_pair(h, ti));
626 break;
627 }
628 }
629 ++found_in_pool;
630 }
631 }
632 txs = sorted_txs;
633 }
634 LOG_PRINT_L2("Found " << found_in_pool << "/" << vh.size() << " transactions in the pool");
635 }
636
637 std::vector<std::string>::const_iterator txhi = req.txs_hashes.begin();
638 std::vector<crypto::hash>::const_iterator vhi = vh.begin();
639 for(auto& tx: txs)
640 {
641 res.txs.push_back(COMMAND_RPC_GET_TRANSACTIONS::entry());
642 COMMAND_RPC_GET_TRANSACTIONS::entry &e = res.txs.back();
643
644 crypto::hash tx_hash = *vhi++;
645 e.tx_hash = *txhi++;
646 e.prunable_hash = epee::string_tools::pod_to_hex(std::get<2>(tx));
647 if (req.split || req.prune || std::get<3>(tx).empty())
648 {
649 // use splitted form with pruned and prunable (filled only when prune=false and the daemon has it), leaving as_hex as empty
650 e.pruned_as_hex = string_tools::buff_to_hex_nodelimer(std::get<1>(tx));
651 if (!req.prune)
652 e.prunable_as_hex = string_tools::buff_to_hex_nodelimer(std::get<3>(tx));
653 if (req.decode_as_json)
654 {
655 cryptonote::blobdata tx_data;
656 cryptonote::transaction t;
657 if (req.prune || std::get<3>(tx).empty())
658 {
659 // decode pruned tx to JSON
660 tx_data = std::get<1>(tx);
662 {
663 pruned_transaction pruned_tx{t};
664 e.as_json = obj_to_json_str(pruned_tx);
665 }
666 else
667 {
668 res.status = "Failed to parse and validate pruned tx from blob";
669 return true;
670 }
671 }
672 else
673 {
674 // decode full tx to JSON
675 tx_data = std::get<1>(tx) + std::get<3>(tx);
677 {
678 e.as_json = obj_to_json_str(t);
679 }
680 else
681 {
682 res.status = "Failed to parse and validate tx from blob";
683 return true;
684 }
685 }
686 }
687 }
688 else
689 {
690 // use non-splitted form, leaving pruned_as_hex and prunable_as_hex as empty
691 cryptonote::blobdata tx_data = std::get<1>(tx) + std::get<3>(tx);
692 e.as_hex = string_tools::buff_to_hex_nodelimer(tx_data);
693 if (req.decode_as_json)
694 {
695 cryptonote::transaction t;
697 {
698 e.as_json = obj_to_json_str(t);
699 }
700 else
701 {
702 res.status = "Failed to parse and validate tx from blob";
703 return true;
704 }
705 }
706 }
707 e.in_pool = pool_tx_hashes.find(tx_hash) != pool_tx_hashes.end();
708 if (e.in_pool)
709 {
710 e.block_height = e.block_timestamp = std::numeric_limits<uint64_t>::max();
711 auto it = per_tx_pool_tx_info.find(tx_hash);
712 if (it != per_tx_pool_tx_info.end())
713 {
714 e.double_spend_seen = it->second.double_spend_seen;
715 e.nonexistent_utxo_seen = it->second.nonexistent_utxo_seen;
716 e.relayed = it->second.relayed;
717 }
718 else
719 {
720 MERROR("Failed to determine pool info for " << tx_hash);
721 e.double_spend_seen = false;
722 e.nonexistent_utxo_seen = false;
723 e.relayed = false;
724 }
725 }
726 else
727 {
728 e.block_height = m_core.get_blockchain_storage().get_db().get_tx_block_height(tx_hash);
729 e.block_timestamp = m_core.get_blockchain_storage().get_db().get_block_timestamp(e.block_height);
730 e.double_spend_seen = false;
731 e.relayed = false;
732 }
733
734 // fill up old style responses too, in case an old wallet asks
735 res.txs_as_hex.push_back(e.as_hex);
736 if (req.decode_as_json)
737 res.txs_as_json.push_back(e.as_json);
738
739 // output indices too if not in pool
740 if (pool_tx_hashes.find(tx_hash) == pool_tx_hashes.end())
741 {
742 bool r = m_core.get_tx_outputs_gindexs(tx_hash, e.output_indices);
743 if (!r)
744 {
745 res.status = "Failed";
746 return false;
747 }
748 }
749 }
750
751 for(const auto& miss_tx: missed_txs)
752 {
753 res.missed_tx.push_back(string_tools::pod_to_hex(miss_tx));
754 }
755
756 LOG_PRINT_L2(res.txs.size() << " transactions found, " << res.missed_tx.size() << " not found");
757 res.status = CORE_RPC_STATUS_OK;
758 return true;
759 }
bool on_get_transactions(const COMMAND_RPC_GET_TRANSACTIONS::request &req, COMMAND_RPC_GET_TRANSACTIONS::response &res, const connection_context *ctx=NULL)
#define MERROR(x)
Definition misc_log_ex.h:73
bool parse_and_validate_tx_from_blob(const blobdata &tx_blob, transaction &tx)
bool parse_and_validate_tx_base_from_blob(const blobdata &tx_blob, transaction &tx)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_txpool_backlog()

bool cryptonote::core_rpc_server::on_get_txpool_backlog ( const COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG::request & req,
COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2593 of file core_rpc_server.cpp.

2594 {
2596 bool r;
2597 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG>(invoke_http_mode::JON_RPC, "get_txpool_backlog", req, res, r))
2598 return r;
2599
2600 if (!m_core.get_txpool_backlog(res.backlog))
2601 {
2603 error_resp.message = "Failed to get txpool backlog";
2604 return false;
2605 }
2606
2607 res.status = CORE_RPC_STATUS_OK;
2608 return true;
2609 }
bool on_get_txpool_backlog(const COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG::request &req, COMMAND_RPC_GET_TRANSACTION_POOL_BACKLOG::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_get_version()

bool cryptonote::core_rpc_server::on_get_version ( const COMMAND_RPC_GET_VERSION::request & req,
COMMAND_RPC_GET_VERSION::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2183 of file core_rpc_server.cpp.

2184 {
2186 bool r;
2187 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GET_VERSION>(invoke_http_mode::JON_RPC, "get_version", req, res, r))
2188 return r;
2189
2190 res.version = CORE_RPC_VERSION;
2191 res.status = CORE_RPC_STATUS_OK;
2192 return true;
2193 }
bool on_get_version(const COMMAND_RPC_GET_VERSION::request &req, COMMAND_RPC_GET_VERSION::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
#define CORE_RPC_VERSION
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_getblockcount()

bool cryptonote::core_rpc_server::on_getblockcount ( const COMMAND_RPC_GETBLOCKCOUNT::request & req,
COMMAND_RPC_GETBLOCKCOUNT::response & res,
const connection_context * ctx = NULL )

Definition at line 1270 of file core_rpc_server.cpp.

1271 {
1273 {
1274 boost::shared_lock<boost::shared_mutex> lock(m_bootstrap_daemon_mutex);
1275 if (m_should_use_bootstrap_daemon)
1276 {
1277 res.status = "This command is unsupported for bootstrap daemon";
1278 return false;
1279 }
1280 }
1281 res.count = m_core.get_current_blockchain_height();
1282 res.status = CORE_RPC_STATUS_OK;
1283 return true;
1284 }
bool on_getblockcount(const COMMAND_RPC_GETBLOCKCOUNT::request &req, COMMAND_RPC_GETBLOCKCOUNT::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_getblockhash()

bool cryptonote::core_rpc_server::on_getblockhash ( const COMMAND_RPC_GETBLOCKHASH::request & req,
COMMAND_RPC_GETBLOCKHASH::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1286 of file core_rpc_server.cpp.

1287 {
1289 {
1290 boost::shared_lock<boost::shared_mutex> lock(m_bootstrap_daemon_mutex);
1291 if (m_should_use_bootstrap_daemon)
1292 {
1293 res = "This command is unsupported for bootstrap daemon";
1294 return false;
1295 }
1296 }
1297 if(req.size() != 1)
1298 {
1300 error_resp.message = "Wrong parameters, expected height";
1301 return false;
1302 }
1303 uint64_t h = req[0];
1304 if(m_core.get_current_blockchain_height() <= h)
1305 {
1307 error_resp.message = std::string("Requested block height: ") + std::to_string(h) + " greater than current top block height: " + std::to_string(m_core.get_current_blockchain_height() - 1);
1308 }
1309 res = string_tools::pod_to_hex(m_core.get_block_id_by_height(h));
1310 return true;
1311 }
bool on_getblockhash(const COMMAND_RPC_GETBLOCKHASH::request &req, COMMAND_RPC_GETBLOCKHASH::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_getblocktemplate()

bool cryptonote::core_rpc_server::on_getblocktemplate ( const COMMAND_RPC_GETBLOCKTEMPLATE::request & req,
COMMAND_RPC_GETBLOCKTEMPLATE::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1330 of file core_rpc_server.cpp.

1331 {
1333 bool r;
1334 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_GETBLOCKTEMPLATE>(invoke_http_mode::JON_RPC, "getblocktemplate", req, res, r))
1335 return r;
1336
1337 if(!check_core_ready())
1338 {
1340 error_resp.message = "Core is busy";
1341 return false;
1342 }
1343
1344 if(req.reserve_size > 255)
1345 {
1347 error_resp.message = "Too big reserved size, maximum 255";
1348 return false;
1349 }
1350
1351 cryptonote::address_parse_info info;
1352
1353 if(!req.wallet_address.size() || !cryptonote::get_account_address_from_str(info, nettype(), req.wallet_address))
1354 {
1356 error_resp.message = "Failed to parse wallet address";
1357 return false;
1358 }
1359 if (info.is_subaddress)
1360 {
1362 error_resp.message = "Mining to subaddress is not supported yet";
1363 return false;
1364 }
1365
1366 block b;
1367 cryptonote::blobdata blob_reserve;
1368 blob_reserve.resize(req.reserve_size, 0);
1370 crypto::hash prev_block;
1371 if (!req.prev_block.empty())
1372 {
1373 if (!epee::string_tools::hex_to_pod(req.prev_block, prev_block))
1374 {
1376 error_resp.message = "Invalid prev_block";
1377 return false;
1378 }
1379 }
1380 if(!m_core.get_block_template(b, req.prev_block.empty() ? NULL : &prev_block, info.address, wdiff, res.height, res.expected_reward, blob_reserve))
1381 {
1383 error_resp.message = "Internal error: failed to create block template";
1384 LOG_ERROR("Failed to create block template");
1385 return false;
1386 }
1387 store_difficulty(wdiff, res.difficulty, res.wide_difficulty, res.difficulty_top64);
1390 if(tx_pub_key == crypto::null_pkey)
1391 {
1393 error_resp.message = "Internal error: failed to create block template";
1394 LOG_ERROR("Failed to get tx pub key in coinbase extra");
1395 return false;
1396 }
1397 res.reserved_offset = slow_memmem((void*)block_blob.data(), block_blob.size(), &tx_pub_key, sizeof(tx_pub_key));
1398 if(!res.reserved_offset)
1399 {
1401 error_resp.message = "Internal error: failed to create block template";
1402 LOG_ERROR("Failed to find tx pub key in blockblob");
1403 return false;
1404 }
1405 if (req.reserve_size)
1406 res.reserved_offset += sizeof(tx_pub_key) + 2; //2 bytes: tag for TX_EXTRA_NONCE(1 byte), counter in TX_EXTRA_NONCE(1 byte)
1407 else
1408 res.reserved_offset = 0;
1409 if(res.reserved_offset + req.reserve_size > block_blob.size())
1410 {
1412 error_resp.message = "Internal error: failed to create block template";
1413 LOG_ERROR("Failed to calculate offset for ");
1414 return false;
1415 }
1416 blobdata hashing_blob = get_block_hashing_blob(b);
1417 res.prev_hash = string_tools::pod_to_hex(b.prev_id);
1418 res.blocktemplate_blob = string_tools::buff_to_hex_nodelimer(block_blob);
1419 res.blockhashing_blob = string_tools::buff_to_hex_nodelimer(hashing_blob);
1420 res.status = CORE_RPC_STATUS_OK;
1421 return true;
1422 }
#define CORE_RPC_ERROR_CODE_WRONG_WALLET_ADDRESS
#define CORE_RPC_ERROR_CODE_CORE_BUSY
#define CORE_RPC_ERROR_CODE_MINING_TO_SUBADDRESS
#define CORE_RPC_ERROR_CODE_TOO_BIG_RESERVE_SIZE
#define LOG_ERROR(x)
Definition misc_log_ex.h:98
const crypto::public_key null_pkey
Definition crypto.cpp:72
POD_CLASS public_key
Definition crypto.h:79
blobdata get_block_hashing_blob(const block &b)
crypto::public_key get_tx_pub_key_from_extra(const std::vector< uint8_t > &tx_extra, size_t pk_index)
size_t slow_memmem(const void *start_buff, size_t buflen, const void *pat, size_t patlen)
bool hex_to_pod(const std::string &hex_str, t_pod_type &s)
CXA_THROW_INFO_T * info
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_hard_fork_info()

bool cryptonote::core_rpc_server::on_hard_fork_info ( const COMMAND_RPC_HARD_FORK_INFO::request & req,
COMMAND_RPC_HARD_FORK_INFO::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2008 of file core_rpc_server.cpp.

2009 {
2011 bool r;
2012 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_HARD_FORK_INFO>(invoke_http_mode::JON_RPC, "hard_fork_info", req, res, r))
2013 return r;
2014
2015 const Blockchain &blockchain = m_core.get_blockchain_storage();
2016 uint8_t version = req.version > 0 ? req.version : blockchain.get_next_hard_fork_version();
2017 res.version = blockchain.get_current_hard_fork_version();
2018 res.enabled = blockchain.get_hard_fork_voting_info(version, res.window, res.votes, res.threshold, res.earliest_height, res.voting);
2019 res.state = blockchain.get_hard_fork_state();
2020 res.status = CORE_RPC_STATUS_OK;
2021 return true;
2022 }
uint8_t version
bool on_hard_fork_info(const COMMAND_RPC_HARD_FORK_INFO::request &req, COMMAND_RPC_HARD_FORK_INFO::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_in_peers()

bool cryptonote::core_rpc_server::on_in_peers ( const COMMAND_RPC_IN_PEERS::request & req,
COMMAND_RPC_IN_PEERS::response & res,
const connection_context * ctx = NULL )

Definition at line 2312 of file core_rpc_server.cpp.

2313 {
2315 m_p2p.change_max_in_public_peers(req.in_peers);
2316 res.status = CORE_RPC_STATUS_OK;
2317 return true;
2318 }
bool on_in_peers(const COMMAND_RPC_IN_PEERS::request &req, COMMAND_RPC_IN_PEERS::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_inject_emergency_vlist()

bool cryptonote::core_rpc_server::on_inject_emergency_vlist ( const COMMAND_RPC_INJECT_EMERGENCY_VLIST::request & req,
COMMAND_RPC_INJECT_EMERGENCY_VLIST::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2666 of file core_rpc_server.cpp.

2667 {
2668 if(!req.blob.empty()) {
2669
2671 arg.serialized_v_list = electroneum::basic::store_t_to_json(req);
2672 cryptonote_connection_context context = boost::value_initialized<cryptonote_connection_context>();
2673
2674
2675 electroneum::basic::list_update_outcome update_outcome = m_core.set_validators_list(arg.serialized_v_list, true);
2678 LOG_PRINT_CCONTEXT_L0("Local list is a legitimate emergency list and will now be relayed.");
2679
2680 if(m_core.get_protocol()->relay_emergency_validator_list(arg, context)){
2681 LOG_PRINT_CCONTEXT_L0("List successfully deployed to peers via p2p.");
2682 return true;
2683 }
2684 }
2685 else {
2686 LOG_ERROR_CCONTEXT("Received incorrect emergency Validators List for relay.");
2687 return false;
2688 }
2689 }
2690
2691 return false;
2692 }
#define AUTO_VAL_INIT(v)
bool store_t_to_json(t_struct &str_in, std::string &json_buff, size_t indent=0, bool insert_newlines=true)
std::unique_ptr< void, terminate > context
Unique ZMQ context handle, calls zmq_term on destruction.
Definition zmq.h:98
#define LOG_ERROR_CCONTEXT(message)
#define LOG_PRINT_CCONTEXT_L0(message)
epee::misc_utils::struct_init< request_t > request
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_is_key_image_spent()

bool cryptonote::core_rpc_server::on_is_key_image_spent ( const COMMAND_RPC_IS_KEY_IMAGE_SPENT::request & req,
COMMAND_RPC_IS_KEY_IMAGE_SPENT::response & res,
const connection_context * ctx = NULL )

Definition at line 761 of file core_rpc_server.cpp.

762 {
764 bool ok;
765 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_IS_KEY_IMAGE_SPENT>(invoke_http_mode::JON, "/is_key_image_spent", req, res, ok))
766 return ok;
767
768 const bool restricted = m_restricted && ctx;
769 const bool request_has_rpc_origin = ctx != NULL;
770 std::vector<crypto::key_image> key_images;
771 for(const auto& ki_hex_str: req.key_images)
772 {
773 blobdata b;
774 if(!string_tools::parse_hexstr_to_binbuff(ki_hex_str, b))
775 {
776 res.status = "Failed to parse hex representation of key image";
777 return true;
778 }
779 if(b.size() != sizeof(crypto::key_image))
780 {
781 res.status = "Failed, size of data mismatch";
782 }
783 key_images.push_back(*reinterpret_cast<const crypto::key_image*>(b.data()));
784 }
785 std::vector<bool> spent_status;
786 bool r = m_core.are_key_images_spent(key_images, spent_status);
787 if(!r)
788 {
789 res.status = "Failed";
790 return true;
791 }
792 res.spent_status.clear();
793 for (size_t n = 0; n < spent_status.size(); ++n)
794 res.spent_status.push_back(spent_status[n] ? SPENT_STATUS::SPENT_IN_BLOCKCHAIN : SPENT_STATUS::UNSPENT);
795
796 // check the pool too
797 std::vector<cryptonote::tx_info> txs;
798 std::vector<cryptonote::spent_key_image_info> ki;
799 r = m_core.get_pool_transactions_and_spent_keys_info(txs, ki, !request_has_rpc_origin || !restricted);
800 if(!r)
801 {
802 res.status = "Failed";
803 return true;
804 }
805 for (std::vector<cryptonote::spent_key_image_info>::const_iterator i = ki.begin(); i != ki.end(); ++i)
806 {
808 crypto::key_image spent_key_image;
809 if (parse_hash256(i->id_hash, hash))
810 {
811 memcpy(&spent_key_image, &hash, sizeof(hash)); // a bit dodgy, should be other parse functions somewhere
812 for (size_t n = 0; n < res.spent_status.size(); ++n)
813 {
814 if (res.spent_status[n] == SPENT_STATUS::UNSPENT)
815 {
816 if (key_images[n] == spent_key_image)
817 {
818 res.spent_status[n] = SPENT_STATUS::SPENT_IN_POOL;
819 break;
820 }
821 }
822 }
823 }
824 }
825
826 res.status = CORE_RPC_STATUS_OK;
827 return true;
828 }
bool on_is_key_image_spent(const COMMAND_RPC_IS_KEY_IMAGE_SPENT::request &req, COMMAND_RPC_IS_KEY_IMAGE_SPENT::response &res, const connection_context *ctx=NULL)
void * memcpy(void *a, const void *b, size_t c)
POD_CLASS key_image
Definition crypto.h:105
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_is_public_output_spent()

bool cryptonote::core_rpc_server::on_is_public_output_spent ( const COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT::request & req,
COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT::response & res,
const connection_context * ctx = NULL )

Definition at line 830 of file core_rpc_server.cpp.

831 {
833 bool ok;
834 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT>(invoke_http_mode::JON, "/is_public_output_spent", req, res, ok))
835 return ok;
836
837 const bool restricted = m_restricted && ctx;
838 const bool request_has_rpc_origin = ctx != NULL;
839 std::vector<txin_to_key_public> public_outputs_to_lookup; // vector of would-be inputs that reference the utxos
840
841 // Pre checks
842 for(const auto& public_output: req.public_outputs)
843 {
844 blobdata b;
845 if(!string_tools::parse_hexstr_to_binbuff(public_output.txid, b))
846 {
847 res.status = "Failed: tx input with public output (" + public_output.txid +
848 ") and relative out index (" +
849 std::to_string(public_output.relative_out_index) +
850 ") failed to parse from hex format.";
851 return true;
852 }
853 if(b.size() != sizeof(crypto::hash))
854 {
855 res.status = "Failed: tx input with public output (" + public_output.txid +
856 ") and relative out index (" +
857 std::to_string(public_output.relative_out_index) +
858 ") has the wrong size tx hash (should be 64 characters)";
859 return true;
860 }
861
862 // Check that the utxo ever existed before checking whether it currently does.
863 // Do this by fetching the transaction. Also check whether it has a number
864 // of outputs > the relative output index in question (which is zero indexed)
865 std::vector<crypto::hash> txs_ids;
866 std::vector<cryptonote::blobdata> txs;
867 std::vector<crypto::hash> missed_txs;
868 crypto::hash tx_hash;
869 epee::string_tools::hex_to_pod(public_output.txid, tx_hash);
870 txs_ids.push_back(tx_hash);
871
872 //we're only pulling one tx.
873 m_core.get_transactions(txs_ids, txs, missed_txs);
874
875 // error out if we have missing tx
876 if(!missed_txs.empty()){
877 res.status = "Failed: tx input with public output (" + public_output.txid +
878 ") and relative out index (" +
879 std::to_string(public_output.relative_out_index) +
880 ") does not exist in the database and therefore doesn't exist on chain";
881 return true;
882 }
883
884 // Check that we have an appropriate number of outputs for the tx going by the relative out index in the req
885 transaction tx;
887 if (tx.vout.size() <= public_output.relative_out_index) { // we're comparing 1 indexed to zero indexed
888 res.status = "Failed: public output (" + public_output.txid +
889 ") and relative out index (" +
890 std::to_string(public_output.relative_out_index) +
891 ") has an out of range relative out index";
892 return true;
893 }
894
895 txin_to_key_public txin;
896 txin.amount = public_output.amount;
897 epee::string_tools::hex_to_pod(public_output.txid, txin.tx_hash);
898 txin.relative_offset = public_output.relative_out_index;
899 public_outputs_to_lookup.emplace_back(txin);
900 }
901
902 //Now everything is parsed and we know all outputs existed at some point, check the spent status of the outputs
903 std::vector<bool> spent_status;
904 spent_status.reserve(public_outputs_to_lookup.size());
905 bool r = m_core.utxo_nonexistant(public_outputs_to_lookup, spent_status);
906 if(!r)
907 {
908 res.status = "Failed to check that UTXOs are spent";
909 return true;
910 }
911 res.spent_status.clear();
912 for (size_t n = 0; n < spent_status.size(); ++n)
913 res.spent_status.push_back(spent_status[n] ? SPENT_STATUS::SPENT_IN_BLOCKCHAIN : SPENT_STATUS::UNSPENT);
914
915 // adjust the statuses in the response derived from the blockchain if the utxos are spent in the pool
916 uint64_t res_counter = 0;
917 for (auto public_output: public_outputs_to_lookup) {
918 if (m_core.pool_has_utxo_as_spent(public_output)) {
919 if (res.spent_status[res_counter] == SPENT_STATUS::UNSPENT)
920 res.spent_status[res_counter] = SPENT_STATUS::SPENT_IN_POOL;
921 res_counter++;
922 }
923 }
924
925 res.status = CORE_RPC_STATUS_OK;
926 return true;
927 }
bool on_is_public_output_spent(const COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT::request &req, COMMAND_RPC_IS_PUBLIC_OUTPUT_SPENT::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_mining_status()

bool cryptonote::core_rpc_server::on_mining_status ( const COMMAND_RPC_MINING_STATUS::request & req,
COMMAND_RPC_MINING_STATUS::response & res,
const connection_context * ctx = NULL )

Definition at line 1079 of file core_rpc_server.cpp.

1080 {
1082
1083 const miner& lMiner = m_core.get_miner();
1084 res.active = lMiner.is_mining();
1085 res.is_background_mining_enabled = lMiner.get_is_background_mining_enabled();
1086 store_difficulty(m_core.get_blockchain_storage().get_difficulty_for_next_block(), res.difficulty, res.wide_difficulty, res.difficulty_top64);
1087
1088 res.block_target = m_core.get_blockchain_storage().get_current_hard_fork_version() < 6 ? DIFFICULTY_TARGET : DIFFICULTY_TARGET_V6;
1089 if ( lMiner.is_mining() ) {
1090 res.speed = lMiner.get_speed();
1091 res.threads_count = lMiner.get_threads_count();
1092 res.block_reward = lMiner.get_block_reward();
1093 }
1094 const account_public_address& lMiningAdr = lMiner.get_mining_address();
1095 res.address = get_account_address_as_str(nettype(), false, lMiningAdr);
1096 const uint8_t major_version = m_core.get_blockchain_storage().get_current_hard_fork_version();
1097 const unsigned variant = major_version >= 7 ? major_version - 6 : 0;
1098 switch (variant)
1099 {
1100 case 0: res.pow_algorithm = "Cryptonight"; break;
1101 case 1: res.pow_algorithm = "CNv1 (Cryptonight variant 1)"; break;
1102 case 2: case 3: res.pow_algorithm = "CNv2 (Cryptonight variant 2)"; break;
1103 case 4: case 5: res.pow_algorithm = "CNv4 (Cryptonight variant 4)"; break;
1104 default: res.pow_algorithm = "I'm not sure actually"; break;
1105 }
1106 if (res.is_background_mining_enabled)
1107 {
1108 res.bg_idle_threshold = lMiner.get_idle_threshold();
1109 res.bg_min_idle_seconds = lMiner.get_min_idle_seconds();
1110 res.bg_ignore_battery = lMiner.get_ignore_battery();
1111 res.bg_target = lMiner.get_mining_target();
1112 }
1113
1114 res.status = CORE_RPC_STATUS_OK;
1115 return true;
1116 }
bool on_mining_status(const COMMAND_RPC_MINING_STATUS::request &req, COMMAND_RPC_MINING_STATUS::response &res, const connection_context *ctx=NULL)
#define DIFFICULTY_TARGET
#define DIFFICULTY_TARGET_V6
std::string get_account_address_as_str(network_type nettype, bool subaddress, account_public_address const &adr)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_out_peers()

bool cryptonote::core_rpc_server::on_out_peers ( const COMMAND_RPC_OUT_PEERS::request & req,
COMMAND_RPC_OUT_PEERS::response & res,
const connection_context * ctx = NULL )

Definition at line 2304 of file core_rpc_server.cpp.

2305 {
2307 m_p2p.change_max_out_public_peers(req.out_peers);
2308 res.status = CORE_RPC_STATUS_OK;
2309 return true;
2310 }
bool on_out_peers(const COMMAND_RPC_OUT_PEERS::request &req, COMMAND_RPC_OUT_PEERS::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_pop_blocks()

bool cryptonote::core_rpc_server::on_pop_blocks ( const COMMAND_RPC_POP_BLOCKS::request & req,
COMMAND_RPC_POP_BLOCKS::response & res,
const connection_context * ctx = NULL )

Definition at line 2438 of file core_rpc_server.cpp.

2439 {
2441
2442 m_core.get_blockchain_storage().pop_blocks(req.nblocks);
2443
2444 res.height = m_core.get_current_blockchain_height();
2445 res.status = CORE_RPC_STATUS_OK;
2446
2447 return true;
2448 }
bool on_pop_blocks(const COMMAND_RPC_POP_BLOCKS::request &req, COMMAND_RPC_POP_BLOCKS::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_prune_blockchain()

bool cryptonote::core_rpc_server::on_prune_blockchain ( const COMMAND_RPC_PRUNE_BLOCKCHAIN::request & req,
COMMAND_RPC_PRUNE_BLOCKCHAIN::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2771 of file core_rpc_server.cpp.

2772 {
2773 try
2774 {
2775 if (!(req.check ? m_core.check_blockchain_pruning() : m_core.prune_blockchain()))
2776 {
2778 error_resp.message = req.check ? "Failed to check blockchain pruning" : "Failed to prune blockchain";
2779 return false;
2780 }
2781 res.pruning_seed = m_core.get_blockchain_pruning_seed();
2782 res.pruned = res.pruning_seed != 0;
2783 }
2784 catch (const std::exception &e)
2785 {
2787 error_resp.message = "Failed to prune blockchain";
2788 return false;
2789 }
2790
2791 res.status = CORE_RPC_STATUS_OK;
2792 return true;
2793 }
Here is the caller graph for this function:

◆ on_relay_tx()

bool cryptonote::core_rpc_server::on_relay_tx ( const COMMAND_RPC_RELAY_TX::request & req,
COMMAND_RPC_RELAY_TX::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2518 of file core_rpc_server.cpp.

2519 {
2521
2522 bool failed = false;
2523 res.status = "";
2524 for (const auto &str: req.txids)
2525 {
2526 cryptonote::blobdata txid_data;
2528 {
2529 if (!res.status.empty()) res.status += ", ";
2530 res.status += std::string("invalid transaction id: ") + str;
2531 failed = true;
2532 continue;
2533 }
2534 crypto::hash txid = *reinterpret_cast<const crypto::hash*>(txid_data.data());
2535
2536 cryptonote::blobdata txblob;
2537 bool r = m_core.get_pool_transaction(txid, txblob);
2538 if (r)
2539 {
2540 cryptonote_connection_context fake_context = AUTO_VAL_INIT(fake_context);
2542 r.txs.push_back(txblob);
2543 m_core.get_protocol()->relay_transactions(r, fake_context);
2544 //TODO: make sure that tx has reached other nodes here, probably wait to receive reflections from other nodes
2545 }
2546 else
2547 {
2548 if (!res.status.empty()) res.status += ", ";
2549 res.status += std::string("transaction not found in pool: ") + str;
2550 failed = true;
2551 continue;
2552 }
2553 }
2554
2555 if (failed)
2556 {
2557 return false;
2558 }
2559
2560 res.status = CORE_RPC_STATUS_OK;
2561 return true;
2562 }
bool on_relay_tx(const COMMAND_RPC_RELAY_TX::request &req, COMMAND_RPC_RELAY_TX::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
epee::misc_utils::struct_init< request_t > request
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_save_bc()

bool cryptonote::core_rpc_server::on_save_bc ( const COMMAND_RPC_SAVE_BC::request & req,
COMMAND_RPC_SAVE_BC::response & res,
const connection_context * ctx = NULL )

Definition at line 1118 of file core_rpc_server.cpp.

1119 {
1121 if( !m_core.get_blockchain_storage().store_blockchain() )
1122 {
1123 res.status = "Error while storing blockchain";
1124 return true;
1125 }
1126 res.status = CORE_RPC_STATUS_OK;
1127 return true;
1128 }
bool on_save_bc(const COMMAND_RPC_SAVE_BC::request &req, COMMAND_RPC_SAVE_BC::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_send_raw_tx()

bool cryptonote::core_rpc_server::on_send_raw_tx ( const COMMAND_RPC_SEND_RAW_TX::request & req,
COMMAND_RPC_SEND_RAW_TX::response & res,
const connection_context * ctx = NULL )

Definition at line 929 of file core_rpc_server.cpp.

930 {
932 bool ok;
933 if (use_bootstrap_daemon_if_necessary<COMMAND_RPC_SEND_RAW_TX>(invoke_http_mode::JON, "/sendrawtransaction", req, res, ok))
934 return ok;
935
937
938 std::string tx_blob;
939 if(!string_tools::parse_hexstr_to_binbuff(req.tx_as_hex, tx_blob))
940 {
941 LOG_PRINT_L0("[on_send_raw_tx]: Failed to parse tx from hexbuff: " << req.tx_as_hex);
942 res.status = "Failed";
943 return true;
944 }
945
946 if (req.do_sanity_checks && !cryptonote::tx_sanity_check(m_core.get_blockchain_storage(), tx_blob))
947 {
948 res.status = "Failed";
949 res.reason = "Sanity check failed";
950 res.sanity_check_failed = true;
951 return true;
952 }
953 res.sanity_check_failed = false;
954
955 cryptonote_connection_context fake_context = AUTO_VAL_INIT(fake_context);
956 tx_verification_context tvc = AUTO_VAL_INIT(tvc);
957 if(!m_core.handle_incoming_tx(tx_blob, tvc, false, false, req.do_not_relay) || tvc.m_verification_failed)
958 {
959 res.status = "Failed";
960 std::string reason = "";
961 if ((res.low_mixin = tvc.m_low_mixin))
962 add_reason(reason, "bad ring size");
963 if ((res.double_spend = tvc.m_double_spend))
964 add_reason(reason, "double spend");
965 if ((res.double_spend = tvc.m_utxo_nonexistent))
966 add_reason(reason, "utxo has been spent already or doesn't exist");
967 if ((res.invalid_input = tvc.m_invalid_input))
968 add_reason(reason, "invalid input");
969 if ((res.invalid_output = tvc.m_invalid_output))
970 add_reason(reason, "invalid output");
971 if ((res.too_big = tvc.m_too_big))
972 add_reason(reason, "too big");
973 if ((res.overspend = tvc.m_overspend))
974 add_reason(reason, "overspend");
975 if ((res.fee_too_low = tvc.m_fee_too_low))
976 add_reason(reason, "fee too low");
977 if ((res.not_rct = tvc.m_not_rct))
978 add_reason(reason, "tx is not ringct");
979 const std::string punctuation = reason.empty() ? "" : ": ";
980 if (tvc.m_verification_failed)
981 {
982 LOG_PRINT_L0("[on_send_raw_tx]: tx verification failed" << punctuation << reason);
983 }
984 else
985 {
986 LOG_PRINT_L0("[on_send_raw_tx]: Failed to process tx" << punctuation << reason);
987 }
988 return true;
989 }
990
991 if(!tvc.m_should_be_relayed)
992 {
993 LOG_PRINT_L0("[on_send_raw_tx]: tx accepted, but not relayed");
994 res.reason = "Not relayed";
995 res.not_relayed = true;
996 res.status = CORE_RPC_STATUS_OK;
997 return true;
998 }
999
1001 r.txs.push_back(tx_blob);
1002 m_core.get_protocol()->relay_transactions(r, fake_context);
1003 //TODO: make sure that tx has reached other nodes here, probably wait to receive reflections from other nodes
1004 res.status = CORE_RPC_STATUS_OK;
1005 return true;
1006 }
bool on_send_raw_tx(const COMMAND_RPC_SEND_RAW_TX::request &req, COMMAND_RPC_SEND_RAW_TX::response &res, const connection_context *ctx=NULL)
#define LOG_PRINT_L0(x)
Definition misc_log_ex.h:99
bool tx_sanity_check(Blockchain &blockchain, const cryptonote::blobdata &tx_blob)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_set_bans()

bool cryptonote::core_rpc_server::on_set_bans ( const COMMAND_RPC_SETBANS::request & req,
COMMAND_RPC_SETBANS::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2048 of file core_rpc_server.cpp.

2049 {
2051
2052 for (auto i = req.bans.begin(); i != req.bans.end(); ++i)
2053 {
2054 epee::net_utils::network_address na;
2055 if (!i->host.empty())
2056 {
2057 auto na_parsed = net::get_network_address(i->host, 0);
2058 if (!na_parsed)
2059 {
2061 error_resp.message = "Unsupported host type";
2062 return false;
2063 }
2064 na = std::move(*na_parsed);
2065 }
2066 else
2067 {
2068 na = epee::net_utils::ipv4_network_address{i->ip, 0};
2069 }
2070 if (i->ban) {
2071 if (i->seconds < -1) {
2073 error_resp.message = "Please pick a value for seconds >= -1";
2074 return false;
2075 } else if (i->seconds == -1) {
2076 m_p2p.block_host(na, uint32_t(std::numeric_limits<time_t>::max()));
2077 } else {
2078 m_p2p.block_host(na, uint32_t(i->seconds));
2079 }
2080 }
2081 else{
2082 m_p2p.unblock_host(na);
2083 }
2084
2085 }
2086
2087 res.status = CORE_RPC_STATUS_OK;
2088 return true;
2089 }
bool on_set_bans(const COMMAND_RPC_SETBANS::request &req, COMMAND_RPC_SETBANS::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
expect< epee::net_utils::network_address > get_network_address(const boost::string_ref address, const std::uint16_t default_port)
Definition parse.cpp:38
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_set_limit()

bool cryptonote::core_rpc_server::on_set_limit ( const COMMAND_RPC_SET_LIMIT::request & req,
COMMAND_RPC_SET_LIMIT::response & res,
const connection_context * ctx = NULL )

Definition at line 2264 of file core_rpc_server.cpp.

2265 {
2267 // -1 = reset to default
2268 // 0 = do not modify
2269
2270 if (req.limit_down > 0)
2271 {
2273 }
2274 else if (req.limit_down < 0)
2275 {
2276 if (req.limit_down != -1)
2277 {
2279 return false;
2280 }
2282 }
2283
2284 if (req.limit_up > 0)
2285 {
2287 }
2288 else if (req.limit_up < 0)
2289 {
2290 if (req.limit_up != -1)
2291 {
2293 return false;
2294 }
2296 }
2297
2300 res.status = CORE_RPC_STATUS_OK;
2301 return true;
2302 }
bool on_set_limit(const COMMAND_RPC_SET_LIMIT::request &req, COMMAND_RPC_SET_LIMIT::response &res, const connection_context *ctx=NULL)
static void set_rate_down_limit(uint64_t limit)
static void set_rate_up_limit(uint64_t limit)
const int64_t default_limit_up
Definition net_node.h:481
const int64_t default_limit_down
Definition net_node.h:482
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_set_log_categories()

bool cryptonote::core_rpc_server::on_set_log_categories ( const COMMAND_RPC_SET_LOG_CATEGORIES::request & req,
COMMAND_RPC_SET_LOG_CATEGORIES::response & res,
const connection_context * ctx = NULL )

Definition at line 1189 of file core_rpc_server.cpp.

1190 {
1192 mlog_set_log(req.categories.c_str());
1193 res.categories = mlog_get_categories();
1194 res.status = CORE_RPC_STATUS_OK;
1195 return true;
1196 }
bool on_set_log_categories(const COMMAND_RPC_SET_LOG_CATEGORIES::request &req, COMMAND_RPC_SET_LOG_CATEGORIES::response &res, const connection_context *ctx=NULL)
std::string mlog_get_categories()
Definition mlog.cpp:276
void mlog_set_log(const char *log)
Definition mlog.cpp:288
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_set_log_hash_rate()

bool cryptonote::core_rpc_server::on_set_log_hash_rate ( const COMMAND_RPC_SET_LOG_HASH_RATE::request & req,
COMMAND_RPC_SET_LOG_HASH_RATE::response & res,
const connection_context * ctx = NULL )

Definition at line 1161 of file core_rpc_server.cpp.

1162 {
1164 if(m_core.get_miner().is_mining())
1165 {
1166 m_core.get_miner().do_print_hashrate(req.visible);
1167 res.status = CORE_RPC_STATUS_OK;
1168 }
1169 else
1170 {
1172 }
1173 return true;
1174 }
bool on_set_log_hash_rate(const COMMAND_RPC_SET_LOG_HASH_RATE::request &req, COMMAND_RPC_SET_LOG_HASH_RATE::response &res, const connection_context *ctx=NULL)
#define CORE_RPC_STATUS_NOT_MINING
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_set_log_level()

bool cryptonote::core_rpc_server::on_set_log_level ( const COMMAND_RPC_SET_LOG_LEVEL::request & req,
COMMAND_RPC_SET_LOG_LEVEL::response & res,
const connection_context * ctx = NULL )

Definition at line 1176 of file core_rpc_server.cpp.

1177 {
1179 if (req.level > 4)
1180 {
1181 res.status = "Error: log level not valid";
1182 return true;
1183 }
1184 mlog_set_log_level(req.level);
1185 res.status = CORE_RPC_STATUS_OK;
1186 return true;
1187 }
bool on_set_log_level(const COMMAND_RPC_SET_LOG_LEVEL::request &req, COMMAND_RPC_SET_LOG_LEVEL::response &res, const connection_context *ctx=NULL)
void mlog_set_log_level(int level)
Definition mlog.cpp:282
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_set_validator_key()

bool cryptonote::core_rpc_server::on_set_validator_key ( const COMMAND_RPC_SET_VALIDATOR_KEY::request & req,
COMMAND_RPC_SET_VALIDATOR_KEY::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2611 of file core_rpc_server.cpp.

2612 {
2613 if(!m_core.set_validator_key(req.validator_key)) {
2615 error_resp.message = "Failed to set Validator Key. Wrong format.";
2616 return false;
2617 }
2618
2619 res.status = CORE_RPC_STATUS_OK;
2620 return true;
2621 }
Here is the caller graph for this function:

◆ on_sign_message()

bool cryptonote::core_rpc_server::on_sign_message ( const COMMAND_RPC_SIGN_MESSAGE::request & req,
COMMAND_RPC_SIGN_MESSAGE::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2641 of file core_rpc_server.cpp.

2642 {
2643 try {
2644 std::string v = m_core.sign_message(boost::algorithm::unhex(req.privateKey), req.message);
2645
2646 if (v.empty()) {
2648 error_resp.message = "Failed to sign message.";
2649 return false;
2650 }
2651
2652 res.signature = v;
2653 }
2654 catch(const std::exception &e)
2655 {
2657 error_resp.message = "Failed to sign message. Please check that you are using a valid private key.";
2658 return false;
2659 }
2660
2661 res.status = CORE_RPC_STATUS_OK;
2662 return true;
2663 }
Here is the caller graph for this function:

◆ on_start_mining()

bool cryptonote::core_rpc_server::on_start_mining ( const COMMAND_RPC_START_MINING::request & req,
COMMAND_RPC_START_MINING::response & res,
const connection_context * ctx = NULL )

Definition at line 1008 of file core_rpc_server.cpp.

1009 {
1012 cryptonote::address_parse_info info;
1013 if(!get_account_address_from_str(info, nettype(), req.miner_address))
1014 {
1015 res.status = "Failed, wrong address";
1016 LOG_PRINT_L0(res.status);
1017 return true;
1018 }
1019 if (info.is_subaddress)
1020 {
1021 res.status = "Mining to subaddress isn't supported yet";
1022 LOG_PRINT_L0(res.status);
1023 return true;
1024 }
1025
1026 unsigned int concurrency_count = boost::thread::hardware_concurrency() * 4;
1027
1028 // if we couldn't detect threads, set it to a ridiculously high number
1029 if(concurrency_count == 0)
1030 {
1031 concurrency_count = 257;
1032 }
1033
1034 // if there are more threads requested than the hardware supports
1035 // then we fail and log that.
1036 if(req.threads_count > concurrency_count)
1037 {
1038 res.status = "Failed, too many threads relative to CPU cores.";
1039 LOG_PRINT_L0(res.status);
1040 return true;
1041 }
1042
1043 cryptonote::miner &miner= m_core.get_miner();
1044 if (miner.is_mining())
1045 {
1046 res.status = "Already mining";
1047 return true;
1048 }
1049 if(!miner.start(info.address, static_cast<size_t>(req.threads_count), req.do_background_mining, req.ignore_battery))
1050 {
1051 res.status = "Failed, mining not started";
1052 LOG_PRINT_L0(res.status);
1053 return true;
1054 }
1055 res.status = CORE_RPC_STATUS_OK;
1056 return true;
1057 }
bool on_start_mining(const COMMAND_RPC_START_MINING::request &req, COMMAND_RPC_START_MINING::response &res, const connection_context *ctx=NULL)
bool is_mining() const
Definition miner.cpp:359
bool start(const account_public_address &adr, size_t threads_count, bool do_background=false, bool ignore_battery=false)
Definition miner.cpp:373
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_start_save_graph()

bool cryptonote::core_rpc_server::on_start_save_graph ( const COMMAND_RPC_START_SAVE_GRAPH::request & req,
COMMAND_RPC_START_SAVE_GRAPH::response & res,
const connection_context * ctx = NULL )

Definition at line 2320 of file core_rpc_server.cpp.

2321 {
2323 m_p2p.set_save_graph(true);
2324 res.status = CORE_RPC_STATUS_OK;
2325 return true;
2326 }
bool on_start_save_graph(const COMMAND_RPC_START_SAVE_GRAPH::request &req, COMMAND_RPC_START_SAVE_GRAPH::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_stop_daemon()

bool cryptonote::core_rpc_server::on_stop_daemon ( const COMMAND_RPC_STOP_DAEMON::request & req,
COMMAND_RPC_STOP_DAEMON::response & res,
const connection_context * ctx = NULL )

Definition at line 1260 of file core_rpc_server.cpp.

1261 {
1263 // FIXME: replace back to original m_p2p.send_stop_signal() after
1264 // investigating why that isn't working quite right.
1265 m_p2p.send_stop_signal();
1266 res.status = CORE_RPC_STATUS_OK;
1267 return true;
1268 }
bool on_stop_daemon(const COMMAND_RPC_STOP_DAEMON::request &req, COMMAND_RPC_STOP_DAEMON::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_stop_mining()

bool cryptonote::core_rpc_server::on_stop_mining ( const COMMAND_RPC_STOP_MINING::request & req,
COMMAND_RPC_STOP_MINING::response & res,
const connection_context * ctx = NULL )

Definition at line 1059 of file core_rpc_server.cpp.

1060 {
1062 cryptonote::miner &miner= m_core.get_miner();
1063 if(!miner.is_mining())
1064 {
1065 res.status = "Mining never started";
1066 LOG_PRINT_L0(res.status);
1067 return true;
1068 }
1069 if(!miner.stop())
1070 {
1071 res.status = "Failed, mining not stopped";
1072 LOG_PRINT_L0(res.status);
1073 return true;
1074 }
1075 res.status = CORE_RPC_STATUS_OK;
1076 return true;
1077 }
bool on_stop_mining(const COMMAND_RPC_STOP_MINING::request &req, COMMAND_RPC_STOP_MINING::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_stop_save_graph()

bool cryptonote::core_rpc_server::on_stop_save_graph ( const COMMAND_RPC_STOP_SAVE_GRAPH::request & req,
COMMAND_RPC_STOP_SAVE_GRAPH::response & res,
const connection_context * ctx = NULL )

Definition at line 2328 of file core_rpc_server.cpp.

2329 {
2331 m_p2p.set_save_graph(false);
2332 res.status = CORE_RPC_STATUS_OK;
2333 return true;
2334 }
bool on_stop_save_graph(const COMMAND_RPC_STOP_SAVE_GRAPH::request &req, COMMAND_RPC_STOP_SAVE_GRAPH::response &res, const connection_context *ctx=NULL)
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_submitblock()

bool cryptonote::core_rpc_server::on_submitblock ( const COMMAND_RPC_SUBMITBLOCK::request & req,
COMMAND_RPC_SUBMITBLOCK::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 1424 of file core_rpc_server.cpp.

1425 {
1427 {
1428 boost::shared_lock<boost::shared_mutex> lock(m_bootstrap_daemon_mutex);
1429 if (m_should_use_bootstrap_daemon)
1430 {
1431 res.status = "This command is unsupported for bootstrap daemon";
1432 return false;
1433 }
1434 }
1436 if(req.size()!=1)
1437 {
1439 error_resp.message = "Wrong param";
1440 return false;
1441 }
1442 blobdata blockblob;
1443 if(!string_tools::parse_hexstr_to_binbuff(req[0], blockblob))
1444 {
1446 error_resp.message = "Wrong block blob";
1447 return false;
1448 }
1449
1450 // Fixing of high orphan issue for most pools
1451 // Thanks Boolberry!
1452 block b;
1453 if(!parse_and_validate_block_from_blob(blockblob, b))
1454 {
1456 error_resp.message = "Wrong block blob";
1457 return false;
1458 }
1459
1460 // Fix from Boolberry neglects to check block
1461 // size, do that with the function below
1462 if(!m_core.check_incoming_block_size(blockblob))
1463 {
1465 error_resp.message = "Block bloc size is too big, rejecting block";
1466 return false;
1467 }
1468
1469 block_verification_context bvc;
1470 if(!m_core.handle_block_found(b, bvc))
1471 {
1473 error_resp.message = "Block not accepted";
1474 return false;
1475 }
1476 res.status = CORE_RPC_STATUS_OK;
1477 return true;
1478 }
#define CORE_RPC_ERROR_CODE_WRONG_BLOCKBLOB_SIZE
#define CORE_RPC_ERROR_CODE_BLOCK_NOT_ACCEPTED
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_sync_info()

bool cryptonote::core_rpc_server::on_sync_info ( const COMMAND_RPC_SYNC_INFO::request & req,
COMMAND_RPC_SYNC_INFO::response & res,
epee::json_rpc::error & error_resp,
const connection_context * ctx = NULL )

Definition at line 2564 of file core_rpc_server.cpp.

2565 {
2567
2568 crypto::hash top_hash;
2569 m_core.get_blockchain_top(res.height, top_hash);
2570 ++res.height; // turn top block height into blockchain height
2571 res.target_height = m_core.get_target_blockchain_height();
2572 res.next_needed_pruning_seed = m_p2p.get_payload_object().get_next_needed_pruning_stripe().second;
2573
2574 for (const auto &c: m_p2p.get_payload_object().get_connections())
2575 res.peers.push_back({c});
2576 const cryptonote::block_queue &block_queue = m_p2p.get_payload_object().get_block_queue();
2577 block_queue.foreach([&](const cryptonote::block_queue::span &span) {
2578 const std::string span_connection_id = epee::string_tools::pod_to_hex(span.connection_id);
2579 uint32_t speed = (uint32_t)(100.0f * block_queue.get_speed(span.connection_id) + 0.5f);
2580 std::string address = "";
2581 for (const auto &c: m_p2p.get_payload_object().get_connections())
2582 if (c.connection_id == span_connection_id)
2583 address = c.address;
2584 res.spans.push_back({span.start_block_height, span.nblocks, span_connection_id, (uint32_t)(span.rate + 0.5f), speed, span.size, address});
2585 return true;
2586 });
2587 res.overview = block_queue.get_overview(res.height);
2588
2589 res.status = CORE_RPC_STATUS_OK;
2590 return true;
2591 }
float get_speed(const boost::uuids::uuid &connection_id) const
bool foreach(std::function< bool(const span &)> f) const
std::string get_overview(uint64_t blockchain_height) const
bool on_sync_info(const COMMAND_RPC_SYNC_INFO::request &req, COMMAND_RPC_SYNC_INFO::response &res, epee::json_rpc::error &error_resp, const connection_context *ctx=NULL)
boost::uuids::uuid connection_id
Definition block_queue.h:56
const char * address
Definition multisig.cpp:37
Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_update()

bool cryptonote::core_rpc_server::on_update ( const COMMAND_RPC_UPDATE::request & req,
COMMAND_RPC_UPDATE::response & res,
const connection_context * ctx = NULL )

Definition at line 2336 of file core_rpc_server.cpp.

2337 {
2339
2340 if (m_core.offline())
2341 {
2342 res.status = "Daemon is running offline";
2343 return true;
2344 }
2345
2346 static const char software[] = "electroneum";
2347#ifdef BUILD_TAG
2348 static const char buildtag[] = BOOST_PP_STRINGIZE(BUILD_TAG);
2349 static const char subdir[] = "cli";
2350#else
2351 static const char buildtag[] = "source";
2352 static const char subdir[] = "source";
2353#endif
2354 LOG_PRINT_L0(req.command << " for software: " << software << "; buildtag: " << buildtag << "; subdir:" << subdir);
2355 if (req.command != "check" && req.command != "download" && req.command != "update")
2356 {
2357 res.status = std::string("unknown command: '") + req.command + "'";
2358 return true;
2359 }
2360
2361 std::string version, hash;
2362 if (!tools::check_updates(software, buildtag, version, hash))
2363 {
2364 res.status = "Error checking for updates";
2365 return true;
2366 }
2367 if (tools::vercmp(version.c_str(), ELECTRONEUM_VERSION) <= 0)
2368 {
2369 res.update = false;
2370 res.status = CORE_RPC_STATUS_OK;
2371 return true;
2372 }
2373 res.update = true;
2374 res.version = version;
2375 res.user_uri = tools::get_update_url(software, subdir, buildtag, version, true);
2376 res.auto_uri = tools::get_update_url(software, subdir, buildtag, version, false);
2377 res.hash = hash;
2378 if (req.command == "check")
2379 {
2380 res.status = CORE_RPC_STATUS_OK;
2381 return true;
2382 }
2383
2384 boost::filesystem::path path;
2385 if (req.path.empty())
2386 {
2387 std::string filename;
2388 const char *slash = strrchr(res.auto_uri.c_str(), '/');
2389 if (slash)
2390 filename = slash + 1;
2391 else
2392 filename = std::string(software) + "-update-" + version;
2394 path /= filename;
2395 }
2396 else
2397 {
2398 path = req.path;
2399 }
2400
2401 crypto::hash file_hash;
2402 if (!tools::sha256sum(path.string(), file_hash) || (hash != epee::string_tools::pod_to_hex(file_hash)))
2403 {
2404 MDEBUG("We don't have that file already, downloading");
2405 if (!tools::download(path.string(), res.auto_uri))
2406 {
2407 MERROR("Failed to download " << res.auto_uri);
2408 return false;
2409 }
2410 if (!tools::sha256sum(path.string(), file_hash))
2411 {
2412 MERROR("Failed to hash " << path);
2413 return false;
2414 }
2415 if (hash != epee::string_tools::pod_to_hex(file_hash))
2416 {
2417 MERROR("Download from " << res.auto_uri << " does not match the expected hash");
2418 return false;
2419 }
2420 MINFO("New version downloaded to " << path);
2421 }
2422 else
2423 {
2424 MDEBUG("We already have " << path << " with expected hash");
2425 }
2426 res.path = path.string();
2427
2428 if (req.command == "download")
2429 {
2430 res.status = CORE_RPC_STATUS_OK;
2431 return true;
2432 }
2433
2434 res.status = "'update' not implemented yet";
2435 return true;
2436 }
bool on_update(const COMMAND_RPC_UPDATE::request &req, COMMAND_RPC_UPDATE::response &res, const connection_context *ctx=NULL)
#define MINFO(x)
Definition misc_log_ex.h:75
std::string & get_current_module_folder()
int vercmp(const char *v0, const char *v1)
Definition util.cpp:915
bool sha256sum(const uint8_t *data, size_t len, crypto::hash &hash)
Definition util.cpp:933
std::string get_update_url(const std::string &software, const std::string &subdir, const std::string &buildtag, const std::string &version, bool user)
Definition updates.cpp:101
bool download(const std::string &path, const std::string &url, std::function< bool(const std::string &, const std::string &, size_t, ssize_t)> cb)
Definition download.cpp:258
bool check_updates(const std::string &software, const std::string &buildtag, std::string &version, std::string &hash)
Definition updates.cpp:41
Here is the call graph for this function:
Here is the caller graph for this function:

Member Data Documentation

◆ arg_bootstrap_daemon_address

const command_line::arg_descriptor< std::string > cryptonote::core_rpc_server::arg_bootstrap_daemon_address
static
Initial value:
= {
"bootstrap-daemon-address"
, "URL of a 'bootstrap' remote daemon that the connected wallets can use while this daemon is still not fully synced"
, ""
}

Definition at line 72 of file core_rpc_server.h.

◆ arg_bootstrap_daemon_login

const command_line::arg_descriptor< std::string > cryptonote::core_rpc_server::arg_bootstrap_daemon_login
static
Initial value:
= {
"bootstrap-daemon-login"
, "Specify username:password for the bootstrap daemon login"
, ""
}

Definition at line 73 of file core_rpc_server.h.

◆ arg_public_node

const command_line::arg_descriptor<bool> cryptonote::core_rpc_server::arg_public_node
static

Definition at line 62 of file core_rpc_server.h.

◆ arg_restricted_rpc

const command_line::arg_descriptor< bool > cryptonote::core_rpc_server::arg_restricted_rpc
static
Initial value:
= {
"restricted-rpc"
, "Restrict RPC to view only commands and do not return privacy sensitive data in RPC calls"
, false
}

Definition at line 65 of file core_rpc_server.h.

◆ arg_rpc_bind_port

const command_line::arg_descriptor< std::string, false, true, 2 > cryptonote::core_rpc_server::arg_rpc_bind_port
static
Initial value:
= {
"rpc-bind-port"
, "Port for RPC server"
, std::to_string(config::RPC_DEFAULT_PORT)
, [](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)
return std::to_string(config::stagenet::RPC_DEFAULT_PORT);
return val;
}
}
uint16_t const RPC_DEFAULT_PORT
uint16_t const RPC_DEFAULT_PORT
uint16_t const RPC_DEFAULT_PORT
const command_line::arg_descriptor< bool, false > arg_testnet_on
const command_line::arg_descriptor< bool, false > arg_stagenet_on

Definition at line 63 of file core_rpc_server.h.

◆ arg_rpc_restricted_bind_port

const command_line::arg_descriptor< std::string > cryptonote::core_rpc_server::arg_rpc_restricted_bind_port
static
Initial value:
= {
"rpc-restricted-bind-port"
, "Port for restricted RPC server"
, ""
}

Definition at line 64 of file core_rpc_server.h.

◆ arg_rpc_ssl

const command_line::arg_descriptor<std::string> cryptonote::core_rpc_server::arg_rpc_ssl
static

Definition at line 66 of file core_rpc_server.h.

◆ arg_rpc_ssl_allow_any_cert

const command_line::arg_descriptor<bool> cryptonote::core_rpc_server::arg_rpc_ssl_allow_any_cert
static

Definition at line 71 of file core_rpc_server.h.

◆ arg_rpc_ssl_allowed_fingerprints

const command_line::arg_descriptor<std::vector<std::string> > cryptonote::core_rpc_server::arg_rpc_ssl_allowed_fingerprints
static

Definition at line 70 of file core_rpc_server.h.

◆ arg_rpc_ssl_ca_certificates

const command_line::arg_descriptor<std::string> cryptonote::core_rpc_server::arg_rpc_ssl_ca_certificates
static

Definition at line 69 of file core_rpc_server.h.

◆ arg_rpc_ssl_certificate

const command_line::arg_descriptor<std::string> cryptonote::core_rpc_server::arg_rpc_ssl_certificate
static

Definition at line 68 of file core_rpc_server.h.

◆ arg_rpc_ssl_private_key

const command_line::arg_descriptor<std::string> cryptonote::core_rpc_server::arg_rpc_ssl_private_key
static

Definition at line 67 of file core_rpc_server.h.


The documentation for this class was generated from the following files:
  • /home/abuild/rpmbuild/BUILD/electroneum-5.1.3.1-build/electroneum-5.1.3.1/src/rpc/core_rpc_server.h
  • /home/abuild/rpmbuild/BUILD/electroneum-5.1.3.1-build/electroneum-5.1.3.1/src/rpc/core_rpc_server.cpp