diff --git a/include/znc/Threads.h b/include/znc/Threads.h index 8d62757a..fd98f83c 100644 --- a/include/znc/Threads.h +++ b/include/znc/Threads.h @@ -307,6 +307,9 @@ private: // condition variable for reporting finished cancellation CConditionVariable m_cancellationCond; + // condition variable for waiting running threads == 0 + CConditionVariable m_exit_cond; + // when this is true, all threads should exit bool m_done; diff --git a/src/Threads.cpp b/src/Threads.cpp index 359be6d7..c2e6bf2d 100644 --- a/src/Threads.cpp +++ b/src/Threads.cpp @@ -84,15 +84,12 @@ void CThreadPool::finishJob(CJob *job) const { } CThreadPool::~CThreadPool() { - /* Anyone has an idea how this can be done less ugly? */ CMutexLocker guard(m_mutex); m_done = true; - while (m_num_threads > 0) { + if (m_num_threads > 0) { m_cond.broadcast(); - guard.unlock(); - usleep(100); - guard.lock(); + m_exit_cond.wait(m_mutex); } } @@ -134,6 +131,9 @@ void CThreadPool::threadFunc() { assert(m_num_threads > 0 && m_num_idle > 0); m_num_threads--; m_num_idle--; + + if (m_num_threads == 0 && m_done) + m_exit_cond.signal(); } void CThreadPool::addJob(CJob *job) {