diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/cryptonote_core/blockchain.cpp | 16 | ||||
-rw-r--r-- | src/cryptonote_core/cryptonote_core.cpp | 12 | ||||
-rw-r--r-- | src/cryptonote_core/cryptonote_core.h | 9 | ||||
-rw-r--r-- | src/cryptonote_core/tx_pool.cpp | 16 | ||||
-rw-r--r-- | src/cryptonote_core/tx_pool.h | 14 | ||||
-rw-r--r-- | src/cryptonote_protocol/cryptonote_protocol_handler.inl | 8 | ||||
-rw-r--r-- | src/daemon/rpc_command_executor.cpp | 2 | ||||
-rw-r--r-- | src/rpc/core_rpc_server.cpp | 4 | ||||
-rw-r--r-- | src/rpc/core_rpc_server_commands_defs.h | 4 |
9 files changed, 51 insertions, 34 deletions
diff --git a/src/cryptonote_core/blockchain.cpp b/src/cryptonote_core/blockchain.cpp index de3af8e02..96b3f6bba 100644 --- a/src/cryptonote_core/blockchain.cpp +++ b/src/cryptonote_core/blockchain.cpp @@ -508,7 +508,7 @@ block Blockchain::pop_block_from_blockchain() // that might not be always true. Unlikely though, and always relaying // these again might cause a spike of traffic as many nodes re-relay // all the transactions in a popped block when a reorg happens. - bool r = m_tx_pool.add_tx(tx, tvc, true, true, version); + bool r = m_tx_pool.add_tx(tx, tvc, true, true, false, version); if (!r) { LOG_ERROR("Error returning transaction to tx_pool"); @@ -2973,7 +2973,7 @@ void Blockchain::return_tx_to_pool(const std::vector<transaction> &txs) // that might not be always true. Unlikely though, and always relaying // these again might cause a spike of traffic as many nodes re-relay // all the transactions in a popped block when a reorg happens. - if (!m_tx_pool.add_tx(tx, tvc, true, true, version)) + if (!m_tx_pool.add_tx(tx, tvc, true, true, false, version)) { LOG_PRINT_L0("Failed to return taken transaction with hash: " << get_transaction_hash(tx) << " to tx_pool"); } @@ -2990,9 +2990,9 @@ bool Blockchain::flush_txes_from_pool(const std::list<crypto::hash> &txids) cryptonote::transaction tx; size_t blob_size; uint64_t fee; - bool relayed; + bool relayed, do_not_relay; LOG_PRINT_L1("Removing txid " << txid << " from the pool"); - if(m_tx_pool.have_tx(txid) && !m_tx_pool.take_tx(txid, tx, blob_size, fee, relayed)) + if(m_tx_pool.have_tx(txid) && !m_tx_pool.take_tx(txid, tx, blob_size, fee, relayed, do_not_relay)) { LOG_PRINT_L0("Failed to remove txid " << txid << " from the pool"); res = false; @@ -3153,7 +3153,7 @@ leave: transaction tx; size_t blob_size = 0; uint64_t fee = 0; - bool relayed = false; + bool relayed = false, do_not_relay = false; TIME_MEASURE_START(aa); // XXX old code does not check whether tx exists @@ -3170,7 +3170,7 @@ leave: TIME_MEASURE_START(bb); // get transaction with hash <tx_id> from tx_pool - if(!m_tx_pool.take_tx(tx_id, tx, blob_size, fee, relayed)) + if(!m_tx_pool.take_tx(tx_id, tx, blob_size, fee, relayed, do_not_relay)) { LOG_PRINT_L1("Block with id: " << id << " has at least one unknown transaction with id: " << tx_id); bvc.m_verifivation_failed = true; @@ -3954,12 +3954,12 @@ void Blockchain::load_compiled_in_block_hashes() size_t blob_size; uint64_t fee; - bool relayed; + bool relayed, do_not_relay; transaction pool_tx; for(const transaction &tx : txs) { crypto::hash tx_hash = get_transaction_hash(tx); - m_tx_pool.take_tx(tx_hash, pool_tx, blob_size, fee, relayed); + m_tx_pool.take_tx(tx_hash, pool_tx, blob_size, fee, relayed, do_not_relay); } } } diff --git a/src/cryptonote_core/cryptonote_core.cpp b/src/cryptonote_core/cryptonote_core.cpp index c63a08ee4..f1574d3c7 100644 --- a/src/cryptonote_core/cryptonote_core.cpp +++ b/src/cryptonote_core/cryptonote_core.cpp @@ -452,7 +452,7 @@ namespace cryptonote return false; } //----------------------------------------------------------------------------------------------- - bool core::handle_incoming_tx(const blobdata& tx_blob, tx_verification_context& tvc, bool keeped_by_block, bool relayed) + bool core::handle_incoming_tx(const blobdata& tx_blob, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay) { tvc = boost::value_initialized<tx_verification_context>(); //want to process all transactions sequentially @@ -501,7 +501,7 @@ namespace cryptonote return false; } - bool r = add_new_tx(tx, tx_hash, tx_prefixt_hash, tx_blob.size(), tvc, keeped_by_block, relayed); + bool r = add_new_tx(tx, tx_hash, tx_prefixt_hash, tx_blob.size(), tvc, keeped_by_block, relayed, do_not_relay); if(tvc.m_verifivation_failed) {LOG_PRINT_RED_L1("Transaction verification failed: " << tx_hash);} else if(tvc.m_verifivation_impossible) @@ -640,13 +640,13 @@ namespace cryptonote return true; } //----------------------------------------------------------------------------------------------- - bool core::add_new_tx(const transaction& tx, tx_verification_context& tvc, bool keeped_by_block, bool relayed) + bool core::add_new_tx(const transaction& tx, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay) { crypto::hash tx_hash = get_transaction_hash(tx); crypto::hash tx_prefix_hash = get_transaction_prefix_hash(tx); blobdata bl; t_serializable_object_to_blob(tx, bl); - return add_new_tx(tx, tx_hash, tx_prefix_hash, bl.size(), tvc, keeped_by_block, relayed); + return add_new_tx(tx, tx_hash, tx_prefix_hash, bl.size(), tvc, keeped_by_block, relayed, do_not_relay); } //----------------------------------------------------------------------------------------------- size_t core::get_blockchain_total_transactions() const @@ -654,7 +654,7 @@ namespace cryptonote return m_blockchain_storage.get_total_transactions(); } //----------------------------------------------------------------------------------------------- - bool core::add_new_tx(const transaction& tx, const crypto::hash& tx_hash, const crypto::hash& tx_prefix_hash, size_t blob_size, tx_verification_context& tvc, bool keeped_by_block, bool relayed) + bool core::add_new_tx(const transaction& tx, const crypto::hash& tx_hash, const crypto::hash& tx_prefix_hash, size_t blob_size, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay) { if(m_mempool.have_tx(tx_hash)) { @@ -669,7 +669,7 @@ namespace cryptonote } uint8_t version = m_blockchain_storage.get_current_hard_fork_version(); - return m_mempool.add_tx(tx, tx_hash, blob_size, tvc, keeped_by_block, relayed, version); + return m_mempool.add_tx(tx, tx_hash, blob_size, tvc, keeped_by_block, relayed, do_not_relay, version); } //----------------------------------------------------------------------------------------------- bool core::relay_txpool_transactions() diff --git a/src/cryptonote_core/cryptonote_core.h b/src/cryptonote_core/cryptonote_core.h index a9e80aeee..fa67ff265 100644 --- a/src/cryptonote_core/cryptonote_core.h +++ b/src/cryptonote_core/cryptonote_core.h @@ -107,10 +107,11 @@ namespace cryptonote * @param tvc metadata about the transaction's validity * @param keeped_by_block if the transaction has been in a block * @param relayed whether or not the transaction was relayed to us + * @param do_not_relay whether to prevent the transaction from being relayed * * @return true if the transaction made it to the transaction pool, otherwise false */ - bool handle_incoming_tx(const blobdata& tx_blob, tx_verification_context& tvc, bool keeped_by_block, bool relayed); + bool handle_incoming_tx(const blobdata& tx_blob, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay); /** * @brief handles an incoming block @@ -641,9 +642,10 @@ namespace cryptonote * @param tx_prefix_hash the transaction prefix' hash * @param blob_size the size of the transaction * @param relayed whether or not the transaction was relayed to us + * @param do_not_relay whether to prevent the transaction from being relayed * */ - bool add_new_tx(const transaction& tx, const crypto::hash& tx_hash, const crypto::hash& tx_prefix_hash, size_t blob_size, tx_verification_context& tvc, bool keeped_by_block, bool relayed); + bool add_new_tx(const transaction& tx, const crypto::hash& tx_hash, const crypto::hash& tx_prefix_hash, size_t blob_size, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay); /** * @brief add a new transaction to the transaction pool @@ -654,12 +656,13 @@ namespace cryptonote * @param tvc return-by-reference metadata about the transaction's verification process * @param keeped_by_block whether or not the transaction has been in a block * @param relayed whether or not the transaction was relayed to us + * @param do_not_relay whether to prevent the transaction from being relayed * * @return true if the transaction is already in the transaction pool, * is already in a block on the Blockchain, or is successfully added * to the transaction pool */ - bool add_new_tx(const transaction& tx, tx_verification_context& tvc, bool keeped_by_block, bool relayed); + bool add_new_tx(const transaction& tx, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay); /** * @copydoc Blockchain::add_new_block diff --git a/src/cryptonote_core/tx_pool.cpp b/src/cryptonote_core/tx_pool.cpp index 59ac534fe..f60c7cea9 100644 --- a/src/cryptonote_core/tx_pool.cpp +++ b/src/cryptonote_core/tx_pool.cpp @@ -83,7 +83,7 @@ namespace cryptonote } //--------------------------------------------------------------------------------- - bool tx_memory_pool::add_tx(const transaction &tx, /*const crypto::hash& tx_prefix_hash,*/ const crypto::hash &id, size_t blob_size, tx_verification_context& tvc, bool kept_by_block, bool relayed, uint8_t version) + bool tx_memory_pool::add_tx(const transaction &tx, /*const crypto::hash& tx_prefix_hash,*/ const crypto::hash &id, size_t blob_size, tx_verification_context& tvc, bool kept_by_block, bool relayed, bool do_not_relay, uint8_t version) { PERF_TIMER(add_tx); if (tx.version == 0) @@ -201,6 +201,7 @@ namespace cryptonote txd_p.first->second.receive_time = time(nullptr); txd_p.first->second.last_relayed_time = time(NULL); txd_p.first->second.relayed = relayed; + txd_p.first->second.do_not_relay = do_not_relay; tvc.m_verifivation_impossible = true; tvc.m_added_to_pool = true; }else @@ -224,9 +225,10 @@ namespace cryptonote txd_p.first->second.receive_time = time(nullptr); txd_p.first->second.last_relayed_time = time(NULL); txd_p.first->second.relayed = relayed; + txd_p.first->second.do_not_relay = do_not_relay; tvc.m_added_to_pool = true; - if(txd_p.first->second.fee > 0) + if(txd_p.first->second.fee > 0 && !do_not_relay) tvc.m_should_be_relayed = true; } @@ -251,12 +253,12 @@ namespace cryptonote return true; } //--------------------------------------------------------------------------------- - bool tx_memory_pool::add_tx(const transaction &tx, tx_verification_context& tvc, bool keeped_by_block, bool relayed, uint8_t version) + bool tx_memory_pool::add_tx(const transaction &tx, tx_verification_context& tvc, bool keeped_by_block, bool relayed, bool do_not_relay, uint8_t version) { crypto::hash h = null_hash; size_t blob_size = 0; get_transaction_hash(tx, h, blob_size); - return add_tx(tx, h, blob_size, tvc, keeped_by_block, relayed, version); + return add_tx(tx, h, blob_size, tvc, keeped_by_block, relayed, do_not_relay, version); } //--------------------------------------------------------------------------------- //FIXME: Can return early before removal of all of the key images. @@ -292,7 +294,7 @@ namespace cryptonote return true; } //--------------------------------------------------------------------------------- - bool tx_memory_pool::take_tx(const crypto::hash &id, transaction &tx, size_t& blob_size, uint64_t& fee, bool &relayed) + bool tx_memory_pool::take_tx(const crypto::hash &id, transaction &tx, size_t& blob_size, uint64_t& fee, bool &relayed, bool &do_not_relay) { CRITICAL_REGION_LOCAL(m_transactions_lock); auto it = m_transactions.find(id); @@ -308,6 +310,7 @@ namespace cryptonote blob_size = it->second.blob_size; fee = it->second.fee; relayed = it->second.relayed; + do_not_relay = it->second.do_not_relay; remove_transaction_keyimages(it->second.tx); m_transactions.erase(it); m_txs_by_fee.erase(sorted_it); @@ -367,7 +370,7 @@ namespace cryptonote for(auto it = m_transactions.begin(); it!= m_transactions.end();) { // 0 fee transactions are never relayed - if(it->second.fee > 0 && now - it->second.last_relayed_time > get_relay_delay(now, it->second.receive_time)) + if(it->second.fee > 0 && !it->second.do_not_relay && now - it->second.last_relayed_time > get_relay_delay(now, it->second.receive_time)) { // if the tx is older than half the max lifetime, we don't re-relay it, to avoid a problem // mentioned by smooth where nodes would flush txes at slightly different times, causing @@ -431,6 +434,7 @@ namespace cryptonote txi.receive_time = txd.receive_time; txi.relayed = txd.relayed; txi.last_relayed_time = txd.last_relayed_time; + txi.do_not_relay = txd.do_not_relay; tx_infos.push_back(txi); } diff --git a/src/cryptonote_core/tx_pool.h b/src/cryptonote_core/tx_pool.h index 32a05b0f4..b330057a6 100644 --- a/src/cryptonote_core/tx_pool.h +++ b/src/cryptonote_core/tx_pool.h @@ -103,7 +103,7 @@ namespace cryptonote * @param id the transaction's hash * @param blob_size the transaction's size */ - bool add_tx(const transaction &tx, const crypto::hash &id, size_t blob_size, tx_verification_context& tvc, bool kept_by_block, bool relayed, uint8_t version); + bool add_tx(const transaction &tx, const crypto::hash &id, size_t blob_size, tx_verification_context& tvc, bool kept_by_block, bool relayed, bool do_not_relay, uint8_t version); /** * @brief add a transaction to the transaction pool @@ -117,11 +117,12 @@ namespace cryptonote * @param tvc return-by-reference status about the transaction verification * @param kept_by_block has this transaction been in a block? * @param relayed was this transaction from the network or a local client? + * @param do_not_relay to avoid relaying the transaction to the network * @param version the version used to create the transaction * * @return true if the transaction passes validations, otherwise false */ - bool add_tx(const transaction &tx, tx_verification_context& tvc, bool kept_by_block, bool relayed, uint8_t version); + bool add_tx(const transaction &tx, tx_verification_context& tvc, bool kept_by_block, bool relayed, bool do_not_relay, uint8_t version); /** * @brief takes a transaction with the given hash from the pool @@ -131,10 +132,11 @@ namespace cryptonote * @param blob_size return-by-reference the transaction's size * @param fee the transaction fee * @param relayed return-by-reference was transaction relayed to us by the network? + * @param do_not_relay return-by-reference is transaction not to be relayed to the network? * * @return true unless the transaction cannot be found in the pool */ - bool take_tx(const crypto::hash &id, transaction &tx, size_t& blob_size, uint64_t& fee, bool &relayed); + bool take_tx(const crypto::hash &id, transaction &tx, size_t& blob_size, uint64_t& fee, bool &relayed, bool &do_not_relay); /** * @brief checks if the pool has a transaction with the given hash @@ -303,7 +305,7 @@ namespace cryptonote #define CURRENT_MEMPOOL_ARCHIVE_VER 11 -#define CURRENT_MEMPOOL_TX_DETAILS_ARCHIVE_VER 11 +#define CURRENT_MEMPOOL_TX_DETAILS_ARCHIVE_VER 12 /** * @brief serialize the transaction pool to/from disk @@ -362,6 +364,7 @@ namespace cryptonote time_t last_relayed_time; //!< the last time the transaction was relayed to the network bool relayed; //!< whether or not the transaction has been relayed to the network + bool do_not_relay; //!< to avoid relay this transaction to the network }; private: @@ -515,6 +518,9 @@ namespace boost if (version < 11) return; ar & td.kept_by_block; + if (version < 12) + return; + ar & td.do_not_relay; } } } diff --git a/src/cryptonote_protocol/cryptonote_protocol_handler.inl b/src/cryptonote_protocol/cryptonote_protocol_handler.inl index b13c1f437..54f1c849e 100644 --- a/src/cryptonote_protocol/cryptonote_protocol_handler.inl +++ b/src/cryptonote_protocol/cryptonote_protocol_handler.inl @@ -328,7 +328,7 @@ namespace cryptonote for(auto tx_blob_it = arg.b.txs.begin(); tx_blob_it!=arg.b.txs.end();tx_blob_it++) { cryptonote::tx_verification_context tvc = AUTO_VAL_INIT(tvc); - m_core.handle_incoming_tx(*tx_blob_it, tvc, true, true); + m_core.handle_incoming_tx(*tx_blob_it, tvc, true, true, false); if(tvc.m_verifivation_failed) { LOG_PRINT_CCONTEXT_L1("Block verification failed: transaction verification failed, dropping connection"); @@ -478,7 +478,7 @@ namespace cryptonote if(!m_core.get_pool_transaction(tx_hash, tx)) { cryptonote::tx_verification_context tvc = AUTO_VAL_INIT(tvc); - if(!m_core.handle_incoming_tx(tx_blob, tvc, true, true) || tvc.m_verifivation_failed) + if(!m_core.handle_incoming_tx(tx_blob, tvc, true, true, false) || tvc.m_verifivation_failed) { LOG_PRINT_CCONTEXT_L1("Block verification failed: transaction verification failed, dropping connection"); m_p2p->drop_connection(context); @@ -682,7 +682,7 @@ namespace cryptonote for(auto tx_blob_it = arg.txs.begin(); tx_blob_it!=arg.txs.end();) { cryptonote::tx_verification_context tvc = AUTO_VAL_INIT(tvc); - m_core.handle_incoming_tx(*tx_blob_it, tvc, false, true); + m_core.handle_incoming_tx(*tx_blob_it, tvc, false, true, false); if(tvc.m_verifivation_failed) { LOG_PRINT_CCONTEXT_L1("Tx verification failed, dropping connection"); @@ -874,7 +874,7 @@ namespace cryptonote BOOST_FOREACH(auto& tx_blob, block_entry.txs) { tx_verification_context tvc = AUTO_VAL_INIT(tvc); - m_core.handle_incoming_tx(tx_blob, tvc, true, true); + m_core.handle_incoming_tx(tx_blob, tvc, true, true, false); if(tvc.m_verifivation_failed) { LOG_ERROR_CCONTEXT("transaction verification failed on NOTIFY_RESPONSE_GET_OBJECTS, \r\ntx_id = " diff --git a/src/daemon/rpc_command_executor.cpp b/src/daemon/rpc_command_executor.cpp index 447783d76..0feeab1a9 100644 --- a/src/daemon/rpc_command_executor.cpp +++ b/src/daemon/rpc_command_executor.cpp @@ -743,6 +743,7 @@ bool t_rpc_command_executor::print_transaction_pool_long() { << "fee: " << cryptonote::print_money(tx_info.fee) << std::endl << "receive_time: " << tx_info.receive_time << " (" << get_human_time_ago(tx_info.receive_time, now) << ")" << std::endl << "relayed: " << [&](const cryptonote::tx_info &tx_info)->std::string { if (!tx_info.relayed) return "no"; return boost::lexical_cast<std::string>(tx_info.last_relayed_time) + " (" + get_human_time_ago(tx_info.last_relayed_time, now) + ")"; } (tx_info) << std::endl + << "do_not_relay: " << (tx_info.do_not_relay ? 'T' : 'F') << std::endl << "kept_by_block: " << (tx_info.kept_by_block ? 'T' : 'F') << std::endl << "max_used_block_height: " << tx_info.max_used_block_height << std::endl << "max_used_block_id: " << tx_info.max_used_block_id_hash << std::endl @@ -823,6 +824,7 @@ bool t_rpc_command_executor::print_transaction_pool_short() { << "fee: " << cryptonote::print_money(tx_info.fee) << std::endl << "receive_time: " << tx_info.receive_time << " (" << get_human_time_ago(tx_info.receive_time, now) << ")" << std::endl << "relayed: " << [&](const cryptonote::tx_info &tx_info)->std::string { if (!tx_info.relayed) return "no"; return boost::lexical_cast<std::string>(tx_info.last_relayed_time) + " (" + get_human_time_ago(tx_info.last_relayed_time, now) + ")"; } (tx_info) << std::endl + << "do_not_relay: " << (tx_info.do_not_relay ? 'T' : 'F') << std::endl << "kept_by_block: " << (tx_info.kept_by_block ? 'T' : 'F') << std::endl << "max_used_block_height: " << tx_info.max_used_block_height << std::endl << "max_used_block_id: " << tx_info.max_used_block_id_hash << std::endl diff --git a/src/rpc/core_rpc_server.cpp b/src/rpc/core_rpc_server.cpp index ddf892cae..cfa1b3b4b 100644 --- a/src/rpc/core_rpc_server.cpp +++ b/src/rpc/core_rpc_server.cpp @@ -528,7 +528,7 @@ namespace cryptonote cryptonote_connection_context fake_context = AUTO_VAL_INIT(fake_context); tx_verification_context tvc = AUTO_VAL_INIT(tvc); - if(!m_core.handle_incoming_tx(tx_blob, tvc, false, false) || tvc.m_verifivation_failed) + if(!m_core.handle_incoming_tx(tx_blob, tvc, false, false, req.do_not_relay) || tvc.m_verifivation_failed) { if (tvc.m_verifivation_failed) { @@ -558,7 +558,7 @@ namespace cryptonote return true; } - if(!tvc.m_should_be_relayed || req.do_not_relay) + if(!tvc.m_should_be_relayed) { LOG_PRINT_L0("[on_send_raw_tx]: tx accepted, but not relayed"); res.reason = "Not relayed"; diff --git a/src/rpc/core_rpc_server_commands_defs.h b/src/rpc/core_rpc_server_commands_defs.h index fa86c08e4..88a594281 100644 --- a/src/rpc/core_rpc_server_commands_defs.h +++ b/src/rpc/core_rpc_server_commands_defs.h @@ -49,7 +49,7 @@ namespace cryptonote // advance which version they will stop working with // Don't go over 32767 for any of these #define CORE_RPC_VERSION_MAJOR 1 -#define CORE_RPC_VERSION_MINOR 4 +#define CORE_RPC_VERSION_MINOR 5 #define CORE_RPC_VERSION (((CORE_RPC_VERSION_MAJOR)<<16)|(CORE_RPC_VERSION_MINOR)) struct COMMAND_RPC_GET_HEIGHT @@ -920,6 +920,7 @@ namespace cryptonote uint64_t receive_time; bool relayed; uint64_t last_relayed_time; + bool do_not_relay; BEGIN_KV_SERIALIZE_MAP() KV_SERIALIZE(id_hash) @@ -934,6 +935,7 @@ namespace cryptonote KV_SERIALIZE(receive_time) KV_SERIALIZE(relayed) KV_SERIALIZE(last_relayed_time) + KV_SERIALIZE(do_not_relay) END_KV_SERIALIZE_MAP() }; |