evaluation version of deadlock detect mutex

This commit is contained in:
Jeff Hill
2003-04-16 20:55:41 +00:00
parent a28065c900
commit b8a2f0495e
2 changed files with 71 additions and 2 deletions

View File

@@ -235,4 +235,56 @@ void epicsMutex :: show ( unsigned level ) const
epicsMutexShow ( this->id, level );
}
static epicsThreadPrivate < epicsDeadlockDetectMutex >
currentMutexLevel;
epicsDeadlockDetectMutex::
epicsDeadlockDetectMutex ( hierarchyLevel_t level ) :
hierarchyLevel ( level ), pPreviousLevel ( 0 )
{
}
epicsDeadlockDetectMutex::~epicsDeadlockDetectMutex ()
{
}
void epicsDeadlockDetectMutex::show ( unsigned level ) const
{
this->mutex.show ( level );
}
void epicsDeadlockDetectMutex::lock ()
{
epicsDeadlockDetectMutex * pPrev = currentMutexLevel.get();
if ( pPrev && pPrev != this ) {
if ( pPrev->hierarchyLevel >= this->hierarchyLevel ) {
errlogPrintf ( "!!!! Deadlock Vulnerability Detected !!!! "
"at level %u and moving to level %u\n",
pPrev->hierarchyLevel,
this->hierarchyLevel );
}
}
this->mutex.lock ();
if ( pPrev && pPrev != this ) {
currentMutexLevel.set ( this );
this->pPreviousLevel = pPrev;
}
}
void epicsDeadlockDetectMutex::unlock ()
{
currentMutexLevel.set ( this->pPreviousLevel );
this->mutex.unlock ();
}
bool epicsDeadlockDetectMutex::tryLock ()
{
bool success = this->mutex.tryLock ();
if ( success ) {
this->pPreviousLevel = currentMutexLevel.get();
currentMutexLevel.set ( this );
}
return success;
}

View File

@@ -25,8 +25,8 @@ typedef enum {
class epicsShareClass epicsMutex {
public:
class mutexCreateFailed {}; // exception
class invalidMutex {}; // exception
class mutexCreateFailed {}; /* exception */
class invalidMutex {}; /* exception */
epicsMutex ();
~epicsMutex ();
void show ( unsigned level ) const;
@@ -39,6 +39,23 @@ private:
epicsMutex & operator = ( const epicsMutex & );
};
class epicsShareClass epicsDeadlockDetectMutex {
public:
typedef unsigned hierarchyLevel_t;
epicsDeadlockDetectMutex ( unsigned hierarchyLevel_t );
~epicsDeadlockDetectMutex ();
void show ( unsigned level ) const;
void lock (); /* blocks until success */
void unlock ();
bool tryLock (); /* true if successful */
private:
epicsMutex mutex;
const hierarchyLevel_t hierarchyLevel;
class epicsDeadlockDetectMutex * pPreviousLevel;
epicsDeadlockDetectMutex ( const epicsDeadlockDetectMutex & );
epicsDeadlockDetectMutex & operator = ( const epicsDeadlockDetectMutex & );
};
#endif /*__cplusplus*/
#ifdef __cplusplus