Mutex.cxx
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #include "Mutex.hxx"
00023 #include "Assert.hxx"
00024 #include "xtime.hxx"
00025 #include "ErrSystem.hxx"
00026
00027 namespace CLAM
00028 {
00029
00030 Mutex::Mutex()
00031 {
00032 int res = 0;
00033
00034 res = pthread_mutex_init( &mMutex, 0 );
00035
00036 CLAM_ASSERT( res == 0, "Not able to initialize mutex" );
00037 }
00038
00039 Mutex::~Mutex()
00040 {
00041 int res = 0;
00042
00043 res = pthread_mutex_destroy( &mMutex );
00044
00045 CLAM_ASSERT( res == 0, "Not able to destroy mutex" );
00046 }
00047
00048 void Mutex::DoLock()
00049 {
00050 int res = 0;
00051
00052 res = pthread_mutex_lock( &mMutex );
00053
00054 if ( res == EDEADLK )
00055 throw LockError();
00056
00057 CLAM_ASSERT( res == 0, "Not able to lock the mutex" );
00058 }
00059
00060 void Mutex::DoUnlock()
00061 {
00062 int res = 0;
00063
00064 res = pthread_mutex_unlock( &mMutex );
00065
00066 if ( res == EPERM )
00067 throw LockError();
00068
00069 CLAM_ASSERT( res == 0, "Not able to Unlock the mutex" );
00070 }
00071
00072 void Mutex::DoLock( ConditionVar& state )
00073 {
00074
00075 }
00076
00077 void Mutex::DoUnlock( ConditionVar& state )
00078 {
00079 state.pmutex = &mMutex;
00080 }
00081
00082 TryMutex::TryMutex()
00083 {
00084 int res = 0;
00085
00086 res = pthread_mutex_init( &mMutex, 0 );
00087
00088 CLAM_ASSERT( res == 0, "Not able to initialize mutex" );
00089
00090 }
00091
00092 TryMutex::~TryMutex()
00093 {
00094 int res = 0;
00095
00096 res = pthread_mutex_destroy( &mMutex );
00097
00098 CLAM_ASSERT( res == 0, "Not able to destroy mutex" );
00099
00100 }
00101
00102 void TryMutex::DoLock()
00103 {
00104 int res = 0;
00105 res = pthread_mutex_lock( &mMutex );
00106 if ( res == EDEADLK )
00107 throw LockError();
00108
00109 CLAM_ASSERT( res == 0, "Not able to lock mutex" );
00110 }
00111
00112 bool TryMutex::DoTryLock()
00113 {
00114 int res = 0;
00115
00116 res = pthread_mutex_trylock(&mMutex );
00117
00118 if ( res == EDEADLK )
00119 throw LockError();
00120
00121 CLAM_ASSERT ( (res == 0) || (res == EBUSY), "Not able to try-lock the mutex" );
00122
00123 return res == 0;
00124 }
00125
00126 void TryMutex::DoUnlock()
00127 {
00128 int res = 0;
00129
00130 res = pthread_mutex_unlock( &mMutex );
00131
00132 if ( res == EPERM )
00133 throw LockError();
00134
00135 CLAM_ASSERT( res == 0, "Not able to Unlock the mutex" );
00136 }
00137
00138 void TryMutex::DoLock( ConditionVar& state )
00139 {
00140
00141 }
00142
00143 void TryMutex::DoUnlock( ConditionVar& state )
00144 {
00145 state.pmutex = &mMutex;
00146 }
00147
00148 TimedMutex::TimedMutex()
00149 : mLocked( false )
00150 {
00151 int res = 0;
00152
00153 res = pthread_mutex_init( &mMutex, 0 );
00154
00155 CLAM_ASSERT( res==0, "Not able to initilize the mutex" );
00156
00157 res = pthread_cond_init( &mCondition, 0 );
00158
00159 if ( res!= 0 )
00160 {
00161 pthread_mutex_destroy( &mMutex );
00162 throw ThreadResourceError("Unable to initialize Condition " );
00163 }
00164 }
00165
00166 TimedMutex::~TimedMutex()
00167 {
00168 CLAM_ASSERT( !mLocked, "Mutex was locked while attempting to destroy it!" );
00169
00170 int res = 0;
00171
00172 res = pthread_mutex_destroy(&mMutex );
00173
00174 CLAM_ASSERT( res == 0, "Unable to destroy the mutex!" );
00175
00176 res = pthread_cond_destroy( &mCondition );
00177
00178 CLAM_ASSERT( res == 0, "Unable to destroy the Condition variable" );
00179 }
00180
00181 void TimedMutex::DoLock( )
00182 {
00183 int res = 0;
00184
00185 res = pthread_mutex_lock( &mMutex );
00186 CLAM_ASSERT( res == 0, "Unable to lock mutex (already locked) " );
00187
00188 while( mLocked )
00189 {
00190 res = pthread_cond_wait( &mCondition, &mMutex );
00191 CLAM_ASSERT( res == 0, "Wait failed" );
00192 }
00193
00194 CLAM_ASSERT( !mLocked, "Spurious value for loop condition" );
00195 mLocked = true;
00196
00197 res = pthread_mutex_unlock( &mMutex );
00198 CLAM_ASSERT( res ==0, "Unable to unlock the mutex" );
00199 }
00200
00201 bool TimedMutex::DoTryLock()
00202 {
00203 int res = 0;
00204
00205 res = pthread_mutex_lock( &mMutex );
00206
00207 CLAM_ASSERT( res == 0, "Unable to lock the mutex" );
00208
00209 bool ret = false;
00210
00211 if ( !mLocked )
00212 {
00213 mLocked = true;
00214 ret = true;
00215 }
00216
00217 res = pthread_mutex_unlock( &mMutex );
00218 CLAM_ASSERT( res==0, "Unable to unlock the mutex" );
00219
00220 return ret;
00221 }
00222
00223 bool TimedMutex::DoTimedLock( const xtime& xt )
00224 {
00225 int res = 0;
00226 res = pthread_mutex_lock( &mMutex );
00227 CLAM_ASSERT( res == 0, "Unable to lock the mutex" );
00228
00229 timespec ts;
00230 to_timespec(xt, ts);
00231
00232 while (mLocked)
00233 {
00234 res = pthread_cond_timedwait(&mCondition, &mMutex, &ts);
00235 CLAM_ASSERT(res == 0 || res == ETIMEDOUT, "Low level error");
00236
00237 if (res == ETIMEDOUT)
00238 break;
00239 }
00240
00241 bool ret = false;
00242 if (!mLocked)
00243 {
00244 mLocked = true;
00245 ret = true;
00246 }
00247
00248 res = pthread_mutex_unlock(&mMutex);
00249 CLAM_ASSERT(res == 0, "Something low level failed!");
00250 return ret;
00251 }
00252
00253 void TimedMutex::DoUnlock()
00254 {
00255 int res = 0;
00256 res = pthread_mutex_lock(&mMutex);
00257 CLAM_ASSERT(res == 0, "Unable to lock the mutex");
00258
00259 CLAM_ASSERT(mLocked, "No condition spurious value change");
00260 mLocked = false;
00261
00262 res = pthread_cond_signal(&mCondition);
00263 CLAM_ASSERT(res == 0, "Not able to change the condition var value");
00264
00265 res = pthread_mutex_unlock(&mMutex);
00266 CLAM_ASSERT(res == 0, "Unable to unlock the mutex");
00267 }
00268
00269 void TimedMutex::DoLock(ConditionVar& v)
00270 {
00271 int res = 0;
00272 while (mLocked)
00273 {
00274 res = pthread_cond_wait(&mCondition, &mMutex);
00275 CLAM_ASSERT(res == 0, "pthread_cond_wait call failed!");
00276 }
00277
00278 CLAM_ASSERT(!mLocked, "Spurious value change");
00279 mLocked = true;
00280
00281 res = pthread_mutex_unlock(&mMutex);
00282 CLAM_ASSERT(res == 0, "pthread_mutex_unlock call failed!");
00283 }
00284
00285 void TimedMutex::DoUnlock(ConditionVar& state)
00286 {
00287 int res = 0;
00288 res = pthread_mutex_lock(&mMutex);
00289 CLAM_ASSERT(res == 0, "pthread_mutex_lock call failed");
00290
00291 CLAM_ASSERT(mLocked, "Spurious value change!");
00292 mLocked = false;
00293
00294 res = pthread_cond_signal(&mCondition);
00295 CLAM_ASSERT(res == 0, "pthread_cond_signal call failed!");
00296
00297 state.pmutex = &mMutex;
00298 }
00299
00300 }
00301