赞
踩
SystemServer进程在启动的过程中会启动PackageManagerService,PackageManagerService启动后会将系统中的应用程序安装完成。在此前已经启动的AMS会将Launcher启动起来。
Launcher的入口为AMS的systemReady方法
1
ActivityManagerDebugConfig frameworks/base/services/core/java/com/android/server/am/ActivityManagerDebugConfig.java
这里首先分享一个技巧 可以把这个类里面的这个属性设置为true这样就可以把ActivityManager相关的log打开了
- // Enable all debug log categories.
- // static final boolean DEBUG_ALL = false;
- static final boolean DEBUG_ALL = true;
2
startOtherServices() frameworks/base/services/java/com/android/server/SystemServer.java
此处是一个Lambda表达式省略的部分是一个回调方法
- mActivityManagerService.systemReady(
- ...
- )
3
systemReady() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
这里关于EventLog分享一个查看log的链接https://www.jianshu.com/p/1c9106dd8284
android日志主要分为 kernel、radio、event、main
adb logcat -b xxx
- 130|generic_x86_64:/ # logcat -b events | grep "3040"
- 06-02 00:18:02.017 1541 1556 I am_pss : [2069,10015,com.android.launcher,31063040,17305600,0]
- 06-02 00:22:02.033 1541 1556 I am_pss : [2069,10015,com.android.launcher,31063040,17305600,0]
- 06-02 04:48:12.311 1541 1556 I am_pss : [2069,10015,com.android.launcher,32285696,18903040,0]
- 06-02 09:19:17.510 1541 1556 I am_pss : [2069,10015,com.android.launcher,33040384,19652608,0]
- 06-02 17:51:00.018 1541 1556 I am_pss : [1710,1001,com.android.phone,31703040,20111360,0]
- 06-02 19:26:00.039 1541 1556 I am_pss : [2069,10015,com.android.launcher,34850816,21463040,0]
- public void systemReady(final Runnable goingCallback, TimingsTraceLog traceLog) {
- traceLog.traceBegin("PhaseActivityManagerReady");
- ...
-
- Slog.i(TAG, "System now ready");
- EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY,
- SystemClock.uptimeMillis());
- ...
- }
关于工厂模式FactoryTest可参考这篇文章 https://blog.csdn.net/thl789/article/details/8053574 这里是正常模式
- ...
- //判断工厂模式
- synchronized(this) {
- // Make sure we have no pre-ready processes sitting around.
-
- if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL)
- ...
startPersistentApps 只启动加密感知的持久应用程序;一旦用户被解锁,我们将返回并启动不知情的应用程序可参考这篇文章
https://blog.csdn.net/yaobao888/article/details/77824950
https://www.jianshu.com/p/c9e43905e6b6
https://www.jianshu.com/p/3db7809f231e
- ...
- synchronized (this) {
- // Only start up encryption-aware persistent apps; once user is
- // unlocked we'll come back around and start unaware apps
- startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_AWARE);
- ...
启动Launcher
startHomeActivityLocked(currentUserId, "systemReady");
4
startHomeActivityLocked() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
这里介绍来自这篇 https://blog.csdn.net/learnframework?spm=1001.2014.3001.5509
这里看到了startHomeActivityLocked(currentUserId, “systemReady”);被调用,从名字既可以看得出他是要启动Home类型的Activtiy,常见的Launcher就是一种Home类型的Activity,但这里其实并不是Launcher,而是设置中的FallbackHome类型的,它也是一个Home类型的Activity,这里FallbackHome是google新加入的,主要就是因为涉及整个android系统的加密等原因,系统在还没有完全解锁前,不可以启动Launcher,因为Launcher中明显和各个第三方应用耦合较多(比如桌面可能显示着一堆的各个应用的Widget),如果直接Launcher作为FallbackHome启动,相对就会要求Launcher依赖的应用也是支持直接解密类型,那就肯定不现实。所以就先启动了FallbackHome一个什么也不显示的界面来作为启动真正Launcher的一个过度。
- boolean startHomeActivityLocked(int userId, String reason) {
- if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL
- && mTopAction == null) {
- // We are running in factory test mode, but unable to find
- // the factory test app, so just sit around displaying the
- // error message and don't try to start anything.
- return false;
- }
- Intent intent = getHomeIntent();
- ...
- }
5
getHomeIntent() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
在这个方法中创建了Intent 并将mTopAction、mTopData传入,
String mTopAction = Intent.ACTION_MAIN;
和若是系统运行模式不是低级工厂模式则将Intent的Category设置为Intent.CATEGORY_HOME后返回。
- Intent getHomeIntent() {
- Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
- intent.setComponent(mTopComponent);
- intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING);
- if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
- intent.addCategory(Intent.CATEGORY_HOME);
- }
- return intent;
- }
6
startHomeActivityLocked() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
继续来分析startHomeActivityLocked方法
resolveActivityInfo 此前已经说过,系统在还没有完全解锁前,不可以启动Launcher。所以这里其实并不是Launcher,而是设置中的FallbackHome类型的,它也是一个Home类型的Activity
ProcessRecord Android系统中用于描述进程的数据结构是ProcessRecord对象,AMS便是管理进程的核心模块 可以参考https://www.cnblogs.com/mingfeng002/p/10573298.html
此处的ProcessRecord app 应该是设置的包名 此时调用getProcessRecordLocked获取的就是设置的进程,因为目前android程序还没有启动所以这是获取不到的 app就返回为null再调用后面的启动
- boolean startHomeActivityLocked(int userId, String reason) {
- ...
- Intent intent = getHomeIntent();
- ActivityInfo aInfo = resolveActivityInfo(intent, STOCK_PM_FLAGS, userId);
- if (aInfo != null) {
- ...
- 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;
- mActivityStarter.startHomeActivityLocked(intent, aInfo, myReason);
- }
- } else {
- Slog.wtf(TAG, "No home screen found for " + intent, new Throwable());
- }
-
- return true;
- }

