近一个月上海疫情越来越严重,已居家办公三周。不得不感慨,平平安安就是福。
这里我基于Android 10.0
画了一下抽象的站在整个Android Framework
来看应用层的启动流程。
通过这几天对Framework
层源码的学习过程中,习得一点经验。
- 不可完全按照书本、博客等资料上说的来人云亦云。不同版本有差异,分析源码要亲力亲为。看别人怎么做的时候,自己也要动手。抱着怀疑、辩证的态度去看。
- 源码体量太大,没法记住每个
API
函数调用链路,个人觉得是没有必要去强行记住。细节真的太多,主要还是以理解为主,抓核心原理就好。 - 虽然不同版本的
framework
实现细节不一样,但它们在交互上的本质Binder
、AIDL
没有变化,外部的架构也没有变化。
下面截取发现ATMS
过程记录一下,上一次详细去读Activity
启动流程当时Android
版本发布到了7.0
,转眼今年13.0
也快出来了。
发现这个不同的点时,我当时正基于12.0
的sdk
源码阅读,从Activity.startActivity(intent)
跟踪下去到Instrumentation.execStartActivity(...)
方法看到了ActivityTaskManager
,有点懵逼了,和我之前理解的不太一样,不应该是AMS
的代理对象么?带着这个疑问我开始就近翻阅不同版本的Instrumentation
,发现从10.0
开始变更。那么我们着重来看这两个版本的差异。
Android 9.0(28)1
2
3
4
5
6// Instrumentation.java execStartActivity(...)
int result = ActivityManager.getService()
.startActivity(whoThread, who.getBasePackageName(), intent,
intent.resolveTypeIfNeeded(who.getContentResolver()),
token, target != null ? target.mEmbeddedID : null,
requestCode, 0, null, options);
Android 10.0(29)1
2
3
4
5
6// Instrumentation.java execStartActivity(...)
int result = ActivityTaskManager.getService()
.startActivity(whoThread, who.getBasePackageName(), intent,
intent.resolveTypeIfNeeded(who.getContentResolver()),
token, target != null ? target.mEmbeddedID : null,
requestCode, 0, null, options);
这里我截取了最关键的调用处Instrumentation.execStartActivity(...)
在9.0
委托给了ActivityManager
,在10.0
以后是ActivityTaskManager
,我们需要关心的应该是getService()
返回的对象。
Android 9.0(28)1
2
3
4
5
6
7
8
9
10
11
12
13
14
15// ActivityManager.java
public static IActivityManager getService() {
return IActivityManagerSingleton.get();
}
private static final Singleton<IActivityManager> IActivityManagerSingleton =
new Singleton<IActivityManager>() {
protected IActivityManager create() {
final IBinder b = ServiceManager.getService(Context.ACTIVITY_SERVICE);
final IActivityManager am = IActivityManager.Stub.asInterface(b);
return am;
}
};
Android 10.0(29)1
2
3
4
5
6
7
8
9
10
11
12
13// ActivityTaskManager.java
public static IActivityTaskManager getService() {
return IActivityTaskManagerSingleton.get();
}
private static final Singleton<IActivityTaskManager> IActivityTaskManagerSingleton =
new Singleton<IActivityTaskManager>() {
protected IActivityTaskManager create() {
final IBinder b = ServiceManager.getService(Context.ACTIVITY_TASK_SERVICE);
return IActivityTaskManager.Stub.asInterface(b);
}
};
不难发现在getService()
的调用上,设计思路没有任何变化,都是通过AIDL
来获取远端的服务,只不过在10.0
版本中获取到的接口变成了IActivityTaskManager
,这里我们拿到的是AIDL
中的Binder
代理对象,我们翻过去看下Server
端的实现类ActivityTaskManagerService.java
。
而9.0
的实现类是ActivityManagerService.java
也就是我们经常提起的AMS
服务。
通过翻阅工程,发现其实在10.0
版本的源码中也存在ActivityManagerService.java
这让人有点迷惑,为什么既有AMS
又有ATMS
。
既然这样只好翻开大名鼎鼎的SystemServer.java
来看看在Framework
初始化各服务时到是怎么工作的?
Android 9.0(28)1
2
3
4
5
6// SystemServer.java
mActivityManagerService = mSystemServiceManager.startService(
ActivityManagerService.Lifecycle.class).getService();
mActivityManagerService.setSystemServiceManager(mSystemServiceManager);
mActivityManagerService.setInstaller(installer);
Android 10.0(29)1
2
3
4
5
6
7
8// SystemServer.java
ActivityTaskManagerService atm = mSystemServiceManager.startService(
ActivityTaskManagerService.Lifecycle.class).getService();
mActivityManagerService = ActivityManagerService.Lifecycle.startService(
mSystemServiceManager, atm);
mActivityManagerService.setSystemServiceManager(mSystemServiceManager);
mActivityManagerService.setInstaller(installer);
可以看到相比9.0
在10.0
版本中同时会把ATMS
和AMS
都初始化,并把ATMS
作为入参给了AMS
。
那么我们来看看在10.0
之后的AMS
会怎么处理。
Android 10.0(29)1
2
3
4
5
6
7
8
9// ActivityManagerService.java
public int startActivity(IApplicationThread caller, String callingPackage,
Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) {
// 委托给了 mActivityTaskManager 来处理
return mActivityTaskManager.startActivity(caller, callingPackage, intent, resolvedType,
resultTo, resultWho, requestCode, startFlags, profilerInfo, bOptions);
}
这里发现在高版本中AMS
中对于调度Activity
相关的内容已转给ATMS
来完成。
同时在ATMS
内部对栈管理也发生了一些变化
12.0
用的ActivityTaskSupervisor
10.0、9.0
用的ActivityStackSupervisor
来管理Activity
栈,特别是10.0
版本中从ActivityStackSupervisor
删除了下面几个stack
,集中由RootActivityContainer
来管理,到了12.0
调整为RootWindowContainer
。
Android 9.0(28)1
2
3
4// ActivityStackSupervisor.java
ActivityStack mHomeStack;
ActivityStack mFocusedStack;
private ActivityStack mLastFocusedStack;
Android 10.0(29)1
2// ActivityStackSupervisor.java
RootActivityContainer mRootActivityContainer;
Android 12.0(29)1
2// ActivityTaskSupervisor.java
RootWindowContainer mRootWindowContainer;
细节不展开了,整套流程还是很复杂,调用链路非常长。可参考下面的链接对 Android 11.0
的Activity
启动分析,我对着12.0
比了一下调用xxxStaskxxx()
相关的函数都改成了xxxTasksxxx()
:
https://zhuanlan.zhihu.com/p/382133130
这里我更加关心一个问题为啥要改成这样?
个人觉得有两个方面:
在名称上把ActivityManager
改成ActivityTaskManager
可能更符合外面对它的认知。直接改名,会造成兼容性问题。虽然Android
官方可以在Framework
层面将所有的调用处都替换成ATMS
但对于应用层各种反射、Hook
手段完成完成诸如插件化加载的事情可能会造成大面积失效。基于此不得不把原来的类保留。(向来sdk
层的改动都是向前先兼容多个版本的,后面可能也会废弃)
不过这两个原因都只是我单方面猜测,不确定Google
的开发者做这件事的时候是怎么思考的。
更正:
经过分析发现在Android 10.0
版本中,ATMS
被设计出来专门调度Activity
生命周期。而AMS
职责没有变,它范围更广泛,需要对四大组件的生命周期、进程进行管理。这么看我觉得这样做的好处是把ATMS
的事情都拆了出来。