rthreads.c:
- In scond_wait(), make use of SignalObjectAndWait() as an optimization.
This commit is contained in:
parent
5d66422b94
commit
538442861b
|
@ -412,41 +412,21 @@ void scond_wait(scond_t *cond, slock_t *lock)
|
||||||
/* 2. a signaller can rush in and signal, and then turn right around and wait */
|
/* 2. a signaller can rush in and signal, and then turn right around and wait */
|
||||||
/* solution: the signaller will get queued behind the waiter, who's enqueued before he releases the mutex */
|
/* solution: the signaller will get queued behind the waiter, who's enqueued before he releases the mutex */
|
||||||
|
|
||||||
for(;;)
|
/* It's my turn if I'm the head of the queue. Check to see if it's my turn. */
|
||||||
{
|
while (cond->head != &myentry)
|
||||||
/* We're always in the mutex here*/
|
|
||||||
|
|
||||||
/* It's my turn if I'm the head of the queue */
|
|
||||||
bool myturn = (cond->head == &myentry);
|
|
||||||
|
|
||||||
if(!myturn)
|
|
||||||
{
|
{
|
||||||
/* As long as someone is even going to be able to wake up when they receive the potato, keep it going round */
|
/* As long as someone is even going to be able to wake up when they receive the potato, keep it going round */
|
||||||
if(cond->wakens>0)
|
if (cond->wakens > 0)
|
||||||
SetEvent(cond->hot_potato);
|
SetEvent(cond->hot_potato);
|
||||||
}
|
|
||||||
|
|
||||||
/* If it's my turn, I hold the potato */
|
|
||||||
|
|
||||||
ReleaseMutex(lock->lock);
|
|
||||||
|
|
||||||
if(myturn)
|
|
||||||
{
|
|
||||||
WaitForSingleObject(cond->event, INFINITE);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
/* Wait to catch the hot potato before checking for my turn again */
|
/* Wait to catch the hot potato before checking for my turn again */
|
||||||
WaitForSingleObject(cond->hot_potato, INFINITE);
|
SignalObjectAndWait(lock->lock, cond->hot_potato, INFINITE, FALSE);
|
||||||
|
slock_lock(lock);
|
||||||
/* Re-acquire the mutex just for interrogating the queue */
|
|
||||||
WaitForSingleObject(lock->lock, INFINITE);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Reacquire the main mutex */
|
/* It's my turn now -- I hold the potato */
|
||||||
WaitForSingleObject(lock->lock, INFINITE);
|
SignalObjectAndWait(lock->lock, cond->event, INFINITE, FALSE);
|
||||||
|
slock_lock(lock);
|
||||||
|
|
||||||
/* Remove ourselves from the queue */
|
/* Remove ourselves from the queue */
|
||||||
cond->head = myentry.next;
|
cond->head = myentry.next;
|
||||||
|
|
Loading…
Reference in New Issue