在调试生成C++中获取调用堆栈失败

Failure to get call stack in a debug build C++

本文关键字:获取 调用 堆栈 失败 C++ 调试      更新时间:2023-10-16

我遇到了一个奇怪的情况。我的游戏肯定是用调试信息构建的,我可以愉快地点击断点、遍历代码和查看数据。没有异常设置。我已经排除了多线程是一个问题。当我有一个实际的错误和一个合法的崩溃时,我没有得到调用堆栈。是一个典型的崩溃错误

First-chance exception at 0x004678da in Democracy3Debug.exe: 0xC0000005: Access violation reading location 0x0000004c.
Unhandled exception at 0x774015de in Democracy3Debug.exe: 0xC0000005: Access violation reading location 0x0000004c.

调用堆栈只是ntdll和一些反汇编。我一定在某个地方改变了一些选择,但无法想象会发生什么。有什么想法吗?

这些错误表示由于您试图访问进程无法读取或写入的内存而导致的硬件异常。特别是,看起来您直接或间接地试图从某个指针引用的地址访问某个元素76字节,但该指针实际上为空(因此访问违规读取位置0x0000004c(。

您的调试信息可能不会以任何方式无效,您可能只是合法地位于nt.dll中的某些代码中——例如,如果您向不允许它们的Windows API函数传递了空指针。如果没有为nt.dll加载符号,则不会得到有用的调用堆栈。

访问违规也可能来自您传递的错误指针,该指针在Windows API调用某些回调之前未使用,这可能解释了为什么您在堆栈框架中的任何位置都看不到代码

在VS IDE中启用break-on-throw(调试->异常,选中相关异常类型的框(可以帮助您在发生这种情况时更早地中断,但如果问题不是直接来自代码,则可能无助于诊断问题。

您还可以使用结构化异常处理来集成这些异常和C++的异常,以实现捕获目的。您可能还想使用符号服务器来获取Windows DLL的符号。

您的异常没有被捕获,所以它一直向上移动到main并终止您的应用程序。

MSDN:

如果找不到的匹配处理程序(或省略号捕获处理程序(当前异常,预定义的终止运行时函数为呼叫。

通常有一个选项允许您在引发异常时暂停调试。

如何:抛出异常时中断(Visual Studio 2012(

您也可以在顶层有一个catch语句,并在捕获异常时检查异常(.wat((通常会给出描述(。

更新:您很可能无法捕获此异常,因为它违反了访问权限(不是C++异常,但暂停应该仍然有效(。如果你在Windows上,你可以使用SEH来捕捉它。