防拆技术和缓解措施

admin 2024年5月7日12:30:49评论1 views字数 1476阅读4分55秒阅读模式

反汇编程序的工作原理

最简单的反汇编程序超级简单,但它们也可能非常复杂。更高级的反汇编器会尝试识别函数(可能具有倍数返回)、跳转表等习语,并且不会被反汇编技巧所欺骗。它们分为两大类。

  1. 线性 - 按顺序分解所有指令,从某个点(通常是二进制文件的入口点)开始。

  2. 面向流 - 它们跟随跳跃和呼叫,并继续从目标中分解。它们也可能在返回指令后停止反汇编,因此请避免显示无法访问的指令(因此可能根本不是代码)。

由于面向流的反汇编程序遵循分支,并且存在条件分支,因此反汇编程序必须做出决定。通常,对于普通代码,反汇编器可以简单地遵循两者(例如,跳跃和不跳跃,从目标和下一条指令中反汇编)。问题在于可能存在矛盾或不兼容的跳跃。

欺骗面向流的反汇编程序

有多种方法可以欺骗反汇编程序。这里只是其中的几个:

  1. 放置两个连续但“相反”的条件分支,例如 a 后跟 a 。jzjnz

  2. 使用常量条件,例如 .xor eax, eax; jz <addr>

  3. 使用一个什么都不做的分支,例如 ,然后在 addr: 处。这通常在 shellcode 中用于获取带内数据的地址,因为在 x86 上,这是获取 PC 周围地址的最简单方法。call <addr>pop <reg>

  4. 使用一系列字节,这些字节将多次执行,作为不同的指令,具体取决于 PC 所在的位置。例如。当反汇编程序将其反汇编(如 x86)时,它将看到 ,然后是 ,这不是有效的操作码,最后是 。EB FF C0 48EB FFjmp 1C048dec eax

    问题是这不是它的执行方式!从指令的开头跳转一个字节(或者更确切地说,从指令的末尾跳转 -1 字节 (0xFF)。这使得 EIP 降落在0xFF上。现在 CPU 解码为 和 和 。最后。这段代码基本上什么都不做。这里的解决方案是:NOP出所有四个字节。jmp 1FF C0inc eax48dec eax

  5. 滥用和扰乱功能边界。例如,这是 .这会将返回地址推送到堆栈上,该地址将是 .然后将此地址弹出到 PC 中,这有效地使这两个入侵组合变得无用。但是,这个 cal 使反汇编程序认为函数到此结束,并且下一条指令是另一个函数的结束。callretE8 00 00 00 00 C3call 5; retretret

  6. 大量使用函数指针。虽然这样做的目的不是为了让逆向工程师的生活更加困难,但它也有同样的效果。从本质上讲,每当复制指针时,地址都会有交叉引用,但是当它被调用时,由于它是从寄存器或内存地址调用的,因此反汇编器通常无法确定何时使用它。

缓解

绕过这些技巧最困难的部分与修补它们无关——这是微不足道的。诀窍在于快速识别它们,而不是浪费时间弄清楚它们的作用。这只能通过实践来完成。我所学到的最重要的反反汇编知识,都是从第16章的《实用恶意软件分析》一书中学到的。这本书包括实验室,我建议你这样做。你可以在这里看到我的文章。

一旦它们被识别出来,IDA Pro 就很容易修复。在大多数情况下,我最喜欢的修复方法是使用 .这可以通过“File > IDC Command...”完成对话框,如果不想提供地址,则可以使用光标的地址。这通常看起来像 .确保为要删除的每个字节运行它。PatchByteScreenEAPatchByte(ScreenEA(), 0x90);

当您知道从函数指针调用哪个函数时(显然,当从此位置调用多个函数时要小心),您可以使用 手动添加外部参照。你要用的就是这样,确保你已经选择了调用指令。您可以对跳跃做同样的事情,用fl_CN代替fl_JNAddCodeXrefAddCodeXref(ScreenEA(), <addr of function>, fl_CN);

原文始发于微信公众号(天启者安全):防拆技术和缓解措施

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2024年5月7日12:30:49
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   防拆技术和缓解措施https://cn-sec.com/archives/2714698.html

发表评论

匿名网友 填写信息