IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Changeset 19120


Ignore:
Timestamp:
Aug 18, 2008, 2:34:00 PM (18 years ago)
Author:
Paul Price
Message:

Adding error checking for mutexes.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/psLib/src/sys/psMutex.h

    r19056 r19120  
    33
    44#include <pthread.h>
     5#include <assert.h>
    56
    67typedef pthread_mutex_t psMutex;        /// Mutual Exclusion using pthreads
     8//#define PS_MUTEX_CAREFUL                // Use error-checking mutexes, trace messages, check the results
     9
     10#ifdef PS_MUTEX_CAREFUL
    711
    812/// Initialize a mutex
    913#define psMutexInit(PTR) { \
     14    psAssert(PTR, "Require non-NULL pointer to initialise mutex"); \
     15    psTrace("psLib.sys.mutex", 3, "Initialising mutex on %s...", #PTR); \
     16    /* Gotta go the long way, since we can't use PTHREAD_MUTEX_INITIALIZER after we declare the variable */ \
     17    pthread_mutexattr_t attr; /* Mutex attributes */ \
     18    pthread_mutexattr_init(&attr); \
     19    pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK_NP); \
     20    pthread_mutex_init(&(PTR)->lock, &attr); \
     21    pthread_mutexattr_destroy(&attr); \
     22}
     23
     24/// Lock a mutex
     25#define psMutexLock(PTR) { \
     26    psAssert(PTR, "Require non-NULL pointer to lock mutex"); \
     27    psTrace("psLib.sys.mutex", 1, "Thread %p waiting for mutex lock on %s...", (void*)pthread_self(), #PTR); \
     28    int pml = pthread_mutex_lock(&(PTR)->lock); \
     29    psTrace("psLib.sys.mutex", 1, "Thread %p locked mutex on %s", (void*)pthread_self(), #PTR); \
     30    if (pml == EINVAL) { \
     31        psAbort("Cannot lock mutex on %s: not initialised", #PTR); \
     32    } \
     33    if (pml == EDEADLK) { \
     34        psAbort("Deadlocked mutex on %s", #PTR); \
     35    } \
     36}
     37
     38/// Unlock a mutex
     39#define psMutexUnlock(PTR) { \
     40    psAssert(PTR, "Require non-NULL pointer to unlock mutex"); \
     41    psTrace("psLib.sys.mutex", 1, "Thread %p unlocking mutex on %s", (void*)pthread_self(), #PTR); \
     42    int pmu = pthread_mutex_unlock(&(PTR)->lock); \
     43    if (pmu == EINVAL) { \
     44        psAbort("Cannot unlock mutex on %s: not initialised", #PTR); \
     45    } \
     46    if (pmu == EPERM) { \
     47        psAbort("Unlocking stolen mutex on %s", #PTR); \
     48    } \
     49}
     50
     51#else  // PS_MUTEX_CAREFUL
     52
     53/// Initialize a mutex
     54#define psMutexInit(PTR) { \
     55    psAssert(PTR, "Require non-NULL pointer to initialise mutex"); \
    1056    /* Gotta go the long way, since we can't use PTHREAD_MUTEX_INITIALIZER after we declare the variable */ \
    1157    pthread_mutexattr_t attr; /* Mutex attributes */ \
     
    1763
    1864/// Lock a mutex
    19 #define psMutexLock(PTR) \
    20 if (pthread_mutex_lock(&(PTR)->lock) == EINVAL) { \
    21     psAbort("Cannot lock mutex on %s: not initialised", #PTR); \
     65#define psMutexLock(PTR) { \
     66    psAssert(PTR, "Require non-NULL pointer to lock mutex"); \
     67    if (pthread_mutex_lock(&(PTR)->lock) == EINVAL) { \
     68        psAbort("Cannot lock mutex on %s: not initialised", #PTR); \
     69    } \
    2270}
    2371
    2472/// Unlock a mutex
    25 #define psMutexUnlock(PTR) \
    26 if (pthread_mutex_unlock(&(PTR)->lock) == EINVAL) { \
    27     psAbort("Cannot unlock mutex on %s: not initialised", #PTR); \
     73#define psMutexUnlock(PTR) { \
     74    psAssert(PTR, "Require non-NULL pointer to unlock mutex"); \
     75    if (pthread_mutex_unlock(&(PTR)->lock) == EINVAL) { \
     76        psAbort("Cannot unlock mutex on %s: not initialised", #PTR); \
     77    } \
    2878}
    2979
     80#endif // PS_MUTEX_CAREFUL
     81
    3082/// Destroy a mutex
    31 #define psMutexDestroy(PTR) \
    32 if (pthread_mutex_destroy(&(PTR)->lock) == EBUSY) { \
    33     psAbort("Cannot destroy mutex on %s: is busy", #PTR); \
     83#define psMutexDestroy(PTR) { \
     84    psAssert(PTR, "Require non-NULL pointer to destroy mutex"); \
     85    if (pthread_mutex_destroy(&(PTR)->lock) == EBUSY) { \
     86        psAbort("Cannot destroy mutex on %s: is busy", #PTR); \
     87    } \
    3488}
    3589
Note: See TracChangeset for help on using the changeset viewer.