IDA Pro配合Hex-Rays Decompiler,可以把已经识别的机器代码转换成接近C语言形式的伪代码,并进一步保存成.c文件。这种结果主要方便阅读程序逻辑,并不等同于恢复原项目源码,原来的变量名、注释、宏定义以及部分类型信息通常已经不存在。导出后发现少了函数、某段只有声明,或者个别位置没有生成代码,也不一定是保存动作出了问题,函数识别状态、反编译失败和类型分析都会影响最终内容。
一、IDA Pro怎么导出C代码
IDA Pro里单个函数通常先通过F5查看Pseudocode,需要一次保存多个函数时,可以直接使用Hex-Rays提供的Create C file功能。导出前先让自动分析跑完,得到的内容通常更完整。
1、先检查目标函数能否正常反编译
准备批量导出以前,可以随便挑几个关键函数试一下。如果这些函数本身就打不开伪代码,直接生成C文件时同样可能缺少内容。
①、打开需要分析的【IDB】或【I64】数据库。
②、进入【Functions】窗口选择目标函数。
③、在函数内部按【F5】。
④、确认能够打开【Pseudocode】窗口。
⑤、使用【Tab】在伪代码和反汇编之间切换检查内容。
2、导出整个程序的伪C代码
①、取消【IDA View】中的代码区域选择。
②、依次打开【File】→【Produce file】→【Create C file】。
③、也可以直接使用【Ctrl+F5】。
④、选择导出文件的保存目录。
⑤、填写需要生成的【.c文件】名称。
⑥、等待Decompiler完成批量处理。
在没有选中代码区域的情况下,Create C file会尝试处理整个应用。这里得到的是反编译文本,更适合作为程序分析材料,不能直接按照原源码理解。
3、只导出指定范围的函数
①、进入【IDA View】。
②、选中包含目标函数的【代码区域】。
③、执行【File】→【Produce file】→【Create C file】。
④、设置输出【.c文件】。
⑤、完成后检查选中函数是否已经写入文件。
二、IDA Pro导出C代码后内容不完整如何处理
导出的文件内容偏少时,可以先回IDA看缺失函数本身能不能按F5打开。如果单独反编译也失败,问题就在Decompiler分析阶段;如果单独正常,则要再检查导出范围和函数识别情况。
1、检查遗漏代码有没有被识别成函数
有些地址已经显示出汇编指令,但IDA没有建立正确的函数边界,批量导出时就不会按照正常函数处理。
①、在【IDA View】定位缺失代码。
②、确认当前位置是否属于【Function】。
③、没有建立函数时定位正确入口。
④、执行【Create function】建立函数。
⑤、检查函数结束位置是否合理。
⑥、按【F5】重新测试。
2、查看该函数是否发生反编译失败
①、进入缺失函数后按【F5】。
②、记录出现的【Decompiler failure】提示。
③、打开【Output window】查看相关信息。
④、检查是否存在栈指针、函数边界或类型错误。
⑤、修正后再次生成【Pseudocode】。
⑥、重新执行【Create C file】。
如果出现invalid basic block、positive sp value、call analysis failed等提示,就要先修复对应函数。Hex-Rays遇到无法可靠处理的函数时,不会凭空补出一段C代码。
3、修正函数类型和调用约定
①、在【Pseudocode】或函数入口定位目标函数。
②、按【Y】打开类型设置。
③、检查返回值和参数数量。
④、确认【Calling Convention】。
⑤、继续核对被调用函数的类型。
⑥、重新执行【F5】查看结果。
错误的函数原型有时会连带影响调用分析,表现出来就是参数异常、变量混乱,严重时直接无法反编译。
4、检查Compiler和数据库分析状态
参数和程序位数没有对应好,也可能让部分函数生成失败。
①、进入【Options】→【Compiler】。
②、确认当前【Compiler】类型。
③、检查基础类型和指针尺寸。
④、返回目标函数查看【Stack frame】。
⑤、确认自动分析已经结束。
⑥、保存数据库后重新执行导出。
三、IDA Pro导出的C代码怎么进一步检查
C文件成功生成以后,最好再抽查几个核心函数。因为伪代码适合辅助理解,函数类型和变量恢复结果仍可能需要人工调整。
1、把导出结果和Pseudocode对照
①、打开生成的【.c文件】。
②、找到准备核对的函数。
③、返回IDA打开同一函数的【Pseudocode】。
④、比较主要条件分支和函数调用。
⑤、再切换到【IDA View】检查关键指令。
发现导出文件少了某段逻辑时,回到单函数视图比较,很容易判断是批量导出问题还是该函数本身没有完整恢复。
2、保存修正后的分析数据库
修过函数边界和类型以后,数据库本身比单独导出的C文件更值得保存。
①、保存当前【IDB】或【I64】。
②、保留已经修改的【Function Type】。
③、再次生成新的【C文件】。
④、把前后两个版本分别保存。
⑤、记录仍然无法反编译的函数位置。
总结
IDA Pro导出C代码更适合用来整理程序逻辑,并不能把编译后的文件完整变回原始工程。发现导出内容少了一块时,先回头看对应函数能不能正常生成伪代码,再检查函数边界、栈和类型信息,通常比反复执行导出更有方向。把人工修正过的数据库一起保留,后面继续分析时也不会丢掉已经整理好的函数和类型信息。
