Android(安卓)Launcher启动流程
Launcher App 由SystemServer启动,而SystemServer由Zygote进程孵化出来的。
Zygote是孵化器,所有其他Dalvik/ART虚拟机进程都是用过zygote孵化(fock)出来的
SystemServer进程是Android系统的核心之一,大部分Android提供的服务都在该进程中,主要包括ActivityManagerService(AMS)、WindowManagerService(WMS)、PackageManagerSerice(PMS)等。
来看zygote-> SystemServer 入口:
位于frameworks/base/services/java/com/android/server/SystemServer.java
public static void main(String[] args) { new SystemServer().run();}
可以看到,这里main方法调用了run方法
private void run() { //...// Start services. traceBeginAndSlog("StartServices"); startBootstrapServices(); //启动引导服务 startCoreServices(); //启动核心服务 startOtherServices(); //启动其他服务 //...}
来看startOtherServices,主要来看SystemServer的systemReady方法,这是Launcher启动的唯一入口。这个方法的作用是只有AMS启动完毕后,才会去回调Runnable中的代码。
private void startOtherServices(){ //...mActivityManagerService.systemReady(() -> { //只有ActivityManagerService启动完之后,才会去启动回调里的这些服务 Slog.i(TAG, "Making services ready"); mSystemServiceManager.startBootPhase( SystemService.PHASE_ACTIVITY_MANAGER_READY); //... } //...}
来看ActivityManagerService.systemReady()
public void systemReady(final Runnable goingCallback, TimingsTraceLog traceLog) { //...mStackSupervisor.resumeFocusedStackTopActivityLocked();//...}
再来看ActivityStackSupervisor.resumeFocusedStackTopActivityLocked
boolean resumeFocusedStackTopActivityLocked( ActivityStack targetStack, ActivityRecord target, ActivityOptions targetOptions) { //... final ActivityRecord r = mFocusedStack.topRunningActivityLocked(); if (r == null || r.state != RESUMED) { mFocusedStack.resumeTopActivityUncheckedLocked(null, null); } else if (r.state == RESUMED) { mFocusedStack.executeAppTransition(targetOptions); } return false;}
再来看ActivityStack.resumeTopActivityUncheckedLocked
boolean resumeTopActivityUncheckedLocked(ActivityRecord prev, ActivityOptions options) { //... boolean result = false; try { mStackSupervisor.inResumeTopActivity = true; result = resumeTopActivityInnerLocked(prev, options); } finally { mStackSupervisor.inResumeTopActivity = false; }//... return result; }
再来看resumeTopActivityInnerLocked
private boolean resumeTopActivityInnerLocked(ActivityRecord prev, ActivityOptions options) { //... if (!hasRunningActivity) { return resumeTopActivityInNextFocusableStack(prev, options, "noMoreActivities"); } //...}
接着来看resumeTopActivityInNextFocusableStack
private boolean resumeTopActivityInNextFocusableStack(ActivityRecord prev, ActivityOptions options, String reason) { //...// Only resume home if on home display return isOnHomeDisplay() && mStackSupervisor.resumeHomeStackTask(prev, reason);}
这里的mStackSupervisor.resumeHomeStackTask
就是真正启动Launcher App的入口了
boolean resumeHomeStackTask(ActivityRecord prev, String reason) { //... return mService.startHomeActivityLocked(mCurrentUser, myReason);}
这里会通过ActivityManagerService.startHomeActivityLocked
来看ActivityManagerService
boolean startHomeActivityLocked(int userId, String reason) { //... Intent intent = getHomeIntent(); ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); if (aInfo != null) { //创建Launcher启动所需的Intent intent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name)); // Don't do this if the home app is currently being // instrumented. aInfo = new ActivityInfo(aInfo); aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); ProcessRecord app = getProcessRecordLocked(aInfo.processName, aInfo.applicationInfo.uid, true); if (app == null || app.instr == null) { intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); final int resolvedUserId = UserHandle.getUserId(aInfo.applicationInfo.uid); // For ANR debugging to verify if the user activity is the one that actually // launched. final String myReason = reason + ":" + userId + ":" + resolvedUserId; //启动Launcher mActivityStarter.startHomeActivityLocked(intent, aInfo, myReason); } } else { Slog.wtf(TAG, "No home screen found for " + intent, new Throwable()); } return true; }
可以看到,这里通过Intent,调用mActivityStarter.startHomeActivityLocked
来看ActivityStarter
void startHomeActivityLocked(Intent intent, ActivityInfo aInfo, String reason) { //将Launcher放入HomeStack中,HomeStack是在ActivityManagerService中定义的用于存储Launcher的变量 mSupervisor.moveHomeStackTaskToTop(reason); mLastHomeActivityStartResult = startActivityLocked(null /*caller*/, intent, null /*ephemeralIntent*/, null /*resolvedType*/, aInfo, null /*rInfo*/, null /*voiceSession*/, null /*voiceInteractor*/, null /*resultTo*/, null /*resultWho*/, 0 /*requestCode*/, 0 /*callingPid*/, 0 /*callingUid*/, null /*callingPackage*/, 0 /*realCallingPid*/, 0 /*realCallingUid*/, 0 /*startFlags*/, null /*options*/, false /*ignoreTargetSecurity*/, false /*componentSpecified*/, mLastHomeActivityStartRecord /*outActivity*/, null /*inTask*/, "startHomeActivity: " + reason); if (mSupervisor.inResumeTopActivity) { // If we are in resume section already, home activity will be initialized, but not // resumed (to avoid recursive resume) and will stay that way until something pokes it // again. We need to schedule another resume. mSupervisor.scheduleResumeTopActivities(); } }
在这里就会去Manifest中寻找Launcher应用,并启动Launcher应用,接下来的启动过程就和Activity的启动过程类似了。
其他
参考
Zygote进程浅析
SystemServer进程浅析
Init进程源码分析
开机SystemServer到ActivityManagerService启动过程分析
更多相关文章
- Android(安卓)服务的五大级别
- Android之Intent的基本使用
- android 进程间通信示例
- android中的四种启动模式launchMode
- Android(安卓)系统属性 Property
- Android中Activity启动模式详解
- Android获取CPU使用率的几种方式
- Android命令行启动程序-am命令的使用-纠正网上大部分资料的错误
- Android面试题整理--1