GNU 汇编器 x86 指令后缀(如“mov.s”中的“.s”)如何工作?

Posted

技术标签:

【中文标题】GNU 汇编器 x86 指令后缀(如“mov.s”中的“.s”)如何工作?【英文标题】:How do GNU assembler x86 instruction suffixes like ".s" in "mov.s" work? 【发布时间】:2018-05-20 06:26:51 【问题描述】:

GNU 汇编器似乎有一些方法可以控制为某些指令发出的操作码的替代形式。例如

.intel_syntax noprefix
mov   eax, ecx
mov.s eax, ecx

使用as test.s -o test.o && objdump -d test.o -M intel 处理上述代码会得到以下反汇编:

0:   89 c8                   mov    eax,ecx
2:   8b c1                   mov    eax,ecx

我们可以看到.s 后缀似乎将89 操作码切换为8b 版本(并适当更改了ModRM 字节)。

这种语法在 GAS 中是如何工作的?我找不到任何相关文档。

【问题讨论】:

按照措辞,这在技术上是题外话,因为您要求的是文档链接,而不是直接询问有关它们如何工作的更多详细信息。 (您可以通过使摘要+文档链接成为一个很好的答案的方式来做到这一点)。无论如何,好问题,即使它违反了规则,它也应该保持开放,IMO。 @Mogsdad:将其改写为主题,并投票重新开放。 【参考方案1】:

从 Binutils 2.29 开始,指令后缀现在是 deprecated,支持伪前缀。您可以在 GNU Assembler (pre-2.29) info pages 中找到记录在案的旧后缀。早些时候info as 页面这样说:

9.15.4.1 指令命名

[剪辑]

可以通过可选的助记符后缀指定不同的编码选项。 .s 后缀在从一个寄存器移动到另一个寄存器时在编码中交换 2 个寄存器操作数。 .d8.d32 后缀在编码中首选 8bit 或 32bit 位移。

记录新的伪前缀,Binutils 2.29(及更高版本)info as 页面被修改为:

可以通过伪前缀指定不同的编码选项:

disp8 - 更喜欢 8 位位移。 disp32 - 更喜欢 32 位置换。 load - 更喜欢加载形式的指令。 store – 更喜欢商店形式的指令。 vex2 – VEX 指令首选 2 字节 VEX 前缀。 vex3 – VEX 指令首选 3 字节 VEX 前缀。 evex – 使用 EVEX 前缀编码。

【讨论】:

如果你能获得objdump 或其他binutils 工具在反汇编时使用这些覆盖,那就太棒了。但我在信息页面索引中看不到任何相关内容。也许像 Agner Fog 的 objconv 这样的第三方反汇编程序可能具有的功能,因为它旨在制作可以重新组装的 asm。

以上是关于GNU 汇编器 x86 指令后缀(如“mov.s”中的“.s”)如何工作?的主要内容,如果未能解决你的问题,请参考以下文章

GNU ARM 汇编指令

ARM汇编基础

帮助理解 x86 内联汇编中的 DIV 指令

X86汇编5.高级指令详解

常用汇编指令

.byte 汇编指令在 gnu 汇编中有啥用?