Android动态加载代码技术

TP4054芯片实战:手把手教你设计USB锂电充电电路(附PCB散热优化技巧) 本文以TP4054芯片为核心,手把手教你设计稳定可靠的USB锂电池充电电路。文章详细解析了芯片的恒流恒压工作模式、关键外围元件选型计算,并重点分享了PCB布局与散热优化的实战技巧,帮助工程师从“能工作”提升到“工作得好”,确保充电效率与系统稳定性。 阅读详情

      在开发Android App的过程当中,可能希望实现插件式软件架构,将一部分代码以另外一个APK的形式单独发布,而在主程序中加载并执行这个APK中的代码。

      实现这个任务的一般方法是:

复制代码
// 加载类cls
Context pluginContext = mainContext.createPackageContext(PLUGIN_PKG, Context.CONTEXT_IGNORE_SECURITY | Context.CONTEXT_INCLUDE_CODE);
ClassLoader loader = pluginContext.getClassLoader();
Class<?> cls = loader.loadClass(CLASS_NAME);
// 通过反射技术,调用cls中的方法,下面是一个示例,实际代码因情况而定
Object obj = cls.newInstance();
Method method = cls.getDeclaredMethod("someMethod");
method.invoke(obj);
复制代码

      但是,这个方法在Android 4.1及之后的系统中存在一些问题:对于收费应用,Google Play会将其安装在一个加密目录之下(具体就是/data/app-asec),而不是一个普通目录之下(具体就是/data/app);安装在加密目录中的应用,我们是无法使用上述方法来加载并执行代码的;而实际情况是,我们经常就是依靠插件应用来收费的。

      解决上述问题的一个方案是:将插件的二进制代码拷贝到SD卡中,主程序从SD卡中加载并执行其代码。

      实现这个任务的具体方法是:

复制代码
Class<?> cls = null;
try {
     // 尝试第一种方法
     cls = loadClass1(mainContext, pkg, entryCls);
} catch (Exception e) {
     // 尝试第二种方法
     cls = loadClass2(mainContext, pkg, entryCls);
}
// 示例代码
Object obj = cls.newInstance();
Method method = cls.getDeclaredMethod("someMethod");
method.invoke(obj);
// 第一种加载方法
private Class<?> loadClass1(Context mainContext, String pkg, String entryCls) throws Exception {
    Context pluginContext = mainContext.createPackageContext(pkg, Context.CONTEXT_INCLUDE_CODE | Context.CONTEXT_IGNORE_SECURITY);
    ClassLoader loader = pluginContext.getClassLoader();
    return loader.loadClass(entryCls); 
}

// 第二种加载方法
private Class<?> loadClass2(Context mainContext, String pkg, String entryCls) throws Exception {
    Context pluginContext = mainContext.createPackageContext(pkg, Context.CONTEXT_INCLUDE_CODE | Context.CONTEXT_IGNORE_SECURITY);
    String path = generatePluginDexPath(mainContext, pkg);
    ensureFileExist(pluginContext, pkg, path);
    // cacheDir必须是主程序的私有目录,否则DexClassLoader可能会拒绝加载
    String cacheDir = mainContext.getApplicationInfo().dataDir;
    ClassLoader parentLoader = pluginContext.getClassLoader();
    DexClassLoader loader = new DexClassLoader(path, cacheDir, null, parentLoader);
    return loader.loadClass(entryCls);
}

// 获取程序版本号
private int getVersionCode(Context context, String pkg) {
    PackageInfo info = null;
    int versionCode = 0;
    try {
         info = context.getPackageManager().getPackageInfo(pkg, PackageManager.GET_ACTIVITIES);
         versionCode = info.versionCode;
    } catch (Exception e) {} 
    return versionCode;
}

// 获取插件二进制代码的存储位置,注意做好版本控制;路径必须是以.dex结束,否则加载会出问题
private String generatePluginDexPath(Context context, String pkg) {
    int version = getVersionCode(context, pkg);
    String path = getMyAppPath() + ".classes/" + pkg + version + ".dex";
    return path;
}

// 主程序在SD卡上的数据目录
private String getMyAppPath() {
    return Environment.getExternalStorageDirectory().getAbsolutePath() + "/MyApp/";
}
// 拷贝插件的二进制代码到SD卡
private void ensureFileExist(Context pluginContext, String pkg, String path) throws Exception {
    File file = new File(path);
    if(file.exists()) return;
    file.getParentFile().mkdirs();
    Resources res = pluginContext.getResources();
    int id = res.getIdentifier("classes", "raw", pkg);
    InputStream in = res.openRawResource(id);
    FileOutputStream out = new FileOutputStream(file);
    try {
         byte[] buffer = new byte[1024 * 1024];
         int n = 0;
         while((n = in.read(buffer)) > 0) {
            out.write(buffer, 0, n);
         } out.flush();
    } catch (IOException e) {
       in.close();
       out.close();
    }
}
复制代码

 

      插件工程这边也需要做相应的修改:

      1.编译插件工程;

      2.将bin目录之下的classes.dex拷贝到/res/raw目录之下;

      3.重新编译插件工程;

      4.发布插件APK。

