基于odex文件结构的Android程序逆向分析方法*论文

基于odex文件结构的Android程序逆向分析方法

徐国天 中国刑事警察学院

摘 要: 研究odex文件的逆向分析方法对公安机关的电子数据检验鉴定工作具有实际意义。由于odex文件与硬件平台紧密相关,将其移植到其它Android平台上,程序通常无法运行。为了解决odex文件的取证分析问题,采用分析odex文件存储结构的方法,将二进制机器代码逐步还原为可直接阅读的smali源代码,进而通过静态方式完成取证分析工作。经实际测试,这种odex文件解析方法可以较好地应用于Android程序逆向分析工作。

关键词: Odex Android逆向 Smali

引言

Android系统应用程序采用APK格式,APK格式与Zip压缩格式相同,程序安装运行时,Android系统对APK文件进行解压缩操作,释放出一个名为class.dex的文件,其中存储了应用程序的二进制代码。为了提高执行效率,程序在Dalvik虚拟机上运行之前,Android系统会针对特定硬件平台对dex文件执行代码精简优化操作,生成一个对应的odex文件,系统实际运行的是这个经过优化处理的odex文件。

社区糖尿病患者的管理需要政府部门对区域医疗资源优化配置,建立信息互联互通,实现上下联动、共同发展。减少糖尿病并发症发生的同时,针对糖尿病前期和正常人群采取措施更符合以预防为主的国家卫生方针,特推荐“以人为本的一体化卫生服务”模式[14]和“三段五级四元联动”一体化服务模式[15]。

目前,Android程序检验鉴定工作主要是从送检的APK程序中提取dex文件,再将dex文件逆向为smali或Java源代码,通过分析源代码完成取证鉴定工作。但是,近几年出现一类新型案件,即恶意程序以系统固件形式直接安装到某一特定类型Android智能终端硬件平台上,在硬件平台上只能提取到优化之后的odex文件,而不存在dex文件,送检对象为安装恶意程序的智能终端。由于odex文件与硬件平台紧密相关,将其移植到其它Android平台上,程序通常无法运行,这导致鉴定人员很难在取证设备上对被检odex程序进行动态调试。因此研究odex文件逆向分析方法,将其转换为对应的smali源代码进行静态取证分析,对公安机关的电子数据检验鉴定工作有实际意义。

一、Odex文件总体存储结构分析

Odex文件磁盘数据存储结构如图1所示。一个odex文件由四部分内容组成,包括DexOptHeader、DexFile、Dependencies和OptData。下面分别研究这四部分内容的磁盘存储结构和数据解析方法。

DexOptHeader存储结构如图2所示,其中主要包括三个指针成员,分别指向DexFile、Dependencies和OptData(chunk)数据结构。DexOptHeader存储结构共占用40个字节空间,1~8字节为magic[8]魔数字,代表这是一个odex文件,值为字符串“dey\n036\0”;9~ 12字节是dexOffset字段,其中存储了odex文件中所包含的dex文件的偏移位置,注意这个dex文件并不是原始dex文件,而是指令优化后的dex文件;第三个字段是dexLength,占4字节,存储odex文件中包含的dex文件的长度;第四个字段是depsOffset,占4字节,表示依赖库列表段Dependencies的偏移位置;第五个字段是depsLength,占4字节,代表依赖库列表段的长度;第六个字段是optOffset,共4字节,表示优化数据段OptData的偏移位置;第七个字段是optLength,共4字节,表示优化数据段的总长度。

图3是对测试文件app10.odex(本文以此文件作为分析对象)的DexOptHeader存储结构实例分析。DexFile文件的偏移位置是0x0028,dex文件的总长度是0x002CA040。注意这个dex文件和原始dex文件大小完全相同,但内容不同。也就是说,在优化过程中原始dex文件被部分修改过;Dependencies依赖字段的偏移地址为0x002CA068,依赖字段的总长度为0x0459。优化数据段OptData的偏移地址为0x002CA4C8,总长度为0x0003A218。

经过上述实验研究,得到对于3号水基钻井废弃泥浆样品来说,最佳药剂投加固化方案为:AP破胶剂2.0%+32.5硅酸盐水泥20.0%+HHJ活性剂+CA促凝增强剂5.0%。

二、Dependencies依赖库存储结构分析

综上所述,妊高症合并宫缩乏力性产后出血患者临床中需要接受良好的护理服务,为患者提供系统的,全面的护理干预措施,有助于患者的恢复,降低出血的几率,提升产妇的产后生活质量,因此临床中应该进行推广使用。

