EventWaitHandle.Set, wait timeout and number of released threads

501 Views Asked by At

From doc (EventWaitHandle.Set)

There is no guarantee that every call to the Set method will release a thread from an EventWaitHandle whose reset mode is EventResetMode.AutoReset. If two calls are too close together, so that the second call occurs before a thread has been released, only one thread is released. It is as if the second call did not happen. Also, if Set is called when there are no threads waiting and the EventWaitHandle is already signaled, the call has no effect.

Consider following code

private AutoResetEvent _are = new AutoResetEvent(false);

private void AnyMethod()
{
  await _are.Set();
}

Case 1

private async Task Method1(long timeout)
{  
  await _are.WaitOneAsync(timeout);
}

private async Task Method2()
{  
  await _are.WaitOneAsync();
}

private static Task WaitOneAsync(this WaitHandle waitHandle, long timeout)
{
    if (waitHandle == null)
        throw new ArgumentNullException("waitHandle");

    var tcs = new TaskCompletionSource<bool>();
    var rwh = ThreadPool.RegisterWaitForSingleObject(waitHandle,
        delegate { tcs.TrySetResult(true); }, null, timeout, true);
    var t = tcs.Task;
    t.ContinueWith( (antecedent) => rwh.Unregister(null));
    return t;
}

Case 2


private void Method1(int timeout)
{  
  _are.WaitOne(timeout);
}

private void Method2()
{  
  _are.WaitOne();
}

Imagine that both Method1 and Method2 are called and then AnyMethod releases one thread right in time when Method1 times out.

Is there guarantee about a thread releasement in the case 1 and 2 or Set method behavior applies generally to any thread releasement when either occurs close to another?

1

There are 1 best solutions below

8
On

From doc...

The documentation quote describes what happens when Set is called and there are no threads waiting. The code in the rest of your question is all about calling Set when threads are waiting, so that paragraph of the docs doesn't apply.

Is there guarantee about thread releasement in case 1 and 2 or Set method behavior applies generally to any thread releasement when either occurs close to another?

Yes; one of the waiting threads will be released. If the event is Set before the timeout, it could be either thread; if the event is Set after the timeout, it will be the thread without the timeout.