firida官网的问题:Can not load Module from x86 Emulator · Issue #1377 · frida/frida (github.com)
官方解决方案:使用真实的物理手机!
我的解决方案:继续用模拟器!!!!肝都痛了才找到解决方案
环境介绍:
- 模拟器雷电、夜神模拟器,安卓版本7.0~9.0都存在的问题,这些模拟器只能模拟x86架构
- 目标apk,存在Native层方法,但是apk只携带了arm版的so文件,不存在x86架构的so文件
- 这个arm的so文件名为libpp.so
- 模拟器雷电、夜神模拟器自带功能,将arm架构汇编转为x86汇编的功能
问题描述:
- 我使用常规的Hook-Native的方法进行hook,Module.findBaseAddress返回为空null
- 使用Module.findExportByName进行查找返回为空null
- 使用Process.enumerateModules遍历所有模块名,也未发现libpp.so文件
- 但是程序可以正常运行!!!
检查hook失败的原因,无非就算上面这些找模块的方法都存在缺陷,因为libpp.so文件肯定是被加载进了程序不然apk根本跑不起来的!!!
1. 检查模块是否存在以及无法frida-Native-hook的原因
使用frida和adb来检查模块是否存在
查看apk是否正常运行:
frida-ps -U
adb shell ps
都可以看见程序正常运行!
查看apk的进程分配的内存空间!!
PS D:\CTF_Study\Reverse\攻防世界\引导模式\难度6\pingpong> adb shell
star2qltechn:/ $ su root
:/ # cat /proc/5167/maps
00010000-00012000 rw-p 00000000 00:00 0
03344000-0b344000 ---p 00000000 00:00 0
0b344000-0b345000 r--p 00000000 08:02 428 /system/lib/arm/nb/libdl.so
0b345000-0b346000 r--p 00000000 08:02 428 /system/lib/arm/nb/libdl.so
0b346000-0b347000 r--p 00000000 00:00 0
0b347000-0b444000 ---p 00000000 00:00 0
0b444000-0b445000 r--p 00000000 08:02 434 /system/lib/arm/nb/ld-android.so
0b445000-0b446000 r--p 00000000 08:02 434 /system/lib/arm/nb/ld-android.so
0b446000-0b447000 r--p 00000000 00:00 0
0b447000-0b544000 ---p 00000000 00:00 0
0b544000-0b548000 r--p 00000000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
0b548000-0b549000 r--p 00003000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
0b549000-0b54a000 rw-p 00004000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
0b54a000-0b644000 ---p 00000000 00:00 0
0b644000-0b664000 r--p 00000000 08:02 423 /system/lib/arm/nb/libm.so
0b664000-0b665000 r--p 00000000 00:00 0
0b665000-0b666000 r--p 00020000 08:02 423 /system/lib/arm/nb/libm.so
0b666000-0b667000 rw-p 00021000 08:02 423 /system/lib/arm/nb/libm.so
0b667000-0b744000 ---p 00000000 00:00 0
...
0d3e3000-0d3e5000 rw-p 00000000 00:00 0 [anon:.bss]
0d3e5000-0d3e8000 rwxp 00000000 00:00 0
0d3e8000-11348000 rwxp 00000000 00:00 0 [anon:Mem_0x20000000]
11348000-1134c000 rwxp 00000000 00:00 0
12c00000-22c00000 rw-p 00000000 00:05 8647 /dev/ashmem/dalvik-main space (region space) (deleted)
56555000-56559000 r-xp 00000000 08:02 1586 /system/bin/app_process32
5655a000-5655b000 r--p 00004000 08:02 1586 /system/bin/app_process32
5655b000-5655c000 rw-p 00000000 00:00 0 [heap]
70a69000-70c8e000 rw-p 00000000 08:12 917520 /data/dalvik-cache/x86/system@framework@boot.art
70c8e000-70ca4000 r--p 00225000 08:12 917520 /data/dalvik-cache/x86/system@framework@boot.art
70ca4000-70d9b000 rw-p 00000000 08:12 917526 /data/dalvik-cache/x86/system@framework@boot-core-libart.art
70d9b000-70dad000 r--p 000f7000 08:12 917526 /data/dalvik-cache/x86/system@framework@boot-core-libart.art
70dad000-70dde000 rw-p 00000000 08:12 917532 /data/dalvik-cache/x86/system@framework@boot-conscrypt.art
70dde000-70de1000 r--p 00031000 08:12 917532 /data/dalvik-cache/x86/system@framework@boot-conscrypt.art
70de1000-70e0e000 rw-p 00000000 08:12 917538 /data/dalvik-cache/x86/system@framework@boot-okhttp.art
....
确实发现了libpp.so文件确实存在于内存空间!! 但为啥frida找不到呢?
0b544000-0b548000 r--p 00000000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
0b548000-0b549000 r--p 00003000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
0b549000-0b54a000 rw-p 00004000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
发现frida无法遍历到so文件的原因:
使用frida遍历模块试试:
发现确实没有这个libpp.so文件,原因是因为frida遍历模块是通过程序基址开始的,而这个arm架构的so文件被加载在了,程序基址上面的位置!
- frida开始遍历的地址是:
56555000-56559000 r-xp 00000000 08:02 1586 /system/bin/app_process32
- 而arm的so文件的地址是:
0b544000-0b548000 r--p 00000000 08:12 918103 /data/app/com.geekerchina.pingpongmachine-4SDV24S62H_wjn0f4-HD8A==/lib/arm/libpp.so
这里就是frida遍历到的数据:
app_process32
libandroid_runtime.so
libbinder.so
libcutils.so
libhwbinder.so
liblog.so
libnativeloader.so
...
linux-vdso.so.1
linker
用来遍历模块的js脚本!
setTimeout(function () {
Java.perform(function () {
//遍历模块找基址
Process.enumerateModules({
onMatch: function (exp) {
if (exp.name) {
send('enumerateModules find');
send(exp.name + "|" + exp.base + "|" + exp.size + "|" + exp.path);
send(exp);
return 'stop';
}
},
onComplete: function () {
send('enumerateModules stop');
}
});
}
},2000);
使用IDA动态调试和adb来检查模块是否存在
教程:
- IDA调试Android的so文件(SWPU 2019-easyapp)-CSDN博客
- ARM学习之 动态调试ida_ida arm版本-CSDN博客
去动态调试之后发现IDA确实可以找到模块但是会不断报错,无法调试,大概是因为模拟器已经将arm转为x86架构的汇编代码,导致ida调试失败!!!
无法frida-Native-hook的原因
原因是:
- 模拟器的架构是x86的所以会对arm架构的so文件进行转译成x86架构的
- frida无法找到模块的原因是因为arm的so文件并未跟随apk进程的创建而创建,而是在调用之后才被转译进入内存中,而且是重新开辟了一片空间来存储arm的so文件的代码
- IDA之所以可以找到模块是由于它调用的是
cat /proc/<pid>/maps
来查找模块的,而且arm的so文件也是最后才被加载的,无法调试的原因是因为arm架构的指令已经被转译成了x86架构导致一直报错 - 最后使用frida通过手动方法查看libpp.so文件的基址去调用方法也报错了,大概也是因为arm架构的指令已经被转译成了x86架构导致一直报错
2. 解决方案使用Android官方提供的AVD Manager模拟器下载arm架构模拟器
教程: Android SDK Manager 和 AVD Manager使用(进行安卓虚拟机的配置)_sdk manager是什么-CSDN博客
下载链接:AndroidDevTools - Android开发工具 Android SDK下载 Android Studio下载 Gradle下载 SDK Tools下载
只有安卓7.0才有arm架构的,所以下载这个模拟器!
下面可以运行程序检查是否存在libpp.so文件了!
D:\CTF_Study\Reverse\攻防世界\引导模式\难度6\pingpong>adb shell
generic_arm64:/ $ su
generic_arm64:/ # cat /proc/2219/maps
12c00000-12e06000 rw-p 00000000 00:04 2105 /dev/ashmem/dalvik-main space (deleted)
12e06000-15c00000 ---p 00206000 00:04 2105 /dev/ashmem/dalvik-main space (deleted)
22c00000-22c01000 rw-p 00000000 00:04 2106 /dev/ashmem/dalvik-main space 1 (deleted)
22c01000-25c00000 ---p 00001000 00:04 2106 /dev/ashmem/dalvik-main space 1 (deleted)
70411000-70909000 rw-p 00000000 fe:20 35250 /data/dalvik-cache/arm/system@framework@boot.art
e9618000-e9678000 rw-p 00000000 00:04 2324 /dev/ashmem/dalvik-large object space allocation (deleted)
e9678000-e9681000 rw-p 00000000 00:04 2319 /dev/ashmem/dalvik-large object space allocation (deleted)
e9684000-e9688000 r-xp 00000000 fe:20 7128 /data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so
e9688000-e9689000 r--p 00003000 fe:20 7128 /data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so
e9689000-e968a000 rw-p 00004000 fe:20 7128 /data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so
e968a000-e968e000 rw-p 00000000 00:04 2317 /dev/ashmem/dalvik-large object space allocation (deleted)
....
成功找到:
e9684000-e9688000 r-xp 00000000 fe:20 7128 /data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so
e9688000-e9689000 r--p 00003000 fe:20 7128 /data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so
e9689000-e968a000 rw-p 00004000 fe:20 7128 /data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so
进行frida也可以找到目标文件了!!!
成功了!!剩下的就是爆破了
D:\CTF_Study\Reverse\攻防世界\引导模式\难度6\pingpong>frida -U -f com.geekerchina.pingpongmachine -l ./NHook.js
____
/ _ | Frida 16.1.11 - A world-class dynamic instrumentation toolkit
| (_| |
> _ | Commands:
/_/ |_| help -> Displays the help system
. . . . object? -> Display information about 'object'
. . . . exit/quit -> Exit
. . . .
. . . . More info at https://frida.re/docs/home/
. . . .
. . . . Connected to Android Emulator 5554 (id=emulator-5554)
Spawned `com.geekerchina.pingpongmachine`. Resuming main thread!
[Android Emulator 5554::com.geekerchina.pingpongmachine ]-> start
message: {'type': 'send', 'payload': 'enumerateModules find'} data: None
message: {'type': 'send', 'payload': 'libpp.so|0xe9684000|24576|/data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so'} data: None
message: {'type': 'send', 'payload': {'name': 'libpp.so', 'base': '0xe9684000', 'size': 24576, 'path': '/data/app/com.geekerchina.pingpongmachine-1/lib/arm/libpp.so'}} data: None
message: {'type': 'send', 'payload': 'enumerateModules stop'} data: None
message: {'type': 'send', 'payload': 'soAddr:0xe9684000'} data: None
message: {'type': 'send', 'payload': 'findExportByName ping():0xe9685309'} data: None
message: {'type': 'send', 'payload': 'findExportByName ping():0xe9685309'} data: None
message: {'type': 'send', 'payload': 'findExportByName pong():0xe9685565'} data: None
message: {'type': 'send', 'payload': 'findExportByName pong():0xe9685565'} data: None