在检索地址方面,MOV和LEA有什么区别

当我使用它们来获取地址时,mov和lea的区别究竟是什么?

假设我有一个程序从第5个字符开始打印出一个字符串,其代码如下所示:

section .text
    global _start
_start:
    mov edx, 0x06  ;the length of msg from its 5th char to the last is 6.
    lea ecx, [msg + 4]
    mov ebx, 1
    mov eax, 4
    int 0x80

section .data
msg db '1234567890'

然后,如果我交换lea ecx, [msg + 4] mov ecx, msg + 4 lea ecx, [msg + 4] mov ecx, msg + 4 ,它会以不同的方式运行吗?

我试了两次,输出结果看起来是一样的。 然而,我从这个链接中读到,LEA指令的目的是什么?在第一个答案的注释部分,似乎有人声称像mov ecx, msg + 4这样的东西是无效的,但我没有看到它。 有人能帮助我理解这一点吗? 提前致谢!


当绝对地址是链接时间常数时, mov r32, imm32lea r32, [addr]将完成作业。 imm32可以是任何有效的NASM表达式。 在这种情况下msg + 4是一个链接时间常量。 链接器会查找msg的最终地址,并将其添加4(因为.o的占位符的位移为+4)。 当将.o的字节复制到链接器输出时,该最终值取代了4B占位符。

对于lea的有效地址中的4B位移,发生了完全相同的事情。


mov编码稍短,并且可以在更多的执行端口上运行。 使用mov除非你可以利用lea与寄存器同时做一些有用的数学运算 。 (例如: lea ecx, [msg + 4 + eax*4 + edx]

在64位模式下,可以进行RIP相对寻址,使用LEA可以生成高效的与位置无关的代码(如果映射到不同的虚拟地址,则无需修改)。 使用mov无法实现此功能。 请参阅参考内存位置的内容。 (x86寻址模式)

另请参阅x86以了解许多良好的链接。


另请注意,您可以使用大小的符号常量。 您还可以更好地格式化和评论您的代码。 (缩进操作数在代码中看起来不那么杂乱,它有一些带有较长助记符的指令)。

section .text
    global _start
_start:
    mov    edx, msgsize - 4
    mov    ecx, msg + 4     ; In MASM syntax, this would be mov ecx, OFFSET msg + 4
    mov    ebx, 1       ; stdout
    mov    eax, 4       ; NR_write
    int    0x80         ; write(1, msg+4, msgsize-4)

    mov    eax, 1       ; NR_exit
    xor    ecx, ecx
    int    0x80         ; exit(0)
    ;; otherwise execution falls through into non-code and segfaults

section .rodata
msg db '1234567890'     ; note, not null-terminated, and no newline
msgsize equ $-msg       ; current position - start of message
链接地址: http://www.djcxy.com/p/12563.html

上一篇: What is the difference between MOV and LEA in terms of retrieving an address

下一篇: Purpose of cmove instruction in x86 assembly?