我是一名初次学习计算机系统的学生(带有计算机系统:程序员的视角)。我们正在组装,我开始了解x86_64的命令后缀,例如在以下内容中使用leaq
:
leaq (%rsp, %rdx), %rax
但是,我无法理解为pop
使用后缀。例如,使用相同的逻辑,对我来说,我们将popl
用于类似的事情:
popl %edi
但是,在网上的文字和其他示例中,我只看到:
pop %edi
有什么区别? popl
甚至有效吗?只是寻找更多的见识。有什么帮助,谢谢。
答案 0 :(得分:2)
您在asm中可以执行的操作受硬件可以执行的操作的限制。源中的隐式或显式操作数大小(带或不带后缀)都不会更改将要汇编到的机器代码。
所以正确的问题是硬件是否可以在64位模式下进行32位推送?不,它不能,因此不存在任何asm源语法,可以使它完全执行您要对一条指令执行的操作。
这就是为什么您的汇编器不接受pop %edi
或popl %edi
的原因。它们完全等效,因为32位寄存器隐含DWORD(l
)操作数大小。 您看到的关于popl
或pop %edi
的示例适用于32位模式,,其中EDI是完整寄存器,而不是RDI的低半部分,并且该指令是可编码的。
只有模棱两可时才需要大小后缀mov $1, (%rdi)
。您的汇编器将为此给出错误,而不是猜测b / w / l / q中的一个。
但是推入有些特殊:push $1
将默认为64位推入,即使可以使用pushw $1
。 How many bytes does the push instruction push onto the stack when I don't specify the operand size?