Activity启动流程
一、执行startActivity
-
Activity.startActivity(Intent intent, @Nullable Bundle options)
@Override public void startActivity(Intent intent, @Nullable Bundle options) { if (options != null) { startActivityForResult(intent, -1, options); } else { // Note we want to go through this call for compatibility with // applications that may have overridden the method. startActivityForResult(intent, -1); } }
-
Activity.startActivityForResult ------requestCode == -1
mInstrumentation.execStartActivity( this, mMainThread.getApplicationThread(), mToken, this, intent, requestCode, options);
“Instrumentation是启动Activity的操作类”,每一个应用程序只有一个Instrumentation对象,每个Activity持有一个该对象的引用。包括了调用Activity的各生命周期方法的callActivityxxx()。
-
Instrumentation.execStartActivty
int result = ActivityManagerNative.getDefault() .startActivity(whoThread, who.getBasePackageName(), intent, intent.resolveTypeIfNeeded(who.getContentResolver()), token, target != null ? target.mEmbeddedID : null, requestCode, 0, null, options);
getDefault()返回的是:
static public IActivityManager getDefault() { return gDefault.get(); }
private static final Singleton<IActivityManager> gDefault = new Singleton<IActivityManager>() { protected IActivityManager create() { IBinder b = ServiceManager.getService("activity"); if (false) { Log.v("ActivityManager", "default service binder = " + b); } IActivityManager am = asInterface(b); if (false) { Log.v("ActivityManager", "default service = " + am); } return am; } };
asInterface{ .... return new ActivityManagerProxy(obj); }
ActivityManagerNative extends Binder
接口的实现关系:
IInterface->IActivityManager–> ActivityManagerNative/ActivityManagerProxy
ActivityManagerNative作为AMS的客户端通过ActivityManagerProxy向AMS发送启动请求。
ActivityManagerService extends ActivityManagerNative
-
ActivityManagerProxy.startActivity()
public int startActivity(IApplicationThread caller, String callingPackage, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int startFlags, ProfilerInfo profilerInfo, Bundle options) throws RemoteException { Parcel data = Parcel.obtain(); Parcel reply = Parcel.obtain(); data.writeInterfaceToken(IActivityManager.descriptor); data.writeStrongBinder(caller != null ? caller.asBinder() : null); data.writeString(callingPackage); intent.writeToParcel(data, 0); data.writeString(resolvedType); data.writeStrongBinder(resultTo); data.writeString(resultWho); data.writeInt(requestCode); data.writeInt(startFlags); if (profilerInfo != null) { data.writeInt(1); profilerInfo.writeToParcel(data, Parcelable.PARCELABLE_WRITE_RETURN_VALUE); } else { data.writeInt(0); } if (options != null) { data.writeInt(1); options.writeToParcel(data, 0); } else { data.writeInt(0); } mRemote.transact(START_ACTIVITY_TRANSACTION, data, reply, 0); reply.readException(); int result = reply.readInt(); reply.recycle(); data.recycle(); return result; }
通过binder向AMS传输数据,AMS调用startActivity()方法
通过Binder向AMS发送启动Activity请求
二、ActivityManagerService接收启动Activity的请求,并控制前台Activity调用onPause
在AMSstartActivity()方法内部,继续调用startActivityAsUser()方法:
- ActivityManagerService.startActivity()
@Override
public final int startActivity(IApplicationThread caller, String callingPackage,
Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
int startFlags, ProfilerInfo profilerInfo, Bundle bOptions) {
return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
resultWho, requestCode, startFlags, profilerInfo, bOptions,
UserHandle.getCallingUserId());
}
-
ActvityiManagerService.startActivityAsUser()
@Override public final int startActivityAsUser(IApplicationThread caller, String callingPackage, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int startFlags, ProfilerInfo profilerInfo, Bundle bOptions, int userId) { .... return mActivityStarter.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, null, null, bOptions, false, userId, null, null); }
该方法返回时,调用了ActivityStarter.startActivityMayWait()方法。
- ActivityStarter是一个专门负责Activity启动的控制类,通过intent和flag决定如何启动一个Activity,并关联到Task和Stack。
ActivityStarter.startActivityMayWait()方法中,返回值如下:
-
ActivityStarter.startActivityMayWait()
int res = startActivityLocked(caller, intent, ephemeralIntent, resolvedType, aInfo, rInfo, voiceSession, voiceInteractor, resultTo, resultWho, requestCode, callingPid, callingUid, callingPackage, realCallingPid, realCallingUid, startFlags, options, ignoreTargetSecurity, componentSpecified, outRecord, container, inTask); ..... return res;
我们可以看到此处调用了ActivityStarter.startActivityLocked()方法,该方法关键部分如下:
-
ActivityStarter.startActivityLocked()
mLastStartActivityResult = startActivity(caller, intent, ephemeralIntent, resolvedType, aInfo, rInfo, voiceSession, voiceInteractor, resultTo, resultWho, requestCode, callingPid, callingUid, callingPackage, realCallingPid, realCallingUid, startFlags, options, ignoreTargetSecurity, componentSpecified, mLastStartActivityRecord, container, inTask); ···· return mLastStartActivityResult;
调用的startActivity()方法:
···· try { mService.mWindowManager.deferSurfaceLayout(); result = startActivityUnchecked(r, sourceRecord, voiceSession, voiceInteractor,startFlags, doResume, options, inTask, outActivity); } ···· return result;;
这里又调用了另一个方法ActivityStarter.startActivityUnchecked(),在该方法中进行了大量逻辑操作,这里挑出部分:
-
ActivityStarter.startActivityUnchecked()
···· final ActivityStack topStack = mSupervisor.mFocusedStack; final ActivityRecord top = topStack.topRunningNonDelayedActivityLocked(mNotTop); ····
关于ActivityStackSupervisor,它用来保存Activity的栈信息
- ActivityStackSupervisor
/** The stack containing the launcher app. Assumed to always be attached to * Display.DEFAULT_DISPLAY. */ ActivityStack mHomeStack; /** The stack currently receiving input or launching the next activity. */ ActivityStack mFocusedStack; /** If this is the same as mFocusedStack then the activity on the top of the focused stack has * been resumed. If stacks are changing position this will hold the old stack until the new * stack becomes resumed after which it will be set to mFocusedStack. */ private ActivityStack mLastFocusedStack;
mHomeStack : 只保存了 Launcher 的 Task;
mLastFocusedStack: 当该值等于mFocusedStack,代表当前栈顶的Activity完成resume;
当该值等于上一个旧栈时,代表activity正在切换;
mIntent.setFlags(mLaunchFlags);//设置启动flag
mReusedActivity = getReusableIntentActivity();//决定是否将新的Activity插入到现有的task
····
final boolean dontStart = top != null && mStartActivity.resultTo == null
&& top.realActivity.equals(mStartActivity.realActivity)
&& top.userId == mStartActivity.userId
&& top.app != null && top.app.thread != null
&& ((mLaunchFlags & FLAG_ACTIVITY_SINGLE_TOP) != 0
|| mLaunchSingleTop || mLaunchSingleTask);
if (dontStart) {
ActivityStack.logStartActivity(AM_NEW_INTENT, top, top.task);
// For paranoia, make sure we have correctly resumed the top activity.
topStack.mLastPausedActivity = null;
if (mDoResume) {
mSupervisor.resumeFocusedStackTopActivityLocked();
}
·····
return START_DELIVERED_TO_TOP;
}
·····
mTargetStack.startActivityLocked(mStartActivity, newTask, mKeepCurTransition, mOptions);//启动Activity、是否开启新task···
····
mSupervisor.updateUserStackLocked(mStartActivity.userId, mTargetStack);//更新last used stack ID
····
-
ActivityStack.startActivityLocked()
···· TaskRecord rTask = r.task; final int taskId = rTask.taskId; // mLaunchTaskBehind tasks get placed at the back of the task stack. if (!r.mLaunchTaskBehind && (taskForIdLocked(taskId) == null || newTask)) { // Last activity in task had been removed or ActivityManagerService is reusing task. // Insert or replace. // Might not even be in. insertTaskAtTop(rTask, r); mWindowManager.moveTaskToTop(taskId); } TaskRecord task = null; if (!newTask) {//如果不是在新的Task中启动,就找出要运行在TaskRecord的对象 // If starting in an existing task, find where that is... boolean startIt = true; for (int taskNdx = mTaskHistory.size() - 1; taskNdx >= 0; --taskNdx) { task = mTaskHistory.get(taskNdx); if (task.getTopActivity() == null) { // All activities in task are finishing. continue; } if (task == r.task) { // Here it is! Now, if this is not yet visible to the // user, then just add it without starting; it will // get started when the user navigates back to it. if (!startIt) { if (DEBUG_ADD_REMOVE) Slog.i(TAG, "Adding activity " + r + " to task " + task, new RuntimeException("here").fillInStackTrace()); task.addActivityToTop(r); r.putInHistory(); addConfigOverride(r, task); if (VALIDATE_TOKENS) { validateAppTokensLocked(); } ActivityOptions.abort(options); return; } break; } else if (task.numFullscreen > 0) { startIt = false; } } } // Place a new activity at top of stack, so it is next to interact // with the user. // If we are not placing the new activity frontmost, we do not want // to deliver the onUserLeaving callback to the actual frontmost // activity ······
-
ActivityStackSupervisor.resumeFocusedStackTopActivityLocked()
boolean resumeFocusedStackTopActivityLocked( ActivityStack targetStack, ActivityRecord target, ActivityOptions targetOptions) { if (targetStack != null && isFocusedStack(targetStack)) { return targetStack.resumeTopActivityUncheckedLocked(target, targetOptions); } final ActivityRecord r = mFocusedStack.topRunningActivityLocked(); if (r == null || r.state != RESUMED) { mFocusedStack.resumeTopActivityUncheckedLocked(null, null); } return false; }
-
ActivityStack.resumeTopActivityUncheckedLocked()
···· result = resumeTopActivityInnerLocked(prev, options); ···· return result;
这里主要调用了mSupervisor.resumeFocusedStackTopActivityLocked()方法,该方法继续调用targetStack.resumeTopActivityUncheckedLocked(target, targetOptions),在
resumeTopActivityUncheckedLocked方法中,继续调用resumeTopActivityInnerLocked(prev, options)并返回。resumeTopActivityInnerLocked方法关键逻辑如下:
-
ActivityStack.resumeTopActivityInnerLocked()
···· /** * Current activity that is resumed, or null if there is none. */ ActivityRecord mResumedActivity = null; ···· //找出还没结束的首个ActivityRecord ActivityRecord next = topRunningActivityLocked(null); ···· boolean pausing = mStackSupervisor.pauseBackStacks(userLeaving, next, dontWaitForPause); ···· //启动前需要暂停前一个Activity if (mResumedActivity != null) { if (DEBUG_STATES) Slog.d(TAG_STATES, "resumeTopActivityLocked: Pausing " + mResumedActivity); pausing |= startPausingLocked(userLeaving, false, next, dontWaitForPause); }
此时,开始进入pause阶段,调用ActivityStack.startPausingLocked()方法,这里截取主要部分:
-
ActivityStack.startPausingLocked()
final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping, boolean resuming, boolean dontWait) { if (mPausingActivity != null) { completePauseLocked(false); } ..... ActivityRecord prev = mResumedActivity; ····· if (prev.app != null && prev.app.thread != null) try { mService.updateUsageStats(prev, false); prev.app.thread.schedulePauseActivity(prev.appToken, prev.finishing, userLeaving, prev.configChangeFlags, dontWait); } catch (Exception e) { mPausingActivity = null; mLastPausedActivity = null; mLastNoHistoryActivity = null; } } else { mPausingActivity = null; mLastPausedActivity = null; mLastNoHistoryActivity = null; } ..... }
这里,prev.app为记录启动Lancher进程的ProcessRecord,prev.app.thread为Lancher进程的远程调用接口IApplicationThead,调用prev.app.thread.schedulePauseActivity,在Lancher进程中消息传
递,调用ActivityThread.handlePauseActivity(),最终调用ActivityThread.performPauseActivity()暂停指定Activity。
ActivityThread.schedulePauseActivity()中发送了一个Message,方法如下:
ActivityThread.schedulePauseActivity()
public final void schedulePauseActivity(IBinder token, boolean finished,
boolean userLeaving, int configChanges, boolean dontReport) {
int seq = getLifecycleSeq();
if (DEBUG_ORDER) Slog.d(TAG, "pauseActivity " + ActivityThread.this
+ " operation received seq: " + seq);
sendMessage(
finished ? H.PAUSE_ACTIVITY_FINISHING : H.PAUSE_ACTIVITY,
token,
(userLeaving ? USER_LEAVING : 0) | (dontReport ? DONT_REPORT : 0),
configChanges,
seq);
}
在handleMessage的PAUSE_ACTIVITY/PAUSE_ACTIVITY_FINISHING case中均调用了handlePauseActivity方法:
private void handlePauseActivity(IBinder token, boolean finished,
boolean userLeaving, int configChanges, boolean dontReport, int seq) {
ActivityClientRecord r = mActivities.get(token);
if (DEBUG_ORDER) Slog.d(TAG, "handlePauseActivity " + r + ", seq: " + seq);
if (!checkAndUpdateLifecycleSeq(seq, r, "pauseActivity")) {
return;
}
if (r != null) {
//Slog.v(TAG, "userLeaving=" + userLeaving + " handling pause of " + r);
if (userLeaving) {
performUserLeavingActivity(r);
}
r.activity.mConfigChangeFlags |= configChanges;
performPauseActivity(token, finished, r.isPreHoneycomb(), "handlePauseActivity");
// Make sure any pending writes are now committed.
if (r.isPreHoneycomb()) {
QueuedWork.waitToFinish();
}
// Tell the activity manager we have paused.
if (!dontReport) { //利用ActivityManagerNative通知ActivityThread已经完成pause
try {
ActivityManagerNative.getDefault().activityPaused(token);
} catch (RemoteException ex) {
throw ex.rethrowFromSystemServer();
}
}
mSomeActivitiesChanged = true;
}
}
该方法内,调用了performPauseActivityIfNeeded()方法,在该方法中主要执行的是performPauseActivityIfNeeded()方法完成pause,这里我们看一下performPauseActivityIfNeeded方法的具体实现:
private void performPauseActivityIfNeeded(ActivityClientRecord r, String reason) {
if (r.paused) {
// You are already paused silly...
return;
}
try {
r.activity.mCalled = false;
mInstrumentation.callActivityOnPause(r.activity);
EventLog.writeEvent(LOG_AM_ON_PAUSE_CALLED, UserHandle.myUserId(),
r.activity.getComponentName().getClassName(), reason);
if (!r.activity.mCalled) {
throw new SuperNotCalledException("Activity " + safeToComponentShortString(r.intent)
+ " did not call through to super.onPause()");
}
} catch (SuperNotCalledException e) {
throw e;
} catch (Exception e) {
if (!mInstrumentation.onException(r.activity, e)) {
throw new RuntimeException("Unable to pause activity "
+ safeToComponentShortString(r.intent) + ": " + e.toString(), e);
}
}
r.paused = true;
}
该方法中,主要调用了mInstrumentation.callActivityOnPause(r.activity) 来执行目标Activity的onPause方法。前面已经说过,“Instrumentation是启动Activity的操作类”,它的callActivityOnPause()如下,Activity.performPause()方法中我们可以看到的确调用了onPause()方法。
/**
* Perform calling of an activity's {@link Activity#onPause} method. The
* default implementation simply calls through to that method.
*
* @param activity The activity being paused.
*/
public void callActivityOnPause(Activity activity) {
activity.performPause();
}
final void performPause() {
mDoReportFullyDrawn = false;
mFragments.dispatchPause();
mCalled = false;
onPause();
mResumed = false;
if (!mCalled && getApplicationInfo().targetSdkVersion
>= android.os.Build.VERSION_CODES.GINGERBREAD) {
throw new SuperNotCalledException(
"Activity " + mComponent.toShortString() +
" did not call through to super.onPause()");
}
mResumed = false;
}
以上完成了执行onPause的过程,然后在handlePauseActivity()方法中,继续调用ActivityManagerNative.getDefault().activityPaused()方法,向AMS通知onPause过程已完成。
ActivityThread中schedulePauseActivity()发送Message后,处理消息逻辑整理如下:
handlePauseActivity-performPauseActivity-performPauseActivityIfNeeded //具体执行目标 | Activity的onpause方法
ActivityManagerNative
|
|—>ActivityMangerProxy—>activityPaused //ActivityMangerProxy通知ActivityThread
|
|—>AMS
ActivityManagerProxy.activityPaused()
public void activityPaused(IBinder token) throws RemoteException
{
Parcel data = Parcel.obtain();
Parcel reply = Parcel.obtain();
data.writeInterfaceToken(IActivityManager.descriptor);
data.writeStrongBinder(token);
mRemote.transact(ACTIVITY_PAUSED_TRANSACTION, data, reply, 0);
reply.readException();
data.recycle();
reply.recycle();
}
ActivityManagerService接收到应用进程创建Activity的请求之后会执行初始化操作,解析启动模式,处理信息等一系列操作。ActivityManagerService保存完请求信息之后会将当前系统栈顶的Activity执行onPause操作。
AMS.activityPaused
@Override
public final void activityPaused(IBinder token) {
final long origId = Binder.clearCallingIdentity();
synchronized(this) {
ActivityStack stack = ActivityRecord.getStackLocked(token);//获取的当前Activity的task的所在栈
if (stack != null) {
stack.activityPausedLocked(token, false);
}
}
Binder.restoreCallingIdentity(origId);
}
ActivityStack.activityPausedLocked
if (mPausingActivity == r) {
if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to PAUSED: " + r
+ (timeout ? " (due to timeout)" : " (pause complete)"));
completePauseLocked(true, null);
return;
}
- Question:
3.任务栈由谁管理,存放在什么地方?
4.启动一个activity都是在主线程中执行的吗?
5.AMS什么时候介入工作的?
6.Binder客户端是怎么和服务端通信的?
7.asinterface含义是什么?
8.整个过程由哪些成员协助完成?
9.他们都起到什么作用?
10.如何图解全过程?