diff options
Diffstat (limited to 'cpp/include')
-rw-r--r-- | cpp/include/IceUtil/Config.h | 6 | ||||
-rw-r--r-- | cpp/include/IceUtil/IceUtil.h | 2 | ||||
-rw-r--r-- | cpp/include/IceUtil/Mutex.h | 85 | ||||
-rw-r--r-- | cpp/include/IceUtil/MutexProtocol.h | 28 | ||||
-rw-r--r-- | cpp/include/IceUtil/MutexPtrLock.h | 83 | ||||
-rw-r--r-- | cpp/include/IceUtil/MutexPtrTryLock.h | 82 | ||||
-rw-r--r-- | cpp/include/IceUtil/RWRecMutex.h | 2 | ||||
-rw-r--r-- | cpp/include/IceUtil/RecMutex.h | 3 | ||||
-rw-r--r-- | cpp/include/IceUtil/StaticMutex.h | 6 | ||||
-rw-r--r-- | cpp/include/IceUtil/Thread.h | 7 | ||||
-rw-r--r-- | cpp/include/IceUtil/Timer.h | 6 |
11 files changed, 286 insertions, 24 deletions
diff --git a/cpp/include/IceUtil/Config.h b/cpp/include/IceUtil/Config.h index 3e8ddd03ff0..01bb4d7042e 100644 --- a/cpp/include/IceUtil/Config.h +++ b/cpp/include/IceUtil/Config.h @@ -241,4 +241,10 @@ public: } #endif + +// +// The default Mutex protocol +// +#define ICE_DEFAULT_MUTEX_PROTOCOL PrioInherit + #endif diff --git a/cpp/include/IceUtil/IceUtil.h b/cpp/include/IceUtil/IceUtil.h index 469e2355189..b10aec7c968 100644 --- a/cpp/include/IceUtil/IceUtil.h +++ b/cpp/include/IceUtil/IceUtil.h @@ -25,7 +25,9 @@ #include <IceUtil/Handle.h> #include <IceUtil/Lock.h> #include <IceUtil/Monitor.h> +#include <IceUtil/MutexProtocol.h> #include <IceUtil/Mutex.h> +#include <IceUtil/MutexPtrLock.h> #include <IceUtil/RWRecMutex.h> #include <IceUtil/RecMutex.h> #include <IceUtil/Shared.h> diff --git a/cpp/include/IceUtil/Mutex.h b/cpp/include/IceUtil/Mutex.h index af0c709f89e..9c1a9518406 100644 --- a/cpp/include/IceUtil/Mutex.h +++ b/cpp/include/IceUtil/Mutex.h @@ -13,6 +13,7 @@ #include <IceUtil/Config.h> #include <IceUtil/Lock.h> #include <IceUtil/ThreadException.h> +#include <IceUtil/MutexProtocol.h> namespace IceUtil { @@ -43,6 +44,7 @@ public: typedef TryLockT<Mutex> TryLock; inline Mutex(); + inline Mutex(MutexProtocol); ~Mutex(); // @@ -72,6 +74,7 @@ public: private: + inline void init(MutexProtocol); // noncopyable Mutex(const Mutex&); void operator=(const Mutex&); @@ -106,11 +109,30 @@ private: // // For performance reasons the following functions are inlined. // - +inline +Mutex::Mutex() +{ #ifdef _WIN32 + init(PrioNone); +#else + init(getDefaultMutexProtocol()); +#endif +} inline -Mutex::Mutex() +Mutex::Mutex(MutexProtocol protocol) +{ +#ifdef _WIN32 + init(PrioNone); +#else + init(protocol); +#endif +} + +#ifdef _WIN32 + +inline void +Mutex::init(MutexProtocol) { InitializeCriticalSection(&_mutex); } @@ -164,33 +186,62 @@ Mutex::lock(LockState&) const #else -inline -Mutex::Mutex() +inline void +Mutex::init(MutexProtocol protocol) { -#ifdef NDEBUG - int rc = pthread_mutex_init(&_mutex, 0); -#else - int rc; -#if defined(__linux) && !defined(__USE_UNIX98) - const pthread_mutexattr_t attr = { PTHREAD_MUTEX_ERRORCHECK_NP }; -#else pthread_mutexattr_t attr; rc = pthread_mutexattr_init(&attr); assert(rc == 0); - rc = pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK); - assert(rc == 0); -#endif - rc = pthread_mutex_init(&_mutex, &attr); + if(rc != 0) + { + pthread_mutexattr_destroy(&attr); + throw ThreadSyscallException(__FILE__, __LINE__, rc); + } + // + // Enable mutex error checking in debug builds + // +#ifndef NDEBUG #if defined(__linux) && !defined(__USE_UNIX98) -// Nothing to do + rc = pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK_NP); #else - rc = pthread_mutexattr_destroy(&attr); + rc = pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_ERRORCHECK); +#endif assert(rc == 0); + if(rc != 0) + { + pthread_mutexattr_destroy(&attr); + throw ThreadSyscallException(__FILE__, __LINE__, rc); + } #endif + + // + // If system has support for priority inheritance we set the protocol + // attribute of the mutex + // +#if defined(_POSIX_THREAD_PRIO_INHERIT) && _POSIX_THREAD_PRIO_INHERIT > 0 + if(PrioInherit == protocol) + { + rc = pthread_mutexattr_setprotocol(&attr, PTHREAD_PRIO_INHERIT); + if(rc != 0) + { + pthread_mutexattr_destroy(&attr); + throw ThreadSyscallException(__FILE__, __LINE__, rc); + } + } #endif + rc = pthread_mutex_init(&_mutex, &attr); + assert(rc == 0); + if(rc != 0) + { + pthread_mutexattr_destroy(&attr); + throw ThreadSyscallException(__FILE__, __LINE__, rc); + } + + rc = pthread_mutexattr_destroy(&attr); + assert(rc == 0); if(rc != 0) { throw ThreadSyscallException(__FILE__, __LINE__, rc); diff --git a/cpp/include/IceUtil/MutexProtocol.h b/cpp/include/IceUtil/MutexProtocol.h new file mode 100644 index 00000000000..b435b457bee --- /dev/null +++ b/cpp/include/IceUtil/MutexProtocol.h @@ -0,0 +1,28 @@ +// ********************************************************************** +// +// Copyright (c) 2003-2008 ZeroC, Inc. All rights reserved. +// +// This copy of Ice is licensed to you under the terms described in the +// ICE_LICENSE file included in this distribution. +// +// ********************************************************************** + +#ifndef ICE_UTIL_MUTEX_PROTOCOL_H +#define ICE_UTIL_MUTEX_PROTOCOL_H + +#include <IceUtil/Config.h> + +namespace IceUtil +{ + +enum MutexProtocol +{ + PrioInherit, + PrioNone +}; + +ICE_UTIL_API MutexProtocol getDefaultMutexProtocol(); + +} // End namespace IceUtil + +#endif diff --git a/cpp/include/IceUtil/MutexPtrLock.h b/cpp/include/IceUtil/MutexPtrLock.h new file mode 100644 index 00000000000..e6fad2ba78d --- /dev/null +++ b/cpp/include/IceUtil/MutexPtrLock.h @@ -0,0 +1,83 @@ +// ********************************************************************** +// +// Copyright (c) 2003-2008 ZeroC, Inc. All rights reserved. +// +// This copy of Ice-E is licensed to you under the terms described in the +// ICEE_LICENSE file included in this distribution. +// +// ********************************************************************** + +#ifndef ICE_UTIL_MUTEX_PTR_LOCK_H +#define ICE_UTIL_MUTEX_PTR_LOCK_H + +#include <IceUtil/Config.h> +#include <IceUtil/ThreadException.h> + +namespace IceUtilInternal +{ + +template<class T> +class MutexPtrLock +{ +public: + + MutexPtrLock<T>(const T* mutex) : + _mutex(mutex), + _acquired(false) + { + if(_mutex) + { + _mutex->lock(); + _acquired = true; + } + } + + ~MutexPtrLock<T>() + { + if(_mutex && _acquired) + { + _mutex->unlock(); + } + } + + void acquire() const + { + if(_mutex) + { + _mutex->lock(); + _acquired = true; + } + } + + void release() const + { + if(_mutex) + { + if(!_acquired) + { + throw IceUtil::ThreadLockedException(__FILE__, __LINE__); + } + _mutex->unlock(); + _acquired = false; + } + } + + bool acquired() const + { + return _acquired; + } + +private: + + // Not implemented; prevents accidental use. + // + MutexPtrLock<T>(const MutexPtrLock<T>&); + MutexPtrLock<T>& operator=(const MutexPtrLock<T>&); + + const T* _mutex; + mutable bool _acquired; +}; + +} // End namespace IceUtilInternal + +#endif diff --git a/cpp/include/IceUtil/MutexPtrTryLock.h b/cpp/include/IceUtil/MutexPtrTryLock.h new file mode 100644 index 00000000000..4dba3a4795d --- /dev/null +++ b/cpp/include/IceUtil/MutexPtrTryLock.h @@ -0,0 +1,82 @@ +// ********************************************************************** +// +// Copyright (c) 2003-2008 ZeroC, Inc. All rights reserved. +// +// This copy of Ice-E is licensed to you under the terms described in the +// ICEE_LICENSE file included in this distribution. +// +// ********************************************************************** + +#ifndef ICE_UTIL_MUTEX_PTR_TRY_LOCK_H +#define ICE_UTIL_MUTEX_PTR_TRY_LOCK_H + +#include <IceUtil/Config.h> +#include <IceUtil/Mutex.h> + +namespace IceUtilInternal +{ + +template<class T> +class MutexPtrTryLock +{ +public: + + MutexPtrTryLock<T>(const T* mutex) : + _mutex(mutex), + _acquired(false) + { + if(_mutex) + { + _acquired = _mutex->tryLock(); + } + } + + ~MutexPtrTryLock<T>() + { + if(_mutex && _acquired) + { + _mutex->unlock(); + } + } + + void acquire() const + { + if(_mutex) + { + _mutex->lock(); + _acquired = true; + } + } + + void release() const + { + if(_mutex) + { + if(!_acquired) + { + throw IceUtil::ThreadLockedException(__FILE__, __LINE__); + } + _mutex->unlock(); + _acquired = false; + } + } + + bool acquired() const + { + return _acquired; + } + +private: + + // Not implemented; prevents accidental use. + // + MutexPtrTryLock<T>(const MutexPtrTryLock&); + MutexPtrTryLock<T>& operator=(const MutexPtrTryLock<T>&); + + const T* _mutex; + mutable bool _acquired; +}; + +} // End namespace IceUtilInternal + +#endif diff --git a/cpp/include/IceUtil/RWRecMutex.h b/cpp/include/IceUtil/RWRecMutex.h index a4cf81b18f5..b2433b62b5d 100644 --- a/cpp/include/IceUtil/RWRecMutex.h +++ b/cpp/include/IceUtil/RWRecMutex.h @@ -175,7 +175,7 @@ public: ~WLockT() { - if (_acquired) + if(_acquired) { _mutex.unlock(); } diff --git a/cpp/include/IceUtil/RecMutex.h b/cpp/include/IceUtil/RecMutex.h index 70aa66109a7..0954f51e829 100644 --- a/cpp/include/IceUtil/RecMutex.h +++ b/cpp/include/IceUtil/RecMutex.h @@ -13,6 +13,7 @@ #include <IceUtil/Config.h> #include <IceUtil/Lock.h> #include <IceUtil/ThreadException.h> +#include <IceUtil/MutexProtocol.h> namespace IceUtil { @@ -36,6 +37,7 @@ public: typedef TryLockT<RecMutex> TryLock; RecMutex(); + RecMutex(const MutexProtocol); ~RecMutex(); // @@ -67,6 +69,7 @@ public: private: + void init(const MutexProtocol); // noncopyable RecMutex(const RecMutex&); void operator=(const RecMutex&); diff --git a/cpp/include/IceUtil/StaticMutex.h b/cpp/include/IceUtil/StaticMutex.h index 9ba6f387c90..d7e4d3c0d72 100644 --- a/cpp/include/IceUtil/StaticMutex.h +++ b/cpp/include/IceUtil/StaticMutex.h @@ -114,12 +114,6 @@ private: # define ICE_STATIC_MUTEX_INITIALIZER { PTHREAD_MUTEX_INITIALIZER } #endif - -// A "shared" global mutex that can be used for very simple tasks -// which should not lock any other mutexes. -// -extern ICE_UTIL_API StaticMutex globalMutex; - // // For performance reasons the following functions are inlined. // diff --git a/cpp/include/IceUtil/Thread.h b/cpp/include/IceUtil/Thread.h index 0d47c810e57..08241d17aa8 100644 --- a/cpp/include/IceUtil/Thread.h +++ b/cpp/include/IceUtil/Thread.h @@ -110,6 +110,7 @@ public: virtual void run() = 0; ThreadControl start(size_t = 0); + ThreadControl start(size_t, int priority); ThreadControl getThreadControl() const; @@ -147,6 +148,12 @@ protected: #endif private: + +#ifdef _WIN32 +#else + ThreadControl start(size_t, bool, int); +#endif + Thread(const Thread&); // Copying is forbidden void operator=(const Thread&); // Assignment is forbidden }; diff --git a/cpp/include/IceUtil/Timer.h b/cpp/include/IceUtil/Timer.h index 2683c87d062..2fcdb41cf5f 100644 --- a/cpp/include/IceUtil/Timer.h +++ b/cpp/include/IceUtil/Timer.h @@ -52,6 +52,12 @@ public: // Timer(); + + // + // Construct a timer and starts its execution thread with the priority. + // + Timer(int priority); + // // Destroy the timer and detach its execution thread if the calling thread // is the timer thread, join the timer execution thread otherwise. |