Merge #13115: addrman: Add Clang thread safety annotations for variables guarded by CAddrMan.cs

3e9f6c821b Add missing locks and locking annotations for CAddrMan (practicalswift)

Pull request description:

  * Add Clang thread safety annotations for variables guarded by `CAddrMan.cs `
  * Add missing `CAddrMan.cs ` locks

Tree-SHA512: c78d56d56eb63a4469333c04c95317545a8f97d5e3a36ff2699ee4a91a6433d416221eed6c5ff168e1e31f6936c2ae101a4c60b635f2b2309f40e3d66a727322
This commit is contained in:
MarcoFalke 2018-10-09 00:54:23 -03:00 committed by pasta
parent 9d0fb5c295
commit b968ebf34c
2 changed files with 31 additions and 26 deletions

View File

@ -192,39 +192,40 @@ static const int64_t ADDRMAN_TEST_WINDOW = 40*60; // 40 minutes
*/ */
class CAddrMan class CAddrMan
{ {
private: protected:
friend class CAddrManTest; friend class CAddrManTest;
protected: protected:
//! critical section to protect the inner data structures //! critical section to protect the inner data structures
mutable CCriticalSection cs; mutable CCriticalSection cs;
private:
//! last used nId //! last used nId
int nIdCount; int nIdCount GUARDED_BY(cs);
//! table with information about all nIds //! table with information about all nIds
std::map<int, CAddrInfo> mapInfo; std::map<int, CAddrInfo> mapInfo GUARDED_BY(cs);
//! find an nId based on its network address //! find an nId based on its network address
std::map<CService, int> mapAddr; std::map<CService, int> mapAddr GUARDED_BY(cs);
//! randomly-ordered vector of all nIds //! randomly-ordered vector of all nIds
std::vector<int> vRandom; std::vector<int> vRandom GUARDED_BY(cs);
// number of "tried" entries // number of "tried" entries
int nTried; int nTried GUARDED_BY(cs);
//! list of "tried" buckets //! list of "tried" buckets
int vvTried[ADDRMAN_TRIED_BUCKET_COUNT][ADDRMAN_BUCKET_SIZE]; int vvTried[ADDRMAN_TRIED_BUCKET_COUNT][ADDRMAN_BUCKET_SIZE] GUARDED_BY(cs);
//! number of (unique) "new" entries //! number of (unique) "new" entries
int nNew; int nNew GUARDED_BY(cs);
//! list of "new" buckets //! list of "new" buckets
int vvNew[ADDRMAN_NEW_BUCKET_COUNT][ADDRMAN_BUCKET_SIZE]; int vvNew[ADDRMAN_NEW_BUCKET_COUNT][ADDRMAN_BUCKET_SIZE] GUARDED_BY(cs);
//! last time Good was called (memory only) //! last time Good was called (memory only)
int64_t nLastGood; int64_t nLastGood GUARDED_BY(cs);
// discriminate entries based on port. Should be false on mainnet/testnet and can be true on devnet/regtest // discriminate entries based on port. Should be false on mainnet/testnet and can be true on devnet/regtest
bool discriminatePorts; bool discriminatePorts;
@ -240,58 +241,58 @@ protected:
FastRandomContext insecure_rand; FastRandomContext insecure_rand;
//! Find an entry. //! Find an entry.
CAddrInfo* Find(const CService& addr, int *pnId = nullptr); CAddrInfo* Find(const CService& addr, int *pnId = nullptr) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! find an entry, creating it if necessary. //! find an entry, creating it if necessary.
//! nTime and nServices of the found node are updated, if necessary. //! nTime and nServices of the found node are updated, if necessary.
CAddrInfo* Create(const CAddress &addr, const CNetAddr &addrSource, int *pnId = nullptr); CAddrInfo* Create(const CAddress &addr, const CNetAddr &addrSource, int *pnId = nullptr) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Swap two elements in vRandom. //! Swap two elements in vRandom.
void SwapRandom(unsigned int nRandomPos1, unsigned int nRandomPos2); void SwapRandom(unsigned int nRandomPos1, unsigned int nRandomPos2) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Move an entry from the "new" table(s) to the "tried" table //! Move an entry from the "new" table(s) to the "tried" table
void MakeTried(CAddrInfo& info, int nId); void MakeTried(CAddrInfo& info, int nId) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Delete an entry. It must not be in tried, and have refcount 0. //! Delete an entry. It must not be in tried, and have refcount 0.
void Delete(int nId); void Delete(int nId) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Clear a position in a "new" table. This is the only place where entries are actually deleted. //! Clear a position in a "new" table. This is the only place where entries are actually deleted.
void ClearNew(int nUBucket, int nUBucketPos); void ClearNew(int nUBucket, int nUBucketPos) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Mark an entry "good", possibly moving it from "new" to "tried". //! Mark an entry "good", possibly moving it from "new" to "tried".
void Good_(const CService &addr, bool test_before_evict, int64_t time); void Good_(const CService &addr, bool test_before_evict, int64_t time) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Add an entry to the "new" table. //! Add an entry to the "new" table.
bool Add_(const CAddress &addr, const CNetAddr& source, int64_t nTimePenalty); bool Add_(const CAddress &addr, const CNetAddr& source, int64_t nTimePenalty) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Mark an entry as attempted to connect. //! Mark an entry as attempted to connect.
void Attempt_(const CService &addr, bool fCountFailure, int64_t nTime); void Attempt_(const CService &addr, bool fCountFailure, int64_t nTime) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Select an address to connect to, if newOnly is set to true, only the new table is selected from. //! Select an address to connect to, if newOnly is set to true, only the new table is selected from.
CAddrInfo Select_(bool newOnly); CAddrInfo Select_(bool newOnly) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! See if any to-be-evicted tried table entries have been tested and if so resolve the collisions. //! See if any to-be-evicted tried table entries have been tested and if so resolve the collisions.
void ResolveCollisions_(); void ResolveCollisions_() EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Return a random to-be-evicted tried table address. //! Return a random to-be-evicted tried table address.
CAddrInfo SelectTriedCollision_(); CAddrInfo SelectTriedCollision_() EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Wraps GetRandInt to allow tests to override RandomInt and make it determinismistic. //! Wraps GetRandInt to allow tests to override RandomInt and make it determinismistic.
virtual int RandomInt(int nMax); virtual int RandomInt(int nMax);
#ifdef DEBUG_ADDRMAN #ifdef DEBUG_ADDRMAN
//! Perform consistency check. Returns an error code or zero. //! Perform consistency check. Returns an error code or zero.
int Check_(); int Check_() EXCLUSIVE_LOCKS_REQUIRED(cs);
#endif #endif
//! Select several addresses at once. //! Select several addresses at once.
void GetAddr_(std::vector<CAddress> &vAddr); void GetAddr_(std::vector<CAddress> &vAddr) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Mark an entry as currently-connected-to. //! Mark an entry as currently-connected-to.
void Connected_(const CService &addr, int64_t nTime); void Connected_(const CService &addr, int64_t nTime) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Update an entry's service bits. //! Update an entry's service bits.
void SetServices_(const CService &addr, ServiceFlags nServices); void SetServices_(const CService &addr, ServiceFlags nServices) EXCLUSIVE_LOCKS_REQUIRED(cs);
//! Get address info for address //! Get address info for address
CAddrInfo GetAddressInfo_(const CService& addr); CAddrInfo GetAddressInfo_(const CService& addr);

View File

@ -47,16 +47,19 @@ public:
CAddrInfo* Find(const CService& addr, int* pnId = nullptr) CAddrInfo* Find(const CService& addr, int* pnId = nullptr)
{ {
LOCK(cs);
return CAddrMan::Find(addr, pnId); return CAddrMan::Find(addr, pnId);
} }
CAddrInfo* Create(const CAddress& addr, const CNetAddr& addrSource, int* pnId = nullptr) CAddrInfo* Create(const CAddress& addr, const CNetAddr& addrSource, int* pnId = nullptr)
{ {
LOCK(cs);
return CAddrMan::Create(addr, addrSource, pnId); return CAddrMan::Create(addr, addrSource, pnId);
} }
void Delete(int nId) void Delete(int nId)
{ {
LOCK(cs);
CAddrMan::Delete(nId); CAddrMan::Delete(nId);
} }
@ -78,6 +81,7 @@ public:
// Simulates connection failure so that we can test eviction of offline nodes // Simulates connection failure so that we can test eviction of offline nodes
void SimConnFail(CService& addr) void SimConnFail(CService& addr)
{ {
LOCK(cs);
int64_t nLastSuccess = 1; int64_t nLastSuccess = 1;
Good_(addr, true, nLastSuccess); // Set last good connection in the deep past. Good_(addr, true, nLastSuccess); // Set last good connection in the deep past.