64:如何做一个相对JMP *%RAX? [英] x64: How to do a relative jmp *%rax?

查看:1933
本文介绍了64:如何做一个相对JMP *%RAX?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想EN codeA相对64位跳到存储在%RAX在64集的地址。 AFAIK,有没有OP code对于这一点,所以我手动计算相应的绝对地址的相对地址,然后我做了一个绝对跳转到绝对地址:

I want to encode a 64 bit relative jump to the address stored in %rax in x64 assembly. AFAIK, there is no opcode for this, so I calculate the corresponding absolute address for the relative address manually and then I do an absolute jump to the absolute address:

# destination address, relative to end of jmp instruction, is stored in %rax
00007ffff7ff6020: 0x0000488d1505000000   lea 0x5(%rip),%rdx # load %rip+5 (rip + size of add and jmpq) into %rdx
00007ffff7ff6027: 0x0000000000004801d0   add %rdx,%rax # calculate absolute address based on %rdx (behind jmpq) and %rax (the relative address)
00007ffff7ff602a: 0x00000000000000ffe0   jmpq *%rax # do an absolute jump to absolute address

不过,这看起来不必要的复杂我。有较少的指令更好的办法?还是有另外一个原因,应避免64位相对跳转?

But this looks unnecessarily complex to me. Is there a better way with less instructions? Or is there another reason why 64 bit relative jumps should be avoided?

推荐答案

所有相对跳转指令都作为即时(=整型常量)操作的跳跃距离EN codeD中的指令。相对跳转(和电话)的存在是为了转移从code一个已知的位置,执行到另一个执行,如的正常过程中执行条件跳转(认为如果运营商在许多高级编程语言),无条件跳转(想想 GOTO 在BASIC或C / C ++或无条件跳转隐藏里面的如果语句)或调用子程序。为此目的(这是一个几乎重要的)是不够的。

All relative jump instructions have the jump distance encoded in the instruction as an immediate (=integer constant) operand. Relative jumps (and calls) exist to divert execution from one known location in the code to another in the normal course of execution, e.g. to perform a conditional jump (think of the if operator in many high level programming languages), an unconditional jump (think of goto in BASIC or C/C++ or unconditional jumps hiding inside of the if or for statements) or call a subroutine. For that purpose (and it's a practically important one) it's enough.

如果您需要访问相关数据进行RIP,你可以这样做,是因为在64位模式下,有一种方法来连接codeA内存操作数为RIP-相对(有没有这样的编码在32位模式下) 。这有助于生成位置无关code,有助于减少计划装修他们所有的code和静态数据到2GB内存的完整的64位地址的开销。

If you need to access data relative to RIP, you can do so because in 64-bit mode there is a way to encode a memory operand as RIP-relative (there's no such encoding in 32-bit mode). This helps with generation of position-independent code and helps reduce the overhead of full 64-bit addresses in programs fitting all of their code and static data into 2GB of memory.

其他XIP相对用途是不常见的。所以是的跳转指令的(除从子程序返回)。跳转指令是实现物像开关的说法,如发现一种常用方法C / C ++,Java的。有实现开关多种方式,但最明显的是有哪里跳,然后只用一个整数索引到它的地址阵列/表检索与之相对应的解决。然后你就可以跳到使用间接跳转,如: JMP RAX (或不管它是在AT& T公司的语法)。您可以获取从数组/表跳的地址一气呵成: JMP [表+ RAX * 8] (调整到您的AT& T公司的语法)

Other xIP-relative uses are less common. And so are computed jumps (other than return from a subroutine). Computed jumps are a common way to implement things like the switch statement, found in e.g. C/C++, Java. There are several ways to implement switch, but the most obvious one is to have an array/table of addresses of where to jump to and then just use an integer index into it to retrieve the corresponding to it address. And then you can jump using an indirect jump, e.g. jmp rax (or whatever it is in AT&T syntax). You can fetch the address from the array/table and jump in one go: jmp [table + rax*8] (adjust to your AT&T syntax).

这篇关于64:如何做一个相对JMP *%RAX?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