【Android】Activity task和Instrumentation杂谈

2024-04-17 01:04

本文主要是介绍【Android】Activity task和Instrumentation杂谈,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

文章目录

  • activity task
  • Instrumentation机制
  • 参考

Android不仅可以装载众多的系统组件,还可以将它们跨进程组成ActivityTask,这个特性使得每个应用都不是孤立的。

activity task

从数据结构角度看,Task有先后之分,源码实现上采取了stack的方式。这种方式不仅符合用户的逻辑思维和使用习惯,还可以极大复用了系统的资源。

在这里插入图片描述
如图,contacts和SMS分属两个进程,当我们在联系人详情activity中调起了短信进程的短信编辑activity,那么这两个activity就被放到同一个task里面了。这是栈管理activity的方式。

但是ActivityTask不能算严格意义的Stack,默认情况和栈是一致的,但是Android提供了更多的操作方式。

affinity即喜好的意思,它代表这个activity希望归属的task,默认情况同一个程序有共同的affinity,<AndroidManifest.xml>中声明的Package Name。我们也可以主动在中使用taskAffinity标签属性来指定整个应用程序的Affinity。

一个activity task的affinity取决于它的根activity

在默认情况下,目标Activity将与startActivity的调用者处于同一Task中。但如果用户特别指定了FLAG_ACTIVITY_NEW_TASK,表明它希望为Activity重新开设一个Task。

这时就有两种情况:假如当前已经有一个Task,它的affinity与新Activity是一样的,那么系统会直接用此Task来完成操作,而不是另外创建一个Task;否则系统需要重启一个Task。

如果Activity指定了allowTaskReparenting,且后期程序的Task转为前台,它会被移动到和它更“亲近”的task中。

还有一种就是我们常见到的android:launchMode了,比较基础,这里就不展开了。

还有Intent的flag,具体可以查看源码或者官方文档。

Instrumentation机制

Base class for implementing application instrumentation code. When running with instrumentation turned on, this class will be instantiated for you before any of the application code, allowing you to monitor all of the interaction the system has with the application. An Instrumentation implementation is described to the system through an AndroidManifest.xml’s tag.
https://developer.android.com/reference/android/app/Instrumentation

Android系统在/system/bin下提供了很多“中介”程序让用户间接使用system server,例如pm、am等。

Instrumentation是ActivityManager的核心功能之一。

这是官方给出的Instrumentation的adb使用方法:
在这里插入图片描述

"-e"用于指定额外参数,这里给个使用例子:

adb shell am instrument -e class com.lxs.instrument.TestCase -w com.lxs.instrument /android.test.InstrumentationTestRunner

下面分析下它的执行"-e"和 [component]处理流程。

"am instrument"命令由runInstrument的am.java负责解析,和 [component]相关的代码如下:

		//cnArg 就是Component字符串String cnArg = nextArgRequired();//unflatten规则就是以“/”为分隔符,前部分是package,剩余是Class。ComponentName cn = ComponentName.unflattenFromString(cnArg);

“-e”后面所有的[name value]被保存到一个Bundle对象中,和其它参数一起传给AMS,AMS在承载它的进程进行关联后,由BindApplication的ActivityThread处理:

