【问题标题】:x86-64 Intel Syntax for rel8 immediate operand?rel8 立即操作数的 x86-64 英特尔语法?
【发布时间】:2013-11-03 09:56:59
【问题描述】:

x86-64 中 JMP 的第一种形式是:

Opcode    Instruction  Description
EB cb     JMP rel8     Jump short, RIP = RIP + 8-bit displacement sign

所以例如JMP rel8=-2eb fefe 是一个单字节有符号的 2s-compliment -2。

如何在 Intel 语法中表达这个 rel8 立即数?

我尝试了以下方法:

test.s:

.intel_syntax noprefix
.global _start
_start:
    jmp -2

编译:

$ gcc -nostdlib test.s
$ objdump -d -M intel

但我明白了:

   e9 00 00 00 00           jmp    5 <_start+0x5>

不是eb fe 所希望的。

(更一般地说,英特尔语法记录在哪里?我在英特尔手册中找不到任何关于它的内容。英特尔手册解释了如何编码操作数,但它没有给出汇编语言的语法。)

更新:

解决办法是:

.intel_syntax noprefix
.global _start
_start:
    jmp .

. 必须代表当前指令的地址。组装和拆卸给出:

4000d4: eb fe      jmp    4000d4 <_start>

eb fe 根据需要。 RIP 相对寻址是根据下一条指令进行的,因此汇编器必须为您调整当前指令的大小。

【问题讨论】:

  • 你试过jmp $+offset吗?或者 jmp $ 在这种情况下
  • @harold: Error: junk '$-2' after expressionError: junk '$' after expression 分别。
  • 好的,jmp . + offset 怎么样?显然 GAS 再次打破传统......
  • @harold:查看更新。谢谢。
  • 关于英特尔语法没有记录的好问题。问题在于它甚至没有标准化,因此不同的汇编器必须记录自己的语法(即使它们通常高度相似)。例如,NASM 和 YASM 文档似乎假设您已经知道 MASM 语法,并指出与它的区别(例如 mov reg, sym 是 mov reg, imm32,而不是 mov reg, [mem])。 IIRC,AT&T 语法的 GNU 文档还不错,因为 gas 是唯一使用它的主要汇编程序。我不得不去检查注册间接jmp rax 的 NASM 语法,但很难找到。

标签: assembly x86 x86-64 gnu-assembler intel-syntax


【解决方案1】:

(G)AS 显然使用. 来表示当前地址(当前指令的地址),这与大多数其他汇编程序不同。

documentation 中有一个小页面记录它。

【讨论】:

    猜你喜欢
    • 2014-04-02
    • 2011-09-18
    • 2011-04-29
    • 2013-02-24
    • 2011-06-16
    • 2012-02-25
    • 1970-01-01
    • 1970-01-01
    • 2018-10-15
    相关资源
    最近更新 更多