原生程序的语义分析:CodeReason技术解析
你是否曾想对原生模式程序进行查询,找出将特定值写入寄存器的程序位置?是否希望自动化解密被混淆的字符串?
逆向工程的挑战
逆向工程原生程序需要从底层理解其语义,直到浮现出高级功能图景。系统化理解原生程序面临的挑战在于:这种理解必须扩展到程序使用的每条指令。分析必须知道哪些指令对内存调用和寄存器产生何种影响。
我们为DARPA网络快速追踪项目开发的CodeReason机器码分析框架应运而生。该框架支持分析x86和ARM原生代码的语义,其核心价值在于能够查询原生代码对程序整体状态的影响机制,这得益于其对原生指令的深度语义理解。
构建语义分析系统
构建这种语义理解体系既耗时又昂贵。现有系统要么门槛过高,要么无法精确满足需求,或缺少语义简化和优化功能。而语义简化能将复杂的优化转化为易于理解的简单表达式。以下通过Flame恶意软件案例说明其应用价值。
Flame恶意软件字符串解密实战
当Flame恶意软件曝光时,其部分二进制文件被上传至malware.lu。该恶意程序将混淆字符串存储在全局数据结构中,结构如下:
|
|
我们使用CodeReason开发了C语言字符串解密器。原始解密逻辑分三步:
- 第一函数检查hasDeobfuscated字段:若为0则返回字符串首指针;否则调用第二函数并将该字段置零。
- 第二函数遍历字符串数组,对每个字符调用第三函数获取解密因子进行减法运算:
|
|
- 第三函数由单基本块构成,包含lea/add/imul/shr/xor等指令序列。
CodeReason的核心优势
通过CodeReason的语义分析系统,我们可以捕获该代码块并获取’eax’寄存器的运算方程,从而在解密器中复现get_decrypt_modifier的功能。虽然可将其反编译为C代码,但我们更关注代码对’eax’的影响而非高级语言表示。
使用CodeReason交互式分析获得如下语义表达式:
|
|
据此可准确实现C语言版本:
|
|
高级应用场景
- IDA插件集成:正在开发IDA插件支持直接查询
- 竞态条件发现:该解密器存在线程安全问题,多线程同时解密会永久破坏字符串
- 动态字符串构造优化:能将通过算术运算动态构建字符串的指令序列优化为直接内存写入:
|
|
技术展望
将机器码转化为可优化和理解的形式具有强大潜力,特别是当这种能力通过编程库提供时。CodeReason不仅能提取字符串混淆函数的语义实现自动解密,还能将混淆代码简化为直接表达解密字符串的形式。我们将在后续文章中介绍更多应用案例。