7
mActivityStarter.startHomeActivityLocked() frameworks/base/services/core/java/com/android/server/am/ActivityStarter.java
这里目前就调用了startActivityLocked()
- void startHomeActivityLocked(Intent intent, ActivityInfo aInfo, String reason) {
- 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);
- ...
- }
- }
8
startActivityLocked() frameworks/base/services/core/java/com/android/server/am/ActivityStarter.java
- int startActivityLocked(IApplicationThread caller, Intent intent, Intent ephemeralIntent,
- String resolvedType, ActivityInfo aInfo, ResolveInfo rInfo,
- IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
- IBinder resultTo, String resultWho, int requestCode, int callingPid, int callingUid,
- String callingPackage, int realCallingPid, int realCallingUid, int startFlags,
- ActivityOptions options, boolean ignoreTargetSecurity, boolean componentSpecified,
- ActivityRecord[] outActivity, TaskRecord inTask, String reason) {
-
- ...
- mLastStartActivityResult = startActivity(caller, intent, ephemeralIntent, resolvedType,
- aInfo, rInfo, voiceSession, voiceInteractor, resultTo, resultWho, requestCode,
- callingPid, callingUid, callingPackage, realCallingPid, realCallingUid, startFlags,
- options, ignoreTargetSecurity, componentSpecified, mLastStartActivityRecord,
- inTask);
- ...
- }

