关于线程冲突的问题
今天看spserver的代码
// 伪代码
// BlockingQueue
HANDLE mutex = CreateMutex;
HANDLE event = CreateEvent(NULL, FALSE, FALSE, NULL);
// non-blocking
void push( void * item )
{
Lock(mutex);
queue->push( item );
SetEvent(event);
UnLock(mutex);
}
// blocking until can pop
void * pop()
{
void * ret = NULL;
Lock(mutex);
if( queue->getLength() == 0 ) {
// 问题在这里 如果下面unlock了 上面push刚好在SetEvent呢?
/*
Caller MUST be holding the mutex lock; the
lock is released and the caller is blocked waiting
on 'cond'. When 'cond' is signaled, the mutex
is re-acquired before returning to the caller.
*/
UnLock(mutex);
WaitForSingleObject( event, INFINITE );
Lock(mutex);
}
ret = queue->pop();
UnLock(mutex);
return ret;
}
[解决办法]
问题在这里 如果下面unlock了 上面push刚好在SetEvent呢?
我觉得这没问题吧?如果下面unlock了,然后push的lock成功,然后queue->push( item );压入数据。
此时pop正在执行unlock下的WaitForSingleObject( event, INFINITE );等待,push会在压入数据之后SetEvent(event);,然后unlock。pop的WaitForSingleObject等待的event有信号,继续执行Lock(mutex);,锁住队列,然后执行 ret = queue->pop();,最后再UnLock(mutex);。
[解决办法]
如果你在哪里unlock了,那么你线程可能执行push,也可能继续往下执行