windows: Prevent queueing of multiple thread cancel APCs

This avoids any races during cleanup invocation if multiple cancel() requests
come in.
This commit is contained in:
Martin Willi
2014-06-04 15:53:01 +02:00
parent 0fa9c95811
commit 9dec601f30
+10 -1
View File
@@ -88,10 +88,15 @@ struct private_thread_t {
bool cancelability; bool cancelability;
/** /**
* Has the thread been cancelled * Has the thread been cancelled by thread->cancel()?
*/ */
bool canceled; bool canceled;
/**
* Did we schedule an APC to docancel()?
*/
bool cancel_pending;
/** /**
* Active condition variable thread is waiting in, if any * Active condition variable thread is waiting in, if any
*/ */
@@ -357,11 +362,15 @@ METHOD(thread_t, cancel, void,
if (this->cancelability) if (this->cancelability)
{ {
threads_lock->lock(threads_lock); threads_lock->lock(threads_lock);
if (!this->cancel_pending)
{
this->cancel_pending = TRUE;
QueueUserAPC((void*)docancel, this->handle, (uintptr_t)this); QueueUserAPC((void*)docancel, this->handle, (uintptr_t)this);
if (this->condvar) if (this->condvar)
{ {
WakeAllConditionVariable(this->condvar); WakeAllConditionVariable(this->condvar);
} }
}
threads_lock->unlock(threads_lock); threads_lock->unlock(threads_lock);
} }
} }