diff options
author | Michael Lutz <michi@icosahedron.de> | 2019-03-11 00:45:39 +0100 |
---|---|---|
committer | Michael Lutz <michi@icosahedron.de> | 2019-04-06 11:27:39 +0200 |
commit | 05f4e7360886e36b221ef5c3af4426625a3de686 (patch) | |
tree | 27aed9756e80eca86ff95f5805901a80048b0fb1 /src/thread | |
parent | 3b86f54fc739510277f434c68e17a93ab6448ed4 (diff) | |
download | openttd-05f4e7360886e36b221ef5c3af4426625a3de686.tar.xz |
Codechange: Replace custom mutex code with C++11 mutex'es.
A conforming compiler with a valid <mutex>-header is expected.
Most parts of the code assume that locking a mutex will never fail unexpectedly,
which is generally true on all common platforms that don't just pretend to
be C++11. The use of condition variables in driver code is checked.
Diffstat (limited to 'src/thread')
-rw-r--r-- | src/thread/thread.h | 67 | ||||
-rw-r--r-- | src/thread/thread_none.cpp | 5 | ||||
-rw-r--r-- | src/thread/thread_os2.cpp | 56 | ||||
-rw-r--r-- | src/thread/thread_pthread.cpp | 81 | ||||
-rw-r--r-- | src/thread/thread_win32.cpp | 56 |
5 files changed, 0 insertions, 265 deletions
diff --git a/src/thread/thread.h b/src/thread/thread.h index 07831bb4b..eca825e25 100644 --- a/src/thread/thread.h +++ b/src/thread/thread.h @@ -51,73 +51,6 @@ public: }; /** - * Cross-platform Mutex - */ -class ThreadMutex { -public: - /** - * Create a new mutex. - */ - static ThreadMutex *New(); - - /** - * Virtual Destructor to avoid compiler warnings. - */ - virtual ~ThreadMutex() {}; - - /** - * Begin the critical section - * @param allow_recursive Whether recursive locking is intentional. - * If false, NOT_REACHED() will be called when the mutex is already locked - * by the current thread. - */ - virtual void BeginCritical(bool allow_recursive = false) = 0; - - /** - * End of the critical section - * @param allow_recursive Whether recursive unlocking is intentional. - * If false, NOT_REACHED() will be called when the mutex was locked more - * than once by the current thread. - */ - virtual void EndCritical(bool allow_recursive = false) = 0; - - /** - * Wait for a signal to be send. - * @pre You must be in the critical section. - * @note While waiting the critical section is left. - * @post You will be in the critical section. - */ - virtual void WaitForSignal() = 0; - - /** - * Send a signal and wake the 'thread' that was waiting for it. - */ - virtual void SendSignal() = 0; -}; - -/** - * Simple mutex locker to keep a mutex locked until the locker goes out of scope. - */ -class ThreadMutexLocker { -public: - /** - * Lock the mutex and keep it locked for the life time of this object. - * @param mutex Mutex to be locked. - */ - ThreadMutexLocker(ThreadMutex *mutex) : mutex(mutex) { mutex->BeginCritical(); } - - /** - * Unlock the mutex. - */ - ~ThreadMutexLocker() { this->mutex->EndCritical(); } - -private: - ThreadMutexLocker(const ThreadMutexLocker &) { NOT_REACHED(); } - ThreadMutexLocker &operator=(const ThreadMutexLocker &) { NOT_REACHED(); return *this; } - ThreadMutex *mutex; -}; - -/** * Get number of processor cores in the system, including HyperThreading or similar. * @return Total number of processor cores. */ diff --git a/src/thread/thread_none.cpp b/src/thread/thread_none.cpp index 91eb50b11..83ae52d46 100644 --- a/src/thread/thread_none.cpp +++ b/src/thread/thread_none.cpp @@ -28,8 +28,3 @@ public: virtual void WaitForSignal() {} virtual void SendSignal() {} }; - -/* static */ ThreadMutex *ThreadMutex::New() -{ - return new ThreadMutex_None(); -} diff --git a/src/thread/thread_os2.cpp b/src/thread/thread_os2.cpp index 976283f23..72ee080d6 100644 --- a/src/thread/thread_os2.cpp +++ b/src/thread/thread_os2.cpp @@ -89,59 +89,3 @@ private: if (thread != NULL) *thread = to; return true; } - -/** - * OS/2 version of ThreadMutex. - */ -class ThreadMutex_OS2 : public ThreadMutex { -private: - HMTX mutex; ///< The mutex. - HEV event; ///< Event for waiting. - uint recursive_count; ///< Recursive lock count. - -public: - ThreadMutex_OS2() : recursive_count(0) - { - DosCreateMutexSem(NULL, &mutex, 0, FALSE); - DosCreateEventSem(NULL, &event, 0, FALSE); - } - - ~ThreadMutex_OS2() override - { - DosCloseMutexSem(mutex); - DosCloseEventSem(event); - } - - void BeginCritical(bool allow_recursive = false) override - { - /* os2 mutex is recursive by itself */ - DosRequestMutexSem(mutex, (unsigned long) SEM_INDEFINITE_WAIT); - this->recursive_count++; - if (!allow_recursive && this->recursive_count != 1) NOT_REACHED(); - } - - void EndCritical(bool allow_recursive = false) override - { - if (!allow_recursive && this->recursive_count != 1) NOT_REACHED(); - this->recursive_count--; - DosReleaseMutexSem(mutex); - } - - void WaitForSignal() override - { - assert(this->recursive_count == 1); // Do we need to call Begin/EndCritical multiple times otherwise? - this->EndCritical(); - DosWaitEventSem(event, SEM_INDEFINITE_WAIT); - this->BeginCritical(); - } - - void SendSignal() override - { - DosPostEventSem(event); - } -}; - -/* static */ ThreadMutex *ThreadMutex::New() -{ - return new ThreadMutex_OS2(); -} diff --git a/src/thread/thread_pthread.cpp b/src/thread/thread_pthread.cpp index afb259183..50fefb531 100644 --- a/src/thread/thread_pthread.cpp +++ b/src/thread/thread_pthread.cpp @@ -108,84 +108,3 @@ private: if (thread != NULL) *thread = to; return true; } - -/** - * POSIX pthread version of ThreadMutex. - */ -class ThreadMutex_pthread : public ThreadMutex { -private: - pthread_mutex_t mutex; ///< The actual mutex. - pthread_cond_t condition; ///< Data for conditional waiting. - pthread_mutexattr_t attr; ///< Attributes set for the mutex. - pthread_t owner; ///< Owning thread of the mutex. - uint recursive_count; ///< Recursive lock count. - -public: - ThreadMutex_pthread() : owner(0), recursive_count(0) - { - pthread_mutexattr_init(&this->attr); - pthread_mutexattr_settype(&this->attr, PTHREAD_MUTEX_ERRORCHECK); - pthread_mutex_init(&this->mutex, &this->attr); - pthread_cond_init(&this->condition, NULL); - } - - ~ThreadMutex_pthread() override - { - int err = pthread_cond_destroy(&this->condition); - assert(err != EBUSY); - err = pthread_mutex_destroy(&this->mutex); - assert(err != EBUSY); - } - - bool IsOwnedByCurrentThread() const - { - return this->owner == pthread_self(); - } - - void BeginCritical(bool allow_recursive = false) override - { - /* pthread mutex is not recursive by itself */ - if (this->IsOwnedByCurrentThread()) { - if (!allow_recursive) NOT_REACHED(); - } else { - int err = pthread_mutex_lock(&this->mutex); - assert(err == 0); - assert(this->recursive_count == 0); - this->owner = pthread_self(); - } - this->recursive_count++; - } - - void EndCritical(bool allow_recursive = false) override - { - assert(this->IsOwnedByCurrentThread()); - if (!allow_recursive && this->recursive_count != 1) NOT_REACHED(); - this->recursive_count--; - if (this->recursive_count != 0) return; - this->owner = 0; - int err = pthread_mutex_unlock(&this->mutex); - assert(err == 0); - } - - void WaitForSignal() override - { - uint old_recursive_count = this->recursive_count; - this->recursive_count = 0; - this->owner = 0; - int err = pthread_cond_wait(&this->condition, &this->mutex); - assert(err == 0); - this->owner = pthread_self(); - this->recursive_count = old_recursive_count; - } - - void SendSignal() override - { - int err = pthread_cond_signal(&this->condition); - assert(err == 0); - } -}; - -/* static */ ThreadMutex *ThreadMutex::New() -{ - return new ThreadMutex_pthread(); -} diff --git a/src/thread/thread_win32.cpp b/src/thread/thread_win32.cpp index 506faa069..fc7a85a91 100644 --- a/src/thread/thread_win32.cpp +++ b/src/thread/thread_win32.cpp @@ -109,59 +109,3 @@ private: if (thread != NULL) *thread = to; return true; } - -/** - * Win32 thread version of ThreadMutex. - */ -class ThreadMutex_Win32 : public ThreadMutex { -private: - CRITICAL_SECTION critical_section; ///< The critical section we would enter. - HANDLE event; ///< Event for signalling. - uint recursive_count; ///< Recursive lock count. - -public: - ThreadMutex_Win32() : recursive_count(0) - { - InitializeCriticalSection(&this->critical_section); - this->event = CreateEvent(NULL, FALSE, FALSE, NULL); - } - - ~ThreadMutex_Win32() override - { - DeleteCriticalSection(&this->critical_section); - CloseHandle(this->event); - } - - void BeginCritical(bool allow_recursive = false) override - { - /* windows mutex is recursive by itself */ - EnterCriticalSection(&this->critical_section); - this->recursive_count++; - if (!allow_recursive && this->recursive_count != 1) NOT_REACHED(); - } - - void EndCritical(bool allow_recursive = false) override - { - if (!allow_recursive && this->recursive_count != 1) NOT_REACHED(); - this->recursive_count--; - LeaveCriticalSection(&this->critical_section); - } - - void WaitForSignal() override - { - assert(this->recursive_count == 1); // Do we need to call Begin/EndCritical multiple times otherwise? - this->EndCritical(); - WaitForSingleObject(this->event, INFINITE); - this->BeginCritical(); - } - - void SendSignal() override - { - SetEvent(this->event); - } -}; - -/* static */ ThreadMutex *ThreadMutex::New() -{ - return new ThreadMutex_Win32(); -} |