00001 #ifndef _sys_Mutex_h
00002 #define _sys_Mutex_h
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #ifdef USE_APR
00026 # include <apr_thread_mutex.h>
00027 # include <apr_pools.h>
00028 # include "apr/APRBase.h"
00029 # include "apr/APRPool.h"
00030 #else
00031 # include <pthread.h>
00032 # include <posix/check.h>
00033 #endif
00034 #include <boost/noncopyable.hpp>
00035
00036 namespace qpid {
00037 namespace sys {
00038
00043 template <class L>
00044 class ScopedLock
00045 {
00046 public:
00047 ScopedLock(L& l) : mutex(l) { l.lock(); }
00048 ~ScopedLock() { mutex.unlock(); }
00049 private:
00050 L& mutex;
00051 };
00052
00056 class Mutex : private boost::noncopyable {
00057 public:
00058 typedef ScopedLock<Mutex> ScopedLock;
00059
00060 inline Mutex();
00061 inline ~Mutex();
00062 inline void lock();
00063 inline void unlock();
00064 inline void trylock();
00065
00066 protected:
00067 #ifdef USE_APR
00068 apr_thread_mutex_t* mutex;
00069 apr_pool_t* pool;
00070 #else
00071 pthread_mutex_t mutex;
00072 #endif
00073 };
00074
00075 #ifdef USE_APR
00076
00077
00078 Mutex::Mutex() {
00079 pool = APRPool::get();
00080 CHECK_APR_SUCCESS(apr_thread_mutex_create(&mutex, APR_THREAD_MUTEX_NESTED, pool));
00081 }
00082
00083 Mutex::~Mutex(){
00084 CHECK_APR_SUCCESS(apr_thread_mutex_destroy(mutex));
00085 APRPool::free(pool);
00086 }
00087
00088 void Mutex::lock() {
00089 CHECK_APR_SUCCESS(apr_thread_mutex_lock(mutex));
00090 }
00091 void Mutex::unlock() {
00092 CHECK_APR_SUCCESS(apr_thread_mutex_unlock(mutex));
00093 }
00094
00095 void Mutex::trylock() {
00096 CHECK_APR_SUCCESS(apr_thread_mutex_trylock(mutex));
00097 }
00098
00099 #else
00100
00101
00106 struct PODMutex
00107 {
00108 typedef ScopedLock<PODMutex> ScopedLock;
00109
00110 inline void lock();
00111 inline void unlock();
00112 inline void trylock();
00113
00114
00115 pthread_mutex_t mutex;
00116 };
00117
00118 #define QPID_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER }
00119
00120
00121 void PODMutex::lock() {
00122 QPID_POSIX_THROW_IF(pthread_mutex_lock(&mutex));
00123 }
00124 void PODMutex::unlock() {
00125 QPID_POSIX_THROW_IF(pthread_mutex_unlock(&mutex));
00126 }
00127
00128 void PODMutex::trylock() {
00129 QPID_POSIX_THROW_IF(pthread_mutex_trylock(&mutex));
00130 }
00131
00132
00133 Mutex::Mutex() {
00134 QPID_POSIX_THROW_IF(pthread_mutex_init(&mutex, 0));
00135 }
00136
00137 Mutex::~Mutex(){
00138 QPID_POSIX_THROW_IF(pthread_mutex_destroy(&mutex));
00139 }
00140
00141 void Mutex::lock() {
00142 QPID_POSIX_THROW_IF(pthread_mutex_lock(&mutex));
00143 }
00144 void Mutex::unlock() {
00145 QPID_POSIX_THROW_IF(pthread_mutex_unlock(&mutex));
00146 }
00147
00148 void Mutex::trylock() {
00149 QPID_POSIX_THROW_IF(pthread_mutex_trylock(&mutex));
00150 }
00151
00152 #endif // USE_APR
00153
00154 }}
00155
00156
00157
00158 #endif