我最近在我的异步代码中遇到了一个奇怪的错误。我在 COM 控件上调用了一个阻塞方法,这似乎允许我的异步继续在它阻塞时运行。
考虑示例代码(仅用于说明目的)
public async void Main()
{
//assume some single threaded dispatcher. eg. WpfDispatcher
Task doAsyncTask = DoAsync();
Console.WriteLine("Start synchronous");
CallSomeCOMControl();
Console.WriteLine("End synchronous");
await doAsyncTask;
}
public async Task DoAsync()
{
Console.WriteLine("Start async");
await Task.Delay(1);
Console.WriteLine("End async");
}
在正常情况下,我希望得到以下输出:
Start async
Start synchronous
End synchronous
End async
我实际上看到的是:
Start async
Start synchronous
End async
End synchronous
现在我没有 COM 控件的源代码,但我知道这是一个非常古老的 C++ 控件,没有异步/等待的概念。然而,它是一个 Active-X 控件。
我不知道 .Net RCW 的实现细节,但我假设必须进行某种消息泵送才能使控件正常工作。我还假设这种泵送允许我继续运行。
我的假设正确吗?还有我应该知道的其他任何情况,我的所谓同步代码可能会被中断吗?