From acc4aca49e246a46e03f8978517c9b3d23b1baea Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Mon, 30 Aug 2010 11:35:06 -0400 Subject: Fix a bug in our win32 condition implementation The do ... while loop in our wait code could spin while waiting because the event object wasn't reset until there were no longer any events waiting to be woken up. We also want to reset the event object if the count of events to wake up reaches zero. Found by Chris Davis. Fixes bug 3053358. --- evthread_win32.c | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'evthread_win32.c') diff --git a/evthread_win32.c b/evthread_win32.c index 795f410f..9bb35486 100644 --- a/evthread_win32.c +++ b/evthread_win32.c @@ -253,20 +253,30 @@ evthread_win32_cond_wait(void *_cond, void *_lock, const struct timeval *tv) --cond->n_waiting; result = 0; waiting = 0; + goto out; } else if (res != WAIT_OBJECT_0) { result = (res==WAIT_TIMEOUT) ? 1 : -1; --cond->n_waiting; waiting = 0; + goto out; } else if (ms != INFINITE) { endTime = GetTickCount(); if (startTime + ms_orig <= endTime) { result = 1; /* Timeout */ --cond->n_waiting; waiting = 0; + goto out; } else { ms = startTime + ms_orig - endTime; } } + /* If we make it here, we are still waiting. */ + if (cond->n_to_wake == 0) { + /* There is nobody else who should wake up; reset + * the event. */ + ResetEvent(cond->event); + } + out: LeaveCriticalSection(&cond->lock); } while (waiting); -- cgit v1.2.1