9
startActivity() frameworks/base/services/core/java/com/android/server/am/ActivityStarter.java
这里更新一个知识点,frameworks/base/services/core/java/com/android/server/am/ActivityManagerDebugConfig.java的
// Enable all debug log categories.
static final boolean DEBUG_ALL = false; 打开debuglog
ActivityRecord Activity的信息记录在ActivityRecord对象, 并通过通过成员变量task指向TaskRecord 可以参考https://blog.csdn.net/b1480521874/article/details/84637592
注意这块最后调用startActivity的第六个参数为 true
- /** DO NOT call this method directly. Use {@link #startActivityLocked} instead. */
- private int startActivity(IApplicationThread caller, Intent intent, Intent ephemeralIntent,
- String resolvedType, ActivityInfo aInfo, ResolveInfo rInfo,
- IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
- IBinder resultTo, String resultWho, int requestCode, int callingPid, int callingUid,
- String callingPackage, int realCallingPid, int realCallingUid, int startFlags,
- ActivityOptions options, boolean ignoreTargetSecurity, boolean componentSpecified,
- ActivityRecord[] outActivity, TaskRecord inTask) {
- ...
- ActivityRecord r = new ActivityRecord(mService, callerApp, callingPid, callingUid,
- callingPackage, intent, resolvedType, aInfo, mService.getGlobalConfiguration(),
- resultRecord, resultWho, requestCode, componentSpecified, voiceSession != null,
- mSupervisor, options, sourceRecord);
- if (outActivity != null) {
- outActivity[0] = r;
- }
- ...
- return startActivity(r, sourceRecord, voiceSession, voiceInteractor, startFlags, true,
- options, inTask, outActivity);
- }

10
startActivity() frameworks/base/services/core/java/com/android/server/am/ActivityStarter.java
显然这个doResume参数为true 继续调用startActivityUnchecked
- private int startActivity(final ActivityRecord r, ActivityRecord sourceRecord,
- IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
- int startFlags, boolean doResume, ActivityOptions options, TaskRecord inTask,
- ActivityRecord[] outActivity) {
- ...
- result = startActivityUnchecked(r, sourceRecord, voiceSession, voiceInteractor,
- startFlags, doResume, options, inTask, outActivity);
- ...
- }
11
startActivityUnchecked() frameworks/base/services/core/java/com/android/server/am/ActivityStarter.java
这里面调用的setInitialState会将mDoResume这个字段置为 true
接下来调用了mSupervisor.resumeFocusedStackTopActivityLocked
- // Note: This method should only be called from {@link startActivity}.
- private int startActivityUnchecked(final ActivityRecord r, ActivityRecord sourceRecord,
- IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
- int startFlags, boolean doResume, ActivityOptions options, TaskRecord inTask,
- ActivityRecord[] outActivity) {
-
- ...
- setInitialState(r, options, inTask, doResume, startFlags, sourceRecord, voiceSession,
- voiceInteractor);
- ...
-
- if (mDoResume) {
- final ActivityRecord topTaskActivity =
- mStartActivity.getTask().topRunningActivityLocked();
- if (!mTargetStack.isFocusable()
- || (topTaskActivity != null && topTaskActivity.mTaskOverlay
- && mStartActivity != topTaskActivity)) {
- ...
- } else {
- // If the target stack was not previously focusable (previous top running activity
- // on that stack was not visible) then any prior calls to move the stack to the
- // will not update the focused stack. If starting the new activity now allows the
- // task stack to be focusable, then ensure that we now update the focused stack
- // accordingly.
- if (mTargetStack.isFocusable() && !mSupervisor.isFocusedStack(mTargetStack)) {
- mTargetStack.moveToFront("startActivityUnchecked");
- }
- mSupervisor.resumeFocusedStackTopActivityLocked(mTargetStack, mStartActivity,
- mOptions);
- }
- } else {
- ...
- }
- }

