【问题标题】:Why do breakpoints jump around in .h files?为什么断点会在 .h 文件中跳来跳去?
【发布时间】:2012-08-13 14:37:34
【问题描述】:

我正在尝试使用 getter / setter 调试 .h 文件,但在附加到我要调试的进程时,当我在某些方法上放置断点时,IDE 会自动将断点跳转到文件中的单独方法.有谁知道为什么会发生这种情况?

我尝试过的一些事情:

  • 重建并链接我正在调试的 .exe
  • 删除 .obj 文件,重新制作包含我要调试的文件的目录
  • 通过任务管理器检查以确保正确的 .exe 正在运行
  • 检查 .pdb 和 .exe 文件的时间戳以确保它们(大致)匹配

这不是解决方案范围内的问题;我只是偶尔看到这个。还有什么我可以尝试的吗?

【问题讨论】:

  • 尝试禁用优化。当您的代码得到优化时,您将失去在调试时正确导航的能力。
  • 另一个原因是从未使用过函数,因此在优化构建中不会为其生成代码。
  • 当您在不生成二进制代码的行上设置断点时,调试器会自动将断点移动到下一行生成的代码。
  • 并非每个 asm 代码都有对应的 C++ 代码,例如函数堆栈框架设置。

标签: c++ visual-studio-2008 breakpoints


【解决方案1】:

考虑一个 Point 类和一个 Rectangle 类。想象一下,Point 有一个名为 GetX() 的 getter,而 Rectangle 有一个名为 GetLeft() 的 getter。在机器指令级别,这两种方法可能是相同的,因为它们都返回对象中的第一个 32 位值。

由于代码相同,编译器和/或链接器可以通过丢弃方法的一份副本并将所有对丢弃的方法的调用解析为对保留的方法的调用来减小二进制文件的大小。例如,链接器可能会从可执行文件中删除 Rectangle::GetLeft(),并将所有对 Rect::GetLeft() 的调用替换为对 Point::GetX() 的调用。

发生这种情况时,调试器将无法再区分 GetX() 和 GetLeft()。即使调用的是 Rect::GetLeft(),指令指针也在属于 Point::GetX() 的代码范围内。您可以通过查看堆栈以查看实际调用了哪个方法来区分差异,但调试器不会为您执行此操作。

通常,您在构建调试版本时禁用优化以避免此类调试混淆。这并不总是可能的。例如,您可能正在调试运行优化二进制文件的客户的故障转储。在这种情况下,您只需了解问题并了解调用上下文即可了解实际情况。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2014-12-29
    • 2016-02-21
    • 1970-01-01
    • 1970-01-01
    • 2010-10-13
    • 1970-01-01
    • 1970-01-01
    • 2010-11-15
    相关资源
    最近更新 更多