OptData优化字段用来实现应用程序中类的快速定位和垃圾回收,提前实现这两种机制对于提高应用程序运行速度很有帮助。OptData优化字段存储了三种类型数据块,存储结构如图6所示。第一个数据块存放dex文件的DexClassLookup结构数据,主要负责实现快速查找、定位dex中的某个类。第二个数据块存放该dex文件的寄存器图(Register Map)信息,主要用来帮助Dalvik虚拟机做精确GC(垃圾回收)。最后一个数据块用于表示结束。下面对DexClassLookup的存储结构进行研究。

图5是app10.odex文件的Dependencies依赖库存储结构实例分析。这个应用程序共使用了19个链接库文件,由于篇幅关系,此处只给出前两个链接库文件信息。第一个链接库存储路径总长度为28字节,存储路径为/system/frame work/core.odex,其后20个字节为该依赖库的SHA1值。

三、OptData优化字段存储结构分析

依赖库存储结构如图4所示,第一个字段modWhen占4字节,存储的是class.dex文件的修改时间;第二个字段占4字节,存储class.dex文件的CRC校验值,文件中任何一个比特位发生变化都会导致CRC校验失败;第三个字段DALVIK_VM_BUILD占4字节,存储当前Dalvik虚拟机版本号,对于Android 4.4.2系统来说,其值是27;第四个字段numDeps占4字节,存储依赖库文件个数,其后是具体每个依赖库信息。依赖库文件存储结构包括三部分,分别是优化文件存储路径字符串总长度、优化文件存储路径字符串和依赖库的SHA1校验值。依赖库列表必须按照64比特位对齐,如果数据不满足这一要求,需要在存储结构末尾进行字节填充,满足8字节对齐要求。

在Android应用程序中,所有类定义及二进制程序代码都存储在dex文件中。一个功能齐全的Android应用程序往往由多个类组成,每个类都由一个特定的类描述符来唯一标识。类描述符是一个特殊的字符串,不同的类不可能有相同的类描述符。类描述符包含类名称和类所在的包名称。例如,一个类所在包名是“java.lang.stringbuilder”,其类名称是“Test”,那么这个类的类描述符就是“Ljava/lang/stringbuilder/Test;”。但是,如果采用常规的字符串逐一比较算法从众多类名称中定位特定类名字符串,比较速度会非常慢,无法满足应用程序高速运行的需要,同时会给用户带来较差的体验。Dalvik虚拟机在加载、运行dex程序文件时,会将一个名为DexClassLookup结构体dump到内存中,用于提高类的查找速度。

DexClassLookup结构体存储结构如图6所示,第一个是size字段,占4个字节,表示这个DexClassLookup结构体实际占用的存储空间大小。这个数值也包含了size字段自己所占用的4个字节。第二个是numEntries字段,占4个字节,表示DexClassLookup结构体具体包含的条目个数。其后是一个table数组,用于存放具体的条目数据。numEntries字段指明了table数组具体包含的元素个数,数组下标从0开始到numEntries-1结束。

与类描述符字串存储位置的确定过程类似,类的查找过程也是先计算类描述符字符串的hash值,再根据条目的个数,取hash值的最低几个比特位作为数组下标。读取这个下标位置的条目内容,如果没有发生冲突,一次查找就能命中目标,如果发生冲突,则需要向后依次探测后续位置,直至找到对应的类描述信息。这种方法可以根据哈希值立即定位到条目数据的存储位置,避免了字符串的逐个字节比较,提高了类的查找速度。

胸腺肽β4对TGF-β1诱导的人肺成纤维细胞的增殖 、分化及促纤维化作用的影响………………………………………………………………………… 程义局,等(12):1375

图7显示的是应用程序中每个类描述符在table数组中具体存储位置的计算过程。首先计算出类描述符的hash值,这是一个4字节数字,之后Android系统会根据条目个数生成一个mask数值,mask数值等于条目总个数减一。例如,条目个数为8,mask值为7,条目个数为16,mask值为15。之后,用生成的mask值与前面计算得到的类描述符字符串hash值做与运算,运算结果即为这个条目在table数组中的存储位置。这种运算方法实际上就是取hash值的后几个比特位数据作为数组下标,例如条目个数为8,就是取hash值的后三个比特位,条目个数为16,就是取后四个比特位。

Table数组中每个条目数据由三个字段构成,每个字段占4字节。第一个字段是classDescriptorHash,用于存储类描述符字符串的哈希值。第二个字段是classDescriptorOffset,用于存储类描述符字符串的偏移位置。第三个字段是classDefOffset,用于存储类定义的偏移位置。