PyCharm安装PyQt5及工具详细教程 PyCharm是一款功能强大的Python集成开发环境(IDE),而PyQt5是一个用于创建GUI应用程序的流行Python库。在本教程中,我将指导您如何在PyCharm中安装PyQt5及其相关工具,并提供相应的源代码示例。安装完成后,启动PyCharm并创建一个新的项目。为了隔离项目的依赖项,我们建议在PyCharm中使用虚拟环境。在创建项目的过程中,您可以选择创建新的虚拟环境或使用现有的环境。根据您的操作系统,选择适当的版本并按照安装向导的指示进行安装。首先,您需要下载并安装PyCharm。 阅读详情

相关推荐

mobaXterm连接vmWare虚拟机上的centOS7提示连接失败的解决方法

1.问题描述: mobaXterm安装后连接虚拟机vmWare上的centOS7发现连接不上,如下图所示: 2.解决方法 先是查了一下centOS的ip 开始错误的以为 virbr0: 后面的inet就是虚拟机的IP 实则不然(正确的ip是在ens33后面的inet中的ip,大佬们勿喷) 这个值需要配置一下的,具体配置过程如下: step1: 进入centOS下的/...

hss19214的博客 7891

app启动页数秒加载 代码_一次有意思的技术降级,iOS 启动广告,直接 push,首页不出现

