内容简介:分析过apkChecker之后,很自然的会想起android studio中的APK分析功能,把一个APK文件丢到IDE里面,会自动分析出里面各种文件的信息。官网上也有相关说明——通过官网上的说明,可以知道相关的命令行工具先体验下如何使用。找了一个RecyclerView的Adapter代理开源库
分析过apkChecker之后,很自然的会想起android studio中的APK分析功能,把一个APK文件丢到IDE里面,会自动分析出里面各种文件的信息。官网上也有相关说明—— Analyze your build with APK Analyzer 。从黑盒上讲,两个 工具 都是通过APK文件的输入,获取一堆相关的分析结果出来,那么这两个工具在具体实现上有哪些异同,在同一个功能点上使用了哪些分析工具,整体上的功能对比是什么样的呢。
通过官网上的说明,可以知道相关的命令行工具 apkanalyzer 。既然可以使用命令行工具实现相关的分析功能,那么AS IDE上的功能对应的底层实现,也逃不掉这个命令行工具了。大致根据文档翻一下这个命令工具的功能如下:
- 展示APK文件属性
- 简要信息(application ID,版本号,版本名)
- 大小、需要的features
- 两个APK文件对比
- 展示APK文件的整体结构
- APK内部文件结构树
- 内部文件内容
- 展示manifest文件信息
- 获取dex文件信息
- 打印dex文件列表
- 打印dex文件中的方法数
- 打印dex文件中的类、包关系树
- 打印dex中某个类、方法的smali代码【m】
- 展示res文件夹和resources.arsc中的资源文件信息
- 打印定义在资源表中的包列表
- 查询指定类型的资源配置列表
- 根据配置、名称和类型获取资源值
- 根据配置和类型获取资源名列表
- 把二进制XML文件的转换成可读的XML文件打印出来【m】
先体验下如何使用。找了一个RecyclerView的Adapter代理开源库 AdapterDelegates 打出来的APK文件做测试。前面三个基本就是把APK文件解压后能获取到的数据,当然其中有解析二进制的manifest文件的功能。这里主要看对dex和resource文件的解析。
dex
-
打印文件列表,很容易理解,即打印出APK文件中所有dex文件的文件名。也是解压后就能看到的信息
lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h dex list app-debug.apk classes.dex
-
打印指定dex中的方法数,这个就需要解析dex文件中的方法内容了
lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h dex references app-debug.apk classes.dex 19807
-
打印APK中的类、包关系
如果不指定具体的参数,这个指令输出结果很大。使用重定向的方法把输出结果放到文件中。
lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h dex packages app-debug.apk > ./packages_result.txt
可以看到,APK文件也就1.8M,但是其中所有的类/包关系信息会输出3.2M的纯文本内容。打开输出文件,随便找一个开源代码中的类作为关键字,比如AbsListItemAdapterDelegate,可以看到文件输出形式是这样的:
P d 125 135 16.1KB com.hannesdorfmann.adapterdelegates3
P d 66 76 9.4KB com.hannesdorfmann.adapterdelegates3.sample
P d 41 41 4.5KB com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates
C d 7 7 645B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate
M d 1 1 80B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate(android.app.Activity)
M d 1 1 78B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate boolean isForViewType(com.hannesdorfmann.adapterdelegates3.sample.model.DisplayableItem,java.util.List,int)
M d 1 1 74B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate boolean isForViewType(java.lang.Object,java.util.List,int)
M d 1 1 105B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate void onBindViewHolder(com.hannesdorfmann.adapterdelegates3.sample.model.Snake,com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate$SnakeViewHolder,java.util.List)
M d 1 1 76B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate void onBindViewHolder(java.lang.Object,android.support.v7.widget.RecyclerView$ViewHolder,java.util.List)
M d 1 1 64B com.hannesdorfmann.adapterdelegates3.sample.adapterdelegates.SnakeListItemAdapterDelegate android.support.v7.widget.RecyclerView$ViewHolder onCreateViewHolder(android.view.ViewGroup)
根据文档,每行的每个输出格式如下:
Example output (type / state / defined methods / referenced methods / byte size / name)
-
打印dex中某个类、方法的smali代码。这就涉及到把dex中的某个类反编译成smali格式的代码。从上面的输出结果中选一个类,试一下结果:
lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h dex code --class com.hannesdorfmann.adapterdelegates3.AbsListItemAdapterDelegate app-debug.apk > ./class_result.txt
某个类的话还好,只有几KB大小,里面还包括文件本身的成本。截取一段smali瞧瞧:
.class public abstract Lcom/hannesdorfmann/adapterdelegates3/AbsListItemAdapterDelegate; .super Lcom/hannesdorfmann/adapterdelegates3/AdapterDelegate; .source "AbsListItemAdapterDelegate.java" # annotations .annotation system Ldalvik/annotation/Signature; value = { "<I:TT;T:", "Ljava/lang/Object;", "VH:", "Landroid/support/v7/widget/RecyclerView$ViewHolder;", ">", "Lcom/hannesdorfmann/adapterdelegates3/AdapterDelegate", "<", "Ljava/util/List", "<TT;>;>;" } .end annotation # direct methods .method public constructor <init>()V .registers 1 .prologue .line 40 .local p0, "this":Lcom/hannesdorfmann/adapterdelegates3/AbsListItemAdapterDelegate;, "Lcom/hannesdorfmann/adapterdelegates3/AbsListItemAdapterDelegate<TI;TT;TVH;>;" invoke-direct {p0}, Lcom/hannesdorfmann/adapterdelegates3/AdapterDelegate;-><init>()V return-void .end method
因为只是采用了Debug包,没有配置混淆。所以这两个命令测试拿到的结果可读性都还好。如果是混淆后的包,可以使用【—proguard】相关参数,传入mapping等相关文件做解析映射。
resource
所谓资源文件解析,实际上就是对 resources.arsc的解析。可以参考网上一些解析arsc的博客,了解下文件结构和定义说明。
-
打印定义在资源表中的包名列表【1】
lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources packages app-debug.apk com.hannesdorfmann.adapterdelegates.sample
关于包列表,上面引用的arsc相关文章有说明。一般的应用只有一个包名。
-
查询指定类型的资源配置列表【2】
lee@MacBook-Pro-34 ~/develop/temp/apkanalyzer ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources configs --type layout app-debug.apk default v11 v13 v16 v17 v21 v22 lee@MacBook-Pro-34 ~/develop/temp/apkanalyzer ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources configs --type drawable app-debug.apk default v11 v21 v23 xhdpi-v4 xxhdpi-v4 ldrtl-xxhdpi-v17 lee@MacBook-Pro-34 ~/develop/temp/apkanalyzer ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources configs --type string app-debug.apk default ca da sw bs-rBA fr-rCA lo-rLA
截取部分结果如上。type都有哪些呢,不去看arsc文件数据结构的话,凭借开发经验也可以猜出一二。源代码目录res里面找找大概就可以了,诸如layout、drawable、string这些都属于类型,返回的则是应用包含这些资源类型的各个子文件夹列表,比如string类型,就返回所有字符串资源的语种,对应的则是源码中不同values文件夹的后缀名。这些返回结果,对应的就是后面命令需要使用的configs。
-
根据配置、名称和类型获取资源值【3】
✘ lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources value --name item_unknown_reptile --config default --type layout app-debug.apk res/layout/item_unknown_reptile.xml
这个功能在文档上会有些倒置的感觉,因为要先知道资源名是什么,才能传 —name 的参数。从结果上看,返回的是在解压后res目录下的文件路径。
-
根据配置和类型获取资源名列表【4】
lee@MacBook-Pro-34 ~/develop/temp/apkanalyzer ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources names --config default --type layout app-debug.apk abc_action_bar_title_item abc_action_bar_up_container abc_action_bar_view_list_nav_layout abc_action_menu_item_layout
截取部分结果如上。这里获取指定config、指定type下的资源文件名列表。
-
把二进制XML文件的转换成可读的XML文件打印出来【5】
lee@MacBook-Pro-34 ~/develop/android/android-sdk/tools/bin/apkanalyzer -h resources xml --file res/layout/item_unknown_reptile.xml app-debug.apk <?xml version="1.0" encoding="utf-8"?> <TextView xmlns:android="http://schemas.android.com/apk/res/android" android:padding="dimension(2049)" android:layout_width="-1" android:layout_height="-2" android:text="Unknown Reptile!" />
xml功能对应的参数实际上是第【3】个命令获取的文件路径。该命令会把指定的资源文件,解析成可读的xml文件。或者可以说resource这一系列命令,最终的目的就是定位到文件,然后解析成xml格式。
小结
草草体验了一遍工具功能之后,再对比下AS上的分析功能。基本上对apkanalyzer有一个简单的认知。
- 解压能力
- 解析dex文件
- 解析xml文件
跟apkChecker相比,apkanalyzer会纯粹一点。它只是解析APK文件本身有哪些东西,没有做进一步的静态质量类的分析。当然,最终的解析姿势可能不一样,但是原理都是一样的——根据APK文件内部结构的特点、dex&arsc文件的数据结构,来反编译得到结果。
后面会简单走读下apkanalyzer的实现原理。
以上所述就是小编给大家介绍的《apkanalyzer(1)-命令使用体验》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:- GO笔记之GO命令快速体验
- GO笔记之GO命令快速体验
- RedisPlus 3.1.0 优化操作体验 新增命令交互
- 降低云游戏延迟优化云游戏体验:贝塞斯达推出Orion技术,还公布了免费体验计划
- PyTorch 初体验
- indexedDB 初体验
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
颠覆式创新:移动互联网时代的生存法则
李善友 / 机械工业出版社 / 2015-3-1
为什么把每件事情都做对了,仍有可能错失城池?为什么无人可敌的领先企业,却在一夜之间虎落平阳?短短三年间诺基亚陨落,摩托罗拉以区区29亿美元出售给联想,芯片业霸主英特尔在移动芯片领域份额几乎为零,风光无限的巨头转眼成为被颠覆的恐龙,默默无闻的小公司一战成名迅速崛起,令人瞠目结舌的现象几乎都能被“颠覆式创新”法则所解释。 颠覆式创新教你在新的商业竞争中“换操作系统”而不是“打补丁”,小公司用破坏......一起来看看 《颠覆式创新:移动互联网时代的生存法则》 这本书的介绍吧!