diff --git a/libraries/chain/include/eosio/chain/transaction_metadata.hpp b/libraries/chain/include/eosio/chain/transaction_metadata.hpp index 5f2be488dc8..60f89e2c4fe 100644 --- a/libraries/chain/include/eosio/chain/transaction_metadata.hpp +++ b/libraries/chain/include/eosio/chain/transaction_metadata.hpp @@ -51,7 +51,7 @@ class transaction_metadata { const flat_set& recover_keys( const chain_id_type& chain_id ); - static void create_signing_keys_future( transaction_metadata_ptr& mtrx, + static void create_signing_keys_future( const transaction_metadata_ptr& mtrx, boost::asio::thread_pool& thread_pool, const chain_id_type& chain_id ); uint32_t total_actions()const { return trx.context_free_actions.size() + trx.actions.size(); } diff --git a/libraries/chain/transaction.cpp b/libraries/chain/transaction.cpp index 6e6639bac52..d2528dc21a3 100644 --- a/libraries/chain/transaction.cpp +++ b/libraries/chain/transaction.cpp @@ -95,9 +95,10 @@ flat_set transaction::get_signature_keys( const vector::type::iterator it = recovery_cache.get().find( sig ); - if( it == recovery_cache.get().end() || it->trx_id != id()) { + const auto& tid = id(); + if( it == recovery_cache.get().end() || it->trx_id != tid) { recov = public_key_type( sig, digest ); - recovery_cache.emplace_back(cached_pub_key{id(), recov, sig} ); //could fail on dup signatures; not a problem + recovery_cache.emplace_back(cached_pub_key{tid, recov, sig} ); //could fail on dup signatures; not a problem } else { recov = it->pub_key; } diff --git a/libraries/chain/transaction_metadata.cpp b/libraries/chain/transaction_metadata.cpp index 9afc1a01fd0..068f711f6b0 100644 --- a/libraries/chain/transaction_metadata.cpp +++ b/libraries/chain/transaction_metadata.cpp @@ -19,8 +19,14 @@ const flat_set& transaction_metadata::recover_keys( const chain return signing_keys->second; } -void transaction_metadata::create_signing_keys_future( transaction_metadata_ptr& mtrx, +void transaction_metadata::create_signing_keys_future( const transaction_metadata_ptr& mtrx, boost::asio::thread_pool& thread_pool, const chain_id_type& chain_id ) { + if( mtrx->signing_keys && mtrx->signing_keys->first == chain_id ) + return; + + if( mtrx->signing_keys.valid() ) // already created + return; + std::weak_ptr mtrx_wp = mtrx; mtrx->signing_keys_future = async_thread_pool( thread_pool, [chain_id, mtrx_wp]() { auto mtrx = mtrx_wp.lock(); diff --git a/plugins/producer_plugin/producer_plugin.cpp b/plugins/producer_plugin/producer_plugin.cpp index 1a1d7d0d515..d0bda3edf0a 100644 --- a/plugins/producer_plugin/producer_plugin.cpp +++ b/plugins/producer_plugin/producer_plugin.cpp @@ -346,6 +346,18 @@ class producer_plugin_impl : public std::enable_shared_from_this>> _pending_incoming_transactions; void on_incoming_transaction_async(const transaction_metadata_ptr& trx, bool persist_until_expired, next_function next) { + chain::controller& chain = chain_plug->chain(); + transaction_metadata::create_signing_keys_future( trx, chain.get_thread_pool(), chain.get_chain_id() ); + boost::asio::post( chain.get_thread_pool(), [self = this, trx, persist_until_expired, next]() { + if( trx->signing_keys_future.valid() ) + trx->signing_keys_future.wait(); + app().get_io_service().post( [self, trx, persist_until_expired, next]() { + self->process_incoming_transaction_async( trx, persist_until_expired, next ); + }); + }); + } + + void process_incoming_transaction_async(const transaction_metadata_ptr& trx, bool persist_until_expired, next_function next) { chain::controller& chain = chain_plug->chain(); if (!chain.pending_block_state()) { _pending_incoming_transactions.emplace_back(trx, persist_until_expired, next); @@ -1245,7 +1257,7 @@ producer_plugin_impl::start_block_result producer_plugin_impl::start_block(bool _pending_incoming_transactions.pop_front(); --orig_pending_txn_size; _incoming_trx_weight -= 1.0; - on_incoming_transaction_async(std::get<0>(e), std::get<1>(e), std::get<2>(e)); + process_incoming_transaction_async(std::get<0>(e), std::get<1>(e), std::get<2>(e)); } if (block_time <= fc::time_point::now()) { @@ -1308,7 +1320,7 @@ producer_plugin_impl::start_block_result producer_plugin_impl::start_block(bool auto e = _pending_incoming_transactions.front(); _pending_incoming_transactions.pop_front(); --orig_pending_txn_size; - on_incoming_transaction_async(std::get<0>(e), std::get<1>(e), std::get<2>(e)); + process_incoming_transaction_async(std::get<0>(e), std::get<1>(e), std::get<2>(e)); if (block_time <= fc::time_point::now()) return start_block_result::exhausted; } }