Skip to content

Is AutoResetEvent really susceptible to dropping Set() calls? #8982

Open
@madelson

Description

@madelson

The docs for AutoResetEvent say:

There is no guarantee that every call to the Set method will release a thread. 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's as if the second call did not happen.

This reads to me as if the following scenario could happen:

  • 2 threads are waiting on the event
  • 2 calls to Set() are made in rapid succession
  • Only one thread is released
    This seems like a pretty major issue! However, I'm wondering whether this bug is actually real and if so whether more information can be provided about it. It could also be that I'm misinterpreting the scenario described in which case perhaps the docs could be clarified.

Some notes:

  • I tried to reproduce this scenario on .NET 7 Windows and failed to do so. I used a program like this:
using var @event = new AutoResetEvent(false);
const int Threads = 100;
var b = new Barrier(Threads + 1);
var tasks = Enumerable.Range(0, Threads).Select(t => Task.Factory.StartNew(() => { b.SignalAndWait(); @event.WaitOne(); }, TaskCreationOptions.LongRunning)).ToArray();
b.SignalAndWait(); // wait for all threads to spin up
Thread.Sleep(3000); // give them time to start waiting on the event

for (var i = 0; i < Threads; ++i) { @event.Set(); } // call Set() in rapid succession
// making all the Set() calls from different threads also seems to work
//b = new Barrier(Threads);
//for (var i = 0; i < Threads; ++i) { Task.Factory.StartNew(() => { b.SignalAndWait(); @event.Set(); }, TaskCreationOptions.LongRunning); }

Console.WriteLine(Task.WaitAll(tasks, TimeSpan.FromSeconds(10))); // True only if each Set() released a thread
  • EventWaitHandle (the parent class) does not mention this issue in its docs that I could find.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Pri3Indicates issues/PRs that are low priorityarea-System.ThreadinguntriagedNew issue has not been triaged by the area owner

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions