石宗育 刘凯 谢飞帆
摘要:该文以Andorid系统的安全机制与权限系统的研究为基础基础,对APK文件进行逆向分析。从最基础的APK文件结构入手,首先对AndroidManifest.xml文件分析,掌握了程序的基本信息后,依次对res资源文件,smali函数文件进行分析,进一步分析此APP应用程序的运行流程。在掌握了此程序的运行流程后,进行逆向工程,对其smali代码进行审计分析,找出其中存在问题的地方,并实施自己的猜想与假设。
关键词:Android;网络安全;逆向工程
中图分类号:TP393 文献标识码:A 文章编号:1009-5039(2018)19-0096-03
1 分析过程
1.1 将APK安装包反编译成Smali文件
使用apktook将down.APK文件反编译成Smali文件,使用的命令为apktool.batd-fdown.apktest。反编译后的文件如图1所示。
其中AndroidManifest.xml文件为Andorid应用配置文件,并且是此应用的入口文件。其中包含一些程序必要的组件和权限信息,在后面的分析中是第一重要的文件。第二重要的是smali文件夹中以.smali结尾所有文件。这些文件支持着整个应用程序的运行,不论是需要程序直观显示的提示信息、功能按钮或页面布局,还是需要程序内部处理的数据传输、变量声明、或函数调用,都是在这些文件中运行完成的[1]。所以当要分析一个程序的运行流程时,这些.smali结尾的文件是重中之重。最后一个需要分析的文件就是res文件夹中的资源文件了,其中包括着一些图片资源和字符资源,大部分的字符串都会在这里声明,当对程序内的字符进行搜索时,会有限在次文件夹中搜索。
1.2 对AndroidManifest.xml文件的分析
在AndroidManifest.xml这个文件中,我们需要分析的有兩个部分,第一部分为此APP应用程序需要获取到我们手机的哪些权限,如图2。
从图2中可以看到,此程序需要获取的权限有读取外部存储、写入外部存储、读取写入文件系统、获取网络状态、访问互联网、获取电话状态、获取无线网状态、系统警报窗口和震动共九个权限,其中除获取电话状态以外全为普通权限,不需要用户授权系统将自动授予这些权限给应用。这些普通权限不会涉及用户的隐私。而获取电话状态这一权限则会获取用户的个人信息,所以当程序申请授予这一权限时,系统将会向用户申请授权,用户可以选择同意或者拒绝。当程序的所有权限都已经申请授权后,程序就可以依赖用户已经授权的权限继续运行[2]。
在Android的系统中,不论是普通权限还是敏感权限,都需要在AndroidManifest.xml文件中声明,在声明之后系统才会进行授权操作。
第二部分则是Application标签中的各个属性,其中除了对程序本身的一些特征进行声明以外,还声明了在Andorid系统中是否与其他应用程序产生交互。如图3
由图3可知,此程序在Application标签中声明了以下属性。分别为允许用户自行清除数据、允许activity更换从属任务、允许该应用在任何时候都保持运行状态、此APP应用程序的图标的图片名称为drawable、为应用程序锁实现的Applicationg子类的全名为com.cyanflxy.magictowet.AppApplication、此APP程序的所有acticity的主题风格为默认。
至此,对AndroidManifest.xml文件的分析就已经完成了,知道了这个APP应用程序获取的九种权限,并且都为正常权限。那么就可以开始进行下一步地分析了。
1.3 对res资源文件进行分析
在res文件夹中,有drawable、layout、raw和values四种不同的文件夹,他们分别保存着程序运行过程中需要用到的不同资源。
drawable文件夹中保存着图片文件,因为手机的屏幕大小与分辨率是不同的,所以这个文件夹中每一种图片都保存了多种不同的大小和分辨率,以便于适应更多的手机使用。
layout文件夹中保存着大量的样式资源、主题和布局。在APP程序运行时,会有不同的页面呈现出来,而这些页面的布局文件就保存在此文件夹中。
raw文件中保存着APP应用程序运行时会使用的音频文件。
最后的values文件夹中则保存着很多字符资源,在对apk文件进行逆向分析时,常用到此文件夹中的public.xml和strings.xml文件。这两个文件夹中保存着APP程序运行时大部分的字符与字符串,有以英文命名的也有以中文命名的。但是在程序中如果直接明文的去使用这些字符是不安全的,所以在这些文件会给每一个字符设置一个id号,当需要调用这个字符时,就获取到这个字符的id号,再进行字符的调用。如图4。
1.4 对smali文件进行分析
在smali文件中保存着此APP应用程序运行时需要的函数,这些函数文件都是以.smali结尾的。在这些函数中,主函数的命名中,除去部分开发者为了APK文件的安全或者APK文件本身经过代码混淆和加固,一般都带有Acticity。如图5。
在对这些文件进行分析时,首先要对Acticity主函数进行分析。之所以说Activity为主函数,是因为在APK文件中,不论其他的子函数在哪个位置,其功能是什么,最后都会直接或间接地被Activity的主函数调用。所以首先分析主函数有利于对整个smali文件结构的分析与规划整理。
此APK的Activity主函数的部分内容如下
.method public onClick(Landroid/view/View;)V
.line 46
const v0, 0x7f0b0058
invoke-virtual {p0, v0}, Lcom/ctf/ctf/CTFActivity;->findViewById(I)Landroid/view/View;
move-result-object v0
check-cast v0, Landroid/widget/Button;
iput-object v0, p0, Lcom/ctf/ctf/CTFActivity;->but:Landroid/widget/Button;
.line 47
const v0, 0x7f0b0059
invoke-virtual {p0, v0}, Lcom/ctf/ctf/CTFActivity;->findViewById(I)Landroid/view/View;
move-result-object v0
check-cast v0, Landroid/widget/TextView;
iput-object v0, p0, Lcom/ctf/ctf/CTFActivity;->tex:Landroid/widget/TextView;
.line 55
const-string v0, "Administrator"
.line 56
.local v0, "admin":Ljava/lang/String;
iget-object v7, p0, Lcom/ctf/ctf/CTFActivity$1;->this$0:Lcom/ctf/ctf/CTFActivity;
invoke-virtual {v7, v0}, Lcom/ctf/ctf/CTFActivity;->string1(Ljava/lang/String;)I
move-result v2
.line 57
.local v2, "ctf1":I
if-ne v2, v1, :cond_0
.line 58
iget-object v7, p0, Lcom/ctf/ctf/CTFActivity$1;->this$0:Lcom/ctf/ctf/CTFActivity;
invoke-virtual {v7, v3}, Lcom/ctf/ctf/CTFActivity;->Flag(Ljava/lang/String;)Ljava/lang/String;
move-result-object v6
.line 59
.local v6, "message_1":Ljava/lang/String;
iget-object v7, p0, Lcom/ctf/ctf/CTFActivity$1;->this$0:Lcom/ctf/ctf/CTFActivity;
iget-object v7, v7, Lcom/ctf/ctf/CTFActivity;->tex:Landroid/widget/TextView;
invoke-virtual {v7, v6}, Landroid/widget/TextView;->setText(Ljava/lang/CharSequence;)V
.line 62
:cond_0
const-string v5, "Sorry Plues try again"
.line 63
.local v5, "message":Ljava/lang/String;
iget-object v7, p0, Lcom/ctf/ctf/CTFActivity$1;->this$0:Lcom/ctf/ctf/CTFActivity;
iget-object v7, v7, Lcom/ctf/ctf/CTFActivity;->tex:Landroid/widget/TextView;
invoke-virtual {v7, v5}, Landroid/widget/TextView;->setText(Ljava/lang/CharSequence;)V
.line 67
return-void
.end method
雖然smali代码是Android系统的底层汇编代码,但是它与X86汇编代码还是有一定的区别的,在smali中不会涉及内存与堆栈的问题,而是通过v寄存器和p寄存器进行数据的存储、传输与运算[3]。
从以上的smali代码中可以看出line46与line47分别为获取Button和TextView两个标签中的id,以便于对其数据进行处理。而line55、line56、line57则是对字符串"Administrator"与id为admin的TextView标签中输入的数据进行比较,如若不同则跳转到line62,通过名为message的变量输出提示信息"Sorry Plues try again".如若相同则不跳转继续运行line58与line59的代码,其内容为调用一个名为Flag的函数,并将这个函数的返回值传入到名为message_1的变量,并通过其进行输出。
在最后的line67中,其内容为返回一个void类型的返回值,这里之所以要返回void类型的返回值,是因为在这一段代码的第一行的最末尾字符V,表示了这个onClick函数是一个返回值类型为void的函数。
那么现在这个主函数的功能就已经分析出来了,这是一个返回值类型为void名为onClick的函数,其功能为将TextView标签中获取的字符串,也就是在APP应用中输入的字符串,与其原本定义好的字符串"Administrator"做比较。如若两者相同,则输出Flag函数中的提示信息,如若不相同,则输出"Sorry Plues try again"提示信息。
2 逆向工程及应用
对于以上smali的代码中,可以进行一个大胆的假设,既然可以看懂这些smali代码,那么是否可以把其中的某些重要的代码做一些修改,改变其原本的运行轨迹,使得这个APK不能实现原有的功能呢。
在以上的smali代码中,存在着可以修改的部分,并且这一部分可以将这个onClick主函数的功能改变。这个主函数的功能就是通过一个判断来确定输出正确的提示信息还是错误的提示信息,那么如果将这个判断修改了,则改变了这个APP的原有功能,从而也达到了对APK文件进行逆向工程的目的。
3 结束语
随着移动设备的普及,Android系统也逐渐地进入人们的视线内。而相比与苹果的IOS系统,Andorid由于是开源的原因,使得其APP应用程序可以被任意一个人开发。而又因为国内并没有一个类似于美国GooglePlay的官方软件下载平台,虽然在我们使用各种APP时带来了许多便利,但是也增加了一些恶意APP浑水摸鱼的情况,使得我们的隐私信息在不知不觉中被他人盗取,所以对APP应用进行全面的分析是非常必要的。在对APP应用进行分析时,就需要用到逆向工程技术,将APK文件进行反编译,查看其smail汇
编代码进行分析。
参考文献:
[1] 丰生强.Android软件安全与逆向分析[M].北京:人民邮电出版社,2013.
[2] 杨峻.Android系统安全和反编译实战[M].北京:人民邮电出版社,2015(5).
[3] 张志远,万月亮,翁越龙,糜波.Android应用逆向分析方法研究[J].信息网络安全,2013(6):65-68.