12
resumeFocusedStackTopActivityLocked() frameworks/base/services/core/java/com/android/server/am/ActivityStackSupervisor.java
这块调用到了targetStack.resumeTopActivityUncheckedLocked(target, targetOptions);
- boolean resumeFocusedStackTopActivityLocked(
- ActivityStack targetStack, ActivityRecord target, ActivityOptions targetOptions) {
-
- ...
-
- if (targetStack != null && isFocusedStack(targetStack)) {
- return targetStack.resumeTopActivityUncheckedLocked(target, targetOptions);
- }
-
- ...
-
- return false;
- }
13
resumeTopActivityUncheckedLocked() frameworks/base/services/core/java/com/android/server/am/ActivityStack.java
这块调用到了result = resumeTopActivityInnerLocked(prev, options);
- boolean resumeTopActivityUncheckedLocked(ActivityRecord prev, ActivityOptions options) {
- ...
- try {
- // Protect against recursion.
- mStackSupervisor.inResumeTopActivity = true;
- result = resumeTopActivityInnerLocked(prev, options);
- } finally {
- mStackSupervisor.inResumeTopActivity = false;
- }
-
- ...
- return result;
- }
14
resumeTopActivityInnerLocked() frameworks/base/services/core/java/com/android/server/am/ActivityStack.java
由于这块代码实在是太多太复杂了 这里只给出结论,无论这中间代码是如何调用的在这个方法的最后打出了一个log
“resumeTopActivityLocked: Restarting” 显然这里面最后调用了 mStackSupervisor.startSpecificActivityLocked(next, true, true);
- private boolean resumeTopActivityInnerLocked(ActivityRecord prev, ActivityOptions options) {
- ...
-
- } else {
- // Whoops, need to restart this activity!
- if (!next.hasBeenLaunched) {
- next.hasBeenLaunched = true;
- } else {
- if (SHOW_APP_STARTING_PREVIEW) {
- next.showStartingWindow(null /* prev */, false /* newTask */,
- false /* taskSwich */);
- }
- if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Restarting: " + next);
- }
- if (DEBUG_STATES) Slog.d(TAG_STATES, "resumeTopActivityLocked: Restarting " + next);
- mStackSupervisor.startSpecificActivityLocked(next, true, true);
- }
- }

15
startSpecificActivityLocked() frameworks/base/services/core/java/com/android/server/am/ActivityStackSupervisor.java
此部分代码进程为空 接下来调用 mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,"activity", r.intent.getComponent(), false, false, true);
注意这个地方倒数第二个参数 isolated 传递的为 false
- void startSpecificActivityLocked(ActivityRecord r,
- boolean andResume, boolean checkConfig) {
- // Is this activity's application already running?
- ProcessRecord app = mService.getProcessRecordLocked(r.processName,
- r.info.applicationInfo.uid, true);
-
- r.getStack().setLaunchTime(r);
-
- if (app != null && app.thread != null) {
- ...
- }
-
- mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
- "activity", r.intent.getComponent(), false, false, true);
- }
16
startProcessLocked() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
调用自己的重载方法
此时 isolated 为 false
entryPoint 为 null
startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, null /* crashHandler */);
- final ProcessRecord startProcessLocked(String processName,
- ApplicationInfo info, boolean knownToBeDead, int intentFlags,
- String hostingType, ComponentName hostingName, boolean allowWhileBooting,
- boolean isolated, boolean keepIfLarge) {
- return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType,
- hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge,
- null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */,
- null /* crashHandler */);
- }
17
startProcessLocked() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
这个方法主要接下来创建进程
isolated 为 false
entryPoint 为 null
最后调用了startProcessLocked(app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs);
- final ProcessRecord startProcessLocked(String processName, ApplicationInfo info,
- boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName,
- boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge,
- String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) {
- if (!isolated) {
- app = getProcessRecordLocked(processName, info.uid, keepIfLarge);
- //这里app还是为null
- checkTime(startTime, "startProcess: after getProcessRecord");
-
- if ((intentFlags & Intent.FLAG_FROM_BACKGROUND) != 0) {
- ...//不走
- } else {
- // When the user is explicitly starting a process, then clear its
- // crash count so that we won't make it bad until they see at
- // least one crash dialog again, and make the process good again
- // if it had been bad.
- if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid
- + "/" + info.processName);
- mAppErrors.resetProcessCrashTimeLocked(info);
- if (mAppErrors.isBadProcessLocked(info)) {
- EventLog.writeEvent(EventLogTags.AM_PROC_GOOD,
- UserHandle.getUserId(info.uid), info.uid,
- info.processName);
- mAppErrors.clearBadProcessLocked(info);
- if (app != null) {
- app.bad = false;
- }
- }
- }
- } else {
- ...
- }
- ...
- if (app == null) {
- checkTime(startTime, "startProcess: creating new process record");
- app = newProcessRecordLocked(info, processName, isolated, isolatedUid);
- if (app == null) {
- ...//不走
- }
- app.crashHandler = crashHandler;
- checkTime(startTime, "startProcess: done creating new process record");
- } else {
- ...//不走
- }
- ...
- startProcessLocked(
- app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs);
- checkTime(startTime, "startProcess: done starting proc!");
- return (app.pid != 0) ? app : null;
- }

