反编译APK

余生长醉 提交于 2019-12-01 08:02:47

  逆向的准备

这里介绍下关于 Android 的逆向准备:

  • Android 真机或模拟器(最好是真机)
  • 安装 Android 5.0 或 6.0 版本
  • Fiddler、Charles 等抓包工具
  • Jadx、ApkTool 等反编译工具
  • dumpDex、FDex2 等脱壳工具
  • Java、Android 开发基础知识
  • Xposed 框架开发基础知识

    逆向步骤

  1.定义目标

  2.反编译

  3.分析代码

 

  反编译

这里使用的反编译工具是 Jadx,它可以将 APK 直接反编译成 Java 代码,并且具有 GUI 界面方便操作

通过包名和一些代码分析,确定是被 360 加固后,接下来需要尝试脱壳。

脱壳使用的是 FDex2,这是一款基于 Xposed 框架的 Hook 插件,对 360 加固比较有效。它的原理是 Hook ClassLoader,然后通过反射调用 getDex 方法获取 Dex 对象并导出,这里的 Dex 就是 APP 真正执行的部分。当然并不是所有加固都可以被 Hook 到,更多脱壳手段还需要进阶研究。

FDex2 使用方式很简单,在 Xposed 框架里激活后,选择目标 APP,然后重新打开 APP 后,被捕获的 Dex 文件会被保存下来

Dex 是什么?简单地说,在 APK 构建过程中,Java 代码编译后产生的 class 文件,需要再转化成 Dex 文件,才能被 Android 虚拟机运行。

因此我们得到的 Dex 文件,就可以再次反编译成 Java 代码,我们还是使用 Jadx,它同样支持 Dex 格式。

由于 Dex 有体积限制,会被分包,如上图我们导出了不止一个文件,可以依次加载它们,通过搜索目标 API 的关键词,来找到目标代码块

代码一般都会被反混淆,变量和方法名都是 a b c d 这样,然后搜索一个方法名,会发现有一万个同名的变量。还好 Jadx 内置了反混淆,开启后变量和方法被重命名为唯一编号,这样搜索时就不会有重名的情况了。

之后我们通过 Jadx 将代码导出成 Gradle 项目,借助 IDEA 的强大功能开始进行代码分析。

  分析代码

由于大部分方法都是被重命名的,导致可读性严重下降,无法推测每个方法到底是什么功能

我们只要遵循一些技巧,就可以大幅减少工作量。由于分析过程比较繁琐,这里就不结合具体代码了,只做一些理论总结:

  1. 从目标 API 开始入手,跟踪执行流程: 比如我们刚才已经搜索到关键词代码,那就从那一行开始,通过 IDEA 查看方法功能,可以一路向下点击。
  2. 只分析涉及代码块,缩小分析范围: 请求过程通常会构建 Request 对象,那参数加密一定就在构建对象之前,我们只要找到构建 Request 对象的代码,然后查看加密参数被传入之前都经过了怎样的处理,其他代码全部无视。
  3. 将部分代码块复制出来进行执行: 虽然反编译的项目代码无法被整体执行,但对于冗长难懂的方法代码,我们可以连同相关代码一起复制到一个新项目中,进行编译执行,方便我们调试。
  4. 尝试搜索一些关键词: 代码并不会所有都被混淆,可以尝试全局搜索一些关键词。比如 Java 常用的加密算法,我们可以搜索 RSA、AES、MD5、Encrypt、public_*key 这些关键词和正则匹配,能搜到再好不过了。

当你找到了加密方法,那么可以复制出来独立执行,然后自己构建参数传入加密,通过模拟请求,看接口是否正常返回。

需要注意,如果不能正常请求,并不一定是你找错了地方,也有可能代码本身有误,反编译的代码是有几率会出现这种情况的,导致你执行的和 APK 执行的结果不同。遇到这种情况,只能通过其他手段来修正代码,如阅读 Smali 代码、通过 Hook 等手段。

  逆向之后

完成代码分析后,恭喜你已经成功完成一次逆向,接下来就可以实现一些功能,比如模拟登录请求。建议直接使用 Java 代码,因为大部分加密用的是 Java 内置的 RSA / AES 加密算法,其他语言的第三方库实现并不充分。

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!