在 Visual Studio 2008 中从 WinDbg 调试 .Net 托管应用程序的 .dmp 文件

发布于 2024-10-02 16:17:14 字数 1316 浏览 3 评论 0原文

我试图找到如何获取 .Net 托管可执行文件的故障转储,然后在 Visual Studio 2008 中打开生成的 .dmp 文件。我想查看源代码中抛出异常的位置、调用堆栈和值栈上函数中的变量。

简化问题,我编写了一个崩溃的迷你应用程序:

……

class Program
{
    static void Main(string[] args)
    {

        int a = 2;           //Variable I want to see value for when debugging

        if (!File.Exists(@"C:\Crasher\bin\Debug\file.txt")) //Doesn't exist
            throw new FileNotFoundException();     //Unhandled exception thrown
    }
}

为了

我进行了调试构建并从 Visual Studio 外部运行它。在 Windbg 中,我单击“附加到进程”并选择我的应用程序。然后我在windbg命令窗口中输入:

          .dump /ma C:\crasher\bin\debug\dump.dmp

然后我在Visual Studio中打开.dmp文件。我转到“工具”->“选项”->“调试”->“符号”并添加以下内容:

          http://msdl.microsoft.com/download/symbols  (saved to local folder)

这为我提供了“模块”窗口中列出的所有 DLL 的符号(例如 Kernel32.dll、gdi32.dll - 我认为所有这些符号列出的都是本机的),但 mscorlib.ni.dll 除外。 Microsoft 符号服务器为我提供了 mscorlib.dll 的符号构建和 .pdbs,但不是 mscorlib.ni.dll。

当我尝试为我的 .exe 本身加载 .pdb 时,它告诉我它与应用程序不匹配。我认为这是因为 .exe 是托管的,而且我们还没有其下所有本机代码的符号 - 也就是说,如果我可以获得 mscorlib.ni.dll 的符号构建和 pdb,这将起作用。

这个推理正确吗?我还缺少其他东西吗?

不管怎样,为什么 mscorlib.ni.dll 在 Microsoft 符号服务器上不可用,我在哪里可以获取符号信息,以及通过 Visual Studio 中的故障转储调试托管代码时我还应该知道什么。

非常感谢 - 任何帮助将不胜感激。

菲尔·惠廷顿

I am trying to find how to take a crash dump of a .Net managed executable and then open the resulting .dmp file in Visual Studio 2008. I want to see where in the source code the exception is thrown, the call stack and the value of variables in functions on the stack.

To simplify the problem, I've written a mini-app that crashes:

...

class Program
{
    static void Main(string[] args)
    {

        int a = 2;           //Variable I want to see value for when debugging

        if (!File.Exists(@"C:\Crasher\bin\Debug\file.txt")) //Doesn't exist
            throw new FileNotFoundException();     //Unhandled exception thrown
    }
}

...

I did a DEBUG build and ran it from outside Visual Studio. In windbg, I clicked "Attach to Process" and selected my app. Then I typed in the windbg command window:

          .dump /ma C:\crasher\bin\debug\dump.dmp

Then I opened the .dmp file in Visual Studio. I went to Tools->Options->Debugging->Symbols and added the following:

          http://msdl.microsoft.com/download/symbols  (saved to local folder)

This gives me symbols for all of the DLLs listed in the Modules window (e.g. Kernel32.dll, gdi32.dll - I think all of them listed are native) with the exception of mscorlib.ni.dll. The Microsoft Symbol Server gives me symbols builds and .pdbs for mscorlib.dll but NOT mscorlib.ni.dll.

When I try to load the .pdb for my .exe itself, it tells me it does not match the app. I think this is because the .exe is managed and we don't yet have symbols for all of the native code beneath it - i.e. if I could get a symbols build and pdb for mscorlib.ni.dll this would work.

Is this reasoning correct? Am I missing something else?

Either way, why is mscorlib.ni.dll not available on the Microsoft Symbol Server, where can I get symbol information and is there anything else I should know for debugging managed code through crash dumps in Visual Studio.

Many thanks - any help will be appreciated.

Phil Whittington

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

慢慢从新开始 2024-10-09 16:17:14

正如 Jason Evans 在他的评论中所说,VS2008 中不支持此操作,但您可以在 WinDbg 中执行此操作。

获得此类崩溃的正确转储的最简单方法是使用 adplus(包含在 Windows 调试工具中)。有多种选项,但要根据进程名称获取故障转储,您可以这样做

>adplus -crash -o c:\dumpdirectory -pn app.exe

这将为您提供两个转储。一个用于第一次机会例外,一个用于第二次机会例外。在这种情况下,它们实际上是相同的,但对于更现实的场景,第一次机会异常转储将向您显示抛出异常时(即发生任何异常处理之前)应用程序的状态。第二次机会异常转储将向您显示未处理异常的状态。

要获取异常,请打开故障转储并通过键入 .loadby sos mscorwks 加载 SOS。

然后使用 !pe 命令打印当前线程(在本例中为故障线程)上的异常。它看起来像这样:

0:000> !pe
Exception object: 024a5114
Exception type: System.IO.FileNotFoundException
Message: Unable to find the specified file.
InnerException: <none>
StackTrace (generated):
    SP       IP       Function
    0020F0F0 005100D6 TestBench!TestBench.Program.Main()+0x66

StackTraceString: <none>
HResult: 80070002

要列出局部变量 a 使用 !clrstack -l,但请记住,由于优化,局部变量在发布模式构建中很少可用。

0:000> !clrstack -l
OS Thread Id: 0x1a50 (0)
ESP       EIP     
0020f04c 7571b727 [HelperMethodFrame: 0020f04c] 
0020f0f0 005100d6 TestBench.Program.Main()
    LOCALS:
        0x0020f0fc = 0x00000002  <--- the value of a
        0x0020f0f8 = 0x00000000

0020f328 51141b5c [GCFrame: 0020f328] 

As Jason Evans says in his comment, this is not supported in VS2008, but you can do it in WinDbg.

The easiest way to get a correct dump for a crash like this is to use adplus (which is included in Debugging Tools for Windows). There are various options, but to get a crash dump based on the process name, you could do

>adplus -crash -o c:\dumpdirectory -pn app.exe

This will give you two dumps. One for the first chance exception and one for the second. In this case they will be virtually identical, but for a more realistic scenario the first chance exception dump will show you the state of the application when the exception was thrown (i.e. before any exception handling occur). The second chance exception dump will show you the state of the unhandled exception.

To get the exception, open the crash dump and load SOS by typing .loadby sos mscorwks.

Then use the !pe command to print the exception on the current thread (which will be the faulting thread in this case). It will look something like this:

0:000> !pe
Exception object: 024a5114
Exception type: System.IO.FileNotFoundException
Message: Unable to find the specified file.
InnerException: <none>
StackTrace (generated):
    SP       IP       Function
    0020F0F0 005100D6 TestBench!TestBench.Program.Main()+0x66

StackTraceString: <none>
HResult: 80070002

To list the local variable a use !clrstack -l, but keep in mind that locals are rarely available in a release mode builds due to optimizations.

0:000> !clrstack -l
OS Thread Id: 0x1a50 (0)
ESP       EIP     
0020f04c 7571b727 [HelperMethodFrame: 0020f04c] 
0020f0f0 005100d6 TestBench.Program.Main()
    LOCALS:
        0x0020f0fc = 0x00000002  <--- the value of a
        0x0020f0f8 = 0x00000000

0020f328 51141b5c [GCFrame: 0020f328] 
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文