准备启动目标Activity
ActivityStack.resumeTopActivityInnerLocked(下半部分,发送Resume请求)
// /frameworks/base/services/core/java/com/android/server/am/ActivityStack.java
@GuardedBy("mService")
private boolean resumeTopActivityInnerLocked(ActivityRecord prev, ActivityOptions options) {
// .....
//以上省略,主要是PasueActivity窗口隐藏,过渡动画等部分
ActivityStack lastStack = mStackSupervisor.getLastStack();
//通过缓存的ProcressRecord中的IApplicationThread来判断进程是否存在
if (next.app != null && next.app.thread != null) {
if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Resume running: " + next
+ " stopped=" + next.stopped + " visible=" + next.visible);
// If the previous activity is translucent, force a visibility update of
// the next activity, so that it's added to WM's opening app list, and
// transition animation can be set up properly.
// For example, pressing Home button with a translucent activity in focus.
// Launcher is already visible in this case. If we don't add it to opening
// apps, maybeUpdateTransitToWallpaper() will fail to identify this as a
// TRANSIT_WALLPAPER_OPEN animation, and run some funny animation.
final boolean lastActivityTranslucent = lastStack != null
&& (lastStack.inMultiWindowMode()
|| (lastStack.mLastPausedActivity != null
&& !lastStack.mLastPausedActivity.fullscreen));
// The contained logic must be synchronized, since we are both changing the visibility
// and updating the {@link Configuration}. {@link ActivityRecord#setVisibility} will
// ultimately cause the client code to schedule a layout. Since layouts retrieve the
// current {@link Configuration}, we must ensure that the below code updates it before
// the layout can occur.
synchronized(mWindowManager.getWindowManagerLock()) {
// This activity is now becoming visible.
if (!next.visible || next.stopped || lastActivityTranslucent) {
next.setVisibility(true);
}
// schedule launch ticks to collect information about slow apps.
next.startLaunchTickingLocked();
ActivityRecord lastResumedActivity =
lastStack == null ? null :lastStack.mResumedActivity;
final ActivityState lastState = next.getState();
mService.updateCpuStats();
if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to RESUMED: " + next
+ " (in existing)");
next.setState(RESUMED, "resumeTopActivityInnerLocked");
mService.updateLruProcessLocked(next.app, true, null);
updateLRUListLocked(next);
mService.updateOomAdjLocked();
// Have the window manager re-evaluate the orientation of
// the screen based on the new activity order.
boolean notUpdated = true;
if (mStackSupervisor.isFocusedStack(this)) {
// We have special rotation behavior when here is some active activity that
// requests specific orientation or Keyguard is locked. Make sure all activity
// visibilities are set correctly as well as the transition is updated if needed
// to get the correct rotation behavior. Otherwise the following call to update
// the orientation may cause incorrect configurations delivered to client as a
// result of invisible window resize.
// TODO: Remove this once visibilities are set correctly immediately when
// starting an activity.
notUpdated = !mStackSupervisor.ensureVisibilityAndConfig(next, mDisplayId,
true /* markFrozenIfConfigChanged */, false /* deferResume */);
}
if (notUpdated) {
// The configuration update wasn't able to keep the existing
// instance of the activity, and instead started a new one.
// We should be all done, but let's just make sure our activity
// is still at the top and schedule another run if something
// weird happened.
ActivityRecord nextNext = topRunningActivityLocked();
if (DEBUG_SWITCH || DEBUG_STATES) Slog.i(TAG_STATES,
"Activity config changed during resume: " + next
+ ", new next: " + nextNext);
if (nextNext != next) {
// Do over!
mStackSupervisor.scheduleResumeTopActivities();
}
if (!next.visible || next.stopped) {
next.setVisibility(true);
}
next.completeResumeLocked();
if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
return true;
}
try {
final ClientTransaction transaction = ClientTransaction.obtain(next.app.thread,
next.appToken);
// Deliver all pending results.
ArrayList<ResultInfo> a = next.results;
if (a != null) {
final int N = a.size();
if (!next.finishing && N > 0) {
if (DEBUG_RESULTS) Slog.v(TAG_RESULTS,
"Delivering results to " + next + ": " + a);
transaction.addCallback(ActivityResultItem.obtain(a));
}
}
if (next.newIntents != null) {
transaction.addCallback(NewIntentItem.obtain(next.newIntents,
false /* andPause */));
}
// Well the app will no longer be stopped.
// Clear app token stopped state in window manager if needed.
next.notifyAppResumed(next.stopped);
EventLog.writeEvent(EventLogTags.AM_RESUME_ACTIVITY, next.userId,
System.identityHashCode(next), next.getTask().taskId,
next.shortComponentName);
next.sleeping = false;
mService.getAppWarningsLocked().onResumeActivity(next);
mService.showAskCompatModeDialogLocked(next);
next.app.pendingUiClean = true;
next.app.forceProcessStateUpTo(mService.mTopProcessState);
next.clearOptionsLocked();
//设置ResumeActivityItem生命周期的执行
transaction.setLifecycleStateRequest(
ResumeActivityItem.obtain(next.app.repProcState,
mService.isNextTransitionForward()));
调度到App进程
mService.getLifecycleManager().scheduleTransaction(transaction);
if (DEBUG_STATES) Slog.d(TAG_STATES, "resumeTopActivityLocked: Resumed "
+ next);
} catch (Exception e) {
// Whoops, need to restart this activity!
if (DEBUG_STATES) Slog.v(TAG_STATES, "Resume failed; resetting state to "
+ lastState + ": " + next);
next.setState(lastState, "resumeTopActivityInnerLocked");
// lastResumedActivity being non-null implies there is a lastStack present.
if (lastResumedActivity != null) {
lastResumedActivity.setState(RESUMED, "resumeTopActivityInnerLocked");
}
Slog.i(TAG, "Restarting because process died: " + next);
if (!next.hasBeenLaunched) {
next.hasBeenLaunched = true;
} else if (SHOW_APP_STARTING_PREVIEW && lastStack != null
&& lastStack.isTopStackOnDisplay()) {
next.showStartingWindow(null /* prev */, false /* newTask */,
false /* taskSwitch */);
}
mStackSupervisor.startSpecificActivityLocked(next, true, false);
if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
return true;
}
}
// From this point on, if something goes wrong there is no way
// to recover the activity.
try {
//进行resume的后续工作
next.completeResumeLocked();
} catch (Exception e) {
// If any exception gets thrown, toss away this
// activity and try the next one.
Slog.w(TAG, "Exception thrown during resume of " + next, e);
requestFinishActivityLocked(next.appToken, Activity.RESULT_CANCELED, null,
"resume-exception", true);
if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
return true;
}
} 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);
}
//进程不存在或无效,执行startSpecificActivityLocked
if (DEBUG_STATES) Slog.d(TAG_STATES, "resumeTopActivityLocked: Restarting " + next);
mStackSupervisor.startSpecificActivityLocked(next, true, true);
}
if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
return true;
}
复制代码
从上面可以看出,这一部分主要是,判断该进程是否存在,存在则直接发送ResumeActivityItem请求,通知APP执行Resume操作,不存在则调用 startSpecificActivityLocked,下面已进程不存在的情况,继续跟踪
启动新的APP进程
ActivityStackSupervisor.startSpecificActivityLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityStackSupervisor.java
void startSpecificActivityLocked(ActivityRecord r,
boolean andResume, boolean checkConfig) {
// Is this activity's application already running?
//获取目标Activity的进程信息
ProcessRecord app = mService.getProcessRecordLocked(r.processName,
r.info.applicationInfo.uid, true);
getLaunchTimeTracker().setLaunchTime(r);
//判断目标进程是否存在
if (app != null && app.thread != null) {
try {
if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0
|| !"android".equals(r.info.packageName)) {
// Don't add this if it is a platform component that is marked
// to run in multiple processes, because this is actually
// part of the framework so doesn't make sense to track as a
// separate apk in the process.
app.addPackage(r.info.packageName, r.info.applicationInfo.longVersionCode,
mService.mProcessStats);
}
realStartActivityLocked(r, app, andResume, checkConfig);
return;
} catch (RemoteException e) {
Slog.w(TAG, "Exception when starting activity "
+ r.intent.getComponent().flattenToShortString(), e);
}
// If a dead object exception was thrown -- fall through to
// restart the application.
}
mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
"activity", r.intent.getComponent(), false, false, true);
}
复制代码
上面方法里面通过getProcessRecordLocked获取目标App的进程,并判断进程是否存在或有效,来确认下一步流程,若进程存在 则调用realStartActivityLocked继续启动流程,若不存在则调用startProcessLocked,启动目标进程
ActivityManagerService.startProcessLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
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) {
long startTime = SystemClock.elapsedRealtime();
ProcessRecord app;
//...省略
if (app == null) {
checkTime(startTime, "startProcess: creating new process record");
//创建ProcessRecord实例,并存入AMS.mProgressNames中保存
app = newProcessRecordLocked(info, processName, isolated, isolatedUid);
if (app == null) {
Slog.w(TAG, "Failed making new process record for "
+ processName + "/" + info.uid + " isolated=" + isolated);
return null;
}
app.crashHandler = crashHandler;
app.isolatedEntryPoint = entryPoint;
app.isolatedEntryPointArgs = entryPointArgs;
checkTime(startTime, "startProcess: done creating new process record");
} else {
// If this is a new package in the process, add the package to the list
app.addPackage(info.packageName, info.versionCode, mProcessStats);
checkTime(startTime, "startProcess: added package to existing proc");
}
// If the system is not ready yet, then hold off on starting this
// process until it is.
//系统未就绪的处理
if (!mProcessesReady
&& !isAllowedWhileBooting(info)
&& !allowWhileBooting) {
if (!mProcessesOnHold.contains(app)) {
mProcessesOnHold.add(app);
}
if (DEBUG_PROCESSES) Slog.v(TAG_PROCESSES,
"System not ready, putting on hold: " + app);
checkTime(startTime, "startProcess: returning with proc on hold");
return app;
}
checkTime(startTime, "startProcess: stepping in to startProcess");
//进一步执行启动进程
final boolean success = startProcessLocked(app, hostingType, hostingNameStr, abiOverride);
checkTime(startTime, "startProcess: done starting proc!");
return success ? app : null;
}
复制代码
这儿又会继续调用startProcessLocked的重载方法,最后会调用到startProcess方法里面
ActivityManagerService.startProcess
// /frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
private ProcessStartResult startProcess(String hostingType, String entryPoint,
ProcessRecord app, int uid, int[] gids, int runtimeFlags, int mountExternal,
String seInfo, String requiredAbi, String instructionSet, String invokeWith,
long startTime) {
try {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " +
app.processName);
checkTime(startTime, "startProcess: asking zygote to start proc");
final ProcessStartResult startResult;
//判断是否为webview_service
if (hostingType.equals("webview_service")) {
startResult = startWebView(entryPoint,
app.processName, uid, uid, gids, runtimeFlags, mountExternal,
app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
app.info.dataDir, null,
new String[] {PROC_START_SEQ_IDENT + app.startSeq});
} else {
startResult = Process.start(entryPoint,
app.processName, uid, uid, gids, runtimeFlags, mountExternal,
app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
app.info.dataDir, invokeWith,
new String[] {PROC_START_SEQ_IDENT + app.startSeq});
}
checkTime(startTime, "startProcess: returned from zygote!");
return startResult;
} finally {
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
}
}
复制代码
判断是否为webview_service,否则调用Process.start启动进程,找到Process.start
Process.start
// /frameworks/base/core/java/android/os/Process.java
public static final ProcessStartResult start(final String processClass,
final String niceName,
int uid, int gid, int[] gids,
int runtimeFlags, int mountExternal,
int targetSdkVersion,
String seInfo,
String abi,
String instructionSet,
String appDataDir,
String invokeWith,
String[] zygoteArgs) {
return zygoteProcess.start(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, zygoteArgs);
}
复制代码
只是间接调用的zygoteProcess.start方法,继续向下
ZygoteProcess.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 runtimeFlags, int mountExternal,
int targetSdkVersion,
String seInfo,
String abi,
String instructionSet,
String appDataDir,
String invokeWith,
String[] zygoteArgs) {
try {
return startViaZygote(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, false /* startChildZygote */,
zygoteArgs);
} catch (ZygoteStartFailedEx ex) {
Log.e(LOG_TAG,
"Starting VM process through Zygote failed");
throw new RuntimeException(
"Starting VM process through Zygote failed", ex);
}
}
复制代码
调用了startViaZygote
ZygoteProcess.startViaZygote
// /frameworks/base/core/java/android/os/ZygoteProcess.java
private Process.ProcessStartResult startViaZygote(final String processClass,
final String niceName,
final int uid, final int gid,
final int[] gids,
int runtimeFlags, int mountExternal,
int targetSdkVersion,
String seInfo,
String abi,
String instructionSet,
String appDataDir,
String invokeWith,
boolean startChildZygote,
String[] extraArgs)
throws ZygoteStartFailedEx {
ArrayList<String> argsForZygote = new ArrayList<String>();
// --runtime-args, --setuid=, --setgid=,
// and --setgroups= must go first
argsForZygote.add("--runtime-args");
argsForZygote.add("--setuid=" + uid);
argsForZygote.add("--setgid=" + gid);
argsForZygote.add("--runtime-flags=" + runtimeFlags);
if (mountExternal == Zygote.MOUNT_EXTERNAL_DEFAULT) {
argsForZygote.add("--mount-external-default");
} else if (mountExternal == Zygote.MOUNT_EXTERNAL_READ) {
argsForZygote.add("--mount-external-read");
} else if (mountExternal == Zygote.MOUNT_EXTERNAL_WRITE) {
argsForZygote.add("--mount-external-write");
}
argsForZygote.add("--target-sdk-version=" + targetSdkVersion);
//...省略这部分代码,主要是设置启动参数
if (extraArgs != null) {
for (String arg : extraArgs) {
argsForZygote.add(arg);
}
}
synchronized(mLock) {
return zygoteSendArgsAndGetResult(openZygoteSocketIfNeeded(abi), argsForZygote);
}
}
复制代码
可以看出这个函数,会计算启动应用进程的各个参数,然后再调用zygoteSendArgsAndGetResult方法
ZygoteProcess.startViaZygote
// /frameworks/base/core/java/android/os/ZygoteProcess.java
private static Process.ProcessStartResult zygoteSendArgsAndGetResult(
ZygoteState zygoteState, ArrayList<String> args)
throws ZygoteStartFailedEx {
try {
// Throw early if any of the arguments are malformed. This means we can
// avoid writing a partial response to the zygote.
int sz = args.size();
for (int i = 0; i < sz; i++) {
if (args.get(i).indexOf('\n') >= 0) {
throw new ZygoteStartFailedEx("embedded newlines not allowed");
}
}
/**
* See com.android.internal.os.SystemZygoteInit.readArgumentList()
* Presently the wire format to the zygote process is:
* a) a count of arguments (argc, in essence)
* b) a number of newline-separated argument strings equal to count
*
* After the zygote process reads these it will write the pid of
* the child or -1 on failure, followed by boolean to
* indicate whether a wrapper process was used.
*/
final BufferedWriter writer = zygoteState.writer;
final DataInputStream inputStream = zygoteState.inputStream;
writer.write(Integer.toString(args.size()));
writer.newLine();
for (int i = 0; i < sz; i++) {
String arg = args.get(i);
writer.write(arg);
writer.newLine();
}
writer.flush();
// Should there be a timeout on this?
Process.ProcessStartResult result = new Process.ProcessStartResult();
// Always read the entire result from the input stream to avoid leaving
// bytes in the stream for future process starts to accidentally stumble
// upon.
result.pid = inputStream.readInt();
result.usingWrapper = inputStream.readBoolean();
if (result.pid < 0) {
throw new ZygoteStartFailedEx("fork() failed");
}
return result;
} catch (IOException ex) {
zygoteState.close();
throw new ZygoteStartFailedEx(ex);
}
}
复制代码
这个函数将这些参数通过socket发送给zygote进程,zygote进程会孵化出新的dalvik应用进程,然后告诉ActivityManagerService新启动的进程的pid 至于zygote具体的孵化过程就不再详细看下去了,不然跑远了,这部分后续会在Android启动流程中再深入研究 当APP进程创建后会调用AMS的attachApplication方法通知进程启动完成
进程启动完成
ActivityManagerService.attachApplicationLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
private final boolean attachApplicationLocked(IApplicationThread thread,
int pid, int callingUid, long startSeq) {
// Find the application record that is being attached... either via
// the pid if we are running in multiple processes, or just pull the
// next app record if we are emulating process with anonymous threads.
ProcessRecord app;
long startTime = SystemClock.uptimeMillis();
if (pid != MY_PID && pid >= 0) {
synchronized (mPidsSelfLocked) {
app = mPidsSelfLocked.get(pid);
}
} else {
app = null;
}
//省略
//标志进程已经准备好启动
boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info);
//省略
// Remove this record from the list of starting applications.
mPersistentStartingProcesses.remove(app);
if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG_PROCESSES,
"Attach application locked removing on hold: " + app);
mProcessesOnHold.remove(app);
boolean badApp = false;
boolean didSomething = false;
// See if the top visible activity is waiting to run in this process...
//查看有没有活动正在等待此进程的启动
if (normalMode) {
try {
if (mStackSupervisor.attachApplicationLocked(app)) {
didSomething = true;
}
} catch (Exception e) {
Slog.wtf(TAG, "Exception thrown launching activities in " + app, e);
badApp = true;
}
}
//省略
return true;
}
复制代码
这里会继续调用mStackSupervisor.attachApplicationLocked
ActivityStackSupervisor.attachApplicationLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityStackSupervisor.java
boolean attachApplicationLocked(ProcessRecord app) throws RemoteException {
final String processName = app.processName;
//标记是否有启动组件
boolean didSomething = false;
//遍历ActivityDisplay(一个ActivityDisplay对应一个显示屏幕)
for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
final ActivityDisplay display = mActivityDisplays.valueAt(displayNdx);
for (int stackNdx = display.getChildCount() - 1; stackNdx >= 0; --stackNdx) {
final ActivityStack stack = display.getChildAt(stackNdx);
if (!isFocusedStack(stack)) {
continue;
}
stack.getAllRunningVisibleActivitiesLocked(mTmpActivityList);
final ActivityRecord top = stack.topRunningActivityLocked();
final int size = mTmpActivityList.size();
for (int i = 0; i < size; i++) {
final ActivityRecord activity = mTmpActivityList.get(i);
if (activity.app == null && app.uid == activity.info.applicationInfo.uid
&& processName.equals(activity.processName)) {
try {
//启动等待resume的Activity
if (realStartActivityLocked(activity, app,
top == activity /* andResume */, true /* checkConfig */)) {
didSomething = true;
}
} catch (RemoteException e) {
Slog.w(TAG, "Exception in new application when starting activity "
+ top.intent.getComponent().flattenToShortString(), e);
throw e;
}
}
}
}
}
if (!didSomething) {
ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
}
return didSomething;
}
复制代码
可以看出AMS在收到APP进程启动完成后,会调用realStartActivityLocked启动因为等待目标进程启动而暂缓的Activity
准备启动目标Activity
ActivityStackSupervisor.realStartActivityLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityStackSupervisor.java
final boolean realStartActivityLocked(ActivityRecord r, ProcessRecord app,
boolean andResume, boolean checkConfig) throws RemoteException {
if (!allPausedActivitiesComplete()) {
// While there are activities pausing we skipping starting any new activities until
// pauses are complete. NOTE: that we also do this for activities that are starting in
// the paused state because they will first be resumed then paused on the client side.
if (DEBUG_SWITCH || DEBUG_PAUSE || DEBUG_STATES) Slog.v(TAG_PAUSE,
"realStartActivityLocked: Skipping start of r=" + r
+ " some activities pausing...");
return false;
}
final TaskRecord task = r.getTask();
final ActivityStack stack = task.getStack();
beginDeferResume();
try {
//省略
try {
if (app.thread == null) {
throw new RemoteException();
}
List<ResultInfo> results = null;
List<ReferrerIntent> newIntents = null;
if (andResume) {
// We don't need to deliver new intents and/or set results if activity is going
// to pause immediately after launch.
results = r.results;
newIntents = r.newIntents;
}
//省略
// Create activity launch transaction.
final ClientTransaction clientTransaction = ClientTransaction.obtain(app.thread,
r.appToken);
//创建LaunchActivityItem并添加到mActivityCallbacks里保存
clientTransaction.addCallback(LaunchActivityItem.obtain(new Intent(r.intent),
System.identityHashCode(r), r.info,
// TODO: Have this take the merged configuration instead of separate global
// and override configs.
mergedConfiguration.getGlobalConfiguration(),
mergedConfiguration.getOverrideConfiguration(), r.compat,
r.launchedFromPackage, task.voiceInteractor, app.repProcState, r.icicle,
r.persistentState, results, newIntents, mService.isNextTransitionForward(),
profilerInfo));
// Set desired final state.
final ActivityLifecycleItem lifecycleItem;
//此时为teue,设置ResumeActivityItem为Activity最终期望的状态
if (andResume) {
lifecycleItem = ResumeActivityItem.obtain(mService.isNextTransitionForward());
} else {
lifecycleItem = PauseActivityItem.obtain();
}
//设置给LifecycleStateRequest
clientTransaction.setLifecycleStateRequest(lifecycleItem);
// Schedule transaction.
//调用给App进程
mService.getLifecycleManager().scheduleTransaction(clientTransaction);
//省略
} catch (RemoteException e) {
if (r.launchFailed) {
// This is the second time we failed -- finish activity
// and give up.
Slog.e(TAG, "Second failure launching "
+ r.intent.getComponent().flattenToShortString()
+ ", giving up", e);
mService.appDiedLocked(app);
stack.requestFinishActivityLocked(r.appToken, Activity.RESULT_CANCELED, null,
"2nd-crash", false);
return false;
}
// This is the first time we failed -- restart process and
// retry.
r.launchFailed = true;
app.activities.remove(r);
throw e;
}
} finally {
endDeferResume();
}
//省略
return true;
}
复制代码
方法中创建ClientTransaction对象,添加LaunchActivityItem和ResumeActivityItem两个子项,并发送给APP进程执行相应处理。 发送过程在Pause中已经跟了一遍了,不继续重复 最后这里会先处理LaunchActivityItem,调用它的execute方法,execute中会创建ActivityClientRecord对象,然后调用ActivityThread的handleLaunchActivity方法并传入ActivityClientRecord
onCreate处理
ActivityThread.handleLaunchActivity
// /frameworks/base/core/java/android/app/ActivityThread.java
public Activity handleLaunchActivity(ActivityClientRecord r,
PendingTransactionActions pendingActions, Intent customIntent) {
// If we are getting ready to gc after going to the background, well
// we are back active so skip it.
//移除GC空闲消息
unscheduleGcIdler();
mSomeActivitiesChanged = true;
if (r.profilerInfo != null) {
mProfiler.setProfiler(r.profilerInfo);
mProfiler.startProfiling();
}
// Make sure we are running with the most recent config.
handleConfigurationChanged(null, null);
if (localLOGV) Slog.v(
TAG, "Handling launch of " + r);
// Initialize before creating the activity
if (!ThreadedRenderer.sRendererDisabled) {
GraphicsEnvironment.earlyInitEGL();
}
WindowManagerGlobal.initialize();
//执行启动Activity并返回Activity实例
final Activity a = performLaunchActivity(r, customIntent);
if (a != null) {
r.createdConfig = new Configuration(mConfiguration);
reportSizeConfigurations(r);
if (!r.activity.mFinished && pendingActions != null) {
pendingActions.setOldState(r.state);
pendingActions.setRestoreInstanceState(true);
pendingActions.setCallOnPostCreate(true);
}
} else {
// If there was an error, for any reason, tell the activity manager to stop us.
try {
ActivityManager.getService()
.finishActivity(r.token, Activity.RESULT_CANCELED, null,
Activity.DONT_FINISH_TASK_WITH_ACTIVITY);
} catch (RemoteException ex) {
throw ex.rethrowFromSystemServer();
}
}
return a;
}
复制代码
看下performLaunchActivity的实现
ActivityThread.performLaunchActivity
// /frameworks/base/core/java/android/app/ActivityThread.java
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
ActivityInfo aInfo = r.activityInfo;
//获取LoadedApk对象
if (r.packageInfo == null) {
r.packageInfo = getPackageInfo(aInfo.applicationInfo, r.compatInfo,
Context.CONTEXT_INCLUDE_CODE);
}
//获取ComponentName
ComponentName component = r.intent.getComponent();
if (component == null) {
//intent中未显示设置,从PackageManagerService中查找匹配的resolveInfo构建的ComponentName
component = r.intent.resolveActivity(
mInitialApplication.getPackageManager());
r.intent.setComponent(component);
}
if (r.activityInfo.targetActivity != null) {
//若Activity设置了别名(targetActivity属性),则使用targetActivity构建ComponentName
component = new ComponentName(r.activityInfo.packageName,
r.activityInfo.targetActivity);
}
//获取ContextImpl实例
ContextImpl appContext = createBaseContextForActivity(r);
Activity activity = null;
try {
java.lang.ClassLoader cl = appContext.getClassLoader();
//通过反射实例化Activity
activity = mInstrumentation.newActivity(
cl, component.getClassName(), r.intent);
StrictMode.incrementExpectedActivityCount(activity.getClass());
r.intent.setExtrasClassLoader(cl);
r.intent.prepareToEnterProcess();
if (r.state != null) {
r.state.setClassLoader(cl);
}
} catch (Exception e) {
if (!mInstrumentation.onException(activity, e)) {
throw new RuntimeException(
"Unable to instantiate activity " + component
+ ": " + e.toString(), e);
}
}
try {
//获取LoadedApk中缓存的Application对象(在App进程启动时实例化)
Application app = r.packageInfo.makeApplication(false, mInstrumentation);
if (localLOGV) Slog.v(TAG, "Performing launch of " + r);
if (localLOGV) Slog.v(
TAG, r + ": app=" + app
+ ", appName=" + app.getPackageName()
+ ", pkg=" + r.packageInfo.getPackageName()
+ ", comp=" + r.intent.getComponent().toShortString()
+ ", dir=" + r.packageInfo.getAppDir());
if (activity != null) {
CharSequence title = r.activityInfo.loadLabel(appContext.getPackageManager());
Configuration config = new Configuration(mCompatConfiguration);
if (r.overrideConfig != null) {
config.updateFrom(r.overrideConfig);
}
if (DEBUG_CONFIGURATION) Slog.v(TAG, "Launching activity "
+ r.activityInfo.name + " with config " + config);
Window window = null;
if (r.mPendingRemoveWindow != null && r.mPreserveWindow) {
window = r.mPendingRemoveWindow;
r.mPendingRemoveWindow = null;
r.mPendingRemoveWindowManager = null;
}
//将Activity赋值给ContextImpl的mOuterContex,使其持有Activity的引用
appContext.setOuterContext(activity);
//进行Activity的成员赋值和初始化等操作
activity.attach(appContext, this, getInstrumentation(), r.token,
r.ident, app, r.intent, r.activityInfo, title, r.parent,
r.embeddedID, r.lastNonConfigurationInstances, config,
r.referrer, r.voiceInteractor, window, r.configCallback);
if (customIntent != null) {
activity.mIntent = customIntent;
}
r.lastNonConfigurationInstances = null;
checkAndBlockForNetworkAccess();
activity.mStartedActivity = false;
int theme = r.activityInfo.getThemeResource();
if (theme != 0) {
//设置主题
activity.setTheme(theme);
}
activity.mCalled = false;
if (r.isPersistable()) {
//设置了Persistable模式,将触发两个参数的onCreate生命周期回调
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
} else {
//触发一个参数的onCreate回调
mInstrumentation.callActivityOnCreate(activity, r.state);
}
if (!activity.mCalled) {
throw new SuperNotCalledException(
"Activity " + r.intent.getComponent().toShortString() +
" did not call through to super.onCreate()");
}
r.activity = activity;
}
//更新ActivityClientRecord中的状态
r.setState(ON_CREATE);
//保存ActivityClientRecord
mActivities.put(r.token, r);
} catch (SuperNotCalledException e) {
throw e;
} catch (Exception e) {
if (!mInstrumentation.onException(activity, e)) {
throw new RuntimeException(
"Unable to start activity " + component
+ ": " + e.toString(), e);
}
}
return activity;
}
复制代码
总结一下该方法 1.获取ComponentName 2.实例化ContextImpl 3.通过反射实例化目标Activity 4.触发onCreate生命周期回调,ActivityClientRecord中mLifecycleState成员(生命周期状态)被设置为ON_CREATE 当LaunchActivityItem处理完后,便轮到了ResumeActivityItem,在TransactionExecutor的executeLifecycleState方法 这个方法在上面Pause的过程中,已经看过了,没印象的可以回头看一下,此时Activity状态为ON_CREATE,但是ResumeActivityItem中保存的期望状态是ON_RESUME, 在cycleToPath方法中会先调用handleStartActivity方法,进行Activity start阶段的处理
onStart处理
ActivityThread.handleStartActivity
// /frameworks/base/core/java/android/app/ActivityThread.java
@Override
public void handleStartActivity(ActivityClientRecord r,
PendingTransactionActions pendingActions) {
final Activity activity = r.activity;
if (r.activity == null) {
// TODO(lifecycler): What do we do in this case?
return;
}
if (!r.stopped) {
throw new IllegalStateException("Can't start activity that is not stopped.");
}
if (r.activity.mFinished) {
// TODO(lifecycler): How can this happen?
return;
}
// Start
//performStart里通过Instrumentation调用Activity的onStart生命周期回调方法
activity.performStart("handleStartActivity");
//设置生命周期状态为ON_START
r.setState(ON_START);
if (pendingActions == null) {
// No more work to do.
return;
}
// Restore instance state
if (pendingActions.shouldRestoreInstanceState()) {
if (r.isPersistable()) {
if (r.state != null || r.persistentState != null) {
mInstrumentation.callActivityOnRestoreInstanceState(activity, r.state,
r.persistentState);
}
} else if (r.state != null) {
mInstrumentation.callActivityOnRestoreInstanceState(activity, r.state);
}
}
// Call postOnCreate()
if (pendingActions.shouldCallOnPostCreate()) {
activity.mCalled = false;
if (r.isPersistable()) {
mInstrumentation.callActivityOnPostCreate(activity, r.state,
r.persistentState);
} else {
mInstrumentation.callActivityOnPostCreate(activity, r.state);
}
if (!activity.mCalled) {
throw new SuperNotCalledException(
"Activity " + r.intent.getComponent().toShortString()
+ " did not call through to super.onPostCreate()");
}
}
}
复制代码
上面方法,调用了onStart生命周期方法,并且将Activity的生命周期状态设置为ON_START 接下来将继续执行handleResumeActivity
onResume处理
ActivityThread.handleResumeActivity
// /frameworks/base/core/java/android/app/ActivityThread.java
@Override
public void handleResumeActivity(IBinder token, boolean finalStateRequest, boolean isForward,
String reason) {
// If we are getting ready to gc after going to the background, well
// we are back active so skip it.
unscheduleGcIdler();
mSomeActivitiesChanged = true;
// TODO Push resumeArgs into the activity for consideration
//该方法中看情况调用onRestart生命周期回调方法,接着调用onResume生命周期方法
final ActivityClientRecord r = performResumeActivity(token, finalStateRequest, reason);
if (r == null) {
// We didn't actually resume the activity, so skipping any follow-up actions.
return;
}
//以下省略
//主要是DecorView、ViewRootImpl、WindowManager相关初始化操作,向WindowManagerService注册窗口,设置视图树可见
r.nextIdle = mNewActivities;
mNewActivities = r;
if (localLOGV) Slog.v(TAG, "Scheduling idle handler for " + r);
//向当前线程添加一个闲时消息
Looper.myQueue().addIdleHandler(new Idler());
}
复制代码
该方法主要时调用onResume生命周期方法,设置状态为ON_RESUME,如果当前Activity是首次启动, 则还需要进行DecorView、ViewRootImpl、WindowManager相关初始化操作,向WindowManagerService注册窗口,设置视图树可见。 由此可以得知,Activity首次启动的时候是在onResume后才真正可见,并不是onStart时就部分可见
该方法最后,往当前线程Looper中的消息队列中添加一个闲时消息Idler,当消息队列中无消息处理时将回调它的queueIdle方法, 在queueIdle中又会通过IActivityManager调用AMS的activityIdle方法
onStop处理
APP进程通过activityIdle方法通知AMS目标Activity的resume操作完成,其中会根据token取得对应的ActivityStack,调用它的activityIdleInternalLocked方法
ActivityStackSupervisor.activityIdleInternalLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityStackSupervisor.java
final ActivityRecord activityIdleInternalLocked(final IBinder token, boolean fromTimeout,
boolean processPausingActivities, Configuration config) {
if (DEBUG_ALL) Slog.v(TAG, "Activity idle: " + token);
ArrayList<ActivityRecord> finishes = null;
ArrayList<UserState> startingUsers = null;
int NS = 0;
int NF = 0;
boolean booting = false;
boolean activityRemoved = false;
ActivityRecord r = ActivityRecord.forTokenLocked(token);
//省略
//获取paused的ActivityRecord集合,ActivityPaused后会加入mStopngActivityies保存
// Atomically retrieve all of the other things to do.
final ArrayList<ActivityRecord> stops = processStoppingActivitiesLocked(r,
true /* remove */, processPausingActivities);
NS = stops != null ? stops.size() : 0;
if ((NF = mFinishingActivities.size()) > 0) {
finishes = new ArrayList<>(mFinishingActivities);
//mFinishingActivities保存的已经stop等待finish的ActivityRecord集合
mFinishingActivities.clear();
}
if (mStartingUsers.size() > 0) {
startingUsers = new ArrayList<>(mStartingUsers);
mStartingUsers.clear();
}
// Stop any activities that are scheduled to do so but have been
// waiting for the next one to start.
for (int i = 0; i < NS; i++) {
//依次取出ActivityRecord,对其执行stop或finish操作
r = stops.get(i);
final ActivityStack stack = r.getStack();
if (stack != null) {
if (r.finishing) {
stack.finishCurrentActivityLocked(r, ActivityStack.FINISH_IMMEDIATELY, false,
"activityIdleInternalLocked");
} else {
stack.stopActivityLocked(r);
}
}
}
//省略
return r;
}
复制代码
这里面主要是获取之前保存的等待stop或则finish的ActivityRecord,执行对应的操作,来看一下stopActivityLocked
ActivityStack.stopActivityLocked
///frameworks/base/services/core/java/com/android/server/am/ActivityStack.java
final void stopActivityLocked(ActivityRecord r) {
if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, "Stopping: " + r);
if ((r.intent.getFlags()&Intent.FLAG_ACTIVITY_NO_HISTORY) != 0
|| (r.info.flags&ActivityInfo.FLAG_NO_HISTORY) != 0) {
if (!r.finishing) {
if (!shouldSleepActivities()) {
if (DEBUG_STATES) Slog.d(TAG_STATES, "no-history finish of " + r);
if (requestFinishActivityLocked(r.appToken, Activity.RESULT_CANCELED, null,
"stop-no-history", false)) {
// If {@link requestFinishActivityLocked} returns {@code true},
// {@link adjustFocusedActivityStack} would have been already called.
r.resumeKeyDispatchingLocked();
return;
}
} else {
if (DEBUG_STATES) Slog.d(TAG_STATES, "Not finishing noHistory " + r
+ " on stop because we're just sleeping");
}
}
}
if (r.app != null && r.app.thread != null) {
adjustFocusedActivityStack(r, "stopActivity");
r.resumeKeyDispatchingLocked();
try {
r.stopped = false;
if (DEBUG_STATES) Slog.v(TAG_STATES,
"Moving to STOPPING: " + r + " (stop requested)");
r.setState(STOPPING, "stopActivityLocked");
if (DEBUG_VISIBILITY) Slog.v(TAG_VISIBILITY,
"Stopping visible=" + r.visible + " for " + r);
if (!r.visible) {
r.setVisible(false);
}
EventLogTags.writeAmStopActivity(
r.userId, System.identityHashCode(r), r.shortComponentName);
//通过StopActivityItem封装的事务,调度到App进程
mService.getLifecycleManager().scheduleTransaction(r.app.thread, r.appToken,
StopActivityItem.obtain(r.visible, r.configChangeFlags));
if (shouldSleepOrShutDownActivities()) {
r.setSleeping(true);
}
//发送超时消息
Message msg = mHandler.obtainMessage(STOP_TIMEOUT_MSG, r);
mHandler.sendMessageDelayed(msg, STOP_TIMEOUT);
} catch (Exception e) {
// Maybe just ignore exceptions here... if the process
// has crashed, our death notification will clean things
// up.
Slog.w(TAG, "Exception thrown during pause", e);
// Just in case, assume it to be stopped.
r.stopped = true;
if (DEBUG_STATES) Slog.v(TAG_STATES, "Stop failed; moving to STOPPED: " + r);
r.setState(STOPPED, "stopActivityLocked");
if (r.deferRelaunchUntilPaused) {
destroyActivityLocked(r, true, "stop-except");
}
}
}
}
复制代码
这里很熟悉,和前面的Pause,和resume流程差不多stopActivityLocked方法中发送ClientTransaction到对应APP进程(之前pause的Activity所在进程),然后调用StopActivityItem的execute方法, 其中将调用ActivityThread的handleStopActivity方法
ActivityThread.handleStopActivity
// /frameworks/base/core/java/android/app/ActivityThread.java
@Override
public void handleStopActivity(IBinder token, boolean show, int configChanges,
PendingTransactionActions pendingActions, boolean finalStateRequest, String reason) {
final ActivityClientRecord r = mActivities.get(token);
r.activity.mConfigChangeFlags |= configChanges;
//继承自Runnable,用于保存stop相关参数和通知AMS的结果
final StopInfo stopInfo = new StopInfo();
// 将调用onStop生命周期的回调方法,设置状态ON_STOP,视情况调用onSveInstanceState回调方法
performStopActivityInner(r, stopInfo, show, true /* saveState */, finalStateRequest,
reason);
if (localLOGV) Slog.v(
TAG, "Finishing stop of " + r + ": show=" + show
+ " win=" + r.window);
updateVisibility(r, show);
// Make sure any pending writes are now committed.
if (!r.isPreHoneycomb()) {
QueuedWork.waitToFinish();
}
stopInfo.setActivity(r);
stopInfo.setState(r.state);
stopInfo.setPersistentState(r.persistentState);
//将stopInfo添加到pendingActions保存
pendingActions.setStopInfo(stopInfo);
mSomeActivitiesChanged = true;
}
复制代码
该方法创建了StopInfo来保存stop过程相关参数,接着调用performStopActivityInner方法,设置状态为ON_STOP, 并且视情况调用onSveInstanceState回调方法,最后将stopInfo添加进pendingActions保存 StopActivityItem在执行完execute方法后,会执行postExecute方法,而在这个方法中会调用ActivityThread的reportStop方法
ActivityThread.reportStop
// /frameworks/base/core/java/android/app/ActivityThread.java
@Override
public void reportStop(PendingTransactionActions pendingActions) {
mH.post(pendingActions.getStopInfo());
}
复制代码
这里从pendingActions中取出先前保存的StopInfo,切换到主线程执行。StopInfo继承自Runnable,将触发它的run方法
PendingTransactionActions.StopInfo.run
// /frameworks/base/core/java/android/app/servertransaction/PendingTransactionActions.java
@Override
public void run() {
// Tell activity manager we have been stopped.
try {
if (DEBUG_MEMORY_TRIM) Slog.v(TAG, "Reporting activity stopped: " + mActivity);
// TODO(lifecycler): Use interface callback instead of AMS.
//调用AMS的ActivityStopped方法通知AMS
ActivityManager.getService().activityStopped(
mActivity.token, mState, mPersistentState, mDescription);
} catch (RemoteException ex) {
// Dump statistics about bundle to help developers debug
final LogWriter writer = new LogWriter(Log.WARN, TAG);
final IndentingPrintWriter pw = new IndentingPrintWriter(writer, " ");
pw.println("Bundle stats:");
Bundle.dumpStats(pw, mState);
pw.println("PersistableBundle stats:");
Bundle.dumpStats(pw, mPersistentState);
if (ex instanceof TransactionTooLargeException
&& mActivity.packageInfo.getTargetSdkVersion() < Build.VERSION_CODES.N) {
Log.e(TAG, "App sent too much data in instance state, so it was ignored", ex);
return;
}
throw ex.rethrowFromSystemServer();
}
}
复制代码
AMS的activityStopped方法中会根据token查找对应的ActivityRecord,再调用其activityStoppedLocked方法
ActivityRecord.activityStoppedLocked
// /frameworks/base/services/core/java/com/android/server/am/ActivityRecord.java
final void activityStoppedLocked(Bundle newIcicle, PersistableBundle newPersistentState,
CharSequence description) {
final ActivityStack stack = getStack();
if (mState != STOPPING) {
Slog.i(TAG, "Activity reported stop, but no longer stopping: " + this);
stack.mHandler.removeMessages(STOP_TIMEOUT_MSG, this);
return;
}
if (newPersistentState != null) {
persistentState = newPersistentState;
service.notifyTaskPersisterLocked(task, false);
}
if (DEBUG_SAVED_STATE) Slog.i(TAG_SAVED_STATE, "Saving icicle of " + this + ": " + icicle);
if (newIcicle != null) {
// If icicle is null, this is happening due to a timeout, so we haven't really saved
// the state.
icicle = newIcicle;
haveState = true;
launchCount = 0;
updateTaskDescription(description);
}
if (!stopped) {
if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to STOPPED: " + this + " (stop complete)");
stack.mHandler.removeMessages(STOP_TIMEOUT_MSG, this);
stopped = true;
setState(STOPPED, "activityStoppedLocked");
mWindowContainerController.notifyAppStopped();
if (finishing) {
clearOptionsLocked();
} else {
if (deferRelaunchUntilPaused) {
stack.destroyActivityLocked(this, true /* removeFromApp */, "stop-config");
mStackSupervisor.resumeFocusedStackTopActivityLocked();
} else {
mStackSupervisor.updatePreviousProcessLocked(this);
}
}
}
}
复制代码
到这里就完成了stop操作,和通知AMS,启动的整个流程也就结束了,当然还有多种情况可以分析的,比如销毁的时候,返回操作的 时候,这里就不一一分析了,主要是了解其流程,理解思路,便于在遇到相关问题时,有更好的处理方法,正所谓知己知彼百战不殆嘛
总结
最后来总结一下整个启动流程
- 首先APP发起startActivity请求
- 经过一系列调用,到AMS的startActivityAsUser方法
- 调用ActivityStartController.obtainStarter,设置所有启动参数,返回一个ActivityStarter对象,同时执行execute方法
- 接着调用ActivityStarter的startActivityMayWait方法,解析出与Intent对应的ActivityInfo,并获取到启动该Activity的前台Tas然后通过startActivity启动Activity并对启动结果进行处理
- startActivity里面会调用startActivityUnchecked,主要是对Activity启动模式的处理,设置对应的task并带到前台之后,开始启动对应的Activity 通过调用ActivityStack.startActivityLocked为新开启的Activity创建Task,并将Task保存在ActivityRecord 然后调用ActivityStackSupervisor.resumeFocusedStackTopActivityLocked,最终会调用到ActivityStack.resumeTopActivityInnerLocked方法
- ActivityStack.resumeTopActivityInnerLocked前半部分通过ActivityStack.startPausingLocked去暂停当前运行的Activity,最终执行ActivityThread.handlePauseActivity
- 调用AMS的activityPaused,通知Activity pause完成
- AMS最终会调用ActivityStack.completePauseLocked来将这次pause的ActivityRecord存入ActivityStackSupervisor的mStoppingActivities成员(ArrayList)中,用于后续再对其执行stop和finish操作
- 当上一个Activity Pause操作结束后,在ActivityStack.resumeTopActivityInnerLocked下半部分,会根据需要确认是否需要创建新的进程
- 需要则通过AMS发起ActivityManagerService.startProcessLocked,最终到Zygote孵化进程,fock新的进程,创建成功后调用AMS的attachApplication方法通知进程启动完成
- AMS在收到APP进程启动完成后,会调用realStartActivityLocked启动因为等待目标进程启动而暂缓的Activity
- 调用ActivityThread.performLaunchActivity,实例化ContextImpl,通过反射实例化目标Activity,触发onCreate生命周期回调,设置生命周期状态为ON_CREATE
- 调用ActivityThread.handleStartActivity方法,触发onStart生命周期方法,并且将Activity的生命周期状态设置为ON_START
- 调用ActivityThread.handleResumeActivity方法,触发onResume生命周期方法,设置状态为ON_RESUME,如果当前Activity是首次启动,则还需要进行DecorView、ViewRootImpl、WindowManager相关初始化操作,向WindowManagerService注册窗口,设置视图树可见
- APP进程通过activityIdle方法通知AMS目标Activity的resume操作完成,最后会调用到ActivityThread.handleStopActivity方法,触发onStop生命周期并设置状态为ON_STOP
- 调用AMS的ActivityStopped方法通知AMS
- AMS的activityStopped方法中会根据token查找对应的ActivityRecord,再调用其activityStoppedLocked方法