PageRenderTime 84ms CodeModel.GetById 17ms app.highlight 44ms RepoModel.GetById 1ms app.codeStats 2ms

/Src/Compilers/CSharp/Test/Semantic/Semantics/BindingAsyncTests.cs

https://github.com/EkardNT/Roslyn
C# | 3780 lines | 3195 code | 137 blank | 448 comment | 1 complexity | 093c3e2421baa2837e93dde09d6dbcc9 MD5 | raw file

Large files files are truncated, but you can click here to view the full file

   1// Copyright (c) Microsoft Open Technologies, Inc.  All Rights Reserved.  Licensed under the Apache License, Version 2.0.  See License.txt in the project root for license information.
   2
   3using System.Collections.Generic;
   4using System.Linq;
   5using Microsoft.CodeAnalysis.CSharp.Symbols;
   6using Microsoft.CodeAnalysis.CSharp.Syntax;
   7using Microsoft.CodeAnalysis.CSharp.Test.Utilities;
   8using Microsoft.CodeAnalysis.Text;
   9using Roslyn.Test.Utilities;
  10using Xunit;
  11
  12namespace Microsoft.CodeAnalysis.CSharp.UnitTests.Semantics
  13{
  14    public class BindingAsyncTests : CompilingTestBase
  15    {
  16        [Fact]
  17        public void AsyncMethod()
  18        {
  19            var source = @"
  20using System.Threading.Tasks;
  21class C
  22{
  23    async void M(Task t)
  24    {
  25        await t;
  26    }
  27}";
  28            var compilation = CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
  29            var method = (SourceMethodSymbol)compilation.GlobalNamespace.GetTypeMembers("C").Single().GetMembers("M").Single();
  30            Assert.True(method.IsAsync);
  31        }
  32
  33        [Fact]
  34        public void AsyncLambdas()
  35        {
  36            var source = @"
  37using System;
  38using System.Threading.Tasks;
  39class C
  40{
  41    public static void Main()
  42    {
  43        Action<Task> f1 = async (Task t) => { await t; };
  44        Action<Task> f2 = async t => { await t; };
  45        Action<Task> f3 = async (t) => { await t; };
  46    }
  47}";
  48            var tree = SyntaxFactory.ParseSyntaxTree(source);
  49            var compilation = CreateCompilationWithMscorlib45(new SyntaxTree[] {tree}).VerifyDiagnostics();
  50
  51            var model = compilation.GetSemanticModel(tree);
  52
  53            var simple = tree.GetCompilationUnitRoot().DescendantNodes().OfType<SimpleLambdaExpressionSyntax>().Single();
  54            Assert.True(((LambdaSymbol)model.GetSymbolInfo(simple).Symbol).IsAsync);
  55
  56            var parens = tree.GetCompilationUnitRoot().DescendantNodes().OfType<ParenthesizedLambdaExpressionSyntax>();
  57            Assert.True(parens.Count() == 2, "Expect exactly two parenthesized lambda expressions in the syntax tree.");
  58            foreach (var paren in parens)
  59            {
  60                Assert.True(((LambdaSymbol)model.GetSymbolInfo(paren).Symbol).IsAsync);
  61            }
  62        }
  63
  64        [Fact]
  65        public void AsyncDelegates()
  66        {
  67
  68            var source = @"
  69using System;
  70using System.Threading.Tasks;
  71class C
  72{
  73    public static void Main()
  74    {
  75        Action<Task> f4 = async delegate(Task t) { await t; };
  76    }
  77}";
  78            var tree = SyntaxFactory.ParseSyntaxTree(source);
  79            var compilation = CreateCompilationWithMscorlib45(new SyntaxTree[] { tree }).VerifyDiagnostics();
  80
  81            var model = compilation.GetSemanticModel(tree);
  82
  83            var del = tree.GetCompilationUnitRoot().DescendantNodes().OfType<AnonymousMethodExpressionSyntax>().Single();
  84            Assert.True(((LambdaSymbol)model.GetSymbolInfo(del).Symbol).IsAsync);
  85        }
  86
  87        [Fact]
  88        public void BadAsyncConstructor()
  89        {
  90            var source = @"
  91class C {
  92    async public C() { } 
  93}";
  94            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
  95                Diagnostic(ErrorCode.ERR_BadMemberFlag, "C").WithArguments("async"));
  96        }
  97
  98        [Fact]
  99        public void BadAsyncDestructor()
 100        {
 101            var source = @"
 102class C
 103{
 104    async extern ~C();
 105}";
 106            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 107                Diagnostic(ErrorCode.ERR_BadMemberFlag, "C").WithArguments("async"),
 108                Diagnostic(ErrorCode.WRN_ExternMethodNoImplementation, "C").WithArguments("C.~C()"));
 109        }
 110
 111        [Fact]
 112        public void BadAsyncEvent()
 113        {
 114            var source = @"
 115public delegate void MyDelegate();
 116
 117class C
 118{
 119    public C() {
 120        MyEvent.Invoke();
 121    }
 122
 123    async event MyDelegate MyEvent;
 124}";
 125            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 126                Diagnostic(ErrorCode.ERR_BadMemberFlag, "MyEvent").WithArguments("async"));
 127        }
 128
 129        [Fact]
 130        public void BadAsyncField()
 131        {
 132            var source = @"
 133class C
 134{
 135    public C(int i)
 136    {
 137        this.i = i;
 138    }
 139
 140    async int i;
 141}";
 142            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 143                Diagnostic(ErrorCode.ERR_BadMemberFlag, "i").WithArguments("async"));
 144        }
 145
 146        [Fact]
 147        public void BadAsyncClass()
 148        {
 149            var source = @"
 150public async class C
 151{
 152}";
 153            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 154                Diagnostic(ErrorCode.ERR_BadMemberFlag, "C").WithArguments("async"));
 155        }
 156
 157        [Fact]
 158        public void BadAsyncStruct()
 159        {
 160            var source = @"
 161internal async struct S
 162{
 163}";
 164            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 165                Diagnostic(ErrorCode.ERR_BadMemberFlag, "S").WithArguments("async"));
 166        }
 167
 168        [Fact]
 169        public void BadAsyncInterface()
 170        {
 171            var source = @"
 172internal async interface I
 173{
 174}";
 175            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 176                Diagnostic(ErrorCode.ERR_BadMemberFlag, "I").WithArguments("async"));
 177        }
 178
 179        [Fact]
 180        public void BadAsyncDelegate()
 181        {
 182            var source = @"
 183public async delegate void MyDelegate();
 184";
 185            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 186                Diagnostic(ErrorCode.ERR_BadMemberFlag, "MyDelegate").WithArguments("async"));
 187        }
 188
 189        [Fact]
 190        public void BadAsyncProperty()
 191        {
 192            var source = @"
 193public async delegate void MyDelegate();
 194";
 195            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 196                Diagnostic(ErrorCode.ERR_BadMemberFlag, "MyDelegate").WithArguments("async"));
 197        }
 198
 199        [Fact]
 200        public void BadAsyncPropertyAccessor()
 201        {
 202            var source = @"
 203public async delegate void MyDelegate();
 204";
 205            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 206                Diagnostic(ErrorCode.ERR_BadMemberFlag, "MyDelegate").WithArguments("async"));
 207        }
 208
 209        [Fact]
 210        public void TaskRetNoObjectRequired()
 211        {
 212            var source = @"
 213using System;
 214using System.Threading.Tasks;
 215
 216class C
 217{
 218    static void InferTask(Func<Task> x) { }
 219    
 220    static void InferTaskOrTaskT(Func<Task> x) { }
 221    static void InferTaskOrTaskT(Func<Task<int>> x) { }
 222
 223    static async Task F1()
 224    {
 225        return await Task.Factory.StartNew(() => 1);
 226    }
 227
 228    static void Main()
 229    {
 230        Func<Task> F2 = async () => { await Task.Factory.StartNew(() => { }); return 1; };
 231        InferTask(async () => { return await Task.Factory.StartNew(() => 1); });
 232        InferTaskOrTaskT(async () => { return await Task.Factory.StartNew(() => 1); });
 233    }
 234}";
 235            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 236    // (14,9): error CS1997: Since 'C.F1()' is an async method that returns 'Task', a return keyword must not be followed by an object expression. Did you intend to return 'Task<T>'?
 237    //         return await Task.Factory.StartNew(() => 1);
 238    Diagnostic(ErrorCode.ERR_TaskRetNoObjectRequired, "return").WithArguments("C.F1()").WithLocation(14, 9),
 239    // (19,79): error CS8030: Async lambda expression converted to a 'Task' returning delegate cannot return a value. Did you intend to return 'Task<T>'?
 240    //         Func<Task> F2 = async () => { await Task.Factory.StartNew(() => { }); return 1; };
 241    Diagnostic(ErrorCode.ERR_TaskRetNoObjectRequiredLambda, "return").WithLocation(19, 79),
 242    // (20,33): error CS8030: Async lambda expression converted to a 'Task' returning delegate cannot return a value. Did you intend to return 'Task<T>'?
 243    //         InferTask(async () => { return await Task.Factory.StartNew(() => 1); });
 244    Diagnostic(ErrorCode.ERR_TaskRetNoObjectRequiredLambda, "return").WithLocation(20, 33)
 245    );
 246        }
 247
 248        [Fact]
 249        public void BadAsyncReturn()
 250        {
 251            var source = @"
 252using System;
 253using System.Threading.Tasks;
 254
 255class MyTask : Task
 256{
 257    public MyTask(Action a) : base(a) { }
 258}
 259
 260class C
 261{
 262    async int F1()
 263    {
 264        await Task.Factory.StartNew(() => { });
 265    }
 266
 267    async MyTask F2()
 268    {
 269        await Task.Factory.StartNew(() => { });
 270    }
 271
 272    async T F3<T>()
 273    {
 274        await Task.Factory.StartNew(() => { });
 275    }
 276
 277    async T F4<T>() where T : Task
 278    {
 279        await Task.Factory.StartNew(() => { });
 280    }
 281}";
 282            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 283                // (17,18): error CS1983: The return type of an async method must be void, Task or Task<T>
 284                //     async MyTask F2()
 285                Diagnostic(ErrorCode.ERR_BadAsyncReturn, "F2"),
 286                // (22,13): error CS1983: The return type of an async method must be void, Task or Task<T>
 287                //     async T F3<T>()
 288                Diagnostic(ErrorCode.ERR_BadAsyncReturn, "F3"),
 289                // (27,13): error CS1983: The return type of an async method must be void, Task or Task<T>
 290                //     async T F4<T>() where T : Task
 291                Diagnostic(ErrorCode.ERR_BadAsyncReturn, "F4"),
 292                // (12,15): error CS1983: The return type of an async method must be void, Task or Task<T>
 293                //     async int F1()
 294                Diagnostic(ErrorCode.ERR_BadAsyncReturn, "F1"),
 295                // (12,15): error CS0161: 'C.F1()': not all code paths return a value
 296                //     async int F1()
 297                Diagnostic(ErrorCode.ERR_ReturnExpected, "F1").WithArguments("C.F1()"),
 298                // (17,18): error CS0161: 'C.F2()': not all code paths return a value
 299                //     async MyTask F2()
 300                Diagnostic(ErrorCode.ERR_ReturnExpected, "F2").WithArguments("C.F2()"),
 301                // (22,13): error CS0161: 'C.F3<T>()': not all code paths return a value
 302                //     async T F3<T>()
 303                Diagnostic(ErrorCode.ERR_ReturnExpected, "F3").WithArguments("C.F3<T>()"),
 304                // (27,13): error CS0161: 'C.F4<T>()': not all code paths return a value
 305                //     async T F4<T>() where T : Task
 306                Diagnostic(ErrorCode.ERR_ReturnExpected, "F4").WithArguments("C.F4<T>()"));
 307        }
 308
 309        [Fact]
 310        public void CantConvAsyncAnonFuncReturns()
 311        {
 312            var source = @"
 313using System;
 314using System.Threading.Tasks;
 315
 316class C
 317{
 318    static void Main()
 319    {
 320        Func<int> f1 = async () => await Task.Factory.StartNew(() => 1);
 321        Func<int> f2 = async () => { return await Task.Factory.StartNew(() => 1); };
 322    }
 323}";
 324            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 325                // (9,24): error CS4010: Cannot convert async lambda expression to delegate type 'System.Func<int>'. An async lambda expression may return void, Task or Task<T>, none of which are convertible to 'System.Func<int>'.
 326                //         Func<int> f1 = async () => await Task.Factory.StartNew(() => 1);
 327                Diagnostic(ErrorCode.ERR_CantConvAsyncAnonFuncReturns, "async () => await Task.Factory.StartNew(() => 1)").WithArguments("lambda expression", "System.Func<int>").WithLocation(9, 24),
 328                // (10,24): error CS4010: Cannot convert async lambda expression to delegate type 'System.Func<int>'. An async lambda expression may return void, Task or Task<T>, none of which are convertible to 'System.Func<int>'.
 329                //         Func<int> f2 = async () => { return await Task.Factory.StartNew(() => 1); };
 330                Diagnostic(ErrorCode.ERR_CantConvAsyncAnonFuncReturns, "async () => { return await Task.Factory.StartNew(() => 1); }").WithArguments("lambda expression", "System.Func<int>").WithLocation(10, 24)
 331            );
 332        }
 333
 334        [Fact]
 335        public void BadAsyncReturnExpression()
 336        {
 337            var source = @"
 338using System;
 339using System.Threading.Tasks;
 340
 341class C
 342{
 343    static void InferTask_T(Func<Task<int>> x) { }
 344
 345    static void Main()
 346    {
 347        Func<Task<int>> f1 = async () => await Task.Factory.StartNew(() => new Task<int>(null));
 348        Func<Task<int>> f2 = async () => { return await Task.Factory.StartNew(() => new Task<int>(null)); };
 349
 350        InferTask_T(async () => await Task.Factory.StartNew(() => new Task<int>(() => 1)));
 351        InferTask_T(async () => { return await Task.Factory.StartNew(() => new Task<int>(() => 1)); });
 352    }
 353}";
 354            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 355                // (11,42): error CS4016: Since this is an async method, the return expression must be of type 'int' rather than 'Task<int>'
 356                //         Func<Task<int>> f1 = async () => await Task.Factory.StartNew(() => new Task<int>(null));
 357                Diagnostic(ErrorCode.ERR_BadAsyncReturnExpression, "await Task.Factory.StartNew(() => new Task<int>(null))").WithArguments("int"),
 358                // (12,51): error CS4016: Since this is an async method, the return expression must be of type 'int' rather than 'Task<int>'
 359                //         Func<Task<int>> f2 = async () => { return await Task.Factory.StartNew(() => new Task<int>(null)); };
 360                Diagnostic(ErrorCode.ERR_BadAsyncReturnExpression, "await Task.Factory.StartNew(() => new Task<int>(null))").WithArguments("int"),
 361                // (14,33): error CS4016: Since this is an async method, the return expression must be of type 'int' rather than 'Task<int>'
 362                //         InferTask_T(async () => await Task.Factory.StartNew(() => new Task<int>(() => 1)));
 363                Diagnostic(ErrorCode.ERR_BadAsyncReturnExpression, "await Task.Factory.StartNew(() => new Task<int>(() => 1))").WithArguments("int"),
 364                // (15,42): error CS4016: Since this is an async method, the return expression must be of type 'int' rather than 'Task<int>'
 365                //         InferTask_T(async () => { return await Task.Factory.StartNew(() => new Task<int>(() => 1)); });
 366                Diagnostic(ErrorCode.ERR_BadAsyncReturnExpression, "await Task.Factory.StartNew(() => new Task<int>(() => 1))").WithArguments("int"));
 367        }
 368
 369        [Fact]
 370        public void AsyncCantReturnVoid()
 371        {
 372            var source = @"
 373using System;
 374using System.Threading.Tasks;
 375
 376class C
 377{
 378    static void InferVoid(Action x) { }
 379    static void InferTask_T<T>(Func<Task<T>> x) { }
 380    static void Infer_T<T>(Func<T> x) { }
 381
 382    static void Main()
 383    {
 384        InferVoid(async () => { return await Task.Factory.StartNew(() => { }); });
 385        InferTask_T(async () => { return await Task.Factory.StartNew(() => { }); });
 386        Infer_T(async () => { return await Task.Factory.StartNew(() => { }); });
 387    }
 388}";
 389            CreateCompilationWithMscorlib45(source, new MetadataReference[] { LinqAssemblyRef, SystemRef }).VerifyDiagnostics(
 390    // (13,33): error CS8029: Anonymous function converted to a void returning delegate cannot return a value
 391    //         InferVoid(async () => { return await Task.Factory.StartNew(() => { }); });
 392    Diagnostic(ErrorCode.ERR_RetNoObjectRequiredLambda, "return").WithLocation(13, 33),
 393    // (14,42): error CS4029: Cannot return an expression of type 'void'
 394    //         InferTask_T(async () => { return await Task.Factory.StartNew(() => { }); });
 395    Diagnostic(ErrorCode.ERR_CantReturnVoid, "await Task.Factory.StartNew(() => { })").WithLocation(14, 42),
 396    // (15,38): error CS4029: Cannot return an expression of type 'void'
 397    //         Infer_T(async () => { return await Task.Factory.StartNew(() => { }); });
 398    Diagnostic(ErrorCode.ERR_CantReturnVoid, "await Task.Factory.StartNew(() => { })").WithLocation(15, 38)
 399    );
 400        }
 401
 402        [Fact]
 403        public void InferAsyncReturn()
 404        {
 405            var source = @"
 406using System;
 407using System.Threading.Tasks;
 408
 409class C
 410{
 411    static void InferVoid(Action x) { }
 412
 413    static void InferTask(Func<Task> x) { }
 414
 415    static void InferTask_T<T>(Func<Task<T>> x) { }
 416
 417    static void Main()
 418    {
 419        InferVoid(async () => { await Task.Factory.StartNew(() => { }); });
 420
 421        InferTask(async () => { await Task.Factory.StartNew(() => { return; }); });
 422
 423        InferTask_T(async () => { return await Task.Factory.StartNew(() => 1); });
 424    }
 425}";
 426            CreateCompilationWithMscorlib45(source, new MetadataReference[] { LinqAssemblyRef, SystemRef }).VerifyDiagnostics();
 427        }
 428
 429        [Fact]
 430        public void BadInferAsyncReturn_T()
 431        {
 432            var source = @"
 433using System;
 434using System.Threading.Tasks;
 435
 436class C
 437{
 438    static void Infer<T>(Func<bool, T> x) { }
 439
 440    static void Main()
 441    {
 442        Infer(async (x) =>
 443        {
 444            await Task.Factory.StartNew(() => { });
 445            if (x)
 446            {
 447                return 1;
 448            }
 449            else
 450            {
 451                return;
 452            }
 453        });
 454    }
 455}";
 456            CreateCompilationWithMscorlib45(source, new MetadataReference[] { LinqAssemblyRef, SystemRef }).VerifyDiagnostics(
 457                // (19,17): error CS0126: An object of a type convertible to 'int' is required
 458                //                 return;
 459                Diagnostic(ErrorCode.ERR_RetObjectRequired, "return").WithArguments("int"));
 460        }
 461
 462        [Fact]
 463        public void BadInferAsyncReturnVoid()
 464        {
 465            var source = @"
 466using System;
 467using System.Threading.Tasks;
 468
 469class C
 470{
 471    static void Infer(Action<bool> x) { }
 472
 473    static void Main()
 474    {
 475        Infer(async (x) =>
 476        {
 477            await Task.Factory.StartNew(() => { });
 478            if (x)
 479            {
 480                return 1;
 481            }
 482            else
 483            {
 484                return;
 485            }
 486        });
 487    }
 488}";
 489            CreateCompilationWithMscorlib45(source, new MetadataReference[] { LinqAssemblyRef, SystemRef }).VerifyDiagnostics(
 490    // (16,17): error CS8029: Anonymous function converted to a void returning delegate cannot return a value
 491    //                 return 1;
 492    Diagnostic(ErrorCode.ERR_RetNoObjectRequiredLambda, "return").WithLocation(16, 17)
 493    );
 494        }
 495
 496        [Fact]
 497        public void BadInferAsyncReturnTask()
 498        {
 499            var source = @"
 500using System;
 501using System.Threading.Tasks;
 502
 503class C
 504{
 505    static void Infer(Func<bool, Task> x) { }
 506
 507    static void Main()
 508    {
 509        Infer(async (x) =>
 510        {
 511            await Task.Factory.StartNew(() => { });
 512            if (x)
 513            {
 514                return 1;
 515            }
 516            else
 517            {
 518                return;
 519            }
 520        });
 521    }
 522}";
 523            CreateCompilationWithMscorlib45(source, new MetadataReference[] { LinqAssemblyRef, SystemRef }).VerifyDiagnostics(
 524    // (16,17): error CS8030: Async lambda expression converted to a 'Task' returning delegate cannot return a value. Did you intend to return 'Task<T>'?
 525    //                 return 1;
 526    Diagnostic(ErrorCode.ERR_TaskRetNoObjectRequiredLambda, "return").WithLocation(16, 17)
 527    );
 528        }
 529
 530        [Fact]
 531        public void BadInferAsyncReturnTask_T()
 532        {
 533            var source = @"
 534using System;
 535using System.Threading.Tasks;
 536
 537class C
 538{
 539    static void Infer<T>(Func<bool, Task<T>> x) { }
 540
 541    static void Main()
 542    {
 543        Infer(async (x) =>
 544        {
 545            await Task.Factory.StartNew(() => { });
 546            if (x)
 547            {
 548                return 1;
 549            }
 550            else
 551            {
 552                return;
 553            }
 554        });
 555    }
 556}";
 557            CreateCompilationWithMscorlib45(source, new MetadataReference[] { LinqAssemblyRef, SystemRef }).VerifyDiagnostics(
 558                // (19,17): error CS0126: An object of a type convertible to 'int' is required
 559                //                 return;
 560                Diagnostic(ErrorCode.ERR_RetObjectRequired, "return").WithArguments("int"));
 561        }
 562
 563        [Fact]
 564        public void TaskReturningAsyncWithoutReturn()
 565        {
 566            var source = @"
 567using System.Threading.Tasks;
 568
 569class C
 570{
 571    async static Task F()
 572    {
 573    }
 574}";
 575            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 576                // (6,23): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread.
 577                //     async static Task F()
 578                Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "F"));
 579        }
 580
 581        [Fact]
 582        public void TestAsyncReturnsNullableT()
 583        {
 584            var source = @"
 585using System;
 586using System.Threading.Tasks;
 587
 588class C
 589{
 590    async static Task<int?> F()
 591    {
 592        await Task.Factory.StartNew(() => { });
 593        return null;
 594    }
 595
 596    static void Main()
 597    {
 598        Func<Task<int?>> f1 = async () => await Task.Factory.StartNew<int?>(() => { return null; });
 599        Func<Task<int?>> f2 = async () => { return await Task.Factory.StartNew<int?>(() => { return null; }); };
 600    }
 601}";
 602            CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
 603        }
 604
 605        [Fact]
 606        public void VarargsAsync()
 607        {
 608            var source = @"
 609using System.Threading.Tasks;
 610
 611class Test
 612{
 613    async static Task M1(__arglist)
 614    {
 615        await Task.Factory.StartNew(() => { });
 616    }
 617}";
 618            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 619                // (6,23): error CS4006: __arglist is not allowed in the parameter list of async methods
 620                //     async static Task M1(__arglist)
 621                Diagnostic(ErrorCode.ERR_VarargsAsync, "M1"));
 622        }
 623
 624        [Fact]
 625        public void VarargsAsyncGeneric()
 626        {
 627            var source = @"
 628using System.Threading.Tasks;
 629
 630class Test
 631{
 632    async static Task M1<T>(__arglist)
 633    {
 634        await Task.Factory.StartNew(() => { });
 635        return;
 636    }
 637}";
 638            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 639                // (6,23): error CS0224: A method with vararg cannot be generic, be in a generic type, or have a params parameter
 640                //     async static Task M1<T>(__arglist)
 641                Diagnostic(ErrorCode.ERR_BadVarargs, "M1"));
 642        }
 643
 644        [Fact]
 645        public void VarargsAsyncInGenericClass()
 646        {
 647            var source = @"
 648using System.Threading.Tasks;
 649
 650class Test
 651{
 652    async static Task M1<T>(__arglist)
 653    {
 654        await Task.Factory.StartNew(() => { });
 655        return;
 656    }
 657}";
 658            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 659                // (6,23): error CS0224: A method with vararg cannot be generic, be in a generic type, or have a params parameter
 660                //     async static Task M1<T>(__arglist)
 661                Diagnostic(ErrorCode.ERR_BadVarargs, "M1"));
 662        }
 663
 664        [Fact]
 665        public void UnsafeAsyncArgType()
 666        {
 667            var source = @"
 668using System.Threading.Tasks;
 669
 670class Test
 671{
 672    unsafe async static Task M1(int* i) { }
 673}";
 674            CreateCompilationWithMscorlib45(source, null, TestOptions.Dll.WithAllowUnsafe(true)).VerifyDiagnostics(
 675                // (6,38): error CS4005: Async methods cannot have unsafe parameters or return types
 676                //     unsafe async static Task M1(int* i)
 677                Diagnostic(ErrorCode.ERR_UnsafeAsyncArgType, "i"),
 678                // (6,30): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread.
 679                //     unsafe async static Task M1(ref int* i)
 680                Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "M1"));
 681        }
 682
 683        [Fact]
 684        public void Ref_and_UnsafeAsyncArgType()
 685        {
 686            var source = @"
 687using System.Threading.Tasks;
 688
 689class Test
 690{
 691    unsafe async static Task M1(ref int* i) { }
 692}";
 693            CreateCompilationWithMscorlib45(source, null, TestOptions.UnsafeDll).VerifyDiagnostics(
 694                // (6,42): error CS1988: Async methods cannot have ref or out parameters
 695                //     unsafe async static Task M1(ref int* i)
 696                Diagnostic(ErrorCode.ERR_BadAsyncArgType, "i"),
 697                // (6,30): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread.
 698                //     unsafe async static Task M1(ref int* i)
 699                Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "M1"));
 700        }
 701
 702        [Fact]
 703        public void RefAsyncArgType()
 704        {
 705            var source = @"
 706using System.Threading.Tasks;
 707
 708class Test
 709{
 710    async static Task M1(ref int i)
 711    {
 712        await Task.Factory.StartNew(() => { });
 713    }
 714}";
 715            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 716                // (6,42): error CS1988: Async methods cannot have ref or out parameters
 717                //     unsafe async static Task M1(ref int* i) { }
 718                Diagnostic(ErrorCode.ERR_BadAsyncArgType, "i"));
 719        }
 720
 721        [Fact]
 722        public void OutAsyncArgType()
 723        {
 724            var source = @"
 725using System.Threading.Tasks;
 726
 727class Test
 728{
 729    async static Task M1(out int i)
 730    {
 731        await Task.Factory.StartNew(() => { });
 732    }
 733}";
 734            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 735                // (6,34): error CS1988: Async methods cannot have ref or out parameters
 736                //     async static Task M1(out int i) { }
 737                Diagnostic(ErrorCode.ERR_BadAsyncArgType, "i"));
 738        }
 739
 740        [Fact]
 741        public void BadAwaitWithoutAsync()
 742        {
 743            var source = @"
 744using System;
 745using System.Threading.Tasks;
 746
 747class MyAttribute : Attribute {
 748    public MyAttribute(int i) { }
 749}
 750
 751[MyAttribute(await C.t)]
 752class C
 753{
 754    public static Task<int> t = new Task<int>(() => 1);
 755
 756    int i = await t;
 757}";
 758            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 759                // (9,14): error CS1992: The 'await' operator can only be used when contained within a method or lambda expression marked with the 'async' modifier
 760                // [MyAttribute(await C.t)]
 761                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsync, "await C.t"),
 762                // (14,13): error CS1992: The 'await' operator can only be used when contained within a method or lambda expression marked with the 'async' modifier
 763                //     int i = await t;
 764                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsync, "await t"));
 765        }
 766
 767        [Fact]
 768        public void BadAwaitWithoutAsync_AnonMeth_Lambda()
 769        {
 770            var source = @"
 771using System;
 772using System.Threading.Tasks;
 773
 774class C
 775{
 776    public static void Main()
 777    {
 778        Action f1 = delegate() { await Task.Factory.StartNew(() => { }); };
 779        Action f2 = () => await Task.Factory.StartNew(() => { });
 780        Action f3 = () => { await Task.Factory.StartNew(() => { }); };
 781    }
 782}";
 783            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 784                // (9,34): error CS4034: The 'await' operator can only be used within an async anonymous method. Consider marking this anonymous method with the 'async' modifier.
 785                //         Action f1 = delegate() { await Task.Factory.StartNew(() => { }); };
 786                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncLambda, "await Task.Factory.StartNew(() => { })").WithArguments("anonymous method"),
 787                // (10,27): error CS4034: The 'await' operator can only be used within an async lambda expression. Consider marking this lambda expression with the 'async' modifier.
 788                //         Action f2 = () => await Task.Factory.StartNew(() => { });
 789                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncLambda, "await Task.Factory.StartNew(() => { })").WithArguments("lambda expression"),
 790                // (11,29): error CS4034: The 'await' operator can only be used within an async lambda expression. Consider marking this lambda expression with the 'async' modifier.
 791                //         Action f3 = () => { await Task.Factory.StartNew(() => { }); };
 792                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncLambda, "await Task.Factory.StartNew(() => { })").WithArguments("lambda expression"));
 793        }
 794
 795        [Fact]
 796        public void IDS_BadAwaitWithoutAsyncMethod_VoidMethod()
 797        {
 798            var source = @"
 799using System.Threading.Tasks;
 800
 801class C
 802{
 803    public static void F()
 804    {
 805        await Task.Factory.StartNew(() => { });
 806    }
 807
 808    public static int G()
 809    {
 810        return await Task.Factory.StartNew(() => 1);
 811    }
 812}";
 813            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 814                // (8,9): error CS4033: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task'.
 815                //         await Task.Factory.StartNew(() => { });
 816                Diagnostic(ErrorCode.ERR_BadAwaitWithoutVoidAsyncMethod, "await Task.Factory.StartNew(() => { })"),
 817                // (13,16): error CS4033: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task<int>'.
 818                //         return await Task.Factory.StartNew(() => 1);
 819                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await Task.Factory.StartNew(() => 1)").WithArguments("int"));
 820        }
 821
 822        [Fact]
 823        public void IDS_BadAwaitAsDefaultParam()
 824        {
 825            var source = @"
 826using System.Threading.Tasks;
 827
 828class Test
 829{
 830    static Task t = new Task(null);
 831
 832    class await { }
 833
 834    static int Foo(int[] arr = await t)
 835    {
 836        return arr.Length;
 837    }
 838
 839    static int Main()
 840    {
 841        return 1;
 842    }
 843}";
 844
 845            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 846                /// (10,32): error CS4032: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task<int>'.
 847                //     static int Foo(int[] arr = await t)
 848                Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await t").WithArguments("int"),
 849                // (10,26): error CS1750: A value of type '?' cannot be used as a default parameter because there are no standard conversions to type 'int[]'
 850                //     static int Foo(int[] arr = await t)
 851                Diagnostic(ErrorCode.ERR_NoConversionForDefaultParam, "arr").WithArguments("?", "int[]"));
 852        }
 853
 854        [Fact]
 855        public void BadAwaitInFinally()
 856        {
 857            var source = @"
 858using System.Threading.Tasks;
 859
 860class Test
 861{
 862    async static Task M1() {
 863        try
 864        {
 865        }
 866        catch
 867        {
 868            try
 869            {
 870            }
 871            catch
 872            {
 873            }
 874            finally
 875            {
 876                await Task.Factory.StartNew(() => { });
 877            }
 878        }
 879        finally
 880        {
 881            try
 882            {
 883            }
 884            catch
 885            {
 886                await Task.Factory.StartNew(() => { });
 887            }
 888            finally
 889            {
 890            }
 891        }
 892    }
 893}";
 894            CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
 895        }
 896
 897        [Fact]
 898        public void BadAwaitInCatch()
 899        {
 900            var source = @"
 901using System.Threading.Tasks;
 902
 903class Test
 904{
 905    async static Task M1() {
 906        try
 907        {
 908        }
 909        catch
 910        {
 911            await Task.Factory.StartNew(() => { });
 912        }
 913        finally
 914        {
 915        }
 916    }
 917}";
 918            CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
 919        }
 920
 921        [Fact]
 922        public void BadAwaitInCatchFilter()
 923        {
 924            var source = @"
 925using System.Threading.Tasks;
 926
 927class Test
 928{
 929    async static Task M1() 
 930    {
 931        try
 932        {
 933        }
 934        catch if (await Task.Factory.StartNew(() => false))
 935        {
 936        }
 937        finally
 938        {
 939        }
 940    }
 941}";
 942            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 943                // (11,19): error CS7094: Cannot await in the filter expression of a catch clause
 944                //         catch if (await Task.Factory.StartNew(() => false))
 945                Diagnostic(ErrorCode.ERR_BadAwaitInCatchFilter, "await Task.Factory.StartNew(() => false)").WithLocation(11, 19)
 946                );
 947        }
 948
 949        [Fact]
 950        public void BadAwaitInLock()
 951        {
 952            var source = @"
 953using System.Threading.Tasks;
 954
 955class Test
 956{
 957    async static Task M1() {
 958
 959        lock (new object())
 960        {
 961            await Task.Factory.StartNew(() => { });
 962
 963            try
 964            {
 965            }
 966            catch
 967            {
 968                await Task.Factory.StartNew(() => { });
 969            }
 970            finally
 971            {
 972                await Task.Factory.StartNew(() => { });
 973            }
 974        }
 975
 976        try
 977        {
 978        }
 979        catch
 980        {
 981            lock (new object())
 982            {
 983                await Task.Factory.StartNew(() => { });
 984            }
 985        }
 986        finally
 987        {
 988            lock (new object())
 989            {
 990                await Task.Factory.StartNew(() => { });
 991            }
 992        }
 993    }
 994}";
 995            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
 996                // (10,13): error CS1996: Cannot await in the body of a lock statement
 997                //             await Task.Factory.StartNew(() => { });
 998                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await Task.Factory.StartNew(() => { })"),
 999                // (17,17): error CS1996: Cannot await in the body of a lock statement
1000                //                 await Task.Factory.StartNew(() => { });
1001                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await Task.Factory.StartNew(() => { })"),
1002                // (21,17): error CS1996: Cannot await in the body of a lock statement
1003                //                 await Task.Factory.StartNew(() => { });
1004                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await Task.Factory.StartNew(() => { })"),
1005                // (32,17): error CS1996: Cannot await in the body of a lock statement
1006                //                 await Task.Factory.StartNew(() => { });
1007                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await Task.Factory.StartNew(() => { })"),
1008                // (39,17): error CS1996: Cannot await in the body of a lock statement
1009                //                 await Task.Factory.StartNew(() => { });
1010                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await Task.Factory.StartNew(() => { })"));
1011        }
1012
1013        [Fact]
1014        public void BadAwaitInLock2()
1015        {
1016            var source = @"
1017using System.Threading.Tasks;
1018
1019class Program
1020{
1021    async void Test()
1022    {
1023        lock(await M()) // fine, not in body of lock
1024            lock (await M()) // error, in body of outer lock
1025            {
1026                await M(); // error, in body of inner lock
1027            }
1028    }
1029
1030    async Task<object> M()
1031    {
1032        return await M();
1033    }
1034}";
1035            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
1036                // (9,19): error CS1996: Cannot await in the body of a lock statement
1037                //             lock (await M()) // error, in body of outer lock
1038                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await M()"),
1039                // (11,17): error CS1996: Cannot await in the body of a lock statement
1040                //                 await M(); // error, in body of inner lock
1041                Diagnostic(ErrorCode.ERR_BadAwaitInLock, "await M()"));
1042        }
1043
1044        [Fact]
1045        public void AwaitingInLockExpressionsIsActuallyOK()
1046        {
1047            var source = @"
1048using System.Threading.Tasks;
1049
1050class Driver
1051{
1052    public static async void F()
1053    {
1054        object o = new object();
1055        lock(await Task.Factory.StartNew(() => o))
1056        {
1057            
1058        }
1059    }
1060
1061    static void Main() { }
1062}";
1063            CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
1064        }
1065
1066        [WorkItem(611150, "DevDiv")]
1067        [Fact]
1068        public void AwaitInLambdaInLock()
1069        {
1070            var source = @"
1071using System.Threading.Tasks;
1072
1073class Test
1074{
1075    static void Main()
1076    {
1077        lock (new object())
1078        {
1079            Task.Run(async () => { await Task.Factory.StartNew(() => { }); });
1080            Task.Run(async () => await Task.Factory.StartNew(() => { }));
1081            Task.Run(async delegate () { await Task.Factory.StartNew(() => { }); });
1082        }
1083    }
1084}";
1085            CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
1086        }
1087
1088        [Fact]
1089        public void BadAwaitInUnsafeContext()
1090        {
1091            var source = @"
1092using System.Threading.Tasks;
1093
1094class Test
1095{
1096    unsafe async static Task M1() {
1097        await Task.Factory.StartNew(() => { });  // not OK
1098    }
1099
1100    async static Task M2()
1101    {
1102        await Task.Factory.StartNew(() => { }); // OK
1103
1104        unsafe
1105        {
1106            await Task.Factory.StartNew(() => { }); // not OK
1107        }
1108    }
1109}";
1110            CreateCompilationWithMscorlib45(source, compOptions: TestOptions.UnsafeDll).VerifyDiagnostics(
1111                // (7,9): error CS4004: Cannot await in an unsafe context
1112                //         await Task.Factory.StartNew(() => { });  // not OK
1113                Diagnostic(ErrorCode.ERR_AwaitInUnsafeContext, "await Task.Factory.StartNew(() => { })"),
1114                // (16,13): error CS4004: Cannot await in an unsafe context
1115                //             await Task.Factory.StartNew(() => { }); // not OK
1116                Diagnostic(ErrorCode.ERR_AwaitInUnsafeContext, "await Task.Factory.StartNew(() => { })"));
1117        }
1118
1119        [Fact]
1120        public void BadAwaitWithoutAsyncInBadContext()
1121        {
1122            var source = @"
1123using System.Threading.Tasks;
1124
1125class Test
1126{
1127    static Task M2()
1128    {
1129        await Task.Factory.StartNew(() => { });
1130
1131        unsafe
1132        {
1133            await Task.Factory.StartNew(() => { });
1134        }
1135
1136        try
1137        {
1138        }
1139        catch
1140        {
1141            await Task.Factory.StartNew(() => { });
1142        }
1143        finally
1144        {
1145            await Task.Factory.StartNew(() => { });
1146        }
1147    }
1148}";
1149            CreateCompilationWithMscorlib45(source, compOptions: TestOptions.UnsafeDll).VerifyDiagnostics(
1150    // (8,9): error CS4032: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task<System.Threading.Tasks.Task>'.
1151    //         await Task.Factory.StartNew(() => { });
1152    Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await Task.Factory.StartNew(() => { })").WithArguments("System.Threading.Tasks.Task").WithLocation(8, 9),
1153    // (12,13): error CS4032: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task<System.Threading.Tasks.Task>'.
1154    //             await Task.Factory.StartNew(() => { });
1155    Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await Task.Factory.StartNew(() => { })").WithArguments("System.Threading.Tasks.Task").WithLocation(12, 13),
1156    // (12,13): error CS4004: Cannot await in an unsafe context
1157    //             await Task.Factory.StartNew(() => { });
1158    Diagnostic(ErrorCode.ERR_AwaitInUnsafeContext, "await Task.Factory.StartNew(() => { })").WithLocation(12, 13),
1159    // (20,13): error CS4032: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task<System.Threading.Tasks.Task>'.
1160    //             await Task.Factory.StartNew(() => { });
1161    Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await Task.Factory.StartNew(() => { })").WithArguments("System.Threading.Tasks.Task").WithLocation(20, 13),
1162    // (24,13): error CS4032: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task<System.Threading.Tasks.Task>'.
1163    //             await Task.Factory.StartNew(() => { });
1164    Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await Task.Factory.StartNew(() => { })").WithArguments("System.Threading.Tasks.Task").WithLocation(24, 13),
1165    // (6,17): error CS0161: 'Test.M2()': not all code paths return a value
1166    //     static Task M2()
1167    Diagnostic(ErrorCode.ERR_ReturnExpected, "M2").WithArguments("Test.M2()").WithLocation(6, 17)
1168);
1169        }
1170
1171        [Fact]
1172        public void AsyncExplicitInterfaceImplementation()
1173        {
1174            var source = @"
1175using System.Threading.Tasks;
1176
1177interface IInterface
1178{
1179    void F(); 
1180}
1181
1182class C : IInterface
1183{
1184    async void IInterface.F()
1185    {
1186        await Task.Factory.StartNew(() => { });
1187    }
1188
1189    static void Main()
1190    {
1191        
1192    }
1193}";
1194            CreateCompilationWithMscorlib45(source).VerifyDiagnostics();
1195        }
1196
1197        [Fact]
1198        public void AsyncInterfaceMember()
1199        {
1200            var source = @"
1201interface IInterface
1202{
1203    async void F(); 
1204}";
1205            CreateCompilationWithMscorlib45(source).VerifyDiagnostics(
1206                // (4,16): error CS0106: The modifier 'async' is not valid for this item
1207                //     async void F(); 
1208                Diagnostic(ErrorCode.ERR_BadMemberFlag, "F").WithArguments("async"));
1209        }
1210
1211        [Fact]
1212        public void MainCantBeAsync()
1213        {
1214            var source = @"
1215using System.Threading.Tasks;
1216
1217class A
1218{
1219    async static void Main()
1220    {
1221        await Task.Factory.StartNew(() => { });
1222    }
1223}";
1224            CreateCompilationWithMscorlib45(source, compOptions: TestOptions.Exe).VerifyDiagnostics(
1225                // (4,23): error CS4009: 'A.Main()': an entry point cannot be marked with the 'async' modifier
1226                //     async static void Main()
1227                Diagnostic(ErrorCode.ERR_MainCantBeAsync, "Main").WithArguments("A.Main()"));
1228        }
1229
1230        [Fact]
1231        public void MainCantBeAsync_AndGeneric()
1232        {
1233            var source = @"
1234using System.Threading.Tasks;
1235
1236class A
1237{
1238    async static void Main<T>()
1239    {
1240        await Task.Factory.StartNew(() => { });
1241    }
1242}";
1243            CreateCompilationWithMscorlib45(source, compOptions: TestOptions.Exe).VerifyDiagnostics(
1244                // (4,23): warning CS0402: 'A.Main<T>()': an entry point cannot be generic or in a generic type
1245                //     async static void Main<T>()
1246                Diagnostic(ErrorCode.WRN_MainCantBeGeneric, "Main").WithArguments("A.Main<T>()"),
1247                // error CS5001: Program does not contain a static 'Main' method suitable for an entry point
1248                Diagnostic(ErrorCode.ERR_NoEntryPoint));
1249        }
1250
1251        [Fact]
1252        public void MainCantBeAsync_AndBadSig()
1253        {
1254            var source = @"
1255using System.Threading.Tasks;
1256
1257class A
1258{
1259    async static void Main(bool truth)
1260    {
1261        await Task.Factory.StartNew(() => { });
1262    }
1263}";
1264            CreateCompilationWithMscorlib45(source, compOptions: TestOptions.Exe).VerifyDiagnostics(
1265                // (4,23): warning CS0028: 'A.Main(bool)' has the wrong signature to be an entry point
1266                //     async static void Main(bool truth)
1267                Diagnostic(ErrorCode.WRN_InvalidMainSig, "Main").WithArguments("A.Main(bool)"),
1268                // error CS5001: Program does not contain a static 'Main' method suitable for an entry point
1269                Diagnostic(ErrorCode.ERR_NoEntryPoint));
1270        }
1271
1272        [Fact]
1273        public void MainCantBeAsync_AndGeneric_AndBadSig()
1274        {
1275            var source = @"
1276using System.Threading.Tasks;
1277
1278class A
1279{
1280    async static void Main<T>(bool truth)
1281    {
1282        await Task.Factory.StartNew(() => { });
1283    }
1284}";
1285            CreateCompilationWithMscorlib45(source, compOptions: TestOptions.Exe).VerifyDiagnostics(
1286                // (4,23): warning CS0028: 'A.Main<T>(bool)' has the wrong signature to be an entry point
1287                //     async static void Main<T>(bool truth)
1288                Diagnostic(ErrorCode.WRN_InvalidMainSig, "Main").WithArguments("A.Main<T>(bool)"),
1289                // error CS5001: Program does not contain a static 'Main' method suitable for an entry point
1290                Diagnostic(ErrorCode.ERR_NoEntryPoint));
1291        }
1292
1293        [Fact]
1294        public void AwaitInQuery_FirstCollectionExpressionOfInitialFrom()
1295        {
1296            var source = @"
1297using System.Linq;
1298using System.Collections.Generic;
1299using System.Threading.Tasks;
1300
1301class Test
1302{
1303    async static Task<List<int>> F1()
1304    {
1305        return await Task.Factory.StartNew(() => new List<int>() { 1, 2, 3 });
1306    }
1307
1308    async static void F2()
1309    {
1310        await Task.Factory.StartNew(() => { });
1311
1312        var ls = new List<int>() {1, 2, 3};
1313
1314        var xs = from l in await F1() where l > 1 select l;
1315    }
1316}";
1317            CreateCompilationWithMscorlib45(source, new MetadataReference[] { SystemRef, LinqAssemblyRef }).VerifyDiagnostics();
1318        }
1319
1320        [Fact]
1321        public void AwaitInQuery_CollectionExpressionOfJoin()
1322        {
1323            var source = @"
1324using System.Linq;
1325using System.Collections.Generic;
1326using System.Threading.Tasks;
1327
1328class Test
1329{
1330    async static Task<List<int>> F1()
1331    {
1332        return await Task.Factory.StartNew(() => new List<int>() { 1, 2, 3 });
1333    }
1334
1335    async static void F2()
1336    {
1337        await Task.Factory.StartNew(() => { });
1338
1339        var ls = new List<int>() {1, 2, 3};
1340
1341        var xs = from l in ls
1342                 join l2 in await F1() on l equals l2
1343                 where l > 1 select l;
1344    }
1345}";
1346            CreateCompilationWithMscorlib45(source, new MetadataReference[] { SystemRef, LinqAssemblyRef }).VerifyDiagnostics();
1347        }
1348
1349        [Fact]
1350        public void BadAwaitInQuery_QueryBody()
1351        {
1352            var source = @"
1353using System.Linq;
1354using System.Collections.Generic;
1355using System.Threading.Tasks;
1356
1357class Test
1358{
1359    async static Task<List<int>> F1()
1360    {
1361        return await Task.Factory.StartNew(() => new List<int>() { 1, 2, 3 });
1362    }
1363
1364    async static void F2()
1365    {
1366        await Task.Factory.StartNew(() => { });
1367
1368        var ls = new List<int>() {1, 2, 3};
1369
1370        var xs = from l in ls
1371                 where l > 1 select await F1();
1372    }
1373}";
1374            CreateCompilationWithMscorlib45(source, new MetadataReference[]{ SystemRef, LinqAssemblyRef }).VerifyDiagnostics(
1375                // (20,37): error CS1995: The 'await' operator may only be used in a query expression within the first collection expression of the initial 'from' clause or within the collection expression of a 'join' clause
1376                //                  where l > 1 select await F1();
1377                Diagnostic(ErrorCode.ERR_BadAwaitInQuery, "await F1()"));
1378        }
1379
1380        [Fact]
1381        public void BadAwaitInQuery_FirstCollectionExpressionOfInitialFrom_InsideQueryBody()
1382        {
1383            var source = @"
1384using System.Linq;
1385using System.Collections.Generic;
1386using System.Threading.Tasks;
1387
1388class Test
1389{
1390    async static Task<List<int>> F1()
1391    {
1392        return await Task.Factory.StartNew(() => new List<int>() { 1, 2, 3 });
1393    }
1394
1395    async static void F2()
1396    {
1397        await Task.Factory.StartNew(() => { });
1398
1399        var ls = new List<int>() { 1, 2, 3 };
1400
1401        var xs = from l in ls
1402                 where l > 1
1403                 select (from l2 in await F1() where l2 > 1 select l2);
1404    }
1405}";
1406            CreateCompilationWithMscorlib45(source, new MetadataReference[] { SystemRef, LinqAssemblyRef }).VerifyDiagnostics(
1407                // (21,37): error CS1995: The 'await' operator may only be used in a query expression within the first collection expression of the initial 'from' clause or within the collection expression of a 'join' clause
1408                //                  select (from l2 in await F1() where l2 > 1 select l2);
1409                Diagnostic(ErrorCode.ERR_BadAwaitInQuery, "await F1()"));
1410        }
1411
1412        [Fact]
1413        public void BadAwaitInQuery_CollectionExpressionOfJoin_InsideQueryBody()
1414        {
1415            var source = @"
1416using System.Linq;
1417using System.Collections.Generic;
1418using System.Threading.Tasks;
1419
1420class Test
1421{
1422    async static Task<List<int>> F1()
1423    {
1424        return await Task.Factory.StartNew(() => new List<int>() { 1, 2, 3 });
1425    }
1426
1427    async static void F2()
1428    {
1429        await Task.Factory.StartNew(() => { });
1430
1431        var ls = new List<int>() { 1, 2, 3 };
1432
1433        var xs = from l in ls
1434                 where l > 1
1435                 select (from l2 in ls
1436                         join l3 in await F1() on l2 equals l3
1437                         where l2 > 1
1438                         select l2);
1439    }
1440}";
1441            CreateCompilationWithMscorlib45(source, new MetadataReference[] { SystemRef, LinqAssemblyRef }).VerifyDiagnostics(
1442                // (22,37): error CS1995: The 'await' operator may only be used in a query expression within the first collection expression of the initial 'from' clause or within the collection expression of a 'join' clause
1443                //                          join l3 in await F1() on l2 equals l3
1444                Diagnostic(ErrorCode.ERR_BadAwaitInQuery, "await F1()"));
1445        }
1446
1447        [Fact]
1448        public void BadAwaitWithoutAsyncInUnsafeQuery()
1449        {
1450            var source = @"
1451using System.Linq;
1452using System.Collections.Generic;
1453using System.Threading.Tasks;
1454
1455class Test
1456{
1457    async static Task<List<int>>

Large files files are truncated, but you can click here to view the full file