1

我发现自己经常无法立即识别数字是十进制还是十六进制(如果十六进制数字没有前缀或字母)。例如,从上一个问题中得到一个数字0000000000400078,但不确定它是哪个。

有没有办法在 x86_64 中显式指定带前缀的十进制数?例如:

 mov     %rsp,       %rbp
 movb    $0x16,      -1(%rbp)
 movb    $0d22       -2(%rbp) # <-- something like this
 movb    $0b10110,   -3(%rbp)

我知道这样做movb $22, -2(%rbx)是可行的,但是有没有办法明确地为其添加前缀/后缀,以便我们知道它是小数?

4

1 回答 1

5

不,不适用于 GAS。 https://sourceware.org/binutils/docs/as/Integers.html -十进制整数以非零数字开头,后跟零或多个数字 ( 0123456789)。

调试器或 objdump 输出中屏幕上的十六进制数字有时会省略 a 0x,例如0000000000400078hex。您必须从上下文中知道地址几乎总是以十六进制打印。

在 asm 源代码中,规则简单、明确且不区分上下文。 在 GAS 源代码中,如果您没有看到明确的基本覆盖,则它是十进制的。这适用于$123立即数、123(%reg)位移、.set xyz, 123汇编指令操作数、.long 123将字节/双字发射到输出中的伪指令,以及 GAS 允许您编写数字文字的所有其他上下文。

它也适用于 GAS 支持的所有 ISA——请注意,GAS 手册的这一部分属于一个特定的 ISA。当然,对于 x86-64,它同时适用于.intel_syntax noprefix模式和 AT&T 模式。


不同的汇编器可能支持不同的方式以不同的基数写入数字,至少对于非十进制基数;这个答案适用于 GNU 汇编器 GAS。

有一些汇编程序,特别是令人讨厌的过时 DOS debug.exe,其中每个数字文字都被视为十六进制。debug.exe 根本不支持十进制。正如@old_timer 喜欢指出的那样,汇编语法是由 assembler 定义的,而不是由 ISA 定义的。

当没有显式修饰符时,大多数 x86 汇编器(NASM、MASM、GAS、Go-asm)默认为十进制。有些可能有显式十进制语法,您可以根据需要使用,但 GAS 没有。

于 2020-08-23T21:15:27.703 回答