Android APK反编译详解
使用工具:
CSDN上下载地址:
apktool (资源文件获取) 下载
dex2jar(源码文件获取) 下载
jd-gui (源码查看) 下载
Android反编译整合工具包(最新) 下载
官方最新版本下载地址:
apktool(google code)
dex2jar(google code)
工具介绍:
apktool
作用:资源文件获取,可以提取出图片文件和布局文件进行使用查看
dex2jar
作用:将apk反编译成java源码(classes.dex转化成jar文件)
jd-gui
作用:查看APK中classes.dex转化成出的jar文件,即源码文件
1. APK的内部结构
APK的全称是AndroidPackage,它是Android安装包。APK文件其实是zip格式,但后缀名被修改为apk,通过UnZip解 压后,可以看到Dex文件,Dex是Dalvik VM executes的全称,即Android Dalvik执行程序,并非Java ME的字节码而是Dalvik字节码。
下面以HelloWorld为例讲解Android应用程序的文件结构及打包过程。
1.1 Android应用程序文件结构
现在编写一个HelloWorld应用程序已经变得非常简单的,在eclipse集成开发环境中只需要点击下一步基本就可以完成此应用程序。图1.1即为由eclipse集成开发环境生成的HelloWorld应用程序的文件结构图。
图1.1 HelloWorld文件结构图
其中,
Src java源文件目录
Gen 自动生成的目录,其中包括了著名的R.java
Android 2.3.3 该应用程序依赖的android SDK包。
Assets 存放原生文件,这个目录保存的文件可以打包在程序里。和res的不同点是,android不为assets下的文件生成ID,如果使用assets下的文件,需要指定文件的路径和文件名。
Bin Java编译输出的路径
Res 存放程序所需要的资源文件,也就是非Java的文件。常见的目录有,
(1)res/animator/ :XML文件,定义动画属性
(2)res/anim/ :XML文件,它们被编译进逐帧动画(frame by frame animation)或补间动画(tweened animation)对象
(3)res/color/:XML文件,定义颜色状态的列表
(4)res/layout/:存放被编译为屏幕布局(或屏幕的一部分)的XML文件
(5)res/menu/:XML文件,用来定义应用的菜单
(6)res/drawable/:存放图片文件,如.png, .jpg, .gif等。放在这里的图像资源可能会被aapt(android assert packaging tool,android资源打包工具)自动地进行无损压缩优化。如果你不想图片被压缩改变,请把图像文件放在 res/raw/目录下,这样可以避免被自动优化。
(7)res/raw/:直接复制到设备中的任意文件,它们无需编译
(8)res/values/:存放可以被编译成很多种类型的资源文件, XML 格式的。常见的文件有:
array.xml :定义数组
colors.xml :定义color drawable和颜色的字符串值。
dimens.xml : 定义尺寸值(dimension value)。
strings.xml :定义字符串(string)值。
styles.xml:定义样式(style)对象。
(9)res/xml/:任意的XML文件,在运行时可通过调用Resources.getXML()读取。
AndroidManifest.xml
这个清单给Android系统提供了关于这个应用程序的基本信息,系统在运行任何程序代码之前必须知些信息。AndroidManifest.xml主要包含以下功能:
(1)命名应用程序的 Java 包,这个包名用来唯一标识应用程序
(2)描述应用程序的组件:活动,服务,广播接收者,以及组成应用程序的内容提供器;对实现每个组件和公布其能力(比如,能处理哪些意图消息)的类进行命名。这些声明使得 Android系统了解这些组件以及在什么条件下可以被启动;
(3)决定应用程序组件运行在哪个进程里面
(4)声明应用程序所必须具备的权限,用以访问受保护的部分 API,以及和其它应用程序交互;
(5)声明应用程序其他的必备权限,用以组件之间的交互;
(6)列举测试设备Instrumentation类,用来提供应用程序运行时所需的环境配置和其他信息,这些声明只是在开发和测试阶段存在,发布前将被删除
(7) 声明应用程序所要求的Android API的最低版本级别;
(8)列举application所需要链接的库
Proguard-project.txt
Android代码混淆器,用于加大反编译的难度。详细描述请见
http://developer.android.com/tools/help/proguard.html
Project.properties
定义一些项目的基本属性。
1.2 打包过程
图1.2为Android应用程序打包流程图。从图中我们可以看到,
a. Java源文件通过javac编译成class, 然后class通过dx.bat生成虚拟机运行的二进制程序。
b. 资源文件通过appt打包。
c. 打包好的源文件及资源文件通过apkbuilder生成未签名的APK。
d. 通过keytool生成key
e. Jarsigner为未签名的APK生成签名。
至此,整个APK打包过程已经完成。
2. APK的反汇编流程
想要探究APK内部结构,就不得不对其进行逆向工程了。图2.1为Android应用程序逆向工程流程图。正如本文开头所述,APK文件其实是 zip格式,因此可以直接通过unzip工具进行解压。解压后主要包含资源文件及dex,注意这些资源文件都是压缩过的,需要通过特殊工具解析才可使用。
从图2.1我们可以看到,实际上可以通过apktool + dex2jar + xjad/JD-GUI实现对APK的逆向工程。下面我们就一一讲解各项工具的使用方法, 解开APK的今生之谜。
图2.1 Android应用程序逆向工程流程图
2.1 APK的内部结构
APK文件其实是zip格式,但后缀名被修改为apk,通过UnZip解压后,可以得到APK文件结构。
2.2 APK的逆向工程
下面我们就开始激动人心的APK逆向工程吧。
1.2.1 资源文件
如果直接解压APK文件,那么对应的资源文件都是经过某种格式压缩过的。因此我们需要一些工具来解析这些文件。Apktool是一个非常棒的解析资源文件的工具,实际上它还可以将dex文件转换成smoli格式的文件。
Ø Apktool
官网: http://code.google.com/p/android-apktool/
在apktool官网上,有两个包需要下载,如果在windows上反编译,下载apktool-install-windows-xx.tar.bz2及apktoolxx.tar.bz2即可。如果在linux上反编译,则下载apktool-install-linux-xx.tar.bz2及apktoolxx.tar.bz2。
apktool运行格式:
apktool d xxx.apk output 反编译xxx.apl到文件夹output
apktool b output 从文件夹output重构apk,输出到output/dist/out.apk
反编译之后的文件如下所示。其中xml文件都已经成功反编译,而dex文件被反编译成smali格式。这种语法很难读懂,我们可以通过其他工具来反编译dex文件。在apktool的官网上,我们看到有如果通过smali来debug apk。看上去还有点意思。http://code.google.com/p/android-apktool/wiki/SmaliDebugging
1.2.2 可执行文件
经过unzip解压之后的APK会生成一个class.dex文件。
Ø dex2jar
官网:https://code.google.com/p/dex2jar/
运行 dex2jar.bat classes.dex
生成 classes_dex2jar.jar
Ø JD-GUI
官网:http://java.decompiler.free.fr/?q=jdgui
用JD-GUI打开dex2jar生成的classes_dex2jar.jar后,就可以看到java源文件啦。如下图所示。
Ø Apkdb
官网:http://code.google.com/p/android-apkdb/
《Android APK+Dex文件反编译及回编译工具》简称:APKDB。是一款,针对Android OS系统APK程序,直接反编译修改的工具。APKDB集合了当今最强悍,最犀利的APK及Dex文件编译工具;正常安装后,它直接在【鼠标右键】创建快捷菜单;非常方便汉化工作者,对APK或Dex文件进行简易的反编译回编译操作。
反编译流程:
一、apk反编译得到程序的源代码、图片、XML配置、语言资源等文件
下载上述工具中的apktool,解压得到3个文件:aapt.exe,apktool.bat,apktool.jar ,将需要反编译的APK文件放到该目录下,
打开命令行界面(运行-CMD) ,定位到apktool文件夹,输入以下命令:apktool.bat d -f test.apk test
(命令中test.apk指的是要反编译的APK文件全名,test为反编译后资源文件存放的目录名称,即为:apktool.bat d -f [apk文件 ] [输出文件夹])
说明获取成功,之后发现在文件夹下多了个test文件,点击便可以查看该应用的所有资源文件了。
如果你想将反编译完的文件重新打包成apk,那你可以:输入apktool.bat b test(你编译出来文件夹)便可,效果如下:
之后在之前的test文件下便可以发现多了2个文件夹:
build
dist(里面存放着打包出来的APK文件)
Apk反编译得到Java源代码
下载上述工具中的dex2jar和jd-gui ,解压
将要反编译的APK后缀名改为.rar或则 .zip,并解压,得到其中的额classes.dex文件(它就是java文件编译再通过dx工具打包而成的),将获取到的classes.dex放到之前解压出来的工具dex2jar-0.0.9.15 文件夹内,
在命令行下定位到dex2jar.bat所在目录,输入dex2jar.bat classes.dex,效果如下:
在改目录下会生成一个classes_dex2jar.jar的文件,然后打开工具jd-gui文件夹里的jd-gui.exe,之后用该工具打开之前生成的classes_dex2jar.jar文件,便可以看到源码了,效果如下:
被混淆过的效果图(类文件名称以及里面的方法名称都会以a,b,c....之类的样式命名):
三、 图形化反编译apk(本人未使用过)
上述步骤一、二讲述了命令行反编译apk,现在提供一种图形化反编译工具:Androidfby
首先,下载上述反编译工具包,打开Androidfby目录,双击Android反编译工具.exe,就可以浏览打开要反编译的apk
通过反编译,你可以获知该应用用到了什么第3方的库文件,它的代码是如何编写的等等。
然而,如果该APK进行了混淆处理,那么你看到的类文件名称以及里面的方法名称都会以a,b,c....之类的样式命名,所以你可以想找到你所想得知的界面代码可能会十分费劲,找到了代码可能看起来也会很费劲,可是一个大体的思路会获得,有了这个思路,你就可以自己去尝试了。
本人曾经想写一个类似唱吧的名人界面布局,可是当初第一次接触不知道如何去写,进进行了反编译,即使他的那个代码是混淆过的,我也看出来他是通过LISTVIEW的TYPE设定不同的ITEM布局实现了。可能好多引用都是采用重写VIEW来实现效果,你可以得到他的大体思路对你的开发有益无害。
反编译失败报错:
1 Exception in thread main brut.androlib.androlibexception multiple resources
解决办法:下载最新的apktool,在google官网上。测试,如果未成功采取第二种方法
2 Exception in thread main org.jf.dexlib.util.exceptionwithcontext index
在cmd命令行,反编译的命令改为apktool.bat d -s即可。其他相同,-s代表只反编译xml文件。