我正在学习用gdb解决一些运行时错误。这里是我的问题:在调试中查找地址信息
时发生运行时错误,因为一些内存的一些访问操作是矛盾的,我可以找出在转储核心内存的地址?
给定一个地址,是否有可能找出哪个变量正在使用它(地址可能在变量内存的开始,结束或中间)?
考虑到变量使用的内存,是否有可能找到它下面和其上方的附近变量?
感谢和问候!
我正在学习用gdb解决一些运行时错误。这里是我的问题:在调试中查找地址信息
时发生运行时错误,因为一些内存的一些访问操作是矛盾的,我可以找出在转储核心内存的地址?
给定一个地址,是否有可能找出哪个变量正在使用它(地址可能在变量内存的开始,结束或中间)?
考虑到变量使用的内存,是否有可能找到它下面和其上方的附近变量?
感谢和问候!
通常是的。假设你的程序 坠毁GDB外,由于SIGSEGV
并留下了一个核心转储,您可以:
答:找出哪些 指令实际上造成了 访问冲突:
(gdb) x/i $pc
这通常是一个内存访问 指令,例如"movl $1,8(%eax)"
。重要的是 那么应该指向有效的 内存的寄存器 有什么价值。
B.找出寄存器的值 :
(gdb) p/x $eax
通常这会是0(你是 通过NULL
指针写), 或一些废话值,例如 0x32314043
(您损坏了 指针,或者用 ASCII
字符串覆盖了它)。
的GDB
"info symbol"
命令会告诉你哪个符号 (如果有的话)是给定的地址附近。
使用相同的"info symbol"
命令来获得稍微小一点的地址,并且稍微大于“目标”变量的地址。
更新:
的info symbol
不在本地(自动)变量的工作方式,因为这样的变量没有与之关联的(符号表)标志。
要查找有关局部变量的信息,请执行"info locals"
。然后,您可以打印他们的地址与
(gdb) print &a_local_variable
我不知道有没有办法做逆(即局部变量的地址映射回其符号名称)。但是,如果您只有少数本地人,通常“手工”将地址映射到其中一个地方通常很简单。如果你有太多的本地人,这是一个糟糕的“代码味道” - 你应该重构你的代码,这样你就不会这样做。
非常感谢! 看起来像“信息符号”只适用于全局变量或非静态变量,但对本地非静态变量的内存地址不起作用,即使我与该变量处于同一帧。那么如何找出使用给定地址的本地非静态变量?如果它可以是有用的,为什么“信息符号”不支持它? – Tim 2009-08-29 19:46:01
非常感谢@Employed,这帮助我解决了另一个问题 – tmow 2012-01-25 16:41:04
“我不知道有什么方法可以做相反的事情” - 有时“info scope”可以帮助确定当前堆栈中某个地方的哪些本地生活帧,尽管它的输出通常很长并且需要一些解密。 – 2015-08-06 07:50:46