随着精英文化的衰落和大众文化的崛起,以身体消费为中心的感官刺激和感性化追求逐渐成为大学生审美情趣的主流。同时,文化符号也开始由先前的文字、语言更多地被图形图像所替代。这就导致当今部分大学生在审美活动中过多地去注重体验,而不是去多加思考,使他们的审美价值观发生了严重错位,并始终处于被重构、被改革的过程中。而审美价值观与世界观中的社会观、政治观、文化观,与人生观中的自我观、道德观等是密切渗透、相互影响的。因此,这对当今大学生思想政治教育工作来说也是一个极大的挑战。

Android应用程序运行时需要大量链接库支持,这些链接库信息以列表形式存储在系统环境变量BOOTCLASSPATH中。依赖库中存储的就是程序运行过程中需要的全部链接库文件相对存储路径。Android应用程序执行时,系统将链接库文件加载到Dalvik虚拟机,之后动态地将链接库文件相对路径替换为特定硬件平台上的绝对路径。为了加快应用程序执行速度,这些库文件被预先加载进Dalvik虚拟机,供程序直接使用,odex文件中这些相对路径也提前被替换为库文件的绝对存储路径,由于省去了相对路径到绝对路径的转换步骤,程序的加载、运行速度得到提高。

计算出条目存储位置后,需要判断这个位置是否已被其它条目占用。如果这个位置上已有其它条目,说明两个类描述符字符串的最低几个比特位数据相同,导致两个类被映射到同一位置,造成冲突。一旦发生冲突,解决办法是将hash值加一,再与mask做一次按位与运算操作,判断新位置是否空闲,持续采用这种冲突处理方法,直至找到一组空闲位置。这个办法实际上就是依次探测首次冲突位置之后的每个位置是否空闲,如果碰撞次数较多,势必会影响到未来类的查询速度。因此,在计算table数组大小时,采用的是以空间换时间的思路,将类的总个数乘以2,再适当扩大存储空间大小,以减少冲突发生的概率。最后,定位一个空闲位置后,将类描述符hash值、类描述符字符串和类的偏移地址等信息,存储到这个空闲位置上。

应用程序第一次加载运行时,Dalvik虚拟机会对dex文件进行优化,生成一个odex文件,之后再次运行时,就是直接加载、运行优化后的odex文件。在第一次优化dex文件时,DexClassLookup结构体被计算出来,之后程序执行时,这个结构体被直接dump到内存中使用,进而提高程序的运行速度和执行效率。

需要注意的是,并不是应用程序中有多少个类就生成多少个条目。使用如下公式确定table数组大小,即numEntries的数值: 2 i-1≤ n×2≤2i,其中n为应用程序中定义的类的总个数,2i为table数组的实际条目数。例如应用程序共有5个类,那么n等于5,5乘以2等于10,比10大的2的幂次方数字是16,因此table数据条目个数等于16。这样设计的目的是向table数组存储条目数据时,可以尽量减少碰撞发生的次数,同时提高条目查询速度。

由于这两次试行都是针对二年级学生进行的,因为本课程的学习对后续课程有着较深远的影响,故而线上教学主要作为课堂教学的补充环节。在授课老师出差、开会等特殊情况,采用全部线上教学的方式。

图8是app10.odex文件的kDexChunkClassLookup存储结构实例分析。NumEntries值为0x1000,即table数组共4096个条目。每个条目占12字节,所以table哈希表总大小为4096×12=49152字节,再加上首部8字节,共49160字节,即0xC008。而第一个size变量是整个kDexChunk ClassLookup存储结构体大小,要求8字节对齐,不足部分需要进行字节填充。在本例中0xC008正好8字节对齐 ,因此两个size变量值相同,均为0xC008。

4.2 植株调整:当植株高30厘米或出现卷须时要及时搭架引蔓,引蔓最好在下午进行,以免损伤茎蔓。引蔓和绑蔓使其茎叶分布均匀,苦瓜有很强的分枝能力,若任其生长,则会造成枝叶过分茂密,消耗养分,且植株间透气性差,易发生病虫害,也会影响主蔓的正常生长和开花结果,因此,在上架同时,将棚架以下的侧枝全部摘除,保证培育健壮的主蔓,在主蔓上架以后,适当选留中上部强壮的侧蔓,以提高产量。在旺盛生长期,枝叶繁茂,要及时摘除植株下部的黄叶和病叶,保证通风透光,延长采收时间,提高产量和质量。

图8中给出了table[0]~table[11]条目内容,其中只有table[4]、table[6]和table[11]条目存储了具体的类信息,其它条目空闲。这些条目在进行哈希查找时,一次计算即可定位目标类,不会发生碰撞情况。以table[4]为例分析条目存储位置的计算过程,因为table数组总的条目数为4096,即212个,因此mask为0x0FFF。这个类描述符字符串的hash值为0x4DAFD004,hash值与mask执行与运算之后,得到存储位置下标为0x04。该位置空闲,没有发生碰撞。table[4]条目的类描述符偏移地址为0x001DB082,定位到这个位置,查看到的内容如图10所示,显示这个类描述符字符串为“/widget/AppCompatAutoCompleteTextView;”。

