-
Notifications
You must be signed in to change notification settings - Fork 5.4k
Closed
Milestone
Description
I'm not sure if this is expected/known behavior, but I've found that it's fairly common for TCSs constructed with the TaskContinuationOptions.RunContinuationsAsynchronously option run their continuation inline anyway.
Here's a simple app that repros the issue:
using System;
using System.Threading;
using System.Threading.Tasks;
namespace RunAsync
{
class Program
{
static void Main(string[] args)
{
for (var i = 0; i < 1000; i++)
{
TestRunAsync(i).Wait();
}
Console.WriteLine("Done!");
}
static async Task TestRunAsync(int testRun)
{
var tcs = new TaskCompletionSource<object>(TaskContinuationOptions.RunContinuationsAsynchronously);
var mre = new ManualResetEventSlim();
var tcsAwaiterTask = Task.Run(async () =>
{
await tcs.Task;
if (!mre.Wait(TimeSpan.FromSeconds(10)))
{
Console.WriteLine("Tcs continuation ran inline in test run {0}. Stack trace: {1}", testRun, Environment.StackTrace);
throw new Exception();
}
});
var tcsSetterTask = Task.Run(() =>
{
tcs.SetResult(null);
mre.Set();
});
await tcsAwaiterTask;
await tcsSetterTask;
}
}
}Expected output:
Done!
Actual output:
Tcs continuation ran inline in test run 3. Stack trace: at System.Environment.get_StackTrace()
at RunAsync.Program.<>c__DisplayClass1_0.<<TestRunAsync>b__0>d.MoveNext() in C:\Users\shalter\Downloads\RunAsync\Program.cs:line 29
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1.AsyncStateMachineBox`1.MoveNext()
at System.Threading.Tasks.AwaitTaskContinuation.RunOrScheduleAction(IAsyncStateMachineBox box, Boolean allowInlining)
at System.Threading.Tasks.Task.RunContinuations(Object continuationObject)
at System.Threading.Tasks.Task`1.TrySetResult(TResult result)
at System.Threading.Tasks.TaskCompletionSource`1.TrySetResult(TResult result)
at System.Threading.Tasks.TaskCompletionSource`1.SetResult(TResult result)
at RunAsync.Program.<>c__DisplayClass1_0.<TestRunAsync>b__1() in C:\Users\shalter\Downloads\RunAsync\Program.cs:line 36
at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
at System.Threading.Tasks.Task.ExecuteWithThreadLocal(Task& currentTaskSlot)
at System.Threading.ThreadPoolWorkQueue.Dispatch()
Unhandled Exception: System.AggregateException: One or more errors occurred. (Exception of type 'System.Exception' was thrown.) ---> System.Exception: Exception of type 'System.Exception' was thrown.
at RunAsync.Program.<>c__DisplayClass1_0.<<TestRunAsync>b__0>d.MoveNext() in C:\Users\shalter\Downloads\RunAsync\Program.cs:line 30
--- End of stack trace from previous location where exception was thrown ---
at RunAsync.Program.TestRunAsync(Int32 testRun) in C:\Users\shalter\Downloads\RunAsync\Program.cs:line 40
--- End of inner exception stack trace ---
at System.Threading.Tasks.Task.Wait(Int32 millisecondsTimeout, CancellationToken cancellationToken)
at System.Threading.Tasks.Task.Wait()
at RunAsync.Program.Main(String[] args) in C:\Users\shalter\Downloads\RunAsync\Program.cs:line 13
This can be reproduced with RC1. @stephentoub
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
No labels