如何将内存中某个地址的值复制到gcc AT&T样式的寄存器中

问题描述 投票:0回答:1

我想使用AT&T样式汇编将内存中某个地址的值复制到寄存器中。我知道这应该不难,我认为在英特尔风格中它是这样的:

mov rdi, [0xdeadbeef]

但我对AT&T风格(或一般的装配)知之甚少。我搜索了它,但我得到的关于mov的所有例子都不包括这个。

所以有人能告诉我这个指令是怎么样的吗?

另外,在哪里可以找到AT&T风格的x86_64汇编指令的完整列表?

assembly x86-64 att
1个回答
1
投票

要将内存中某个地址的值复制到32位模式的寄存器,我们使用

mov edi, [0xdeadbeef] ; Intel
movl 0xdeadbeef, %edi ; AT&T

在AT&T any literal that is not prefixed by $ is an address

但是在x86_64 64-bit absolute addressing is not allowed中,所以你不能像上面那样使用movq 0xdeadbeef, %rdi。唯一具有64位立即数的指令是mov(气体中的movabs),它可以为任何寄存器分配64位常数,或者move value at a 64-bit absolute address to Areg

mov rax, [0xdeadbeef]   ; Intel
movabs 0xdeadbeef, %rax ; AT&T

如果你真的需要将值从64位绝对地址移动到不同于Areg的寄存器,你必须use indirect addressing instead

mov rdi, 0xdeadbeef     ; Intel
mov rdi, [rdi]

movq $0xdeadbeef, %rdi  ; AT&T
movq (%rdi), %rdi

或者如果你想将值复制到rax和rdi那么

mov rax, [0xdeadbeef]   ; Intel
mov rdi, rax

movabs 0xdeadbeef, %rax ; AT&T
movq %rax, %rdi

这里的q后缀表示四字(64位)寄存器

在AT&T语法中,存储器操作数的大小由指令助记符的最后一个字符确定。 bwlq的助记符后缀指定字节(8位),字(16位),长(32位)和四字(64位)存储器引用。英特尔语法通过使用byte ptrword ptrdword ptrqword ptr为内存操作数(不是指令助记符)添加前缀来实现此目的。因此,英特尔mov al, byte ptr foo是AT&T语法中的movb foo, %al

在64位代码中,movabs可用于使用64位位移或立即操作数对mov指令进行编码。

https://sourceware.org/binutils/docs/as/i386_002dVariations.html

有关64位mov指令的更多信息,请访问:Difference between movq and movabsq in x86-64。正如您所看到的,从32位绝对地址移动到64位寄存器没有任何版本,因此即使在极少数情况下地址适合像0xdeadbeef这样的32位时,您仍然必须使用movabs Areg, moffs64

© www.soinside.com 2019 - 2024. All rights reserved.