GDB 反汇编使用不一致的寄存器命名

Posted

技术标签:

【中文标题】GDB 反汇编使用不一致的寄存器命名【英文标题】:GDB disassembly uses inconsistent register naming 【发布时间】:2013-08-03 18:58:53 【问题描述】:

我正在调试/反汇编一个非常简单的 C 程序,我只是为了学习目的而编写的。但是,我注意到 GDB 似乎在反汇编输出与我在断点后输入“信息寄存器”时告诉我的内容之间的寄存器使用不一致的符号。

这是反汇编输出的一部分(在我的断点附近):

0x0000000100000d15 <main+181>:  xor    %dl,%dl
0x0000000100000d17 <main+183>:  mov    %ecx,%edi
0x0000000100000d19 <main+185>:  mov    %dl,%al
0x0000000100000d1b <main+187>:  callq  0x100000da0 <checkLicense>
0x0000000100000d20 <main+192>:  mov    %eax,%ecx
0x0000000100000d22 <main+194>:  cmp    $0x0,%ecx
0x0000000100000d25 <main+197>:  je     0x100000d47 <main+231>
0x0000000100000d27 <main+199>:  lea    0x1bb(%rip),%rax        # 0x100000ee9
0x0000000100000d2e <main+206>:  mov    %rax,%rdi

这是我在 GDB 中调用“信息寄存器”命令时得到的部分输出:

(gdb) info registers
rax            0x1  1
rbx            0x0  0
rcx            0x1  1
rdx            0x1  1
rsi            0x3  3
rdi            0x3  3

我在 cmp 操作发生的地方设置了断点。正如您所看到的,它将寄存器 ECX 中的值与 0 进行比较,但是,ECX 似乎并不是一个真正的寄存器。当我得到“信息寄存器”的结果时,它似乎确实返回了真正的寄存器,即 rcx。例如,当我尝试使用“set $ecx = 1”来操作 GDB 中的寄存器时,它没有任何效果,但是当我执行“set $rcx = 1”时,它似乎确实有效。

这种不一致是怎么回事,有办法解决吗?

【问题讨论】:

【参考方案1】:

这种不一致是怎么回事?

指令cmp $0x0,%ecx将寄存器rcx低32位0进行比较,所以反汇编是正确的。

"info registers" 它确实返回了真实的寄存器,即 rcx

正确。

例如"set $ecx = 1" 没有效果

它确实对我有影响:

(gdb) info reg rcx
rcx            0xffffffffffffffff   -1
(gdb) set $ecx = 0
(gdb) info reg rcx
rcx            0xffffffff00000000   -4294967296

如果set $ecx = 1 真的对你没有任何影响,那可能是一个 GDB 错误。

【讨论】:

以上是关于GDB 反汇编使用不一致的寄存器命名的主要内容,如果未能解决你的问题,请参考以下文章

LINUX下GDB反汇编和调试

[反汇编分析]调用函数传入参数不一致时可能寄存器传入参数

[GDB]设置gdb反汇编语法为intel

gdb 反汇编:以 16 为基数显示函数偏移量

VS2010查看源码对应的汇编语言

反汇编正在运行的内核