四、获取odex文件对应的smali源代码实例

图11是以app10.odex文件为例,对RegisterMaps存储结构进行实例分析。Type字段值为0x50414D52,表示这是一块kDexChunkRegisterMap类型数据,结构体大小为0x02E1F8。该dex文件中共有0x06BD(即1725)个类,其后是1725个地址指针,每个地址指针占4字节,指向某个类的RegisterMaps相对于存储结构首部的偏移地址。

下面以odex文件中第1715个类为例分析RegisterMaps存储结构。如图11所示,第1715个类的偏移地址为0x0002DE50,这个地址是相对于结构体首部的偏移位置,首部地址是0x002D64E0,跳转到第1715个类的起始地址,查看到的RegisterMap结构如图12所示。MethodCount字段值为2,表示这个类共有两个方法,图中给出了第一个方法的RegisterMap存储结构分析。Format字段值为0x02,表示kRegMapFormatCompact8类型,即该方法内指令个数少于256条,使用一个字节表示指令地址。RegWidth字段值为0x01,表示该方法使用的寄存器数量少于8个,因此使用1个字节表示寄存器状态。NumEntries字段值为0x0002,表示共记录了两个GC安全检查点的寄存器状态,其后4个字节数据0x00010301即为具体的记录数据。

为了分析第一个方法的记录数据,这里使用dexdump -d app10.odex解析目标odex文件存储结构,在解析结果中找到第1715个类的解析结果,定位方法是在解析结果中搜索关键词“Class#1715”,即可命中目标类信息。图13给出了第一个方法的机器代码分析,可以看到这个方法只使用了1个寄存器,共包含两条smali代码,第一条指令地址为0x0000、第二条为0x0003。注意此处的指令地址是将原始机器代码内容按照2字节进行分组后的编号,原始机器代码为0x7010 7d30 0000 0e00,指令编号为0x0000~0x0003。

图12中方法的记录数据为0x00010301,第1个字节0x00表示第1个GC安全检查指令的地址编号,即图13中第1条指令。第2个字节是第1条指令使用的寄存器状态位图为0x01,即二进制0000 0001,这个GC安全检查指令使用V0寄存器存储了一个对象类型数据,对照图13可以看到,第1条指令使用了V0寄存器,且在其中存储了this对象。第3个字节为0x03,表示第2条GC安全检查指令的地址编号,即图13中第2条指令,这是一条return指令。第4个字节为0x01,表示这条指令也使用了V0寄存器。

五、结语

本文详细分析了odex文件的存储结构,通过实例分析了将odex文件转换为对应的smali源代码的具体方法,研究内容对公安机关的电子数据检验鉴定工作有实际意义。但是文章仅对odex文件的静态分析方法进行了研究,由于odex文件与特定的硬件平台紧密相关,将送检Android设备上的odex文件移植到取证设备上很难运行,即很难在取证设备上对odex文件进行动态调试。下一步,计划重点研究odex文件向不同硬件平台的自动化移植方法,以达到动态调试的目的。

参考文献

[1] Roland_sun.Dalvik虚拟机中RegisterMap结构解析[EB/OL].https://blog.csdn.net/roland_sun/article/details/46832341,20150710.

[2] 吴威.利用逆向分析法基于Android的恶意APK分析[J].警察技术,2016(3):53-56.

[3] 杨卫军,余彦,张佩军,等.Android手机恶意软件取证技术研究[J].警察技术,2012(5)8-11.

[4] 李强,刘宝旭,姜政伟,等.一种Android系统下的QQ取证模型分析[J].信息网络安全,2016,16(1):40-44.

[5] 文伟平,张汉,曹向磊.基于Android可执行文件重组的混淆方案的设计与实现[J].信息网络安全,2016,16(5):71-77.

⋆基金项目: 中央高校基本科研业务费项目(编 号:3242017013);辽宁省自然科学基金课题(编号:20180550841);辽宁省自然科学基金课题(编号:2015020091);公安部理论及软科学研究计划(编号:2016LLYJXJXY013);公安部技术研究计划(编号:2016JSYJB06);辽宁省经济社会发展研究重大课题(2018LSLKTZD-028);辽宁省社会科学规划基金项目(编号:L16BFX012)

标签:;  ;  ;  ;  ;  

基于odex文件结构的Android程序逆向分析方法*论文
下载Doc文档

猜你喜欢