zwo*_*wol 12
在AT&T中,语法$
意味着将后面的内容视为直接常量而不是内存地址.换一种说法,
movl $_start, %eax
Run Code Online (Sandbox Code Playgroud)
将符号的地址加载_start
到%eax;
movl _start, %eax
Run Code Online (Sandbox Code Playgroud)
从内存中读取4个字节_start
到%eax 的地址.如果你看看两者的反汇编:
0: b8 00 00 00 00 mov $0x0,%eax
1: R_386_32 _start
5: a1 00 00 00 00 mov 0x0,%eax
6: R_386_32 _start
Run Code Online (Sandbox Code Playgroud)
你可以看到唯一的区别是操作码.方便的,有点自私的命名,英特尔 ®64 和IA-32架构软件开发人员手册(你想要第2卷,这是指令集参考)说,操作码B8到BF编码"加载立即16/32位常数到寄存器"(这是注定要加载到32位代码段的代码,所以它是32位加载;对于16位加载,你有一个"操作数大小覆盖"前缀字节,66)和操作码A1编码"在DS(或任何其他段,具有适当的前缀字节)的指定32位偏移处加载32位数量到EAX中." 使用典型的"平坦"内存模型,这就是"在指定的32位绝对地址下加载32位数量"的道德等价物,但您可以看到x86如何在机器级别上获得其可笑的复杂声誉.
如果您想知道,如果我们使用EBX,它就会是这样:
a: bb 00 00 00 00 mov $0x0,%ebx
b: R_386_32 _start
f: 8b 1d 00 00 00 00 mov 0x0,%ebx
11: R_386_32 _start
Run Code Online (Sandbox Code Playgroud)
Load-immediate仍然可以通过不计算操作数的单字节指令来完成(它是BB而不是B9,正如您所预期的那样,因为内部寄存器顺序是AX,CX,DX,BX,SP,BP, SI,DI - 严重)但是从绝对地址加载现在有一个双字节指令,8B 1D; 第二个字节是英特尔称之为"ModRM"的字节,它指定EBX和后面的绝对4字节地址.
归档时间: |
|
查看次数: |
5815 次 |
最近记录: |