18
startProcessLocked() frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
entryPoint 为 null
if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 构建启动参数 这个参数是最后剩下的在Zygote中用来反射调用main函数的
最后调用了这个 Process.start(entryPoint, app.processName, uid, uid, gids, debugFlags, mountExternal, app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet, app.info.dataDir, invokeWith, entryPointArgs);
注意这个时候把新new出来的ProcessRecord放到mPidsSelfLocked中 this.mPidsSelfLocked.put(startResult.pid, app);
- private final void startProcessLocked(ProcessRecord app, String hostingType,
- String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) {
- ...
- if (entryPoint == null) entryPoint = "android.app.ActivityThread";
- Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " +
- app.processName);
- checkTime(startTime, "startProcess: asking zygote to start proc");
- ProcessStartResult startResult;
- if (hostingType.equals("webview_service")) {
- ...//不走
- } else {
- startResult = Process.start(entryPoint,
- app.processName, uid, uid, gids, debugFlags, mountExternal,
- app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
- app.info.dataDir, invokeWith, entryPointArgs);
- }
- ...
- synchronized (mPidsSelfLocked) {
- this.mPidsSelfLocked.put(startResult.pid, app);
- if (isActivityProcess) {
- Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG);
- msg.obj = app;
- mHandler.sendMessageDelayed(msg, startResult.usingWrapper
- ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT);
- }
- }
- }

19
Process.start() frameworks/base/core/java/android/os/Process.java
一眼望去 zygoteProcess.start(processClass, niceName, uid, gid, gids, debugFlags, mountExternal, targetSdkVersion, seInfo, abi, instructionSet, appDataDir, invokeWith, zygoteArgs);
- public static final ProcessStartResult start(final String processClass,
- final String niceName,
- int uid, int gid, int[] gids,
- int debugFlags, int mountExternal,
- int targetSdkVersion,
- String seInfo,
- String abi,
- String instructionSet,
- String appDataDir,
- String invokeWith,
- String[] zygoteArgs) {
- return zygoteProcess.start(processClass, niceName, uid, gid, gids,
- debugFlags, mountExternal, targetSdkVersion, seInfo,
- abi, instructionSet, appDataDir, invokeWith, zygoteArgs);
- }
20
start() frameworks/base/core/java/android/os/ZygoteProcess.java
- public final Process.ProcessStartResult start(final String processClass,
- final String niceName,
- int uid, int gid, int[] gids,
- int debugFlags, int mountExternal,
- int targetSdkVersion,
- String seInfo,
- String abi,
- String instructionSet,
- String appDataDir,
- String invokeWith,
- String[] zygoteArgs) {
- try {
- return startViaZygote(processClass, niceName, uid, gid, gids,
- debugFlags, mountExternal, targetSdkVersion, seInfo,
- abi, instructionSet, appDataDir, invokeWith, zygoteArgs);
- } catch (ZygoteStartFailedEx ex) {
- Log.e(LOG_TAG,
- "Starting VM process through Zygote failed");
- throw new RuntimeException(
- "Starting VM process through Zygote failed", ex);
- }
- }

Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。