5

关于相对跳跃,我有以下问题:

  1. 我知道这JMP SHORT <displacement>将跳转到<displacement>相对于当前 PC 的字节。那是对的吗?
  2. 汇编器是否会自动生成相对跳转的操作码?即当我刚刚写的时候JMP <label>,如果该标签位于当前PC 128 字节之外,它会产生相对跳转?
  3. 如果我确实想使用JMP SHORT <displacement>,计算位移的正确方法是什么?通过检查列表文件并计算偏移量?
4

2 回答 2

5

每个汇编器(程序)和汇编器的每个版本都可以选择默认为长或短。因此,我不会寻找所有汇编程序默认为一件事的笼统声明。如果好奇,试试看会发生什么。

使用 x86 和可变长度指令,简单地编写位移代码将非常棘手,必须提醒自己永远不要接触跳转和目标之间的代码。

是的,我首先让汇编器使用标签对指令进行编码,然后获取指令集参考手册和带有地址的反汇编,并弄清楚如何计算位移。如果汇编器允许您自己设置位移,这可能是汇编器特定的东西,并且您需要知道它可能需要该位移的单位。x86 可能是字节,但是固定字长指令集可能必须以指令为单位而不是字节来给出位移。或字节不是指令,所以我会使用位移然后再次反汇编以查看它计算了正确的指令。

于 2012-06-22T18:34:29.260 回答
2

假设汇编器自动使用短编码或普通编码。乍一看,如果可能,总是切换到短编码似乎没问题,但实际上有可能这样做,以便必须再次将其他一些分支更改为长编码。

例如(未经测试或任何东西,只是为了得到这个想法):

  jmp _skip          ; relative offset depends on
               the size of "other code", which may include other jumps
  ; other code
_skip:

所以你不能做一个“向前”传球来确定尺寸——当你在那个跳跃时,你还不知道它是否适合,因为你还没有决定如何处理其他跳跃.

那么倒退?(未经测试或任何东西,只是为了得到这个想法)

  .fill 124
  jmp _somewhere     ; 2 bytes, or 5?
  jmp _quiteFarAway  ; relative offset is either 130 or 127
  .align 256
_quiteFarAway:

不,也不能向后传递,在决定跳转到 _quiteFarAway 的编码时,您还不知道它是否适合,因为您还没有决定如何处理其他跳转。

做你的第 2 点很难,有很多不同的方法可以解决这个问题。例如采用显式“短”修饰符,显式“长”修饰符,进行安全猜测并最终得到在极少数情况下不需要的长版本等。

于 2012-06-22T20:24:46.253 回答