What is the cost of async/await?

2011/12/15

no comments

What is the cost of async/await?

.NET 4.5 (C# 5) had brought the new async/await syntax.

I will cover async/await syntax in more details in future post, but in the meanwhile in case that you are not yet familiar with this syntax, what’s  you should have to know is that the syntactic compiler transform that syntax (and the lines that follow the await keyword) into IL, the generated IL is following the concept of the TPL ContinueWith.

the syntactic compiler is actually generating fair amount of IL which represent a state-machine of the async execution.

async/await

we do gain lot of benefit from the new async/await syntax (in terms of readability and more) but as I said I will discuss this aspect on latter posts.

the questions which this post is trying to answer is:

  • How match do we pay for it?
  • Does the compiler is smart enough to minimize the overhead involve with this feature?

the answer for the question is: not only that the compiler is smart enough to mitigate the cost,
it is actually (in most cases) doing better job compare with direct using of ContinueWith.

Benchmark:

I have extend Joseph E. Hoag’s benchmark, and I have find consistence improvement of the async/await over the ContinueWith, both in terms of performance and memory allocation.

the benchmarks is targeting both:

real task execution:

Code Snippet
  1. private static Task AsyncMethod()
  2. {
  3.     return Task.Factory.StartNew(() => { });
  4. }

and conceptual task execution:

Code Snippet
  1. private static Task ConceptualAsyncMethod()
  2. {
  3.     var t = new TaskCompletionSource<object>();
  4.     t.SetResult(null);
  5.     return t.Task;
  6. }

and I was testing the following scenarios:

1. Continuation/Unwarp on both real and conceptual task.

Code Snippet
  1. private static Task DoContinuations(int ntasks)
  2. {
  3.     Task curr = AsyncMethod();
  4.     for (int i = 1; i < ntasks; i++)
  5.         curr = curr.ContinueWith(_ => AsyncMethod()).Unwrap(); return curr;
  6. }

 

Code Snippet
  1. private static Task DoContinuationsConceptual(int ntasks)
  2. {
  3.     Task curr = ConceptualAsyncMethod();
  4.     for (int i = 1; i < ntasks; i++)
  5.         curr = curr.ContinueWith(_ => ConceptualAsyncMethod()).Unwrap(); return curr;
  6. }

2. await against real and conceptual.

Code Snippet
  1. private static async Task DoAwaits(int ntasks)
  2. {
  3.     for (int i = 0; i < ntasks; i++)
  4.         await AsyncMethod();
  5. }

 

Code Snippet
  1. private static async Task DoAwaitsConceptual(int ntasks)
  2. {
  3.     for (int i = 0; i < ntasks; i++)
  4.         await ConceptualAsyncMethod();
  5. }

3. then I was testing the Task.FromResult for ContinueWith and await.

Code Snippet
  1.  
  2. private static Task DoContinuationsFromResult(int ntasks)
  3. {
  4.     Task curr = Task.FromResult(42);
  5.     for (int i = 1; i < ntasks; i++)
  6.         curr = curr.ContinueWith(t => Task.FromResult(42));
  7.     return curr;
  8. }

 

Code Snippet
  1. private static async Task DoAwaitsFromResult(int ntasks)
  2. {
  3.     for (int i = 0; i < ntasks; i++)
  4.         await Task.FromResult(42);
  5. }

4. to make sure that it isn’t the Unwarp thing which is causing the overhead I added the following benchmark.h

Code Snippet
  1. private static Task DoContinuationsConceptualWithoutUnwrap(int ntasks)
  2. {
  3.     Task curr = ConceptualAsyncMethod();
  4.     for (int i = 1; i < ntasks; i++)
  5.         curr = curr.ContinueWith(t => {/* empty */ });
  6.     return curr;
  7. }

all result come in favor of the async/await syntax,
while everything was running under .NET 4.5.

the execution result for 100000 iterations, under virtual machine with 2 cores and 2G of RAM were:

async/await

Summary

not only async\await doesn’t come with overhead, it is actually perform much better in terms of speed and memory allocation.

It seem that we have benefit both from simplicity and efficiency.

 

Shout it

Add comment
facebook linkedin twitter email

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>