app shield 算法分析 13 / 13
- app shield 参数加密破解|unidbg
- shield 参数加密破解 - python 执行 c++
- app sessionid searchid|算法分析
- app sessionid searchid|算法还原
- pc timestamp2 加密参数分析破解
- app shield so 加密算法分析破解还原|前言
- app shield so 加密算法分析破解还原|so 算法简单分析
- app shield so 加密算法分析破解还原|aes 算法分析破解
- app shield so 加密算法分析破解还原|md5 算法分析破解
- app shield so 加密算法分析破解还原|xydata 算法分析破解
- app shield so 加密算法分析破解还原|总结
- app hmac 参数分析
- 7261 版 shield 算法分析破解
前言
下载地址: https://www.wandoujia.com/apps/6233739/history_v7261002
7.26.1 版本(分析的时候还是最新版,第二天又更新了一个版本,吐了)
参考文章: https://bbs.pediy.com/thread-269214.htm
内容已被删除,有需要的在群里吆喝一声会有大佬分享的
加密函数定位
新版的小黄书没有 shield.so
了,先使用 frida hook native
看一下在哪里
查看日志在 libxyass.so
里,注意这个 so
是加密的,需要先修复
dump libxyass.so
上面的参考文章中使用的是 ida + 动态调试修复
,奈何本人太菜鸡只能使用大佬写好的 dump
脚本来修复了
执行 python3 dump_so.py libxyass.so
,修复完成后就可以看到大部分的逻辑了
unidbg
之前龙哥写的脚本复制过来就能用改改 apk so
即可
随便找个接口验证一下,结果相同
算法还原
shield
加密算法是 aes + hmac-md5 + rc4
其中 aes + md5
都是魔改的 hmac + rc4
是标准的,咱们一步步跟之前的老版本的算法比较一下,看看哪里有变动
String traceFile = "";
PrintStream traceStream = null;
try {
traceStream = new PrintStream(new FileOutputStream(traceFile), true);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
emulator.traceCode(module.base, module.base + module.size).setRedirect(traceStream);
先使用 unidbg trace
所有的指令,保存到文件中
aes 算法
aes
算法是根据 hmac, device_id
进行解密,结果会当做 hmac-md5
的 key
。hmac
算法会使用 0x36, 0x5c
先跟 key
进行异或
在 trace log
里直接全局搜索,0x36
关键词,找到 eor
异或指令
ida
里跳过去,这里的逻辑跟老版本 6.87
的看起来差不多
查看汇编指令,这里的 r2
就是 key
在这里 hook, trace
都是可以的
emulator.traceCode(module.base + 0x2D4A0, module.base + 0x2D4A0).setRedirect(traceStream);
博主这里是 trace
方式
查看 trace log
这里 aes
解密的结果全部 trace
出来
在跟 python
还原的算法对比一下,结果相同,新版的 aes
算法并没有变动
hmac-md5 算法
同理先去 trace log
里搜索 md5
算法常量
ida
里跳过去,直接定位到 md5 transform
函数
public void inlineHookMd5Result() {
emulator.getBackend().hook_add_new(new CodeHook() {
@Override
public void onAttach(UnHook unHook) {
}
@Override
public void detach() {
}
@Override
public void hook(Backend backend, long address, int size, Object user) {
if (address == (module.base + 0x2E082)) {
Arm32RegisterContext ctx = emulator.getContext();
long lr = ctx.getLR();
System.out.println("md5 update a result: 0x" + Long.toHexString(lr));
}
}
}, module.base + 0x2E082, module.base + 0x2E082, null);
emulator.getBackend().hook_add_new(new CodeHook() {
@Override
public void onAttach(UnHook unHook) {
}
@Override
public void detach() {
}
@Override
public void hook(Backend backend, long address, int size, Object user) {
if (address == (module.base + 0x2E09C)) {
Arm32RegisterContext ctx = emulator.getContext();
long r2 = ctx.getR2Long();
System.out.println("md5 update b result: 0x" + Long.toHexString(r2));
}
}
}, module.base + 0x2E09C, module.base + 0x2E09C, null);
emulator.getBackend().hook_add_new(new CodeHook() {
@Override
public void onAttach(UnHook unHook) {
}
@Override
public void detach() {
}
@Override
public void hook(Backend backend, long address, int size, Object user) {
if (address == (module.base + 0x2E0A4)) {
Arm32RegisterContext ctx = emulator.getContext();
long r3 = ctx.getR3Long();
System.out.println("md5 update c result: 0x" + Long.toHexString(r3));
}
}
}, module.base + 0x2E0A4, module.base + 0x2E0A4, null);
emulator.getBackend().hook_add_new(new CodeHook() {
@Override
public void onAttach(UnHook unHook) {
}
@Override
public void detach() {
}
@Override
public void hook(Backend backend, long address, int size, Object user) {
if (address == (module.base + 0x2E0AA)) {
Arm32RegisterContext ctx = emulator.getContext();
long r7 = ctx.getR7Long();
System.out.println("md5 update d result: 0x" + Long.toHexString(r7));
}
}
}, module.base + 0x2E0AA, module.base + 0x2E0AA, null);
}
先 hook
最后 abcd
的值
发现 python
的结果跟 unidbg
并不同,看来新版的 md5
算法改了
这里具体是哪里改了,就需要一步步排查了,具体过程就不叙述了,最终排查到是修改了 常数组 T(正弦函数表)
再来跑一下,结果相同
rc4 算法
这一部分是没有修改的,老版本的算法拿来直接用