恢复C#异步方法时,System.Diagnostics.StackTrace中缺少Visual Studio 2017调用堆栈中可见的堆栈帧

恢复C#异步方法时,System.Diagnostics.StackTrace中缺少Visual Studio 2017调用堆栈中可见的堆栈帧,c#,.net,visual-studio,stack,stack-trace,C#,.net,Visual Studio,Stack,Stack Trace,我有以下使用asyc方法的简单C#代码片段: class SUT { public async Task<int> GetValue() { await Task.Delay(1000); return 42; } } class Program { static async Task<int> CallAsync() { SUT sut = new SUT(); i

我有以下使用asyc方法的简单C#代码片段:

class SUT
{
    public async Task<int> GetValue()
    {
        await Task.Delay(1000);
        return 42;
    }
}

class Program
{
    static async Task<int> CallAsync()
    {
        SUT sut = new SUT();
        int result = await sut.GetValue();
        return result;
    }
    static void Main(string[] args)
    {
        CallAsync().GetAwaiter().GetResult();
    }
}
类SUT
{
公共异步任务GetValue()
{
等待任务。延迟(1000);
返回42;
}
}
班级计划
{
静态异步任务CallAsync()
{
SUT SUT=新SUT();
int result=wait sut.GetValue();
返回结果;
}
静态void Main(字符串[]参数)
{
CallAsync().GetAwaiter().GetResult();
}
}
我将断点放在“return 42”语句上,观察Visual Studio调用堆栈和从System.Diagnostics.StackTrace()获得的StackTrace。如下图所示,VS调用堆栈窗口中有一些帧未显示在堆栈跟踪中:


是否有一种方法可以使用System.Diagnostics.StackTrace获取堆栈跟踪,就像在Visual Studio调用堆栈窗口中观察到的那样?

好吧,如果您想一想StackTrace是什么,它实际上是一个调用方法的堆栈。其中最深的方法位于堆栈顶部。 如果您考虑以下程序,主呼叫先呼叫,先呼叫秒,第二呼叫第三。p>
class Program
{
    static void Main(string[] args) => First();
    static void First() => Second();
    static void Second() => Third();
    static void Third() => Console.WriteLine("Third method.");

}
当您在第三个方法中时,堆栈将如下所示(左侧为堆栈顶部):

Third-Second-First-Main

当第三个完成时,第三个从堆栈中弹出,跟踪如下所示:

Second-First-Main

等等等等

现在,当不涉及异步代码时,这很容易理解。让我们看看你的例子中发生了什么:

static void Main(string[] args) => First().Wait();

static async Task First()
{
    Console.WriteLine("First method starting");
    await Task.Delay(1000);
    Console.WriteLine("First method finishing.");
}
当您在
first
方法的第一行中放置断点时,调用堆栈与上面类似,因为代码一直同步执行到该点。但是,该方法实际上是在调用
wait Task.Delay
时返回,将
第一个方法从堆栈中弹出。在此之后,访问第三行的唯一方法是框架在第三行创建“continuation”。现在可能很清楚,这个延续必须由我们自己的代码以外的东西调用,这就是为什么callstack包含所有这些奇怪的方法

因此,您无法获得仅包含代码的调用堆栈,因为它已不存在,但在Visual Studio设置中,您可以启用。在最后一个示例中,当您在
First
方法的第3行中断时,可能会出现这种情况。不完全是你要找的,但很接近

(VSCode截图)