为什么关闭我的地址计算?

时间:2016-08-27 19:30:31

标签: assembly x86

为什么两条箭头线的地址不同?

我在.exe文件中的机器代码中插入蓝线,并期望它在ADD指令之后对同一地址中的值进行AND,但显然AND根据反汇编程序在不同的地址中占用。

enter image description here

我想到这可能是因为地址偏移但是C5 - BE = 7而F8 - EF = 9因此偏移量甚至不匹配,我不知道地址转换之间发生了什么;当机器代码中给出的地址为0x0193A4EF时,如何计算0x0131132A

2 个答案:

答案 0 :(得分:5)

您正在使用RIP相对偏移量 解码指令时,反汇编程序对你撒谎 The correct decoding is

66 01 1D 2A 13 31 01              add WORD PTR [rip+0x131132a],bx  
66 81 25 2A 13 31 01 7F FF        and WORD PTR [rip+0x131132a],0xff7f

由于RIP始终处于移动状态,因此您需要在下一个指令的开头采用RIP,而不是完全按照列出的方式应用偏移:6291BE + 7 + 131132A = 193A4EF。<登记/> 因为下一条指令长度为9个字节,并且您使用相同的RIP偏移量,所以现在需要添加9个字节,因此目标变为:6291C5 + 9 + 131132A = 193 A4F8,再次与列出的完全相同。

如果您希望两条指令都链接到同一地址,则需要使用不同的RIP偏移量。

始终将使用RIP寻址的指令长度添加到该指令的起始地址,然后应用偏移量。

我想知道为什么你的汇编程序不会自动为你执行此操作。许多汇编程序都有REL伪寻址模式来解决这个问题 参见例如section 3.3 of the NASM Manual

  

在64位模式下,NASM默认会生成绝对地址。 REL关键字使其生成RIP相关地址。

关于REL的好处是,您不必为自己计算偏移量而烦恼,只需输入您在REL之后链接到的任何内容的引用。汇编程序将弄清楚其余部分。

其他评论
无论你用什么反汇编程序来分析你的代码都会被破坏 and值为FF7F,因为x64为little endian。如果在指令字节中显示7FFF,您(以及您的反汇编程序)应该知道CPU将读取FF7F,因为最低有效字节首先出现。
请放弃那块垃圾并找一个像样的反汇编程序来分析你的机器代码。

答案 1 :(得分:1)

RIP相对寻址从当前指令的结尾开始计数(下一个指令的开始)。

如果你想到一个非常简单的CPU,它是有道理的:它解码一条指令,然后运行它。当它完成解码时,程序计数器(RIP)指向当前指令的结束(下一条指令的开始),因此当指示当前指令运行时,PC指向下一条指令。

相对跳跃也是一样的。 (例如jmp,其中rel8 = 0是一个缓慢的无操作。

我认为大多数具有相对跳跃的架构都是这样工作的。还有其他可以访问程序计数器的架构。