QFutureInterface: wrap a pair of {release,reserve}Thread() calls with RAII
Rationale: a wait on a condition-variable is usually a cancellation point. On Posix, and probably in C++ at some point, a thread cancellation is done by (a kind of) exception unwinding the stack. To ensure that we call reserveThread() in all cases, wrap the function pair in a RAII class. Even if we currently don't seem to support exceptions in QtCore, this is low-hanging fruit, and no worse than what we had before. Change-Id: Ifb0f428ea50f9ac12be14e620615f46e00d3dd91 Reviewed-by: Stephen Kelly <stephen.kelly@kdab.com>
This commit is contained in:
parent
4cebef621b
commit
6611f04879
@ -57,6 +57,19 @@ enum {
|
||||
MaxProgressEmitsPerSecond = 25
|
||||
};
|
||||
|
||||
namespace {
|
||||
class ThreadPoolThreadReleaser {
|
||||
QThreadPool *m_pool;
|
||||
public:
|
||||
explicit ThreadPoolThreadReleaser(QThreadPool *pool)
|
||||
: m_pool(pool)
|
||||
{ if (pool) pool->releaseThread(); }
|
||||
~ThreadPoolThreadReleaser()
|
||||
{ if (m_pool) m_pool->reserveThread(); }
|
||||
};
|
||||
} // unnamed namespace
|
||||
|
||||
|
||||
QFutureInterfaceBase::QFutureInterfaceBase(State initialState)
|
||||
: d(new QFutureInterfaceBasePrivate(initialState))
|
||||
{ }
|
||||
@ -182,11 +195,9 @@ void QFutureInterfaceBase::waitForResume()
|
||||
return;
|
||||
|
||||
// decrease active thread count since this thread will wait.
|
||||
QThreadPool::globalInstance()->releaseThread();
|
||||
const ThreadPoolThreadReleaser releaser(QThreadPool::globalInstance());
|
||||
|
||||
d->pausedWaitCondition.wait(&d->m_mutex);
|
||||
|
||||
QThreadPool::globalInstance()->reserveThread();
|
||||
}
|
||||
|
||||
int QFutureInterfaceBase::progressValue() const
|
||||
|
Loading…
Reference in New Issue
Block a user