diff --git a/src/cpp/ripple/HashedObject.cpp b/src/cpp/ripple/HashedObject.cpp index 49a451050a..cfa9dcdace 100644 --- a/src/cpp/ripple/HashedObject.cpp +++ b/src/cpp/ripple/HashedObject.cpp @@ -12,7 +12,8 @@ SETUP_LOG(); DECLARE_INSTANCE(HashedObject); HashedObjectStore::HashedObjectStore(int cacheSize, int cacheAge) : - mCache("HashedObjectStore", cacheSize, cacheAge), mWriteGeneration(0), mWritePending(false) + mCache("HashedObjectStore", cacheSize, cacheAge), mNegativeCache("HashedObjectNegativeCache", 0, 120), + mWriteGeneration(0), mWritePending(false) { mWriteSet.reserve(128); } diff --git a/src/cpp/ripple/KeyCache.h b/src/cpp/ripple/KeyCache.h index e5ec5262d0..e4a1d87270 100644 --- a/src/cpp/ripple/KeyCache.h +++ b/src/cpp/ripple/KeyCache.h @@ -1,6 +1,8 @@ #ifndef KEY_CACHE__H #define KEY_CACHE__H +#include + #include #include @@ -12,40 +14,58 @@ public: typedef typename map_type::iterator map_iterator; protected: - boost::mutex mNCLock; - map_type mCache; - int mTargetSize, mTargetAge; + const std::string mName; + boost::mutex mNCLock; + map_type mCache; + int mTargetSize, mTargetAge; - uint64_t mHits, mMisses; - public: - KeyCache(int size = 0, int age = 120) : mTargetSize(size), mTargetAge(age), mHits(0), mMisses(0) + KeyCache(const std::string& name, int size = 0, int age = 120) : mName(name), mTargetSize(size), mTargetAge(age) { assert((mTargetSize >= 0) && (mTargetAge > 2)); } - void getStats(int& size, uint64_t& hits, uint64_t& misses) + void getSize() { boost::mutex::scoped_lock sl(mNCLock); - - size = mCache.size(); - hits = mHits; - misses = mMisses; + return mCache.size(); } - bool isPresent(const key_type& key) + void getTargetSize() + { + boost::mutex::scoped_lock sl(mNCLock); + return mTargetSize; + } + + void getTargetAge() + { + boost::mutex::scoped_lock sl(mNCLock); + return mTargetAge; + } + + void setTargets(int size, int age) + { + boost::mutex::scoped_lock sl(mNCLock); + mTargetSize = size; + mTargetAge = age; + assert((mTargetSize >= 0) && (mTargetAge > 2)); + } + + const std::string& getName() + { + return mName; + } + + bool isPresent(const key_type& key, bool refresh = true) { // Check if an entry is cached, refresh it if so boost::mutex::scoped_lock sl(mNCLock); map_iterator it = mCache.find(key); if (it == mCache.end()) - { - ++mMisses; return false; - } - it->second = time(NULL); - ++mHits; + if (refresh) + it->second = time(NULL); return true; } diff --git a/src/cpp/ripple/LedgerAcquire.cpp b/src/cpp/ripple/LedgerAcquire.cpp index 5fce7a9ee6..e3ad9a92d7 100644 --- a/src/cpp/ripple/LedgerAcquire.cpp +++ b/src/cpp/ripple/LedgerAcquire.cpp @@ -74,8 +74,9 @@ void PeerSet::TimerEntry(boost::weak_ptr wptr, const boost::system::err ptr->invokeOnTimer(); } -LedgerAcquire::LedgerAcquire(const uint256& hash) : PeerSet(hash, LEDGER_ACQUIRE_TIMEOUT), mHaveBase(false), - mHaveState(false), mHaveTransactions(false), mAborted(false), mSignaled(false), mAccept(false), mByHash(true) +LedgerAcquire::LedgerAcquire(const uint256& hash) : PeerSet(hash, LEDGER_ACQUIRE_TIMEOUT), + mHaveBase(false), mHaveState(false), mHaveTransactions(false), mAborted(false), mSignaled(false), mAccept(false), + mByHash(true) { #ifdef LA_DEBUG cLog(lsTRACE) << "Acquiring ledger " << mHash; @@ -724,57 +725,10 @@ SMAddNode LedgerAcquireMaster::gotLedgerData(ripple::TMLedgerData& packet, Peer: return SMAddNode::invalid(); } -void LedgerAcquireMaster::logFailure(const uint256& hash) -{ - time_t now = time(NULL); - boost::mutex::scoped_lock sl(mLock); - - std::map::iterator it = mRecentFailures.begin(); - while (it != mRecentFailures.end()) - { - if (it->first == hash) - { - it->second = now; - return; - } - if (it->second > now) - { // time jump or discontinuity - it->second = now; - ++it; - } - else if ((it->second + 180) < now) - mRecentFailures.erase(it++); - else - ++it; - } - mRecentFailures[hash] = now; -} - -bool LedgerAcquireMaster::isFailure(const uint256& hash) -{ - time_t now = time(NULL); - boost::mutex::scoped_lock sl(mLock); - - std::map::iterator it = mRecentFailures.find(hash); - if (it == mRecentFailures.end()) - return false; - - if (it->second > now) - { - it->second = now; - return true; - } - - if ((it->second + 180) < now) - { - mRecentFailures.erase(it); - return false; - } - return true; -} - void LedgerAcquireMaster::sweep() { + mRecentFailures.sweep(); + time_t now = time(NULL); boost::mutex::scoped_lock sl(mLock); diff --git a/src/cpp/ripple/LedgerAcquire.h b/src/cpp/ripple/LedgerAcquire.h index b5c3386123..9c63a5d6bf 100644 --- a/src/cpp/ripple/LedgerAcquire.h +++ b/src/cpp/ripple/LedgerAcquire.h @@ -18,6 +18,11 @@ #include "InstanceCounter.h" #include "ripple.pb.h" +// How long before we try again to acquire the same ledger +#ifndef LEDGER_REACQUIRE_INTERVAL +#define LEDGER_REACQUIRE_INTERVAL 180 +#endif + DEFINE_INSTANCE(LedgerAcquire); class PeerSet @@ -123,10 +128,10 @@ class LedgerAcquireMaster protected: boost::mutex mLock; std::map mLedgers; - std::map mRecentFailures; + KeyCache mRecentFailures; public: - LedgerAcquireMaster() { ; } + LedgerAcquireMaster() : mRecentFailures("LedgerAcquireRecentFailures", 0, LEDGER_REACQUIRE_INTERVAL) { ; } LedgerAcquire::pointer findCreate(const uint256& hash); LedgerAcquire::pointer find(const uint256& hash); @@ -134,8 +139,8 @@ public: void dropLedger(const uint256& ledgerHash); SMAddNode gotLedgerData(ripple::TMLedgerData& packet, Peer::ref); - void logFailure(const uint256&); - bool isFailure(const uint256&); + void logFailure(const uint256& h) { mRecentFailures.add(h); } + bool isFailure(const uint256& h) { return mRecentFailures.isPresent(h, false); } void sweep(); };