【问题标题】:Help postmorten debugging of a mixed mode Win32 application帮助对混合模式 Win32 应用程序进行事后调试
【发布时间】:2010-10-18 13:12:23
【问题描述】:

情况如下:

背景

我有一个在 Visual Studio 2008 中开发的混合模式 .NET/Native 应用程序。

我所说的混合模式是指前端是用 C++ .NET 编写的,它调用本机 C++ 库。本机代码在应用程序中完成大部分工作,包括根据需要启动新线程。 .NET 代码仅用于 UI 目的(赢取表单)。

我有一个发布版本的应用程序在测试人员的计算机上运行。

本机库经过全面优化编译,但也启用了调试(“调试信息格式”设置为“程序数据库”)。

这意味着我在 PDB 文件中有应用程序的调试符号。

问题

因此,无论如何,其中一位测试人员遇到了该应用程序的问题,该应用程序偶尔会在 XP 上崩溃。使用 Dr Watson 运行几次后,我已经能够获得崩溃的小型转储。

当我调试它时(使用 minidump - 我实际上并没有调试真正的应用程序),所有调试符号都正确加载:我可以正确看到所有本机线程的完整堆栈跟踪。其他线程(可能是 .NET 线程)没有堆栈跟踪,但它们至少都显示了线程是在哪个 dll 上启动的(即 ntdll.dll)。

它正确报告失败的线程(“用户(5).dmp中0x0563d652处的未处理异常:0xC0000005:访问冲突读取位置0x00000000)。

但是,当我进入线程时,它显示没有任何用处。在堆栈跟踪中有一个条目,它的内存地址为“0563d652()”(甚至不是“ntldll.dll”)。

当我进行反汇编时,它只显示大约 30 条指令的随机部分。内存地址的任何一侧都只是“???”。它几乎看起来不是我的源代码的一部分(您的二进制文件不是按顺序加载到内存中吗?在中间有一组随机的汇编语句是否正常?)。

我的问题

所以基本上我的问题是三方面的。

1) 谁能解释调试器缺少信息的原因?

2) 请记住,我无法显示我的代码中发生的错误,任何人都可以提出失败的原因

3) 我可以做些什么来帮助我在未来诊断当前的问题吗?

救命!

约翰

更新:

这是来自 WinDBG 的失败线程的堆栈转储

 # ChildEBP RetAddr  
WARNING: Frame IP not in any known module. Following frames may be wrong.
00 099bf414 02d0e7fc 0x563d652
01 00000000 00000000 0x2d0e7fc

很奇怪吧?甚至不显示 DLL。

是否有可能我已经以某种方式破坏了堆栈/堆,导致线程刚刚被破坏......?

【问题讨论】:

    标签: c++ debugging managed-c++ mixed-mode postmortem-debugging


    【解决方案1】:

    您的 EIP 刚刚损坏。
    假设 ESP 有效,您可以查看调用堆栈,只需键入:
    dds esp [进入]
    dds [输入]

    您还可以使用内存窗口:
    将地址设置为:esp
    设置格式为:指针&符号

    【讨论】:

      【解决方案2】:

      在您获取并安装了windbg 的副本并在那里打开转储文件后,您能否发布错误线程的堆栈? 我们可以从那里开始。

      【讨论】:

      • 非常友好的提议,谢谢 - 请查看更新后的问题。
      • 好吧,堆栈中的内容不多。你修好了符号(你的私人和公共系统)吗?寄存器的状态(windbg 中的“r”)是什么? eip 是否指向有效代码? (windbg 中的“u eip”)?
      【解决方案3】:

      我们遇到了与此类似的问题,即 MSVC2K5 SP1 中的代码错误是静默的,但如果您安装了 MSVC2K5 SP2 运行时,则会导致未指向有效代码的错误。

      部分问题是,当您开始将数据作为代码执行时,您可能正在做任何事情,因此崩溃位置变得毫无用处,因为您甚至无法返回到有效的堆栈跟踪。

      当新的 .Net 运行时安装在 SxS 目录中安装了更新版本的 MSVC C++ 运行时时,我们遇到了这种情况。

      最终,我们解决问题的方法是让崩溃频繁发生,并根据需要添加尽可能多的日志记录以对其进行本地化。

      【讨论】:

      • 好建议 - 我怀疑我有 VC2008 SP1 redist 而测试机器有 VC2008(不是 SP)。可能会升级机器,看看是否有帮助。
      【解决方案4】:

      你在使用 WinDbg 吗?如果是这样,您是否使用了罢工之子扩展程序?

      Bugslayer: Son-of-Strike

      -或-

      Drill Into .NET Framework Internals to See How the CLR Creates Runtime Objects?

      【讨论】:

      • 否,使用 Visual Studio 2008 集成调试器。不过,我会给 WinDbg 一个很好的建议,谢谢。
      • 恐怕与 WinDBG 的结果相同。至于 SOS,它建议您使用完整转储而不是小型转储(这就是我所拥有的)。看看我能不能得到一个完整的转储来试试。
      • 好吧,从某种意义上说,minidump 也可以是一个完整的转储 - 取决于创建它的选项。此外,使用 windbg 总是一个好主意;o)
      • 约翰,不要打扰亲爱的博士。 wtsn 的小型转储。如果您有 Windbg(这是正确的方法,恕我直言),请将 adplus 附加到您的应用程序,并让它在崩溃时创建一个完整的转储。 QA 可能快到了,为什么要满足于小型转储?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-01-19
      • 1970-01-01
      • 2017-08-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-06-15
      相关资源
      最近更新 更多