是的,这可能是 AT&T 语法中的设计错误。它们通常遵循从 Intel 语法反转操作数的模式,并重命名符号/零扩展助记符 (cdq => cltq, movsx eax, byte[mem] => movsbl)。与此的偏差可被视为设计错误。
除非旧版本不同,否则不会出现实现错误。当 AT&T 随心所欲地为不同的指令制定自己的规则时,这是有效的(但令人不快)。这可能是与原始 Unixware 汇编器兼容的另一种情况。 (见下文)。
The bound instruction 不写入任何一个输入操作数,因此两者都不是真正的目的地。与cmp 不同,操作数顺序没有任何意义。它只是根据上限/下限检查寄存器,如果超出范围则引发#BR 异常。
它只有一个操作码,它需要寄存器 + 内存操作数(在 ModR/M r 和 r/m 字段中。
objdump -d 在 AT&T 和 Intel 语法中首先列出寄存器操作数。
我用 NASM 组装了db 0x62, 0x2c, 0x24 并将它与ld -melf_i386 链接到一个 32 位 ELF 可执行文件中(因为我有一个包装脚本,它使得组装+链接+反汇编比 只是 组装)。
objdump -drwC -Mintel
8048060: 62 2c 24 bound ebp,QWORD PTR [esp]
objdump -drwC -Matt
8048060: 62 2c 24 bound %ebp,(%esp)
这似乎是在 binutils 中实现的 AT&T 语法的一个怪癖 (as / objdump / gdb) bound 需要注册 arg 以首先列出。
bound %eax, (%edx) # assembles fine
bound (%edx), %eax # foo.s:2: Error: operand size mismatch for `bound'
我认为在 Intel 语法模式下它要求寄存器 arg 是第一个是相同的。这里的意思没有歧义,只是一个奇怪的设计选择,不反转操作数与 Intel 语法。
相关:AT&T syntax also has "bugs" according to the GAS manual:
9.15.16 AT&T 语法错误
UnixWare 汇编器,可能还有其他 AT&T 派生的 ix86 Unix 汇编器,在某些情况下生成具有反向源和目标寄存器的浮点指令。不幸的是,gcc 和可能的许多其他程序都使用这种相反的语法,所以我们坚持使用它。
例如
fsub %st,%st(3)
导致%st(3) 更新为%st - %st(3),而不是预期的%st(3) - %st。这发生在所有具有两个寄存器操作数的非交换算术浮点运算中,其中源寄存器为%st,目标寄存器为%st(i)。
因此,AT&T 语法存在实际错误,其中两个命令都有效并且意味着 不同 事物。我认为我们可以将这个操作数“反转”归为一组。
ndisasm -b32 将其反汇编为622C24 bound ebp,[esp],与 Intel 手册的操作数顺序匹配。