Changeset View
Changeset View
Standalone View
Standalone View
src/sync.cpp
Show First 20 Lines • Show All 136 Lines • ▼ Show 20 Lines | for (const LockStackItem &i : lock_stack) { | ||||
if (i.first == c) { | if (i.first == c) { | ||||
break; | break; | ||||
} | } | ||||
const LockPair p1 = std::make_pair(i.first, c); | const LockPair p1 = std::make_pair(i.first, c); | ||||
if (lockdata.lockorders.count(p1)) { | if (lockdata.lockorders.count(p1)) { | ||||
continue; | continue; | ||||
} | } | ||||
lockdata.lockorders.emplace(p1, lock_stack); | |||||
const LockPair p2 = std::make_pair(c, i.first); | const LockPair p2 = std::make_pair(c, i.first); | ||||
lockdata.invlockorders.insert(p2); | |||||
if (lockdata.lockorders.count(p2)) { | if (lockdata.lockorders.count(p2)) { | ||||
auto lock_stack_copy = lock_stack; | |||||
lock_stack.pop_back(); | |||||
potential_deadlock_detected(p1, lockdata.lockorders[p2], | potential_deadlock_detected(p1, lockdata.lockorders[p2], | ||||
lockdata.lockorders[p1]); | lock_stack_copy); | ||||
// potential_deadlock_detected() does not return. | |||||
} | } | ||||
lockdata.lockorders.emplace(p1, lock_stack); | |||||
lockdata.invlockorders.insert(p2); | |||||
} | } | ||||
} | } | ||||
static void pop_lock() { | static void pop_lock() { | ||||
LockData &lockdata = GetLockData(); | LockData &lockdata = GetLockData(); | ||||
std::lock_guard<std::mutex> lock(lockdata.dd_mutex); | std::lock_guard<std::mutex> lock(lockdata.dd_mutex); | ||||
LockStack &lock_stack = lockdata.m_lock_stacks[std::this_thread::get_id()]; | LockStack &lock_stack = lockdata.m_lock_stacks[std::this_thread::get_id()]; | ||||
▲ Show 20 Lines • Show All 103 Lines • ▼ Show 20 Lines | void DeleteLock(void *cs) { | ||||
InvLockOrders::iterator invit = lockdata.invlockorders.lower_bound(item); | InvLockOrders::iterator invit = lockdata.invlockorders.lower_bound(item); | ||||
while (invit != lockdata.invlockorders.end() && invit->first == cs) { | while (invit != lockdata.invlockorders.end() && invit->first == cs) { | ||||
const LockPair invinvitem = std::make_pair(invit->second, invit->first); | const LockPair invinvitem = std::make_pair(invit->second, invit->first); | ||||
lockdata.lockorders.erase(invinvitem); | lockdata.lockorders.erase(invinvitem); | ||||
lockdata.invlockorders.erase(invit++); | lockdata.invlockorders.erase(invit++); | ||||
} | } | ||||
} | } | ||||
bool LockStackEmpty() { | |||||
LockData &lockdata = GetLockData(); | |||||
std::lock_guard<std::mutex> lock(lockdata.dd_mutex); | |||||
const auto it = lockdata.m_lock_stacks.find(std::this_thread::get_id()); | |||||
if (it == lockdata.m_lock_stacks.end()) { | |||||
return true; | |||||
} | |||||
return it->second.empty(); | |||||
} | |||||
bool g_debug_lockorder_abort = true; | bool g_debug_lockorder_abort = true; | ||||
#endif /* DEBUG_LOCKORDER */ | #endif /* DEBUG_LOCKORDER */ |