@@ -78,21 +78,16 @@ typedef std::map<std::pair<void*, void*>, LockStack> LockOrders;
7878typedef std::set<std::pair<void *, void *> > InvLockOrders;
7979
8080struct LockData {
81- // Very ugly hack: as the global constructs and destructors run single
82- // threaded, we use this boolean to know whether LockData still exists,
83- // as DeleteLock can get called by global RecursiveMutex destructors
84- // after LockData disappears.
85- bool available;
86- LockData () : available(true ) {}
87- ~LockData () { available = false ; }
88-
8981 LockOrders lockorders;
9082 InvLockOrders invlockorders;
9183 std::mutex dd_mutex;
9284};
85+
9386LockData& GetLockData () {
94- static LockData lockdata;
95- return lockdata;
87+ // This approach guarantees that the object is not destroyed until after its last use.
88+ // The operating system automatically reclaims all the memory in a program's heap when that program exits.
89+ static LockData& lock_data = *new LockData ();
90+ return lock_data;
9691}
9792
9893static thread_local LockStack g_lockstack;
@@ -207,10 +202,6 @@ void AssertLockNotHeldInternal(const char* pszName, const char* pszFile, int nLi
207202void DeleteLock (void * cs)
208203{
209204 LockData& lockdata = GetLockData ();
210- if (!lockdata.available ) {
211- // We're already shutting down.
212- return ;
213- }
214205 std::lock_guard<std::mutex> lock (lockdata.dd_mutex );
215206 std::pair<void *, void *> item = std::make_pair (cs, nullptr );
216207 LockOrders::iterator it = lockdata.lockorders .lower_bound (item);
0 commit comments