相关疑难解决方法(0)

为什么分支位移的"起始小"算法不是最优的?

[底部加粗的问题]

当汇编程序生成二进制编码时,它需要决定是使每个分支变长还是短,如果可能的话,短路更好.汇编程序的这一部分称为分支位移优化(BDO)算法.一种典型的方法是汇编程序使所有分支编码变短(如果它们小于某个阈值),然后迭代地增加任何分支跳转到未到达的long.当然,这可以导致其他分支转换为跳远.因此,汇编程序必须不断通过跳转列表,直到不再需要升迁.这种二次时间方法对我来说似乎是一种最优算法,但据推测BDO是NP完全的,这种方法实际上并不是最优的.

兰德尔海德提供了一个反例:

                  .386 
                  .model  flat, syscall
00000000          .code
00000000          _HLAMain        proc


00000000  E9 00000016          jmpLbl:         jmp     [near ptr] target
00000005 = 00000005            jmpSize         =       $-jmpLbl
00000005  00000016 [                           byte    32 - jmpSize*2
dup
(0)
            00
           ]
0000001B                       target:
0000001B                       _HLAMain        endp
                                                end
Run Code Online (Sandbox Code Playgroud)

通过在括号"[near ptr]"中添加部分并强制进行5字节编码,二进制实际上最终会变短,因为分配的数组比跳跃大小的两倍小.因此,通过使跳转编码更短,最终代码实际上更长.

这对我来说似乎是一个非常病态的情况,并不是真正相关的,因为分支编码仍然较小,它只是对程序的非分支部分的这种奇怪的副作用,导致二进制变大.由于分支编码本身仍然较小,我并不认为这是"开始小"算法的有效反例.

我可以将start-small算法视为最佳BDO算法,还是存在一个实际情况,即它不能为所有分支提供最小的编码大小?

algorithm optimization assembly encoding

3
推荐指数
2
解决办法
268
查看次数

大会中LONG和FAR跳跃之间有什么区别?

我正在查看一些用于汇编的练习代码,并且赋值基本上是用另一个跳转点替换.

原始jmp是SHORT jmp,使用此指令无法到达我需要接近的终点.

我现在有三个选项,我要么删除'SHORT',要么插入'LONG'或者我插入'FAR'.

如果有任何文件指出它们之间的差异,我还没有找到它.任何人都可以在这里帮助吗?

x86 assembly

2
推荐指数
2
解决办法
8379
查看次数

标签 统计

assembly ×2

algorithm ×1

encoding ×1

optimization ×1

x86 ×1