Checking a Critical Section


#1

Hi,
Is there a way (for debugging purposes) to unobtrusively check if a critical section IS or IS NOT locked?
I might even consider an algorithm that is working only 99% of the times.


#2

No, but that might indeed be a handy debugging tool. Don’t know if it’s possible on all OSes though.


#3

Perhaps your own CriticalSection class could be augmented with a simple boolean or thread index to indicate if/who has locked it?

Edit: But whatever the implementation it should not be enabled by default unless it can be done safely and quickly, which it probably couldn’t.


#4
enter() 
{
    // Previous code here

    // Remember who locked it:
    #ifdef _DEBUG
        ownerLockID = Thread::getCurrentThreadId();
    #endif
}

exit()
{
   #ifdef _DEBUG
       ownerLockID = 0; // Beware that there might be a very small amount of time where the ownerLockID will be 0, yet locked
   #endif
   // Previous code here
}

#ifdef _DEBUG
// Added for debugging purpose
unsigned long long CriticalSection::getOwnerThreadId() const { return ownerLockID; }
#endif 

#5

Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?
[color=#800000]Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection? [/color]
[color=#BF4000]Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?[/color]
[color=#FFBF00]Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection? [/color]
[color=#FFFF00]Perhaps that can be protected by a CriticalSection?
Perhaps that can be protected by a CriticalSection?[/color]


#6

No, it’s not an issue (and I got the joke). While the criticalSection is locked, the ownerLockID can’t be changed anyway.
The only downside, is if you read the ownerLockID from another thread at the exact moment between ownerID = 0 and lock.trueExit(), then you’ll see 0, but it’s fundamentally safe (any other thread waiting for the CriticalSection will be blocked in enter() so if you break your program at this exact moment, you’d be able to find out which CriticalSection it’s blocked upon, or you can sample your application a ms later and get correct result anyway).

If you need the feature, it’s because you’ve a deadlock, and you want to figure out where it comes from, right ?

Also ownerLockID is an Atomic, so the read in getOwnerThreadId() does actually use the good memory barrier (it’s not reordered by your compiler/CPU).
BTW, if you want a very very fast debugging help, trigger gdb, and print the “CriticalSection”. One of the mutex’s internal field is the count (which should be 0 if free), and another one is the thread owner.