00001 /*---------------------------------------------------------------------\ 00002 | ____ _ __ __ ___ | 00003 | |__ / \ / / . \ . \ | 00004 | / / \ V /| _/ _/ | 00005 | / /__ | | | | | | | 00006 | /_____||_| |_| |_| | 00007 | | 00008 \---------------------------------------------------------------------*/ 00011 #include <zypp/thread/Mutex.h> 00012 #include <zypp/thread/MutexException.h> 00013 00014 00016 namespace zypp 00017 { 00018 00020 namespace thread 00021 { 00022 00023 // ------------------------------------------------------------- 00024 Mutex::Mutex() 00025 { 00026 pthread_mutexattr_t attr; 00027 00028 int ret = pthread_mutexattr_init(&attr); 00029 if( ret != 0) 00030 { 00031 ZYPP_THROW_ERRNO_MSG(zypp::thread::MutexException, 00032 "Can't initialize mutex attributes"); 00033 } 00034 00035 ret = pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE); 00036 if( ret != 0) 00037 { 00038 ZYPP_THROW_ERRNO_MSG(MutexException, 00039 "Can't set recursive mutex attribute"); 00040 } 00041 00042 ret = pthread_mutex_init(&m_mutex, &attr); 00043 if( ret != 0) 00044 { 00045 ZYPP_THROW_ERRNO_MSG(MutexException, 00046 "Can't initialize recursive mutex"); 00047 } 00048 } 00049 00050 // ------------------------------------------------------------- 00051 Mutex::~Mutex() 00052 { 00053 if( pthread_mutex_destroy(&m_mutex) != 0 && errno == EBUSY) 00054 { 00055 // try to unlock and to destroy again... 00056 if( pthread_mutex_unlock(&m_mutex) == 0) 00057 { 00058 pthread_mutex_destroy(&m_mutex); 00059 } 00060 /* 00061 else 00062 { 00063 ZYPP_THROW_ERRNO_MSG(MutexException, 00064 "Can't destroy mutex owned by another thread"); 00065 } 00066 */ 00067 } 00068 } 00069 00070 // ------------------------------------------------------------- 00071 void Mutex::lock() 00072 { 00073 if( pthread_mutex_lock(&m_mutex) != 0) 00074 { 00075 ZYPP_THROW_ERRNO_MSG(MutexException, 00076 "Can't acquire the mutex lock"); 00077 } 00078 } 00079 00080 // ------------------------------------------------------------- 00081 void Mutex::unlock() 00082 { 00083 if( pthread_mutex_unlock(&m_mutex) != 0) 00084 { 00085 ZYPP_THROW_ERRNO_MSG(MutexException, 00086 "Can't release the mutex lock"); 00087 } 00088 } 00089 00090 // ------------------------------------------------------------- 00091 bool Mutex::trylock() 00092 { 00093 return (pthread_mutex_trylock(&m_mutex) == 0); 00094 } 00095 00096 00098 } // namespace thread 00100 00102 } // namespace zypp 00104 00105 /* 00106 ** vim: set ts=2 sts=2 sw=2 ai et: 00107 */