浅谈安卓apk加固原理和实现

article/2025/10/6 15:46:42

640?wx_fmt=jpeg

转载本文需注明出处:微信公众号EAWorld,违者必究。


引言:


在安卓开发中,打包发布是开发的最后一个环节,apk是整个项目的源码和资源的结合体;对于懂点反编译原理的人可以轻松编译出apk的源码资源,并且可以修改资源代码、重新打包编译,轻轻松松变成自己的apk或者修改其中一部分窃取用户信息。

代码被反编译对于apk的开发者和使用者而言十分苦恼。apk加固、防止反编译此时显得尤为重要。虽然有好多给apk加固的第三方,可能并不需要自己做apk加固,但是了解apk加固原理还是很有必要的。本文主要向大家介绍apk加固原理和简单实现。


目录:


一、apk常见加固方式

二、apk加固原理

三、apk加固实现

四、apk该方式加固后缺陷


一、apk常见加固方式


(1)代码层级加密--代码混淆


代码混淆是一种常用的加密方式。本质是把工程中原来的有具体含义的类名、变量名、方法名,修改成让人看不懂的名字。常见的代码混淆工具proguard(有兴趣的可以自己看一下该工具:http://t.cn/ELjgHdi)。该加密方式只是对工程提供了最小的保护,并不是说不能逆向破解;只是说难度增加,需要耐心。


(2) Dex文件加密


dex是Android工程中的代码资源文件,通过dex可以反编译出java代码。dex的加壳是常见的加密方式。通过对dex文件加密拼接加壳,可以有效的对工程代码进行保护。apk工程在安装成功后,app启动时会有dex解密的过程,然后重新加载解密后的dex文件。


第二种加密方式也就是本文要为大家分享的加密方式。基本原理是在jni层, 使用DexClassLoader动态加载技术完成对加密classex.dex的动态加载,dex文件可以附属在assert或raw目录。


二、apk加固原理


(1)apk文件结构


解压一个apk包,可以看到如下目录结构:


assets:存放工程资源(图片、本地html等)文件的目录


Lib:存放ndk编译出来的so文件(so:C/C++编译出的文件)


META-INF

该目录下存放的是签名信息,用来保证apk包的完整性和系统的安全性:

CERT.RSA:保存着该应用程序的证书和授权信息

CERT.SF:保存着SHA-1信息资源列表

MANIFEST.MF:清单信息


res:存放资源(布局xml、布局xml引用图片等)文件的目录


AndroidManifest.xml:清单文件,它描述了应用的名字、版本、权限、注册的服务等信息


classes.dex:java源码编译经过编译后生成的dalvik字节码文件,主要在Dalvik虚拟机上运行的主要代码部分


resources.arsc:编译后的二进制资源文件


META-INF文件主要是跟签名有关的文件,保证了apk的完整性和安全性。apk每次重新签名需要删除该文件夹。

需要大家主要关注的是classes.dex文件:因为apk加固主要是对dex文件进行的加密。


 (2)Dex文件结构


640?wx_fmt=png

Java源文件生成Dex文件的映射关系


dex文件可以理解为由java文件编译生产的,直观表现就是dex文件可以编译出java源码;


dex文件的作用是记录整个工程(通常是一个Android工程)的所有类文件的信息;


dex文件是从class文件演变而来的,class文件存在冗余信息,dex文件则去掉了冗余,并且整合了整个工程的类信息。


640?wx_fmt=png

Dex文件结构


文件头header包含了dex文件的信息,也是大家需要关注的部分。因为下面的操作中会有dex文件的修改操作,而判断是否是正确的dex文件是由header部分决定的。


下面看一下header部分的信息:


struct DexFile { 	DexHeader     header; 	DexStringId     StringIds[StringIdsSize]; 	DexTypeId      TypeIds[typeIdsSize];	DexProtoId     ProtoIds[protoIdsSize]; 	DexFieldId      FieldIds[fieldIdsSize]; 	DexMethodId   MethodIds[methodIdsSize]; 	DexClassDef    Data[]; 	DexLink        LinkData; }

Dex文件header部分结构体信息


Header部分有需要注意的三个字段:checksum字段、signature字段、filesize字段。


checksum字段: checksum是校验码字段,校验dex数据的完整性

signature字段: signature是SHA-1签名字段,dex数据完整性校验

signature字段:保存classes.dex文件总长度


之所以关注这三个字段,是因为后面会有对dex的重新拼接。dex拼接后要修改这三个字段,字段修改正确后才可以保证dex的正确加载。


 (3)Dex文件整体加固原理


640?wx_fmt=png


上图对象解析:


源apk:需要加密的apk程序,源dex来自于源apk

壳程序:Android工程,提供壳dex,壳dex主要作为工程入口,解密出源dex,映射到源dex等操作

加密程序:java工程,主要是做对源dex加密且和壳dex合并成新dex的操作


 (4)整个工程加载原理


APP启动——>自定义Application中attachBaseContext()方法——>自定义Application工程onCreate()方法——>源Application


1、自定义Application来自于壳程序的dex,加密合成的新dex前半部分就是壳程序的dex,这部分是没任何问题,可以正常加载。该Application中attachBaseContext方法会做解密操作,解密出源dex并放置在固定目录下,添加dex的加载映射;映射到源dex目录。


2、自定义Application工程onCreate()方法添加源dex加载的入口;即源dex的application和mainActivity。


3、程序正常启动;源dex被正确加载。


三、apk加固实现


准备:


SourceProject

需要加密源程序,自定义application为:

com. targetapk

MyApplication,主activity为:

com. targetapk.MainActivity


jiaguApk:java工程,dex加密合并操作


shellApk:android工程,提供壳dex;自定义Application设定为:

org.hackcode.ProxyApplication


SourceProject是简单的Android工程demo,编译生成生成被壳加密的sourceProject.apk

jiaguApk主要作用是加密源sourceProject.apk中dex文件;然后拼接到壳dex后面生成新的dex

shellApk是壳工程,主要是作为加密后apk的伪入口,加密后的apk工程会先加载壳工程提供Application:org.hackcode.ProxyApplication,解密、映射等操作


整体加密步骤:


1.反编译目标app(sourceProject.apk),得到sourceProject文件;sourceProject.apk来源于SourceProject工程


2.修改sourceProject文件中的manifest文件,将自定义Application设定为“org.hackcode.ProxyApplication”


3.拿到sourceProject文件中的dex文件,压缩为TargetApk.zip


4.反编译壳apk:apktool.bat d shellApk.apk,得到shellApk文件


5.拿到shellApk文件下的classes.dex和TargetApk.zip,加密合成新的classes.dex文件


6.新合成的class.dex替换sourceProject文件中的class.dex


7.删除sourceProject文件中的META-INF文件,重压缩成zip文件


8.重新签名


步骤2主要是是为了加载壳dex中的代码;正确解析dex。

步骤6主要是jiaguApk工程的工作。


jiaguApk关键代码


640?wx_fmt=png


以上代码主要作用是源程序dex压缩成TargetApk.zip后加密,加密后拼接在壳dex的后面,然后生成新的dex文件,dex文件修改头部参数,保证dex文件正确读取。


此时生成的新的dex文件前部分是能正确被运行的壳dex的代码。


shellApk壳工程关键代码


640?wx_fmt=png


attachBaseContext方法:

主要作用是程序apk中dex拷贝、解密出源dex放在data/data目录下;设置dex加载目录映射。


640?wx_fmt=png


onCreate:

主要作用替换源应用dex的application,使解密出的源dex正确加载;保证源入口正确,保证项目正确加载。


以上就是apk加壳实现整个过程。实现起来基本没什么问题,需要注意的点是源工程有多dex问题:源程序中有多个dex的时候,多个dex同时一块压缩成TargetApk.zip,然后其他步骤不变。亲测没问题!


四、apk该方式加固后缺陷


(1)首次打开加载慢的问题。加固后的工程首次打开会有延时,延时时间会跟源工程的dex大小有关。就拿普元客户端来说,里面有两个dex,总共有8M左右;加固后首次打开会慢3s左右;而且以后每次打开会有2s左右的延时。


(2)安全性问题。大家会发现源dex文件还是会落地,在工程的data/data目录下面,越狱的手机可以直接看到。拿到dex资源,一样可以通过反编译拿到java代码。网上有不落地的方法,尝试一直没有成功;如果哪位大神有可行方法的话,欢迎分享交流。


精选提问:


问1:能讲讲.so加固吗?


.so反编译比较困难,比dex的反编译困难。一般做法是抽取Android工程的关键java代码转为c/c++, 然后生成so文件。so加密我只是了解了一下破坏.so部分头文件的方式加固。


问2:加固里面的VMP(虚拟机)是什么?


答:VMP(虚拟软件保护技术)大概思路就是自定义一套虚拟机指令和对应的解释器,并将标准的指令转换成自己的指令,然后由解释器将自己的指令给对应的解释器。


推荐阅读

基于RN+微应用打造多业务支撑的企业官方App

企业全面移动化实践指南

浅谈BDD下的自动化测试框架


640?wx_fmt=png关于作者张存征,普元移动高级研发工程师,普元移动产品研发团队成员之一,拥有首钢集团、邮政集团等移动平台项目实施研发经验。


640?wx_fmt=jpeg关于EAWorld:微服务,DevOps,数据治理,移动架构原创技术分享。长按二维码关注!


课程预告! 12月7日(周五)下午14:30普元开发工程师李中文为大家分享《微服务架构下的服务调用与鉴权》,在此公众回复“YG+微信号”马上入群并完成报名!


640?wx_fmt=jpeg



http://chatgpt.dhexx.cn/article/wjdAxxq4.shtml

相关文章

安卓逆向笔记--apk加固

安卓逆向笔记–apk加固 资料来源: 浅谈安卓apk加固原理和实现 Android中的Apk的加固(加壳)原理解析和实现 前两个太老了所以具体代码借鉴下面的 Android Apk加壳技术实战详解 一、apk常见加固方法 (1)代码层级加密–代码混淆 代码混淆是一种常见的加密方式。本质是把工程中原…

imx6ull uboot移植

以下内容来自:正点原子Linux驱动文档 一、简介 uboot移植主要是根据原厂的uboot移植:芯片厂商通常会做一块自己的评估板并发布BSP,当我们需要定制自己的开发板时可以根据自己的需求(硬件上的不同),对原厂…

全志V3S嵌入式驱动开发(uboot移植)

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】 安装了ubuntu操作系统,有了开发板,下面就可以进行我们的开发工作了。第一步,我们要面临的问题就是uboot移植。一般来说,嵌入式的基础环境就是uboot、linux和rootfs。uboot完成一…

2021-09-14 uboot移植开发

引言:最近要改动uboot,实现像微软PC上,u盘一键刷机或手机上安全模式下刷机的操作 专门去好好研究了点uboot的启动过程;以下为总结: 嵌入式系统 微软-PC ——…

iTOP4412 uboot移植教程

好多刚开始学习uboot移植的同学总是觉得uboot好难,但是再难的问题如果把它一步步拆开,一个个解决,问题也就将迎刃而解。做uboot移植,我们首先就得了解uboot的编译流程,这里以在iTOP4412精英版2G内存的板子上移植u-boot…

<Linux开发> -之-系统移植 uboot移植过程详细记录(第二部分)

<Linux开发> -之-系统移植 uboot移植过程详细记录(第二部分) 第一部分链接:系统移植-之-uboot移植第一部分 第一部分主要讲解了,uboot移植过程中使用的一些工具的安装,以及测试nxp远程uboot&a…

X210开发板(S5PV210芯片)uboot移植DM9000驱动移植

前言 本文是介绍在uboot中如何移植DM9000的驱动,并不深入去讲解DM9000芯片的操作时序和内部寄存器,想要读懂驱动代码要仔细阅读DM9000芯片的数据手册。移植的基础是手里有DM9000芯片可以用的驱动代码,只需要根据开发板中DM9000芯片的接线方式…

嵌入式linux UBoot移植篇

如何在U-boot添加自己的linux板卡并启动呢? uboot 的移植并不是说我们完完全全的从零开始将 uboot 移植到我们现在所使用的开发板或者开发平台上。这个对于我们来说基本是不可能的,这个工作一般是半导体厂商做的, 半导体厂商负责将 uboot 移…

Uboot移植流程

linux-Bootloader(Uboot)移植流程 前言 最近在做ZigBee的温室大棚项目,将自己学习的过程和经验分享给大家。本文基于linux3.4.39内核版本,s5p6818开发板实现。 1、uboot启动简介 uboot启动的过程比较复杂,这里就只…

IMX6ULL Uboot 移植

使用的开发板:正点原子ALPHA V2.2 Uboot简介 在学习STM32的过程中使用过IAP在线升级就会知道,有引导程序APP程序,即bootloader程序APP。在学习嵌入式Linux的时候也一样,这个引导程序就是Uboot. uboot移植主要是根据原厂的uboot移…

二、uboot移植

二、uboot移植 版本作者时间备注V 1.0bug设计工程师2021/11/10创建文件软件网盘链接0交叉编译工具链接:https://pan.baidu.com/s/1yFO2NDMet9_b1E1q1rMwEA提取码:42kluboot源码同上linux源码同上文件系统工具同上tftp工具同上2.1 简单说明 uboot制作结束会生成 u-boot-etc44…

linux-uboot 移植四 uboot的移植

概述 前边的章节中介绍到如果要移植uboot的话,最好的参考就是由官方提供的demo。 1、移植 1.1 添加board对应的板级文件夹 uboot 中每个板子都有一个对应的文件夹来存放板级文件,比如开发板上外设驱动文件等等。 NXP 的 I.MX 系列芯片的所有板级文件…

[uboot 移植]uboot 移植过程

文章目录 uboot 移植1 修改顶层 Makefile2 在 board 文件夹下添加开发板对应的板级文件2.1 imximage_lpddr2.cfg 和 imximage.cfg 文件2.2 plugin.S 文件2.3 Kconfig 文件2.4 igkboard.c 文件2.5 MAINTAINERS 文件2.6 Makefile 文件 3 添加 igkboard_defconfig 配置文件4 添加开…

UBoot 移植

1 NXP官方开发板uboot编译测试 1 查找 NXP 官方的开发板默认配置文件 因为我们的开发板是参考 NXP 官方的 I.MX6ULL EVK 开发板做的硬件,因此我们在移植 uboot 的时候就可以以 NXP 官方的 I.MX6ULL EVK 开发板为蓝本。 在 NXP 官方 I.MX6UL/6ULL 默认配置文件中找…

大话uboot 移植

结合作者多年的移植经验,尽量简单的为大家描述一个uboot 的移植过程。希望通过描述,给初入移植行道的你带来美好的希望。接下来,我们通过以下几个方面来描述。 1. arm soc 的启动方式 在描述soc 前,我们先看下一个简单的arm soc:…

uboot移植步骤

Uboot移植具体步骤(本例子为Samsung origen板) 第一步:准备源码 网上下载现成的uboot开源代码:https://ftp.denx.de/pub/u-boot/ 在该网站中选择与板子兼容的uboot源文件(公司中一般咨询硬件工程师) 在Linux系统下解压 tar xf 压缩包名 第二步:修改源码 1.抄板:将和你板子兼容…

(二)uboot移植--从零开始自制linux掌上电脑(F1C200S)<嵌入式项目>

目录 一、前言 二、F1C200s上电启动顺序 三、前期准备 四、新建用户 五、交叉编译环境配置 六、uboot简介 七、uboot移植 🍏 uboot下载 🍏 uboot默认配置 🍏 uboot图形界面配置 🍏 uboot编译 🍏 烧录bin…

U-Boot 移植初探

1. NXP官方开发板uboot编译测试 uboot移植不需要从零开始将uboot移植到使用的开发板上。因为半导体厂商通常都会自己做一个开发板, 将uboot移植到他们自己的原厂开发板上,再将这个uboot(原厂BSP 包)发布出去。因此使用自已的开发…

U-Boot移植

一、U-Boot Linux 系统要启动就必须需要一个 bootloader 程序,芯片上电以后先运行一段bootloader程序。 bootloader程序会先初始化DDR等外设,然后将Linux内核从flash(NAND,NOR FLASH, SD, eMMC 等)拷贝到 DDR 中&…

uboot移植

一、我们知道uboot就是一个Bootloader。但是,arm不像我们的pc机一样,用一个老毛桃随便找一个网站下一个windows镜像就可以直接装了。 我们的uboot对应的就是老毛桃里面刷的引导程序。 虽然uboo支持很多架构很多不同的厂家的板子,但是UBOOT它…