我正在尝试为PE,PE +和ELF可执行文件编写自己的反汇编程序,但是我在PE和PE +可执行文件上遇到了一个大问题。

我通过将输出与objdump,我发现一些(错误的)操作码出现在反汇编程序中。我立即查看了使用说明书以控制这些值。它们在使用说明书中显示为无效。一些示例:

PE文件中的示例:

40dad1:       d6                      (bad)


其他一些:

402f1c:       ff                      (bad)
402f1d:       ff                      (bad)
402f1e:       ff                      (bad)
402f1f:       ff 01                   incl   (%ecx) #at last a valid instruction


当我阅读手册时这些是有效的,但是我不明白(这是一个PE +文件,体系结构是AMD64):无效的间接x87操作码,我们继续阅读,因为它是有效的操作码?我想objdump选择了这条路径。

这些(不好的)指令是做什么用的?显然,它们不适合对齐。还是我做错什么了?

Btw,我正在尝试分解旧项目和FireFox以检查程序是否正常运行。我正在使用objdump -z -d -M intel XXYYZZ.exe进行拆卸。

#1 楼

您是正确的,objdump实际上是错误的反汇编此类指令,只是在以后的阶段将其标记为(bad)

这是它的工作方式: />
db是87个FPU扩展之一,而a5实际上是Mod / rm字节。现在,对于FPU扩展,所有其他mod / rm指令的rm部分都“照常”,但是mod部分从此小表格中指示要使用的指令:

>
其中/x数字表示在mod / rm字节的mod部分中编码的内容(出于完整性考虑:db eX也形成一些有效的操作码)。

在所有可用代码中,那些使用..001.....100....110...的mod / rm模式形成“错误”代码-但只有在解析mod / rm字节并检查此特定表的操作码DB后,您才知道这一点。 objdump在检查基本指令是否有效之前,先分析整个指令-包括4字节立即数。我想这只是一张表,上面写着

db a5 4e 9c 95 68    lock (bad) [rbp+0x68959c4e]


,而(bad)条目被当作实际上是有效的使用。这是无关紧要的,因为两种方式都可以得出结论,操作码是“错误的”,但是使用objdump的方法,您不仅会将第一个字节丢弃为“错误”,而且还会丢弃整个6个字节。至少从理论上讲,第一个字节(这将导致整个下一个序列无效)是数据,但紧随其后的是正确的代码,然后它将以序列a5 4e 9c 95 68开始-完全被objdump跳过。 br />
..这些(不良)说明有什么用途?


我想,看看您显示的其他说明,您正在分解的错误部分可执行文件,它根本不是代码,而是数据。

您应该检查PE / PE ++标头以找到这些部分,然后仅尝试在其Characteristics字段中标记为“ code”和/或“ executable”的部分上进行反汇编。即使这样,也有可能从``错误''位置开始(例如在较长指令的中间)或在内部数据(也可能位于.code部分内部)开始。

评论


我已经解析了标头,只是尝试按照您所说的仅反汇编“ .text”部分,我认为您可能不是指令而是数据是正确的。我想知道是否还有另一个表或类似的表来指示.text部分的代码部分。.由于我使用线性扫描方法来进行反汇编(如objdump),所以我认为指令之间的这些数据让我很忙。

–Efe Can
16年11月24日在16:34

@EfeCan:不,线性扫描只会导致疼痛。 objdump对于临时看代码来说“足够好”,但是对于更认真的反汇编程序,您应该看一下IDA Pro(如果我没记错的话,他们仍然有一个免费的演示程序,可以在PE上实现奇迹)。我用于最新反汇编程序的方法是函数驱动的-完全可行,因为我正在研究的可执行文件是用OOP语言编写的。

–杂件
16年11月24日在16:39

是的,我认为我应该考虑交换递归方法。我将尝试IDA以获得更多想法。

–Efe Can
16-11-24在17:26