diff options
Diffstat (limited to 'src/cryptonote_core')
-rw-r--r-- | src/cryptonote_core/account.cpp | 8 | ||||
-rw-r--r-- | src/cryptonote_core/blockchain.cpp | 14 | ||||
-rw-r--r-- | src/cryptonote_core/cryptonote_core.cpp | 11 | ||||
-rw-r--r-- | src/cryptonote_core/tx_pool.cpp | 32 | ||||
-rw-r--r-- | src/cryptonote_core/tx_pool.h | 15 |
5 files changed, 51 insertions, 29 deletions
diff --git a/src/cryptonote_core/account.cpp b/src/cryptonote_core/account.cpp index 602561489..bd703eee2 100644 --- a/src/cryptonote_core/account.cpp +++ b/src/cryptonote_core/account.cpp @@ -82,7 +82,9 @@ DISABLE_VS_WARNINGS(4244 4345) if (recover) { - m_creation_timestamp = std::max(mktime(×tamp), (long)0); + m_creation_timestamp = mktime(×tamp); + if (m_creation_timestamp == (uint64_t)-1) // failure + m_creation_timestamp = 0; // lowest value } else { @@ -105,7 +107,9 @@ DISABLE_VS_WARNINGS(4244 4345) timestamp.tm_min = 0; timestamp.tm_sec = 0; - m_creation_timestamp = std::max(mktime(×tamp), (long)0); + m_creation_timestamp = mktime(×tamp); + if (m_creation_timestamp == (uint64_t)-1) // failure + m_creation_timestamp = 0; // lowest value } //----------------------------------------------------------------- void account_base::create_from_viewkey(const cryptonote::account_public_address& address, const crypto::secret_key& viewkey) diff --git a/src/cryptonote_core/blockchain.cpp b/src/cryptonote_core/blockchain.cpp index aabed36b2..deae72a54 100644 --- a/src/cryptonote_core/blockchain.cpp +++ b/src/cryptonote_core/blockchain.cpp @@ -3383,9 +3383,10 @@ bool Blockchain::add_new_block(const block& bl_, block_verification_context& bvc void Blockchain::check_against_checkpoints(const checkpoints& points, bool enforce) { const auto& pts = points.get_points(); + bool stop_batch; CRITICAL_REGION_LOCAL(m_blockchain_lock); - m_db->batch_start(); + stop_batch = m_db->batch_start(); for (const auto& pt : pts) { // if the checkpoint is for a block we don't have yet, move on @@ -3409,7 +3410,8 @@ void Blockchain::check_against_checkpoints(const checkpoints& points, bool enfor } } } - m_db->batch_stop(); + if (stop_batch) + m_db->batch_stop(); } //------------------------------------------------------------------ // returns false if any of the checkpoints loading returns false. @@ -3483,6 +3485,7 @@ bool Blockchain::cleanup_handle_incoming_blocks(bool force_sync) CRITICAL_REGION_LOCAL(m_blockchain_lock); TIME_MEASURE_START(t1); + m_db->batch_stop(); if (m_sync_counter > 0) { if (force_sync) @@ -3547,11 +3550,18 @@ bool Blockchain::prepare_handle_incoming_blocks(const std::list<block_complete_e { LOG_PRINT_YELLOW("Blockchain::" << __func__, LOG_LEVEL_3); TIME_MEASURE_START(prepare); + bool stop_batch; CRITICAL_REGION_LOCAL(m_blockchain_lock); if(blocks_entry.size() == 0) return false; + while (!(stop_batch = m_db->batch_start(blocks_entry.size()))) { + m_blockchain_lock.unlock(); + epee::misc_utils::sleep_no_w(1000); + m_blockchain_lock.lock(); + } + if ((m_db->height() + blocks_entry.size()) < m_blocks_hash_check.size()) return true; diff --git a/src/cryptonote_core/cryptonote_core.cpp b/src/cryptonote_core/cryptonote_core.cpp index c63a08ee4..c2da7aaea 100644 --- a/src/cryptonote_core/cryptonote_core.cpp +++ b/src/cryptonote_core/cryptonote_core.cpp @@ -312,9 +312,9 @@ namespace cryptonote LOG_PRINT_L0("Loading blockchain from folder " << folder.string() << " ..."); const std::string filename = folder.string(); - // temporarily default to fastest:async:1000 + // default to fast:async:1 blockchain_db_sync_mode sync_mode = db_async; - uint64_t blocks_per_sync = 1000; + uint64_t blocks_per_sync = 1; try { @@ -327,12 +327,12 @@ namespace cryptonote for(const auto &option : options) LOG_PRINT_L0("option: " << option); - // default to fast:async:1000 + // default to fast:async:1 uint64_t DEFAULT_FLAGS = DBS_FAST_MODE; if(options.size() == 0) { - // temporarily default to fastest:async:1000 + // default to fast:async:1 db_flags = DEFAULT_FLAGS; } @@ -348,7 +348,10 @@ namespace cryptonote else if(options[0] == "fast") db_flags = DBS_FAST_MODE; else if(options[0] == "fastest") + { db_flags = DBS_FASTEST_MODE; + blocks_per_sync = 1000; // default to fastest:async:1000 + } else db_flags = DEFAULT_FLAGS; } diff --git a/src/cryptonote_core/tx_pool.cpp b/src/cryptonote_core/tx_pool.cpp index 59ac534fe..028585741 100644 --- a/src/cryptonote_core/tx_pool.cpp +++ b/src/cryptonote_core/tx_pool.cpp @@ -177,6 +177,8 @@ namespace cryptonote return false; } + time_t receive_time = time(nullptr); + crypto::hash max_used_block_id = null_hash; uint64_t max_used_block_height = 0; tx_details txd; @@ -198,7 +200,7 @@ namespace cryptonote txd_p.first->second.last_failed_height = 0; txd_p.first->second.last_failed_id = null_hash; txd_p.first->second.kept_by_block = kept_by_block; - txd_p.first->second.receive_time = time(nullptr); + txd_p.first->second.receive_time = receive_time; txd_p.first->second.last_relayed_time = time(NULL); txd_p.first->second.relayed = relayed; tvc.m_verifivation_impossible = true; @@ -221,7 +223,7 @@ namespace cryptonote txd_p.first->second.max_used_block_height = max_used_block_height; txd_p.first->second.last_failed_height = 0; txd_p.first->second.last_failed_id = null_hash; - txd_p.first->second.receive_time = time(nullptr); + txd_p.first->second.receive_time = receive_time; txd_p.first->second.last_relayed_time = time(NULL); txd_p.first->second.relayed = relayed; tvc.m_added_to_pool = true; @@ -246,7 +248,7 @@ namespace cryptonote tvc.m_verifivation_failed = false; - m_txs_by_fee.emplace((double)blob_size / fee, id); + m_txs_by_fee_and_receive_time.emplace(std::pair<double, std::time_t>((double)blob_size / fee, receive_time), id); return true; } @@ -301,7 +303,7 @@ namespace cryptonote auto sorted_it = find_tx_in_sorted_container(id); - if (sorted_it == m_txs_by_fee.end()) + if (sorted_it == m_txs_by_fee_and_receive_time.end()) return false; tx = it->second.tx; @@ -310,7 +312,7 @@ namespace cryptonote relayed = it->second.relayed; remove_transaction_keyimages(it->second.tx); m_transactions.erase(it); - m_txs_by_fee.erase(sorted_it); + m_txs_by_fee_and_receive_time.erase(sorted_it); return true; } //--------------------------------------------------------------------------------- @@ -321,7 +323,7 @@ namespace cryptonote //--------------------------------------------------------------------------------- sorted_tx_container::iterator tx_memory_pool::find_tx_in_sorted_container(const crypto::hash& id) const { - return std::find_if( m_txs_by_fee.begin(), m_txs_by_fee.end() + return std::find_if( m_txs_by_fee_and_receive_time.begin(), m_txs_by_fee_and_receive_time.end() , [&](const sorted_tx_container::value_type& a){ return a.second == id; } @@ -342,13 +344,13 @@ namespace cryptonote LOG_PRINT_L1("Tx " << it->first << " removed from tx pool due to outdated, age: " << tx_age ); remove_transaction_keyimages(it->second.tx); auto sorted_it = find_tx_in_sorted_container(it->first); - if (sorted_it == m_txs_by_fee.end()) + if (sorted_it == m_txs_by_fee_and_receive_time.end()) { LOG_PRINT_L1("Removing tx " << it->first << " from tx pool, but it was not found in the sorted txs container!"); } else { - m_txs_by_fee.erase(sorted_it); + m_txs_by_fee_and_receive_time.erase(sorted_it); } m_timed_out_transactions.insert(it->first); auto pit = it++; @@ -608,9 +610,9 @@ namespace cryptonote size_t max_total_size = 2 * median_size - CRYPTONOTE_COINBASE_BLOB_RESERVED_SIZE; std::unordered_set<crypto::key_image> k_images; - LOG_PRINT_L2("Filling block template, median size " << median_size << ", " << m_txs_by_fee.size() << " txes in the pool"); - auto sorted_it = m_txs_by_fee.begin(); - while (sorted_it != m_txs_by_fee.end()) + LOG_PRINT_L2("Filling block template, median size " << median_size << ", " << m_txs_by_fee_and_receive_time.size() << " txes in the pool"); + auto sorted_it = m_txs_by_fee_and_receive_time.begin(); + while (sorted_it != m_txs_by_fee_and_receive_time.end()) { auto tx_it = m_transactions.find(sorted_it->second); LOG_PRINT_L2("Considering " << tx_it->first << ", size " << tx_it->second.blob_size << ", current block size " << total_size << "/" << max_total_size << ", current coinbase " << print_money(best_coinbase)); @@ -675,13 +677,13 @@ namespace cryptonote LOG_PRINT_L1("Transaction " << get_transaction_hash(it->second.tx) << " is too big (" << it->second.blob_size << " bytes), removing it from pool"); remove_transaction_keyimages(it->second.tx); auto sorted_it = find_tx_in_sorted_container(it->first); - if (sorted_it == m_txs_by_fee.end()) + if (sorted_it == m_txs_by_fee_and_receive_time.end()) { LOG_PRINT_L1("Removing tx " << it->first << " from tx pool, but it was not found in the sorted txs container!"); } else { - m_txs_by_fee.erase(sorted_it); + m_txs_by_fee_and_receive_time.erase(sorted_it); } auto pit = it++; m_transactions.erase(pit); @@ -712,14 +714,14 @@ namespace cryptonote LOG_ERROR("Failed to load memory pool from file " << state_file_path); m_transactions.clear(); - m_txs_by_fee.clear(); + m_txs_by_fee_and_receive_time.clear(); m_spent_key_images.clear(); } // no need to store queue of sorted transactions, as it's easy to generate. for (const auto& tx : m_transactions) { - m_txs_by_fee.emplace((double)tx.second.blob_size / tx.second.fee, tx.first); + m_txs_by_fee_and_receive_time.emplace(std::pair<double, time_t>((double)tx.second.blob_size / tx.second.fee, tx.second.receive_time), tx.first); } // Ignore deserialization error diff --git a/src/cryptonote_core/tx_pool.h b/src/cryptonote_core/tx_pool.h index 32a05b0f4..9258a0c38 100644 --- a/src/cryptonote_core/tx_pool.h +++ b/src/cryptonote_core/tx_pool.h @@ -54,23 +54,25 @@ namespace cryptonote /************************************************************************/ //! pair of <transaction fee, transaction hash> for organization - typedef std::pair<double, crypto::hash> tx_by_fee_entry; + typedef std::pair<std::pair<double, std::time_t>, crypto::hash> tx_by_fee_and_receive_time_entry; class txCompare { public: - bool operator()(const tx_by_fee_entry& a, const tx_by_fee_entry& b) + bool operator()(const tx_by_fee_and_receive_time_entry& a, const tx_by_fee_and_receive_time_entry& b) { // sort by greatest first, not least - if (a.first > b.first) return true; - else if (a.first < b.first) return false; + if (a.first.first > b.first.first) return true; + else if (a.first.first < b.first.first) return false; + else if (a.first.second < b.first.second) return true; + else if (a.first.second > b.first.second) return false; else if (a.second != b.second) return true; else return false; } }; //! container for sorting transactions by fee per unit size - typedef std::set<tx_by_fee_entry, txCompare> sorted_tx_container; + typedef std::set<tx_by_fee_and_receive_time_entry, txCompare> sorted_tx_container; /** * @brief Transaction pool, handles transactions which are not part of a block @@ -473,7 +475,8 @@ private: epee::math_helper::once_a_time_seconds<30> m_remove_stuck_tx_interval; //TODO: look into doing this better - sorted_tx_container m_txs_by_fee; //!< container for transactions organized by fee per size + //!< container for transactions organized by fee per size and receive time + sorted_tx_container m_txs_by_fee_and_receive_time; /** * @brief get an iterator to a transaction in the sorted container |