1 问题描述
发现一类新的对抗,修改了zip格式中的compression
数据(用于确定是哪种压缩方式,压缩方式只有stored和deflated),导致自动化分析出错,但是此apk却能正常安装使用
可以发现此apk的manifest文件压缩方式的值是错误的,同时其解压前后大小一致,应该是stored方法,但是android源码中并没有通过压缩前后大小来判断压缩方式的逻辑,需要弄清楚apk安装过程中,到底是如何判断这个manifest的压缩方式的
2 分析
2.1 先说结论
刚开始直接在zip解析的源码中找相关的逻辑,结果毫无头绪,后续从apk安装的java代码(pm命令相关代码)开始跟,然后同时从zip解析的c++代码往回看,终于理清楚了与此问题相关的代码逻辑。
原因其实就是:android在安装apk时,解析manifest的过程中,是调用的assetsManager读取的文件,而assetsManager的native接口中,其解压过程只判定了method == deflated
,满足条件就解压,否则直接按stored处理.......
这样就造成了zip文件格式中的compression_method
可以随便写(只要不等于8),然后文件以stored方式保存,但是android还能正常识别的情况。
分析完成后,自己生成了一个demo apk,手动修改压缩方式为ff ff
,之后使用官方的apksigner重签名过程报错,之后再验证吧(给apk签名时这么严格,安装apk时却漏洞百出。。)
后续自己修改了一下apksigner成功签名,并且正常安装到手机,可以确认是上面说的原因了
2.2 粗略的分析过程
在android源码中寻找androidManifest关键词(apk安装过程的apk解析代码在frameworks/base/services/core/java/com/android/server/pm/parsing/
)
之后跟踪其调用,发现是通过android.content.res.AssetManager
中的openXmlResourceParser
方法读取AndroidManifest,继续跟踪,可发现最终调用的是native方法
通过google源码搜索很容易搜到对应的代码
继续跟踪其引用,即可找到了核心逻辑代码,此处只判断了解压类型是不是deflated,如果是就按deflated处理,不是就直接按stored处理 (代码太长了,只截取到deflated处理结束的地方)
2.3 随便说点
android zip库里面还有其他地方有处理解压方式的逻辑,同时判定了deflated和stored两种方法,到了assets相关的解压,就偷懒只判定一种。。。也想不明白为啥没有统一的解压接口,整个zip库实在是太复杂了,估计里面还有挺多坑可以被利用的
另外此事件分析过程中,刚好遇到apk解析的java部分在重写,希望以后更简单易读吧。