使用objdump时,我会看到以下反汇编代码:当我签入gdb时,我看到的是0x8049445处的真实代码:

8049436:    89 04 24                mov    DWORD PTR [esp],eax
8049439:    e8 52 f7 ff ff          call   8048b90 <gtk_entry_get_text@plt>
804943e:    89 44 24 24             mov    DWORD PTR [esp+0x24],eax
8049442:    eb 01                   jmp    8049445 <gtk_grid_new@plt+0x6c5>
8049444:    1d c7 04 24 0b          sbb    eax,0xb2404c7
8049449:    00 00                   add    BYTE PTR [eax],al
804944b:    00 e8                   add    al,ch
804944d:    0f f7 ff                maskmovq mm7,mm7
8049450:    ff eb                   jmp    <internal disassembler error>


现在,我的问题是:是否可以告诉objdump可以忽略0x8049444处的字节为了拆卸的目的?一种明显的方法是实际修补文件,但是还有另一种方法吗?

如果没有使用objdump,是否还有其他工具可以做到这一点?尽管我宁愿使用Linux附带的基本工具,以便更好地熟悉这些工具。

评论

是的,但请记住,拆卸不是一门精确的科学

#1 楼

大多数工具不支持“忽略该字节以进行反汇编”功能,只有IDA,Hopper和其他一些工具不支持。您的头脑,而不是依靠基本工具。

评论


都是很好的建议。对于选项(1),搜索jmp +1,将下一个字节设置为nop并愉快地继续使用objdump。我会选择选项(2)-就我自己编写的程度而言。

–杂件
13-10-16在10:15



#2 楼

那不是混淆,而只是糟糕的反汇编引擎的输出。

请改用IDA Pro。您可以从此处下载Linux的评估版。

评论


这与“糟糕”无关。它仅使用线性扫描分解策略(与递归遍历相反)。两种策略在某些情况下/针对不同的反拆卸技术均会失败。

– newgre
13-10-15在20:55



关于满足原始海报需求的“ Lousy”。他应该使用递归下降反汇编程序,例如IDA Pro。

–詹森·格夫纳(Jason Geffner)
13-10-15在20:58

IDA Pro实际上同时使用了IIRC和IIRC。首先,它尝试从程序入口点进行评估(该入口点已经为OP的代码生成了正确的清单)。然后,它扫描剩余的数据以查找函数序幕,然后才对不完整的字节进行四舍五入(剩余的字节应该不多了)。

–杂件
13-10-15在21:26

我尝试过IDA Pro。对于这种特殊情况,它的拆卸比objdump制造的拆卸要少。但是,一旦调试,它就会自行修复。或者我也可以手动修复它。

–密
13-10-16在18:42

#3 楼

此问题来自objdump分解二进制文件的方式。此处使用的技术称为线性扫描,它是通过在所有标记为CODE的段中的每个符号的开头开始并在指令之后反汇编指令(假定指令之后也是指令)来完成的。这种反汇编技术的问题在于,如果您将代码和数据混合在一起,则数据也将被解释为代码。例如:

...
0x0    mov DWORD PTR [esp+0x24],eax
0x4    jmp *0x10
0x6    DATA 0xfffa2345
0x10   mov DWORD PTR [esp+0x20],eax
...


此处,对十六进制代码应用线性扫描技术将导致错误地解释数据,该数据将被视为代码。而且,如果您真的很倒霉,那么数据后面的一些指令也会被打乱。

正如其他答案中已经建议的那样,发现真实代码的唯一方法是使用另一种反汇编技术。不幸的是,objdump仅提供了一种(线性扫描),因此您需要使用另一种工具。

还请注意,其他答案(递归遍历)中建议的另一种技术在此特定情况下效果很好,但可以在其他一些示例上,还会对原始代码进行错误的反汇编。因此,您也不能信任它。

#4 楼

就像其他人说的那样,在这种情况下,这是由于线性扫描而引起的。由于编码器可以在运行时更改代码,因此仅信任EIP上的值,而别无其他作为正确的代码。