/*frameworks/base/core/java/android/app/ActivityThread.java*/private void handleBindApplication(AppBindData data) {if (data.instrumentationName != null) {//instrumentationName是一个ComponentName对象InstrumentationInfo ii = null;try {ii = appContext.getPackageManager().getInstrumentationInfo(data.instrumentationName, 0);} catch (PackageManager.NameNotFoundException e) {}…mInstrumentationPackageName = ii.packageName;LoadedApk pi = getPackageInfo(instrApp, data.compatInfo,appContext.getClassLoader(), false, true, false);ContextImpl instrContext = ContextImpl.createAppContext(this, pi);try {java.lang.ClassLoader cl = instrContext.getClassLoader();mInstrumentation = (Instrumentation)cl.loadClass(data.instrumentationName.getClassName()).newInstance();} catch (Exception e) {}mInstrumentation.init(this, instrContext, appContext,new ComponentName(ii.packageName, ii.name), data.instrumentationWatcher,data.instrumentationUiAutomationConnection);} else {mInstrumentation = new Instrumentation();}try {Application app = data.info.makeApplication(data.restrictedBackupMode, null);mInitialApplication = app;try {mInstrumentation.onCreate(data.instrumentationArgs);}catch (Exception e) {}try {mInstrumentation.callApplicationOnCreate(app);} catch (Exception e) {}} finally {StrictMode.setThreadPolicy(savedPolicy);}}

AppBindData保存了和应用启动相关的所有关键数据。data.instrumentationArgs对应的是“am instrument”命令中“-e”所指定的额外参数;而data.instrumentationName对应的是“am instrument”命令中的 < COMPONENT >,我们可以根据这个参数构造出用户指定的Instrumentation对象(例如android.test.InstrumentationTestRunner)。当然,如果应用程序并没有Instrumentation组件,那么系统会使用默认的Instrumentation类。

由handleBindApplication的处理可以知道,一个Instrumentation对象的生命周期包括但不限于:

newInstance-> init-> onCreate->onStart-> callApplicationOnCreate->callActivityOnCreate
->callActivityXXX->onDestroy->

Instrumentation提供了一种允许用户获取/改变应用和系统之间的交互流程的机制,自动化测试框架只是其中一种应用形式。InstrumentationTestRunner的原理框架如图:
在这里插入图片描述

如果用户没有指定Instrumentation的话,它的很多行为是“伪实现”,来看下:

/*frameworks/base/core/java/android/app/Instrumentation.java*/public void onCreate(Bundle arguments) {//空实现
}
    public void callActivityOnPause(Activity activity) {activity.performPause();//默认情况下,将直接调用Activity元素的onPause
}

它们之间的关系:
在这里插入图片描述
Instrumentation和ActivityThread运行于同一进程之中,那么它们是否还处于同一个线程呢?
默认情况是肯定的,但是Instrumentation提供了一个方法:

/*frameworks/base/core/java/android/app/Instrumentation.java*/
public void start() {if (mRunner != null) {throw new RuntimeException("Instrumentation already started");}mRunner = new InstrumentationThread("Instr: " + getClass().getName());mRunner.start();}

通过这个方法,会运行在新开的一个线程中。

参考

《深入理解Android内核设计思想》

这篇关于【Android】Activity task和Instrumentation杂谈的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/910393

相关文章

Android实现任意版本设置默认的锁屏壁纸和桌面壁纸(两张壁纸可不一致)

客户有些需求需要设置默认壁纸和锁屏壁纸  在默认情况下 这两个壁纸是相同的  如果需要默认的锁屏壁纸和桌面壁纸不一样 需要额外修改 Android13实现 替换默认桌面壁纸: 将图片文件替换frameworks/base/core/res/res/drawable-nodpi/default_wallpaper.*  (注意不能是bmp格式) 替换默认锁屏壁纸: 将图片资源放入vendo

Android平台播放RTSP流的几种方案探究(VLC VS ExoPlayer VS SmartPlayer)

技术背景 好多开发者需要遴选Android平台RTSP直播播放器的时候,不知道如何选的好,本文针对常用的方案,做个大概的说明: 1. 使用VLC for Android VLC Media Player(VLC多媒体播放器),最初命名为VideoLAN客户端,是VideoLAN品牌产品,是VideoLAN计划的多媒体播放器。它支持众多音频与视频解码器及文件格式,并支持DVD影音光盘,VCD影

android-opencv-jni

//------------------start opencv--------------------@Override public void onResume(){ super.onResume(); //通过OpenCV引擎服务加载并初始化OpenCV类库,所谓OpenCV引擎服务即是 //OpenCV_2.4.3.2_Manager_2.4_*.apk程序包,存

从状态管理到性能优化:全面解析 Android Compose

文章目录 引言一、Android Compose基本概念1.1 什么是Android Compose?1.2 Compose的优势1.3 如何在项目中使用Compose 二、Compose中的状态管理2.1 状态管理的重要性2.2 Compose中的状态和数据流2.3 使用State和MutableState处理状态2.4 通过ViewModel进行状态管理 三、Compose中的列表和滚动

Android 10.0 mtk平板camera2横屏预览旋转90度横屏拍照图片旋转90度功能实现

1.前言 在10.0的系统rom定制化开发中,在进行一些平板等默认横屏的设备开发的过程中,需要在进入camera2的 时候,默认预览图像也是需要横屏显示的,在上一篇已经实现了横屏预览功能,然后发现横屏预览后,拍照保存的图片 依然是竖屏的,所以说同样需要将图片也保存为横屏图标了,所以就需要看下mtk的camera2的相关横屏保存图片功能, 如何实现实现横屏保存图片功能 如图所示: 2.mtk

android应用中res目录说明

Android应用的res目录是一个特殊的项目,该项目里存放了Android应用所用的全部资源,包括图片、字符串、颜色、尺寸、样式等,类似于web开发中的public目录,js、css、image、style。。。。 Android按照约定,将不同的资源放在不同的文件夹中,这样可以方便的让AAPT(即Android Asset Packaging Tool , 在SDK的build-tools目

Android fill_parent、match_parent、wrap_content三者的作用及区别

这三个属性都是用来适应视图的水平或者垂直大小,以视图的内容或尺寸为基础的布局,比精确的指定视图的范围更加方便。 1、fill_parent 设置一个视图的布局为fill_parent将强制性的使视图扩展至它父元素的大小 2、match_parent 和fill_parent一样,从字面上的意思match_parent更贴切一些,于是从2.2开始,两个属性都可以使用,但2.3版本以后的建议使

Android Environment 获取的路径问题

1. 以获取 /System 路径为例 /*** Return root of the "system" partition holding the core Android OS.* Always present and mounted read-only.*/public static @NonNull File getRootDirectory() {return DIR_ANDR

认知杂谈52

今天分享 有人说的一段争议性的话 I I 1拓展人脉很重要** 咱们活在这世上啊,得明白一件事儿,知识、逻辑能力和实战经验虽然重要,但确实都不是最关键的。真正关键的是要懂得怎么和那些手里有资源的人打交道。人脉那可真是一笔无形的大财富呢。你想想看,有时候一个有影响力的人帮你一把,那效果可比你累死累活干一年都强得多。 I I 就比如说,你要是认识个行业里的大牛,他可能给你介绍个特别好的工

Android逆向(反调,脱壳,过ssl证书脚本)

文章目录 总结 基础Android基础工具 定位关键代码页面activity定位数据包参数定位堆栈追踪 编写反调脱壳好用的脚本过ssl证书校验抓包反调的脚本打印堆栈bilibili反调的脚本 总结 暑假做了两个月的Android逆向,记录一下自己学到的东西。对于app渗透有了一些思路。 这两个月主要做的是代码分析,对于分析完后的持久化等没有学习。主要是如何反编译源码,如何找到