
unidbg逆向工程:原理与实践
📦 Download Book
- 模拟执行SO文件:使用unidbg在PC上模拟Android环境,无需真机即可运行so库。
- 简化逆向流程:通过补环境、Hook和Patch技术,快速分析so文件的功能和算法。
- 深入理解原理:源码级剖析unidbg内部机制,掌握其工作原理和实现细节。
- 解决生产问题:通过大量实战案例,应对I/O重定向、设备风控、反调试等真实场景。
- 批量部署应用:学会将so部署到x86服务器,实现大规模分析和风控对抗。
- 逆向工程专家:需要深入掌握unidbg原理,解决复杂so文件分析难题。
- 移动安全研究员:利用unidbg进行漏洞挖掘、协议分析和风控对抗。
- CTF高级玩家:通过unidbg模拟执行,快速解决逆向类赛题。
- 风控工程师:学习批量部署so,提升黑灰产对抗能力。
- 先掌握基础操作:阅读第1-3章,学会环境搭建和基本用法。
- 深入原理部分:第4-8章是核心,建议结合源码阅读,理解机制。
- 实战演练:第9-12章案例丰富,动手实践巩固知识。
- 学习反制技巧:最后四章讲解检测绕过和部署,适合进阶提升。
- 精通unidbg使用:能够独立完成so文件加载、补环境和模拟执行。
- 深入理解原理:掌握Unicorn模拟器、ELF加载、JNI交互等核心机制。
- 解决实战难题:通过案例学习,应对I/O重定向、反调试等复杂场景。
- 提升对抗能力:学会检测绕过和服务器部署,增强风控对抗实力。
- 积累生产经验:掌握批量分析技术,为实际工作提供支持。
📖 Book Introduction
(2)原理讲解深入:通过深入解析unidbg主要功能和模块的源代码来讲解unidbg的工作原理和实现细节,授人予渔。
(3)包含大量案例:通过大量案例讲解和演示了如何利用unidbg来解决各种逆向工程的难题,手把手教。
(4)注重生产实践:无论是理论讲解,还是实战案例,都直接瞄准生产环境,带领读者解决工程环境中的真实问题。
内容介绍
这是一本从原理和实践角度讲解unidbg的著作,不仅深入解析了unidbg的使用方法、工作原理、实现细节,而且详细讲解了如何用unidbg解决生产环境中的各种逆向工程难题。它是作者多年安全工作经验的总结,得到了unidbg框架作者的高度评价和推荐。
全书共31章,分为四个部分。
第一部分(第1~3章) unidbg基础
主要介绍了unidbg的基本使用和操作,包括工作环境的准备、so文件加载、简单补环境、Hook和Patch的方法等。
第二部分(第4~15章) unidbg原理与实现
通过源码分析的方式对unidbg的原理与实现进行了详细的剖析,首先分析了Unicorn模拟linker实现so的加载、链接、初始化的原理,然后深入分析了unidbg主要功能和模块的源码实现,包括AndroidEmulator、JNI交互流程追踪、DalvikVM、Memory、Hook等。
第三部分(第16~26章) 补环境与模拟执行实战
通过实战案例讲解了unidbg在生产环境中的使用,包括如I/O重定向、Debugger自吐,指针参数与Debugger、魔改Base64还原、使用unidbg动态分析内存中的数据、使用unidbg主动调用fork进程,并对补环境中的补环境入门、标识记录、设备风控、补环境加强等进行分析,指导读者编写实际的补环境代码,更好地将理论知识运用于实践中。
第四部分(第27~31章) 反制与生产环境部署。
介绍了环境变量检测、xHook框架检测、JNI层常见函数处理等,对常规检测进行了总结,并介绍了在检测之后如何把so部署到x86服务器上。这部分内容对批量生产与对抗、大数据风控非常有价值,对于打击黑灰产、遏制网络犯罪有着非常积极的意义。
陈佳林 (ID:r0ysue)
资深安全技术专家,在逆向工程、移动安全领域积累了丰富的经验。曾为政府机关单位提供涉密项目研究开发,多次为银行和电信行业以及政府部门提供安全方面的培训服务。看雪论坛的版主和资深讲师,看雪“安卓高级研修班”负责人,在看雪安全开发者峰会、GeekPwn 发表主题演讲,在看雪论坛、安全客、Freebuf 等平台发表大量技术文章。著有《安卓 Frida 逆向与抓包实战》《安卓Frida 逆向与协议分析》《Frida 安卓 SO 逆向深入实践》等书籍。开源项目r0capture 在 Github 的 star 数量超过 5000 个。
前 言
第一部分 进入unidbg的世界
第1章 unidbg环境准备与快速
上手 2
1.1 r0env环境介绍与集成 2
1.1.1 r0env各组件介绍 2
1.1.2 r0env下载及安装 5
1.2 IDEA安装及配置 6
1.3 第一个unidbg项目 7
1.3.1 unidbg介绍 7
1.3.2 unidbg下载与运行示例 8
1.3.3 unidbg示例讲解 9
1.4 本章小结 13
第2章 unidbg模拟执行初探 14
2.1 第一个NDK项目 14
2.1.1 使用Android Studio创建NDK项目 14
2.1.2 编写自己的so业务代码 16
2.2 unidbg的符号调用与地址调用 18
2.2.1 unidbg主动调用前置准备 18
2.2.2 unidbg主动调用so函数 19
2.2.3 unidbg部分API简单讲解 22
2.3 本章小结 24
第3章 unidbg补环境、Hook与
Patch 25
3.1 为so添加交互:使用JNI接口
编写md5方法 25
3.2 使用unidbg修补执行环境并
模拟执行 27
3.3 脱离编译器,使用命令行
编译so 34
3.4 unidbg的Hook 36
3.5 unidbg的Patch 39
3.6 本章小结 42
第二部分 unidbg原理
第4章 ELF文件执行视图解析 44
4.1 ELF文件结构 44
4.1.1 ELF头部结构 45
4.1.2 程序头部表 47
4.1.3 动态节区_DYNAMIC段 51
4.2 深入jelf代码细节,探究ELF
解析 54
4.2.1 分析原版jelf代码 54
4.2.2 分析unidbg版jelf代码 56
4.3 本章小结 60
第5章 Unicorn的初级使用与初探Linker 61
5.1 Unicorn的初级使用:模拟执行与Hook 61
5.1.1 使用Unicorn进行模拟
执行 61
5.1.2 Unicorn的Hook 64
5.1.3 Keystone与Capstone 70
5.2 初探Android系统源码 71
5.2.1 Java层代码追踪 73
5.2.2 Native层代码追踪 75
5.3 本章小结 78
第6章 深入Linker:so的加载、
链接、初始化 79
6.1 so的加载过程 79
6.2 so的链接过程 90
6.3 so的初始化操作 100
6.4 本章小结 102
第7章 使用Unicorn模拟Linker:so的加载过程 103
7.1 模拟Linker :环境准备 103
7.2 模拟Linker :so的加载 109
7.3 动态调试Linker,探究so的内存
布局图 118
7.4 本章小结 122
第8章 使用Unicorn模拟Linker:
so的链接过程 123
8.1 so的依赖库加载过程 123
8.2 so的动态链接 127
8.3 初尝试:使用unidbg模拟执行
简单so文件 131
8.4 探究unidbg的Linker代码
细节 133
8.4.1 unidbg加载so文件代码
入口 134
8.4.2 处理so信息并载入内存 135
8.4.3 对so的依赖库进行处理 137
8.4.4 重定位操作 138
8.4.5 处理so的初始化信息与生成module对象 140
8.4.6 执行初始化 141
8.5 本章小结 142
第9章 R0dbg实战与Unidbg_FindKey 143
9.1 模拟Linker :so的初始化过程 143
9.2 指令追踪与排错 147
9.2.1 TLS线程局部存储环境
初始化 148
9.2.2 R0dbg对系统调用进行
处理 150
9.3 使用R0dbg模拟执行so 152
9.4 Unidbg_FindKey牛刀小试 154
9.5 本章小结 157
第10章 unidbg源码解析:AndroidEmulator 158
10.1 创建AndroidEmulator 158
10.2 创建FileSystem 165
10.3 创建Backend 168
10.4 创建SvcMemory 169
10.5 本章小结 172
第11章 unidbg源码解析:
DalvikVM 173
11.1 分析createDalvikVM() 173
11.2 Dvm相关类介绍 178
11.2.1 BaseVM解析 179
11.2.2 DalvikVM解析 184
11.2.3 DvmObject解析 185
11.2.4 DvmClass解析 187
11.3 本章小结 188
第12章 unidbg源码解析:模拟
执行流程追踪 189
12.1 编写含JNI交互的MD5算法并
模拟执行 189
12.1.1 编写含JNI交互的so 189
12.1.2 使用unidbg进行模拟
执行 190
12.2 模拟执行流程追踪:寻找
函数 192
12.3 模拟执行流程追踪:处理参数
并模拟执行 195
12.4 本章小结 202
第13章 unidbg源码解析:JNI
交互流程追踪 203
13.1 JNI注册 203
13.2 JNI指令执行 208
13.3 本章小结 217
第14章 unidbg源码解析:
Memory 218
14.1 Memory模块的创建 218
14.2 AndroidElfLoader的方法实现 219
14.2.1 内存相关方法实现 219
14.2.2 栈空间相关方法实现 226
14.2.3 用户常用方法解析 227
14.2.4 虚拟模块 230
14.3 加载so的loader功能 231
14.4 本章小结 237
第15章 unidbg源码解析:
Hook 238
15.1 unidbg的Hook框架 238
15.1.1 Hook框架的使用 238
15.1.2 Hook源码分析 243
15.2 Debugger模块解析 245
15.2.1 Console Debugger的
使用 245
15.2.2 Debugger源码分析 246
15.3 本章小结 256
第三部分 模拟执行与补环境实战
第16章 unidbg实战:I/O重定向 258
16.1 分析App的内部逻辑 258
16.1.1 了解App的运行流程 258
16.1.2 Java层逻辑分析 259
16.1.3 so层逻辑分析 262
16.2 unidbg模拟执行分析 267
16.2.1 unidbg模拟执行saveSN()
方法 267
16.2.2 unidbg的I/O重定向 269
16.3 本章小结 272
第17章 unidbg实战:Debugger
自吐 273
17.1 分析App的内部逻辑 273
17.1.1 了解App的运行流程 273
17.1.2 Java层逻辑分析 273
17.1.3 so层逻辑分析 275
17.2 使用unidbg工具进行分析 277
17.2.1 使用unidbg进行模拟
执行 277
17.2.2 使用Debugger模块实现
自吐 281
17.2.3 使用Patch进行自吐 283
17.3 本章小结 286
第18章 unidbg实战:指针参数与Debugger 287
18.1 指针参数的使用 287
18.1.1 对App进行分析 287
18.1.2 使用unidbg进行模拟
执行 290
18.2 快速识别AES算法 295
18.2.1 对App进行分析 295
18.2.2 使用unidbg进行模拟
执行 297
18.3 本章小结 301
第19章 unidbg实战:魔改Base64还原 302
19.1 逆向环境搭建 302
19.2 APK分析 303
19.3 so文件详细分析 304
19.3.1 基本类型手动修改 304
19.3.2 主体代码分析 308
19.4 使用unidbg辅助分析so 309
19.4.1 使用unidbg主动调用
Native层的算法 309
19.4.2 魔改Base64核心步骤
分析 312
19.5 本章小结 321
第20章 unidbg实战:使用unidbg
动态分析内存中的数据 322
20.1 环境搭建 322
20.2 APK基本分析 323
20.2.1 按钮事件分析 323
20.2.2 对输入框的内容进行
判断 325
20.3 使用IDA静态分析so并使用unidbg动态验证 326
20.3.1 静态代码块说明 326
20.3.2 IDA分析 326
20.4 本章小结 337
第21章 unidbg实战:使用unidbg
主动调用fork进程 338
21.1 样本情景复现 338
21.2 样本反编译分析 339
21.3 so中代码的分析 342
21.4 使用unidbg对fork进程中的
函数做处理 350
21.5 本章小结 356
第22章 unidbg补环境实战:
补环境入门 357
22.1 为什么要补环境 357
22.2 unidbg补环境的案例情景
复现 357
22.3 模拟执行so 361
22.3.1 参数获取 361
22.3.2 unidbg代码初始化 362
22.3.3 目标函数的调用 363
22.3.4 补环境说明 363
22.3.5 补环境实战 364
22.4 本章小结 374
第23章 unidbg补环境实战:标识记录 375
23.1 样本一:如何补JNI_OnLoad
环境 375
23.1.1 基本环境搭建 375
23.1.2 运行项目,异常分析 376
23.2 样本二:文件标识的补环境
策略 384
23.2.1 环境搭建 384
23.2.2 文件标识策略 386
23.3 样本总结 395
23.4 本章小结 395
第24章 unidbg补环境实战:设备风控 396
24.1 Android系统API补全策略 396
24.1.1 ActivityThread 398
24.1.2 android_id 399
24.2 目录获取 402
24.3 样本最后一个函数的调用 407
24.4 本章小结 416
第25章 unidbg补环境实战:
补环境加强 417
25.1 上文回顾 417
25.2 样本的框架搭建 417
25.3 补环境实操 420
25.3.1 getApplication环境
补充 420
25.3.2 无障碍服务的补环境 423
25.4 本章小结 437
第26章 unidbg补环境实战:
总结 438
26.1 补环境初始化 438
26.1.1 架构选择 438
26.1.2 进程名称初始化 439
26.1.3 处理器后端的设置 439
26.1.4 Android根目录设置 440
26.1.5 Android虚拟机创建 440
26.1.6 加载so 440
26.2 补环境适用场景 441
26.2.1 unidbg的报错 441
26.2.2 何时补环境 444
26.3 补环境的规范 450
26.3.1 通用规则 451
26.3.2 复杂类型的规则 452
26.4 本章小结 457
第四部分 反制与生产环境部署
第27章 Anti-unidbg系列:环境
变量检测 460
27.1 Linux中的环境变量 460
27.2 Android中的环境变量 462
27.2.1 查看和设置环境变量 462
27.2.2 常见环境变量说明 463
27.3 环境变量源码解析 465
27.3.1 Java层环境变量读取和
设置 466
27.3.2 Native层环境变量读取和
设置 468
27.3.3 情景模拟 469
27.4 unidbg如何设置环境
变量 470
27.5 本章小结 472
第28章 Anti-unidbg系列:xHook检测 473
28.1 xHook的基本使用 473
28.1.1 项目简介 473
28.1.2 项目编译 474
28.1.3 xHook API介绍 476
28.1.4 样本编写 478
28.2 xHook的原理阐述 479
28.2.1 文件编译和测试 479
28.2.2 出现的问题 482
28.2.3 ELF文件格式 482
28.2.4 Linker 486
28.2.5 重定向追踪 487
28.2.6 内存检索 489
28.2.7 跳转验证 491
28.3 xHook检测实现 492
28.3.1 获取ELF文件在内存中的
首地址 493
28.3.2 Linker的复写 495
28.4 unidbg xHook检测 506
28.5 补充Inline Hook检测 508
28.5.1 Inline Hook通用检测
思路 508
28.5.2 Inline Hook模块检测
思路 515
28.6 本章小结 516
第29章 Anti-unidbg系列:JNI层
常见函数处理 517
29.1 FindClass反制策略 517
29.1.1 FindClass介绍 517
29.1.2 FindClass基本使用 521
29.2 methodID反制策略 524
29.3 本章小结 528
第30章 Anti-unidbg系列:unidbg
常规检测总结 529
30.1 检测说明 529
30.2 基地址检测 530
30.3 JNI环境之JNI调用 530
30.4 JNI环境之类检测 530
30.5 文件描述符 532
30.6 uname 532
30.7 运行时间检测 534
30.8 检测Unicorn 534
30.9 本章小结 537
第31章 unidbg生产环境部署 538
31.1 Spring Boot框架的基本使用
方法 538
31.2 Spring Boot和unidbg
结合 542
31.3 unidbg-boot-server简介 548
31.3.1 简介 549
31.3.2 常规配置项说明 549
31.4 unidbg-boot-server项目
实例 549
31.4.1 项目演示 549
31.4.2 添加模拟执行 551
31.5 本章小结 555
Preface?前 言
写作背景
现在的App,只要是稍微对安全有一些要求的,都会把核心逻辑、加解密算法或者保护机制,比如一些反调试手段,使用NDK开发的方式写到Native库中,最终生成so文件。
so文件的逆向比Java层的DEX要困难很多,如果文件中还有比较严重的混淆或者花指令的话,可能连正常的反编译都成问题,更不用说查看它采用的是什么算法了。不仅如此,现在ARM平台上还出现了让算法完全消失的虚拟机保护(Virtual Machine Protect)技术,该技术通过自定义字节码的方式实现一套自己的CPU。如果不能理解这套虚拟机的运行流程,逆向算法便无从谈起。
下图为一个经过OLLVM强混淆的简单RC4算法,仅仅几行代码就能混淆出千头万绪、杂乱无章、面目全非的数万行伪代码。如果再嵌套几个手写的非标准算法,还原难度可以达到“地狱级”。
“兵来将挡,水来土掩。”幸运的是,随着技术的发展,可以应对这样场景的对抗方案出现了。正如AlphaGo在大战李世石时依赖暴力下棋法一样,我们也可以不还原某段算法,而是凭借现代计算机的超高算力,直接暴力执行这段算法。
在模拟执行的过程中,算法是黑盒,我们并不直接分析这个黑盒,而是直接让它运行,它需要什么我们就给它补充什么,以确保它能顺利地执行完算法,生成我们需要的结果。
这个模拟执行的框架就是unidbg。
本书特点
1)由浅至深。我们先让unidbg框架运行起来,比如能够加载so文件,完成基础的补环境,排除基本报错,支持Hook功能,执行so文件中的算法。待基本的使用没有问题之后,再进阶到原理部分,详解so文件是如何加载和运行的,以及内存、信号、虚拟机、系统调用等是如何模拟真实的Android系统环境的,带领大家实现一个类似框架。
2)授人以鱼,同时授人以渔。在使用unidbg框架的时候,各种报错千奇百怪,尤其是难以定位的内存问题。很多时候,在A处没有进行处理或者初始化,却在B处报错。此时如果不能进行全局综合分析,或者缺乏对so的初始化和函数调用流程的完整把握与清晰认知,那么我们将无从下手。因此在学习本书的过程中,更重要的是知识深度与广度的积累,只有真正理解并掌握unidbg的原理,高屋建瓴、把握全局,最终才能做到游刃有余。
3)内容翔实、丰富,实用性强。本书介绍unidbg的方方面面,从应用到原理,从案例到检测,不仅可以运行算法,还可以辅助算法还原,因此可以作为unidbg的操作宝典来学习、参考。
阅读对象
本书是一本理论与实战并举,全方位介绍unidbg的使用、原理及实现细节的著作,适合以下几类读者阅读:
移动应用安全方向的安全工程师。
计算机组成原理和软件模拟方向的应用开发者。
自动化领域的爬虫工程师。
反欺诈/风控领域的安全工程师。
如何阅读本书
本书共31章,分为4部分。
第一部分(第1~3章) 进入unidbg的世界。通过阅读该部分,读者可以简单了解unidbg的基础知识,通过unidbg执行一些基本的操作,包括环境准备、so文件加载、简单补环境、Hook和Patch的方法等。
第二部分(第4~15章) unidbg原理。由于unidbg主要是用Java写的,代码比较通俗易懂,且核心原理参照的是Android系统,可以说是一个缩小版AndroidLite,因此如果有哪部分看不懂,可以直接参考Android源码。读完该部分,读者会对unidbg核心原理有比较完整的认识。
第三部分(第16~26章) 模拟执行与补环境实战。该部分主要介绍unidbg实战中的各种具体技术案例,如I/O重定向、Debugger自吐、指针参数与Debugger、魔改Base64还原、使用unidbg动态分析内存中的数据、使用unidbg主动调用fork进程,并对补环境中的补环境入门、标识记录、设备风控、补环境加强等进行分析,指导读者编写实际的补环境代码,更好地将理论知识运用于实践。
第四部分(第27~31章) 反制与生产环境部署。该部分介绍环境变量检测、xHook框架检测、JNI层常见函数处理等,并对常规检测进行总结,还介绍通过检测之后如何把so部署到x86服务器上运行。该部分是大家最关心的批量生产与对抗的内容,也是最敏感的支持风控数据与决策的内容,对于打击黑灰产、遏制网络犯罪有着非常积极的意义。
资源与勘误
本书相关资源也会上传到该地址,读者可自行下载、查阅。
致谢
感谢我的父母。感谢凯R开源unidbg这个功能如此强大的框架。感谢bxl、冻鱼战神、Forgo7ten,感谢看雪学院和段钢先生,感谢寒冰冷月、imyang、灰翔的猫,感谢白龙、寄予蓝,感谢葫芦娃、非虫,感谢52pojie、国防科技大学,是你们的支持和帮助让这本书顺利
面市!
📑 Table of Contents
- 第一部分 进入unidbg的世界
- 第1章 unidbg环境准备与快速上手
- 第2章 unidbg模拟执行初探
- 第3章 unidbg补环境、Hook与Patch
- 第二部分 unidbg原理
- 第4章 ELF文件执行视图解析
- 第5章 Unicorn模拟器与so加载
- 第6章 AndroidEmulator与JNI交互
- 第7章 DalvikVM与Memory模块
- 第8章 Hook机制详解
- 第三部分 补环境与模拟执行实战
- 第9章 I/O重定向与Debugger
- 第10章 魔改Base64还原
- 第11章 动态分析内存数据
- 第12章 主动调用fork进程
- 第四部分 反制与生产环境部署
- 第13章 环境变量检测与绕过
- 第14章 xHook框架检测
- 第15章 JNI层处理与服务器部署