PM 提了个需求,启动广告界面点击了, 就直接进,不需要闪一下主界面。要这种:实现的思路,多 window 模式一般的广告界面就是 Key Window 上面的遮罩(子视图)。要从广告界面 push,自然广告界面是一个控制器了。 提升广告界面的层级,才可以。这里提升为 window 。然后就是切换展示的窗口了,通过系统单例 AppDelegate , [delegate.window makeKe...

weixin_39731456的博客 232

NX二次开发编译时dll自动数字签名及拷贝

在UG5.0开始,所有基于UG二次开发的DLL都要“签名”后才能被客户端上正版的NX调用。

菜鸟爱飞不飞的博客 2686

提前加载数据:让应用启动速度更快

???? 使用PreLoader,实现预加载数据,提升您的应用启动速度与用户体验。 ## 项目介绍 **PreLoader** 是一个强大的Android库,旨在减少用户等待时间,通过在Activity打开前预先加载数据,然后在界面初始化完成后展示这些数据。它允许您在任何地方开始预加载任务,并通过唯一的`preLoaderId`监听数据加载完成的事件。 ## 项目技术分析 PreLoader ...

gitblog_00100的博客 1262

SpringBoot使用mybatis-plus的自动代码生成器

一.SpringBoot使用mybatis-plus+自动代码生成 使用mybatis-plus可以自动帮我们生成通用的 controller,service,dao,mapper 二.加入依赖 <!-- MP 核心库 --> <dependency> <groupId>com.baomidou</groupId> <artif...

农民娃儿的博客 2267

Win10家庭版如何添加本地用户和组

在众多Windows版本中,Windows 10以其丰富的功能和卓越的性能吸引了大量用户。然而,对于使用Win10家庭版的用户来说,他们可能会遇到一些功能上的限制,特别是在用户和组管理方面。虽然家庭版在某些高级功能上有所缩减,但我们仍然可以通过一些技巧来实现对本地用户和组的管理。本文将详细介绍如何在Win10家庭版中添加本地用户和组,以便用户能够更好地管理计算机资源。

nntxthml的博客 4558

【Android开发那点破事】打开APP加载页面实现

今天的破事呢就说说APP加载页面的实现。一般情况下,当APP打开的时候,我们需要做很多事情,比如检查网络连接啊,初始化一些配置啊等等。我们可以让这些事情在APP完全打开之前做完,然后呢在打开的过程中显示一些logo信息。想必大家都见过。先贴个运行效果:好,我们进入正题。首先我们先配置下AndroidManifest.xml在application节点里面添加一个自定义的activity:

Cross 1万+

Simulink仿真模块-Signal Generator

Signal Generator:生成各种波形 所在的位置库为:Simulink / Sources 模型为: 说明 Signal Generator模块可以产生四种不同波形: 正弦波 方波 锯齿波 随机 可以使用 hertz 或 rad/sec 为单位表示信号参数。双击模型可以选择需要生成的波形,如图所示: 使用默认参数值,可以获得下列波形之一: 波形 波形输出 正弦波 ...

jk_101的博客 2656

iOS 底层探索 - 应用加载

App 从被用户在主屏幕上点击之后就开启了它的生命周期,那么在这之中,究竟发生了什么呢?让我们从 App 启动开始探索。在探索之前,我们需要熟悉一些前导知识点。 一、前导知识 以下参考自 WWDC 2016 Optimizing App Startup Time : 1.1 Mach-O Mach-O is a bunch of file types for different run ...

Write the code Change the world 690

脑机接口中的视觉信号解码:原理、技术与应用

脑机接口中的视觉信号解码:原理、技术与应用​ ,人工智能,计算机视觉,大模型,AI,脑机接口(Brain - Computer Interface,BCI)作为一种革命性的技术,致力于搭建人脑与外部设备之间的直接通信桥梁,绕开传统的神经肌肉输出通路。其核心目标是解读大脑活动产生的信号,从而实现对外部设备的精准控制或信息交互。在众多脑机接口研究方向中,视觉信号解码因其独特的优势和广泛的应用前景,吸引了大量科研人员的关注。

不踩坑,不知道坑有多深;不总结,踩过的坑白踩。 20万+

30天入门 SAP BTP 开发系列之八:动手在 SAP BTP 上开发第一个 ABAP 透明表

ABAP Cloud 环境下创建透明表的方法与数据迁移实践 本文介绍了在 SAP BTP ABAP 环境中创建透明表并迁移数据的完整流程。与传统的 SE11 事务码不同,ABAP Cloud 需通过 ABAP Development Tool 创建数据库表,使用代码定义表结构。作者详细演示了如何: 在开发包中创建名为 Z优快云_TRAVEL 的透明表 使用 ABAP 代码定义表字段和约束 通过 ABAP 类实现数据从标准表/DMO/TRAVEL 到新建表的迁移 验证数据迁移结果 文中还提供了相关技术概念的

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 1789

APK反破解之四:Android代码动态加载技术

Android应用开发在一般情况下,常规的开发方式和代码架构就能满足我们的普通需求。但是有些特殊问题,常常引发我们进一步的沉思。我们从沉思中产生顿悟,从而产生新的技术形式。 如何开发一个可以自定义控件的Android应用?就像eclipse一样,可以动态加载插件;如何让Android应用执行服务器上的不可预知的代码?如何对Android应用加密,而只在执行时自解密,从而防止被破解?……

ImKing 3465

复分析 阿尔福斯(Ahlfors) 第三版答案 英文

答案分为十章,有部分习题没有答案,全英文复分析阿尔福斯(Ahlfors) 第三版答案

动态versioncode_Android动态加载代码技术

Class> cls = null;try {// 尝试第一种方法cls = loadClass1(mainContext, pkg, entryCls);} catch (Exception e) {// 尝试第二种方法cls = loadClass2(mainContext, pkg, entryCls);}// 示例代码Object obj = cls.newInstance();Me...

weixin_29557763的博客 258

老版QQ原生表情gif动态

这是老版的QQ表情,不过全是动态的的,Windows照片查看器是不会动的,可以右击用浏览器打开查看,再说一遍是老版的,只是分享给宁愿用老版也要动态的人。

STM32F407中文手册

STM32f407中文手册 本参考手册面向应用开发人员,提供有关使用 STM32F405xx/07xx、STM32F415xx/17xx、 STM32F42xxx 和 STM32F43xxx 微控制器存储器与外设的完整信息。STM32F405xx/07xx、STM32F415xx/17xx、STM32F42xxx 和 STM32F43xxx 构成一个微 控制器系列,各产品具有不同的存储器大小、封装和外设。有关订购信息以及器件的机械与电气特性,请参见数据手册。有关 ARM Cortex™-M4F 内核的信息,请参见《Cortex™-M4F 技术参考手册》。

APK反破解Android代码动态加载技术

Android应用开发在一般情况下,常规的开发方式和代码架构就能满足我们的普通需求。但是有些特殊问题,常常引发我们进一步的沉思。我们从沉思中产生顿悟,从而产生新的技术形式。     如何开发一个可以自定义控件的Android应用?就像eclipse一样,可以动态加载插件;如何让Android应用执行服务器上的不可预知的代码?如何对Android应用加密,而只在执行时自解密,从而防止被破解?…

u012244799的专栏 528

霍尼韦尔SoftMaster使用说明

霍尼韦尔SoftMaster使用说明

【转载】APK反破解之四:Android代码动态加载技术

转载请注明出处:http://www.blogjava.net/zh-weir/arch...29/362294.html Android类动态加载技术 Android应用开发在一般情况下,常规的开发方式和代码架构就能满足我们的普通需求。但是有些特殊问题,常常引发我们进一步的沉思。我们从沉思中产生顿悟,从而产生新的技术形式。 如何开发一个可以自定义控件的Android应用?...

weixin_33852020的博客 91

Android应用安全防护:代码混淆与动态加载技术详解

在移动应用开发中,代码混淆和动态加载是提升安全性的关键技术。代码混淆通过重命名标识符、优化代码结构等方式,使反编译后的代码难以阅读,ProGuard是Android平台的标准工具。动态加载技术则将核心逻辑分离,运行时加载加密的插件文件,有效防止静态分析。这两种技术组合使用,可构建分层防护体系,适用于金融、支付等高安全需求场景。随着黑产技术升级,结合LLVM混淆和RASP等前沿方案能进一步提升防护强度。

weixin_29325007的博客 238

Android之动态加载技术

下面是我看过Android动态加载技术的几篇博文,分享~

gfdgdfgdg的专栏 1271
上一篇: Android中的动态加载机制
下一篇: 如何利用dex2jar反编译APK
codepython
博客等级 码龄20年 125粉丝 6原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值