Android Activity啟動過程源碼分析
Activity啟動過程源碼分析
- Android 6.0 & API Level 23
- Github: Nvsleep
- 郵箱: lizhenqiao@126.com
- QQ: 522910000
簡述
主要分析從Launch啟動器點擊APP圖標到APP主Activity啟動顯示的過程
S1: Launcher.onClick()
Android桌面本身也是一個啟動器程序,系統默認啟動器程序的核心activity實現類是Launcher:
/**
Default launcher application.
*/
public class Launcher extends Activity implements View.OnClickListener....{
...
public void onClick(View v) {
....
Object tag = v.getTag();
if (tag instanceof ShortcutInfo) {
onClickAppShortcut(v);
} else if (tag instanceof FolderInfo) {
if (v instanceof FolderIcon) {
onClickFolderIcon(v);
}
} else if (v == mAllAppsButton) {
onClickAllAppsButton(v);
} else if (tag instanceof AppInfo) {
// 點擊某個APP圖標
startAppShortcutOrInfoActivity(v);
} else if (tag instanceof LauncherAppWidgetInfo) {
if (v instanceof PendingAppWidgetHostView) {
onClickPendingWidget((PendingAppWidgetHostView) v);
}
}
}
....
@Thunk
void startAppShortcutOrInfoActivity(View v) {
Object tag = v.getTag();
final ShortcutInfo shortcut;
final Intent intent;
if (tag instanceof ShortcutInfo) {
shortcut = (ShortcutInfo) tag;
intent = shortcut.intent;
int[] pos = new int[2];
v.getLocationOnScreen(pos);
intent.setSourceBounds(new Rect(pos[0], pos[1],
pos[0] + v.getWidth(), pos[1] + v.getHeight()));
} else if (tag instanceof AppInfo) {
shortcut = null;
intent = ((AppInfo) tag).intent;
} else {
throw new IllegalArgumentException("Input must be a Shortcut or AppInfo");
}
// 準備startActivity
boolean success = startActivitySafely(v, intent, tag);
mStats.recordLaunch(v, intent, shortcut);
if (success && v instanceof BubbleTextView) {
mWaitingForResume = (BubbleTextView) v;
mWaitingForResume.setStayPressed(true);
}
}
public boolean startActivitySafely(View v, Intent intent, Object tag) {
boolean success = false;
if (mIsSafeModeEnabled && !Utilities.isSystemApp(this, intent)) {
Toast.makeText(this, R.string.safemode_shortcut_error, Toast.LENGTH_SHORT).show();
return false;
}
try {
// 準備startActivity
success = startActivity(v, intent, tag);
} catch (ActivityNotFoundException e) {
Toast.makeText(this, R.string.activity_not_found, Toast.LENGTH_SHORT).show();
Log.e(TAG, "Unable to launch. tag=" + tag + " intent=" + intent, e);
}
return success;
}
}</code></pre>
Launcher的點擊APP圖標經過一些處理之后在startActivity(v, intent, tag)中調用了父類Activity的startActivity(Intent intent, @Nullable Bundle options)
S2: Activity.startActivityForResult()
@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);
}
}
public void startActivityForResult(Intent intent, int requestCode, @Nullable Bundle options) {
if (mParent == null) {
// 讓mInstrumentation這個負責APP與系統交互的對象去執行startActivity具體請求
Instrumentation.ActivityResult ar =
mInstrumentation.execStartActivity(
this, mMainThread.getApplicationThread(), mToken, this,
intent, requestCode, options);
if (ar != null) {
mMainThread.sendActivityResult(
mToken, mEmbeddedID, requestCode, ar.getResultCode(),
ar.getResultData());
}
....
}</code></pre>
- 每個Activity在啟動之后都會初始化一個Instrumentation對象,用于橋接處理與系統交互的一些操作,比如說要啟動其他的activity.
- mMainThread.getApplicationThread()獲取的是Launcher類的ActivityThread對象的內部類ApplicationThread成員變量;ApplicationThread主要負責APP進程與系統進程之間的Binder通信,通俗的說將APP進程的ApplicationThread對象通過Binder傳遞給系統進程用于系統進程調用APP進程的某些方法讓APP進程做出一些操作,比如生成,啟動,恢復該進程的acitivity,啟動該進程的Service等,后面會用到.
S3: Instrumentation.execStartActivity()
public ActivityResult execStartActivity(
Context who, IBinder contextThread, IBinder token, Activity target,
Intent intent, int requestCode, Bundle options) {
// Launcher啟動器程序進程的用于跨進程通信的IApplicationThread對象
IApplicationThread whoThread = (IApplicationThread) contextThread;
Uri referrer = target != null ? target.onProvideReferrer() : null;
if (referrer != null) {
intent.putExtra(Intent.EXTRA_REFERRER, referrer);
}
if (mActivityMonitors != null) {
synchronized (mSync) {
final int N = mActivityMonitors.size();
for (int i=0; i<N; i++) {
final ActivityMonitor am = mActivityMonitors.get(i);
if (am.match(who, null, intent)) {
am.mHits++;
if (am.isBlocking()) {
return requestCode >= 0 ? am.getResult() : null;
}
break;
}
}
}
}
try {
intent.migrateExtraStreamToClipData();
intent.prepareToLeaveProcess();
// 通過Binder跨進程到系統進程讓ActivityManagerService去執行啟動activity操作
int result = ActivityManagerNative.getDefault()
.startActivity(whoThread, who.getBasePackageName(), intent,
intent.resolveTypeIfNeeded(who.getContentResolver()),
token, target != null ? target.mEmbeddedID : null,
requestCode, 0, null, options);
checkStartActivityResult(result, intent);
} catch (RemoteException e) {
throw new RuntimeException("Failure from system", e);
}
return null;
}
樂器對象Instrumentation直接把要啟動activity的操作交給ActivityManagerNative.getDefault()得到的IActivityManager接口實現對象了,下面看看具體的調用
S4: ActivityManagerNative.getDefault()
public abstract class ActivityManagerNative extends Binder implements IActivityManager{
/**
* Retrieve the system's default/global activity manager.
*/
static public IActivityManager getDefault() {
// 通過單例封裝類Singleton去得到一個需要的單例對象
return gDefault.get();
}
private static final Singleton<IActivityManager> gDefault = new Singleton<IActivityManager>() {
// 具體產生被包裝的單例對象的方法,如果當前單例封裝類內還沒有需要的單例對象就會調用其create()方法初始化一個
protected IActivityManager create() {
// 得到系統進程啟動時候生成的ActivityManagerService對象在本地進程的代理Binder對象
IBinder b = ServiceManager.getService("activity");
if (false) {
Log.v("ActivityManager", "default service binder = " + b);
}
// 生成ActivityManagerProxy對象
IActivityManager am = asInterface(b);
if (false) {
Log.v("ActivityManager", "default service = " + am);
}
return am;
}
};
/**
* Cast a Binder object into an activity manager interface, generating
* a proxy if needed.
*/
static public IActivityManager asInterface(IBinder obj) {
if (obj == null) {
return null;
}
IActivityManager in =
(IActivityManager)obj.queryLocalInterface(descriptor);
if (in != null) {
return in;
}
return new ActivityManagerProxy(obj);
}
}</code></pre>
可以看出ActivityManagerNative.getDefault()實際上是得到了一個ActivityManagerNative的內部類ActivityManagerProxy代理對象,接下來通過Binder進程間通訊機制進入ActivityManagerService進程執行啟動activity操作
S5: 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 options) {
return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo,
resultWho, requestCode, startFlags, profilerInfo, options,
UserHandle.getCallingUserId());
}
@Override
public final int startActivityAsUser(IApplicationThread caller, String callingPackage,
Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode,
int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) {
enforceNotIsolatedCaller("startActivity");
userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId,
false, ALLOW_FULL_ONLY, "startActivity", null);
// TODO: Switch to user app stacks here.
return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent,
resolvedType, null, null, resultTo, resultWho, requestCode, startFlags,
profilerInfo, null, null, options, false, userId, null, null);
}</code></pre>
使用ActivityManagerService的一個成員變量ActivityStackSupervisor對象mStackSupervisor去執行接下來操作,mStackSupervisor在AMS對象構造函數中生成.
S6: ActivityStackSupervisor.startActivityMayWait()
final int startActivityMayWait(IApplicationThread caller, int callingUid,
String callingPackage, Intent intent, String resolvedType,
IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
IBinder resultTo, String resultWho, int requestCode, int startFlags,
ProfilerInfo profilerInfo, WaitResult outResult, Configuration config,
Bundle options, boolean ignoreTargetSecurity, int userId,
IActivityContainer iContainer, TaskRecord inTask) {
....
// 解析需要啟動的activity信息,核心調用了PackageManagerService.resolveIntent()方法
ActivityInfo aInfo =
resolveActivity(intent, resolvedType, startFlags, profilerInfo, userId);
....
// 下一步操作
int res = startActivityLocked(caller, intent, resolvedType, aInfo,
voiceSession, voiceInteractor, resultTo, resultWho,
requestCode, callingPid, callingUid, callingPackage,
realCallingPid, realCallingUid, startFlags, options, ignoreTargetSecurity,
componentSpecified, null, container, inTask);
....
}
final int startActivityLocked(IApplicationThread caller,
Intent intent, String resolvedType, ActivityInfo aInfo,
IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor,
IBinder resultTo, String resultWho, int requestCode,
int callingPid, int callingUid, String callingPackage,
int realCallingPid, int realCallingUid, int startFlags, Bundle options,
boolean ignoreTargetSecurity, boolean componentSpecified, ActivityRecord[] outActivity,
ActivityContainer container, TaskRecord inTask) {
....
// 封裝即將要啟動的activity相關信息
// options參數封裝了包含啟動動畫的信息
// resultRecord==null,后續r.resultTo==null
ActivityRecord r = new ActivityRecord(mService, callerApp, callingUid, callingPackage,
intent, resolvedType, aInfo, mService.mConfiguration, resultRecord, resultWho,
requestCode, componentSpecified, voiceSession != null, this, container, options);
.....
// 下一步操作
err = startActivityUncheckedLocked(r, sourceRecord, voiceSession, voiceInteractor,
startFlags, true, options, inTask);
....
}
final int startActivityUncheckedLocked(final ActivityRecord r, ActivityRecord sourceRecord,
IVoiceInteractionSession voiceSession, IVoiceInteractor voiceInteractor, int startFlags,
boolean doResume, Bundle options, TaskRecord inTask) {
....
ActivityStack targetStack;
....
boolean newTask = false;
// Should this be considered a new task?
if (r.resultTo == null && inTask == null && !addingToTask
&& (launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
newTask = true;
// 獲取要啟動目標activity的ActivityStack,幾乎Android里面的app的activity都用同一個
// ActivityStack來維護的
targetStack = computeStackFocus(r, newTask);
targetStack.moveToFront("startingNewTask");
if (reuseTask == null) {
// 生成一個新的TaskRecord對象,并賦值給要啟動的activityRecord的task變量
// launchTaskBehind==false,所以會同時將目標activity的TaskRecord放到targetStack的成
// 員變量ArrayList<TaskRecord> mTaskHistory最top處
r.setTask(targetStack.createTaskRecord(getNextTaskId(),
newTaskInfo != null ? newTaskInfo : r.info,
newTaskIntent != null ? newTaskIntent : intent,
voiceSession, voiceInteractor, !launchTaskBehind /* toTop */),
taskToAffiliate);
if (DEBUG_TASKS) Slog.v(TAG_TASKS,
"Starting new activity " + r + " in new task " + r.task);
} else {
r.setTask(reuseTask, taskToAffiliate);
}
....
}
....
// 進入ActivityStack去啟動目標activity
targetStack.startActivityLocked(r, newTask, doResume, keepCurTransition, options);
....
}</code></pre>
上面的代碼邏輯好復雜,省略的一些代碼主要用于判斷當前棧里面是否就有將要啟動的activity,某些情況下,是不需要重新啟動這個activity的實例,和activity啟動模式以及前期傳入intent中參數有關系.執行到這里,是要開辟一個新的activity任務棧來啟動這個activity了.
S7: ActivityStack.startActivityLocked()
final void startActivityLocked(ActivityRecord r, boolean newTask,
boolean doResume, boolean keepCurTransition, Bundle options) {
....
TaskRecord task = null;
task = r.task;
// 每個TaskRecord中都有一個ArrayList<ActivityRecord> mActivities用于記錄當前任務棧中的歷史activity
// 設置將要啟動activity相關信息ActivityRecord對象推到所在TaskRecord成員變量final
// ArrayList<ActivityRecord> mActivities的棧頂
task.addActivityToTop(r);
task.setFrontOfTask();
....
// 傳過來的doResume為true,返回交由ActivityStackSupervisor對象繼續處理
if (doResume) {
mStackSupervisor.resumeTopActivitiesLocked(this, r, options);
}
....
}</code></pre>
省略的代碼主要做了目標activity與WindowManagerService相關的一些交互操作
S8: ActivityStackSupervisor.resumeTopActivitiesLocked()
boolean resumeTopActivitiesLocked(ActivityStack targetStack, ActivityRecord target,
Bundle targetOptions) {
if (targetStack == null) {
targetStack = mFocusedStack;
}
// Do targetStack first.
boolean result = false;
// 上一步S7已經設置,這里if里面的判斷為true
if (isFrontStack(targetStack)) {
result = targetStack.resumeTopActivityLocked(target, targetOptions);
}
for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
final ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks;
for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) {
final ActivityStack stack = stacks.get(stackNdx);
if (stack == targetStack) {
// Already started above.
// 上面if中判斷后已經執行,故跳過
continue;
}
if (isFrontStack(stack)) {
stack.resumeTopActivityLocked(null);
}
}
}
return result;
}</code></pre>
S9: ActivityStack.resumeTopActivityLocked()
final boolean resumeTopActivityLocked(ActivityRecord prev, Bundle options) {
if (mStackSupervisor.inResumeTopActivity) {
// Don't even start recursing.
return false;
}
boolean result = false;
try {
// Protect against recursion.
mStackSupervisor.inResumeTopActivity = true;
if (mService.mLockScreenShown == ActivityManagerService.LOCK_SCREEN_LEAVING) {
mService.mLockScreenShown = ActivityManagerService.LOCK_SCREEN_HIDDEN;
mService.updateSleepIfNeededLocked();
}
result = resumeTopActivityInnerLocked(prev, options);
} finally {
mStackSupervisor.inResumeTopActivity = false;
}
return result;
}
private boolean resumeTopActivityInnerLocked(ActivityRecord prev, Bundle options) {
....
// 找到ActivityStack的ArrayList<TaskRecord> mTaskHistory頂部的TaskRecord的頂部的
// ActivityRecord 信息,因為前面已經設置將要啟動的ActivityRecord信息處于頂部之頂部
final ActivityRecord next = topRunningActivityLocked(null);
....
// If the top activity is the resumed one, nothing to do.
// 如果將要啟動的activity已經出于resumed狀態,則什么都不用做了
if (mResumedActivity == next && next.state == ActivityState.RESUMED &&
mStackSupervisor.allResumedActivitiesComplete()) {
....
}
....
// If we are sleeping, and there is no resumed activity, and the top
// activity is paused, well that is the state we want.
// 如果系統休眠同時將要啟動的activity處于棧頂,則什么都不做
if (mService.isSleepingOrShuttingDown()
&& mLastPausedActivity == next
&& mStackSupervisor.allPausedActivitiesComplete()) {
....
}
....
// If we are currently pausing an activity, then don't do anything
// until that is done.
// 如果當前正有acitivity正在進入paused狀態,則也什么都不做
if (!mStackSupervisor.allPausedActivitiesComplete()) {
....
}
....
// 上述幾個情況都不滿足時候,先把當前出于resumed狀態的activity先推到paused狀態,才可以啟動下一個目標activity
// 由于是從Launcher這個activity點擊啟動app的,所以接下來要把Launcher推入paused狀態
if (mResumedActivity != null) {
if (DEBUG_STATES) Slog.d(TAG_STATES,
"resumeTopActivityLocked: Pausing " + mResumedActivity);
pausing |= startPausingLocked(userLeaving, false, true, dontWaitForPause);
}
}</code></pre>
接下來要去將Launcher這個啟動器activity推到paused狀態
S10: ActivityStack.startPausingLocked()
final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping, boolean resuming,
boolean dontWait) {
....
ActivityRecord prev = mResumedActivity;
....
mResumedActivity = null;
mPausingActivity = prev;
mLastPausedActivity = prev;
....
if (prev.app != null && prev.app.thread != null) {
if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Enqueueing pending pause: " + prev);
try {
....
// 實際執行代碼
prev.app.thread.schedulePauseActivity(prev.appToken, prev.finishing,
userLeaving, prev.configChangeFlags, dontWait);
} catch (Exception e) {
// Ignore exception, if process died other code will cleanup.
Slog.w(TAG, "Exception thrown during pause", e);
mPausingActivity = null;
mLastPausedActivity = null;
mLastNoHistoryActivity = null;
}
} else {
mPausingActivity = null;
mLastPausedActivity = null;
mLastNoHistoryActivity = null;
}
}
....
}</code></pre>
這里的mResumedActivity就是當前顯示的activity,這里當然是launcher這個activity,這里把launcher這個app的進程的ActivityThread內部類ApplicationThread的一個遠程接口拿來,通過binder進程間通訊跳轉到Launcher進程
S11: ApplicationThread.schedulePauseActivity()
public final void schedulePauseActivity(IBinder token, boolean finished,
boolean userLeaving, int configChanges, boolean dontReport) {
sendMessage(
finished ? H.PAUSE_ACTIVITY_FINISHING : H.PAUSE_ACTIVITY,
token,
(userLeaving ? 1 : 0) | (dontReport ? 2 : 0),
configChanges);
}
private void sendMessage(int what, Object obj, int arg1, int arg2) {
sendMessage(what, obj, arg1, arg2, false);
}
// 通過外部類ActivityThread的一個成員Handler對象向Launcher進程的主線程發送一個Message消息
private void sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
if (DEBUG_MESSAGES) Slog.v(
TAG, "SCHEDULE " + what + " " + mH.codeToString(what)
+ ": " + arg1 + " / " + obj);
Message msg = Message.obtain();
msg.what = what;
msg.obj = obj;
msg.arg1 = arg1;
msg.arg2 = arg2;
if (async) {
msg.setAsynchronous(true);
}
mH.sendMessage(msg);
}</code></pre>
S11: ActivityThread.handlePauseActivity()
private void handlePauseActivity(IBinder token, boolean finished,
boolean userLeaving, int configChanges, boolean dontReport) {
ActivityClientRecord r = mActivities.get(token);
if (r != null) {
//Slog.v(TAG, "userLeaving=" + userLeaving + " handling pause of " + r);
if (userLeaving) {
performUserLeavingActivity(r);
}
r.activity.mConfigChangeFlags |= configChanges;
// 去執行acitivity的pause
performPauseActivity(token, finished, r.isPreHoneycomb());
// Make sure any pending writes are now committed.
if (r.isPreHoneycomb()) {
QueuedWork.waitToFinish();
}
// Tell the activity manager we have paused.
if (!dontReport) {
try {
// 進入AMS系統進程去告知當前acitivity已經推到paused狀態
ActivityManagerNative.getDefault().activityPaused(token);
} catch (RemoteException ex) {
}
}
mSomeActivitiesChanged = true;
}
}
final Bundle performPauseActivity(IBinder token, boolean finished,
boolean saveState) {
ActivityClientRecord r = mActivities.get(token);
return r != null ? performPauseActivity(r, finished, saveState) : null;
}
final Bundle performPauseActivity(ActivityClientRecord r, boolean finished,
boolean saveState) {
....
mInstrumentation.callActivityOnPause(r.activity);
....
}
// Instrumentation類的方法
public void callActivityOnPause(Activity activity) {
activity.performPause();
}
//Activity類
final void performPause() {
mDoReportFullyDrawn = false;
mFragments.dispatchPause();
mCalled = false;
// acitivity生命周期的pause狀態回調
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;
}</code></pre>
S12:ActivityManagerService.activityPaused()
@Override
public final void activityPaused(IBinder token) {
final long origId = Binder.clearCallingIdentity();
synchronized(this) {
ActivityStack stack = ActivityRecord.getStackLocked(token);
if (stack != null) {
stack.activityPausedLocked(token, false);
}
}
Binder.restoreCallingIdentity(origId);
}
S13:ActivityStack.activityPausedLocked()
final void activityPausedLocked(IBinder token, boolean timeout) {
if (DEBUG_PAUSE) Slog.v(TAG_PAUSE,
"Activity paused: token=" + token + ", timeout=" + timeout);
final ActivityRecord r = isInStackLocked(token);
if (r != null) {
mHandler.removeMessages(PAUSE_TIMEOUT_MSG, r);
if (mPausingActivity == r) {
....
// 繼續,參數resumeNext==true
completePauseLocked(true);
} else {
....
}
}
}
private void completePauseLocked(boolean resumeNext) {
....
if (resumeNext) {
final ActivityStack topStack = mStackSupervisor.getFocusedStack();
if (!mService.isSleepingOrShuttingDown()) {
// 當前系統不是休眠狀態,繼續恢復啟動之前設置的棧頂要啟動的activity
mStackSupervisor.resumeTopActivitiesLocked(topStack, prev, null);
} else {
mStackSupervisor.checkReadyForSleepLocked();
ActivityRecord top = topStack.topRunningActivityLocked(null);
if (top == null || (prev != null && top != prev)) {
// If there are no more activities available to run,
// do resume anyway to start something. Also if the top
// activity on the stack is not the just paused activity,
// we need to go ahead and resume it to ensure we complete
// an in-flight app switch.
mStackSupervisor.resumeTopActivitiesLocked(topStack, null, null);
}
}
}
....
}</code></pre>
S14: ActivityStackSupervisor.resumeTopActivitiesLocked()
// 前面走過一次,繼續調用當前ActivityStack去回復啟動頂部將要啟動的activity
boolean resumeTopActivitiesLocked(ActivityStack targetStack, ActivityRecord target,
Bundle targetOptions) {
if (targetStack == null) {
targetStack = mFocusedStack;
}
// Do targetStack first.
boolean result = false;
if (isFrontStack(targetStack)) {
result = targetStack.resumeTopActivityLocked(target, targetOptions);
}
....
S15: ActivityStack.resumeTopActivityInnerLocked()
// 前面走過一次
final boolean resumeTopActivityLocked(ActivityRecord prev, Bundle options) {
if (mStackSupervisor.inResumeTopActivity) {
// Don't even start recursing.
return false;
}
boolean result = false;
try {
// Protect against recursion.
mStackSupervisor.inResumeTopActivity = true;
if (mService.mLockScreenShown == ActivityManagerService.LOCK_SCREEN_LEAVING) {
mService.mLockScreenShown = ActivityManagerService.LOCK_SCREEN_HIDDEN;
mService.updateSleepIfNeededLocked();
}
// 依然走這里
result = resumeTopActivityInnerLocked(prev, options);
} finally {
mStackSupervisor.inResumeTopActivity = false;
}
return result;
}
// 再次走resumeTopActivityInnerLocked()方法,看這次跟上次有何不同
private boolean resumeTopActivityInnerLocked(ActivityRecord prev, Bundle options) {
.....
// 跟前面一樣獲取之前設置的將要啟動的activity的信息封裝對象
final ActivityRecord next = topRunningActivityLocked(null);
// 前面一些判斷和上一次一樣
......
// 這是上次判斷要去將Launcher推入paused狀態的地方,注意在startPausingLocked()方法中已經把
mResumedActivity=null,而且Launcher這個activity也已經推入到paused狀態
if (mResumedActivity != null) {
if (DEBUG_STATES) Slog.d(TAG_STATES,
"resumeTopActivityLocked: Pausing " + mResumedActivity);
pausing |= startPausingLocked(userLeaving, false, true, dontWaitForPause);
}
....
// 因為前面在生成目標activity的AcitivityRecord對象時候.app成員變量均沒有賦值,故為false
// next.app表示目標activity的ProcessRecord進程信息
// next.app.thread表示目標activity進程的AcitivityThread對象的ApplicationThread成員變量信息
// Android 每個應用程序進程都有一個ActivityThread對象對應,因為程序進程的入口函數是ActivityThread.main()方法
if (next.app != null && next.app.thread != null) {
.....
} else {
// Whoops, need to restart this activity!
if (!next.hasBeenLaunched) {
next.hasBeenLaunched = true;
} else {
if (SHOW_APP_STARTING_PREVIEW) {
mWindowManager.setAppStartingWindow(
next.appToken, next.packageName, next.theme,
mService.compatibilityInfoForPackageLocked(
next.info.applicationInfo),
next.nonLocalizedLabel,
next.labelRes, next.icon, next.logo, next.windowFlags,
null, true);
}
if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Restarting: " + next);
}
if (DEBUG_STATES) Slog.d(TAG_STATES, "resumeTopActivityLocked: Restarting " + next);
// 去啟動目標acitivity
mStackSupervisor.startSpecificActivityLocked(next, true, true);
}
....
}</code></pre>
S16: ActivityStackSupervisor.startSpecificActivityLocked()
// 這里去判斷是否需要開啟一個進程去啟動當前activity
void startSpecificActivityLocked(ActivityRecord r,
boolean andResume, boolean checkConfig) {
// Is this activity's application already running?
// 這里從ActivityManagerService根據進程名和uid去查詢對應ProcessRecord對象
// 如果是第一次啟動目前程序,則app==null
ProcessRecord app = mService.getProcessRecordLocked(r.processName,
r.info.applicationInfo.uid, true);
r.task.stack.setLaunchTime(r);
// 這里判斷為true表明,當前要啟動的程序進程和進程里面的入口ActivityThread.main()已經調用,ActivityThread對象已經生成
// 第一次從Launcher點擊app圖標啟動的話,這里的app==null
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.versionCode,
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.
}
// 第一次從Launcher點擊app圖標,故要先為了該應用程序去啟動一個進程
mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
"activity", r.intent.getComponent(), false, false, true);
}</code></pre>
S17: ActivityManagerService.startProcessLocked()
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 /);
}
// 上面傳過來的entryPoint==null
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) {
....
startProcessLocked(
app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs);
....
}
// 上面傳過來的entryPoint==null
private final void startProcessLocked(ProcessRecord app, String hostingType,
String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) {
....
// Start the process. It will either succeed and return a result containing
// the PID of the new process, or else throw a RuntimeException.
// 傳過來的entryPoint==null
boolean isActivityProcess = (entryPoint == null);
// 指定進程入口函數
if (entryPoint == null) entryPoint = "android.app.ActivityThread";
checkTime(startTime, "startProcess: asking zygote to start proc");
// 去啟動該app進程
Process.ProcessStartResult startResult = Process.start(entryPoint,
app.processName, uid, uid, gids, debugFlags, mountExternal,
app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet,
app.info.dataDir, entryPointArgs);
....
// 設置進程的pid到當前ProcessRecord對象中
app.setPid(startResult.pid);
synchronized (mPidsSelfLocked) {
// 這里存放到SparseArray<ProcessRecord> 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);
}
}
....
}</code></pre>
S18: Process.start()
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[] zygoteArgs) {
try {
// 通過Zygote系統機制去啟動一個APP進程
return startViaZygote(processClass, niceName, uid, gid, gids,
debugFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, zygoteArgs);
} catch (ZygoteStartFailedEx ex) {
Log.e(LOG_TAG,
"Starting VM process through Zygote failed");
throw new RuntimeException(
"Starting VM process through Zygote failed", ex);
}
}
private static ProcessStartResult startViaZygote(final String processClass,
final String niceName,
final int uid, final int gid,
final int[] gids,
int debugFlags, int mountExternal,
int targetSdkVersion,
String seInfo,
String abi,
String instructionSet,
String appDataDir,
String[] extraArgs)
throws ZygoteStartFailedEx {
synchronized(Process.class) {
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);
if ((debugFlags & Zygote.DEBUG_ENABLE_JNI_LOGGING) != 0) {
argsForZygote.add("--enable-jni-logging");
}
if ((debugFlags & Zygote.DEBUG_ENABLE_SAFEMODE) != 0) {
argsForZygote.add("--enable-safemode");
}
if ((debugFlags & Zygote.DEBUG_ENABLE_DEBUGGER) != 0) {
argsForZygote.add("--enable-debugger");
}
if ((debugFlags & Zygote.DEBUG_ENABLE_CHECKJNI) != 0) {
argsForZygote.add("--enable-checkjni");
}
if ((debugFlags & Zygote.DEBUG_ENABLE_JIT) != 0) {
argsForZygote.add("--enable-jit");
}
if ((debugFlags & Zygote.DEBUG_GENERATE_DEBUG_INFO) != 0) {
argsForZygote.add("--generate-debug-info");
}
if ((debugFlags & Zygote.DEBUG_ENABLE_ASSERT) != 0) {
argsForZygote.add("--enable-assert");
}
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);
//TODO optionally enable debuger
//argsForZygote.add("--enable-debugger");
// --setgroups is a comma-separated list
if (gids != null && gids.length > 0) {
StringBuilder sb = new StringBuilder();
sb.append("--setgroups=");
int sz = gids.length;
for (int i = 0; i < sz; i++) {
if (i != 0) {
sb.append(',');
}
sb.append(gids[i]);
}
argsForZygote.add(sb.toString());
}
if (niceName != null) {
argsForZygote.add("--nice-name=" + niceName);
}
if (seInfo != null) {
argsForZygote.add("--seinfo=" + seInfo);
}
if (instructionSet != null) {
argsForZygote.add("--instruction-set=" + instructionSet);
}
if (appDataDir != null) {
argsForZygote.add("--app-data-dir=" + appDataDir);
}
argsForZygote.add(processClass);
if (extraArgs != null) {
for (String arg : extraArgs) {
argsForZygote.add(arg);
}
}
return zygoteSendArgsAndGetResult(openZygoteSocketIfNeeded(abi), argsForZygote);
}
}</code></pre>
- 首先組裝將要啟動的進程參數到ArrayList<String> argsForZygote對象中
-
然后調用openZygoteSocketIfNeeded()判斷是否需要啟動當前進程ActivityManagerService所在的 SystemServer進程是否與Zygote通過Socket通訊連接,如果沒有,則通過socket方式連接用于后續進程間 通訊.
private static ZygoteState openZygoteSocketIfNeeded(String abi) throws ZygoteStartFailedEx {
if (primaryZygoteState == null || primaryZygoteState.isClosed()) {
try {
// 與Zygote進程建立socket連接
primaryZygoteState = ZygoteState.connect(ZYGOTE_SOCKET);
} catch (IOException ioe) {
throw new ZygoteStartFailedEx("Error connecting to primary zygote", ioe);
}
}
if (primaryZygoteState.matches(abi)) {
return primaryZygoteState;
}
// The primary zygote didn't match. Try the secondary.
if (secondaryZygoteState == null || secondaryZygoteState.isClosed()) {
try {
// 與Zygote進程建立socket連接
secondaryZygoteState = ZygoteState.connect(SECONDARY_ZYGOTE_SOCKET);
} catch (IOException ioe) {
throw new ZygoteStartFailedEx("Error connecting to secondary zygote", ioe);
}
}
if (secondaryZygoteState.matches(abi)) {
return secondaryZygoteState;
}
throw new ZygoteStartFailedEx("Unsupported zygote ABI: " + abi);
}
// 通過socket流對象向通道中寫入數據
private static ProcessStartResult zygoteSendArgsAndGetResult(
ZygoteState zygoteState, ArrayList<String> args)
throws ZygoteStartFailedEx {
try {
final BufferedWriter writer = zygoteState.writer;
final DataInputStream inputStream = zygoteState.inputStream;
writer.write(Integer.toString(args.size()));
writer.newLine();
int sz = args.size();
for (int i = 0; i < sz; i++) {
String arg = args.get(i);
if (arg.indexOf('\n') >= 0) {
throw new ZygoteStartFailedEx(
"embedded newlines not allowed");
}
writer.write(arg);
writer.newLine();
}
writer.flush();
// Should there be a timeout on this?
ProcessStartResult result = new ProcessStartResult();
result.pid = inputStream.readInt();
if (result.pid < 0) {
throw new ZygoteStartFailedEx("fork() failed");
}
result.usingWrapper = inputStream.readBoolean();
return result;
} catch (IOException ex) {
zygoteState.close();
throw new ZygoteStartFailedEx(ex);
}
}</code></pre> </li>
</ul>
接下來,Android系統啟動時候的Zygote進程監聽到ActivityManagerService所在進程通過socket發送過來的信息,就會調用每個進程的入口函數:ActivityThread.main().
S19: ActivityThread.main()
public static void main(String[] args) {
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "ActivityThreadMain");
SamplingProfilerIntegration.start();
// CloseGuard defaults to true and can be quite spammy. We
// disable it here, but selectively enable it later (via
// StrictMode) on debug builds, but using DropBox, not logs.
CloseGuard.setEnabled(false);
Environment.initForCurrentUser();
// Set the reporter for event logging in libcore
EventLogger.setReporter(new EventLoggingReporter());
AndroidKeyStoreProvider.install();
// Make sure TrustedCertificateStore looks in the right place for CA certificates
final File configDir = Environment.getUserConfigDirectory(UserHandle.myUserId());
TrustedCertificateStore.setDefaultUserDirectory(configDir);
Process.setArgV0("<pre-initialized>");
// 首先準備每個APP進程(主線程)的Looper消息循環對象和MessageQueue消息隊列
Looper.prepareMainLooper();
// 為每個APP進程創建一個ActivityThread對象,同時會初始化一個Binder內部類成員變量用于
// Binder通訊 final ApplicationThread mAppThread = new ApplicationThread();
ActivityThread thread = new ActivityThread();
// 關鍵方法,調用attach()函數
thread.attach(false);
if (sMainThreadHandler == null) {
sMainThreadHandler = thread.getHandler();
}
if (false) {
Looper.myLooper().setMessageLogging(new
LogPrinter(Log.DEBUG, "ActivityThread"));
}
// End of event ActivityThreadMain.
Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
// 將當前進程(主線程)進入消息循環
Looper.loop();
throw new RuntimeException("Main thread loop unexpectedly exited");
}</code></pre>
}
S20: ActivityThread.attach()
private void attach(boolean system) {
sCurrentActivityThread = this;
mSystemThread = system;
// 當前是APP進程,非系統進程,所以上面傳入的參數boolean system == false
if (!system) {
ViewRootImpl.addFirstDrawHandler(new Runnable() {
@Override
public void run() {
ensureJitEnabled();
}
});
android.ddm.DdmHandleAppName.setAppName("<pre-initialized>",
UserHandle.myUserId());
RuntimeInit.setApplicationObject(mAppThread.asBinder());
// 通過Binder進程間通訊進入ActivityManagerService所在進程
final IActivityManager mgr = ActivityManagerNative.getDefault();
try {
mgr.attachApplication(mAppThread);
} catch (RemoteException ex) {
// Ignore
}
....
} else {
....
}
....
}
S21: ActivityManagerService.attachApplication()
@Override
public final void attachApplication(IApplicationThread thread) {
synchronized (this) {
// 在S17中調用Process.start()之后已經將pid賦值到ProcessRecord中
int callingPid = Binder.getCallingPid();
final long origId = Binder.clearCallingIdentity();
attachApplicationLocked(thread, callingPid);
Binder.restoreCallingIdentity(origId);
}
}
private final boolean attachApplicationLocked(IApplicationThread thread,
int pid) {
ProcessRecord app;
if (pid != MY_PID && pid >= 0) {
synchronized (mPidsSelfLocked) {
// S17中已經存放,所以這里可以取出來
app = mPidsSelfLocked.get(pid);
}
} else {
app = null;
}
....
// 將thread賦值給ProcessRecord app的thread成員變量
app.makeActive(thread, mProcessStats);
// 為true
boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info);
....
try {
....
// 夸進程通訊到剛才APP啟動的進程去做一些操作
thread.bindApplication(processName, appInfo, providers, app.instrumentationClass,
profilerInfo, app.instrumentationArguments, app.instrumentationWatcher,
app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace,
isRestrictedBackupMode || !normalMode, app.persistent,
new Configuration(mConfiguration), app.compat,
getCommonServicesLocked(app.isolated),
mCoreSettingsObserver.getCoreSettingsLocked());
updateLruProcessLocked(app, false, null);
app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis();
} catch (Exception e) {
app.resetPackageList(mProcessStats);
app.unlinkDeathRecipient();
startProcessLocked(app, "bind fail", processName);
return false;
}
....
boolean badApp = false;
// See if the top visible activity is waiting to run in this process...
if (normalMode) {
try {
// 去啟動目標activity
if (mStackSupervisor.attachApplicationLocked(app)) {
didSomething = true;
}
} catch (Exception e) {
Slog.wtf(TAG, "Exception thrown launching activities in " + app, e);
badApp = true;
}
}
}</code></pre>
S22: ActivityStackSupervisor.attachApplicationLocked()
boolean attachApplicationLocked(ProcessRecord app) throws RemoteException {
final String processName = app.processName;
boolean didSomething = false;
for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks;
for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) {
final ActivityStack stack = stacks.get(stackNdx);
// 前面已經設置,當前的ActivityStack已經置頂,如果不是,則跳過,前面S6已經設置
if (!isFrontStack(stack)) {
continue;
}
// 從當前的ActivityStack棧中找到處于最頂的將要啟動的目標acitivity,前面S6已經設置
ActivityRecord hr = stack.topRunningActivityLocked(null);
if (hr != null) {
if (hr.app == null && app.uid == hr.info.applicationInfo.uid
&& processName.equals(hr.processName)) {
try {
// Whoops! 真正去啟動acitivity了!
if (realStartActivityLocked(hr, app, true, true)) {
didSomething = true;
}
} catch (RemoteException e) {
Slog.w(TAG, "Exception in new application when starting activity "
+ hr.intent.getComponent().flattenToShortString(), e);
throw e;
}
}
}
}
}
if (!didSomething) {
ensureActivitiesVisibleLocked(null, 0);
}
return didSomething;
}
final boolean realStartActivityLocked(ActivityRecord r,
ProcessRecord app, boolean andResume, boolean checkConfig)
throws RemoteException {
....
r.app = app;
....
try {
app.forceProcessStateUpTo(mService.mTopProcessState);
// 通過Binder夸進程到剛才APP啟動的進程去執行啟動目標acitivity的操作
// 利用的是前面夸進程傳過來的APP進程的ActivityThread內的ApplicationThread這個Binder對象
app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken,
System.identityHashCode(r), r.info, new Configuration(mService.mConfiguration),
new Configuration(stack.mOverrideConfig), r.compat, r.launchedFromPackage,
task.voiceInteractor, app.repProcState, r.icicle, r.persistentState, results,
newIntents, !andResume, mService.isNextTransitionForward(), profilerInfo);
} catch (RemoteException e) {
....
app.activities.remove(r);
throw e;
}
}</code></pre>
S23: ApplicationThread.scheduleLaunchActivity()
// we use token to identify this activity without having to send the
// activity itself back to the activity manager. (matters more with ipc)
@Override
public final void scheduleLaunchActivity(Intent intent, IBinder token, int ident,
ActivityInfo info, Configuration curConfig, Configuration overrideConfig,
CompatibilityInfo compatInfo, String referrer, IVoiceInteractor voiceInteractor,
int procState, Bundle state, PersistableBundle persistentState,
List<ResultInfo> pendingResults, List<ReferrerIntent> pendingNewIntents,
boolean notResumed, boolean isForward, ProfilerInfo profilerInfo) {
updateProcessState(procState, false);
ActivityClientRecord r = new ActivityClientRecord();
r.token = token;
r.ident = ident;
r.intent = intent;
r.referrer = referrer;
r.voiceInteractor = voiceInteractor;
r.activityInfo = info;
r.compatInfo = compatInfo;
r.state = state;
r.persistentState = persistentState;
r.pendingResults = pendingResults;
r.pendingIntents = pendingNewIntents;
r.startsNotResumed = notResumed;
r.isForward = isForward;
r.profilerInfo = profilerInfo;
r.overrideConfig = overrideConfig;
updatePendingConfiguration(curConfig);
// 發個消息到app進程的主線程,前面在該進程啟動入口函數的ActivityThread.main()調用的時候,已經準備好Looper消息循環
sendMessage(H.LAUNCH_ACTIVITY, r);
}
private void sendMessage(int what, Object obj) {
sendMessage(what, obj, 0, 0, false);
}
private void sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
if (DEBUG_MESSAGES) Slog.v(
TAG, "SCHEDULE " + what + " " + mH.codeToString(what)
+ ": " + arg1 + " / " + obj);
Message msg = Message.obtain();
msg.what = what;
msg.obj = obj;
msg.arg1 = arg1;
msg.arg2 = arg2;
if (async) {
msg.setAsynchronous(true);
}
// 在生成該進程ActivityThread對象的時候已經初始化了一個Handler對象 mH
mH.sendMessage(msg);
}</code></pre>
通過Handler發送消息對象切換到當前進程主線程的ActivityThread對象去執行具體啟動acitivity操作
S24: ActivityThread.handleLaunchActivity()
private void handleLaunchActivity(ActivityClientRecord r, Intent customIntent) {
// If we are getting ready to gc after going to the background, well
// we are back active so skip it.
unscheduleGcIdler();
mSomeActivitiesChanged = true;
....
// Initialize before creating the activity
WindowManagerGlobal.initialize();
// 去啟動acitivity,主要生成acitivity對象,調用其生命周期onCreate(),onStart()方法
Activity a = performLaunchActivity(r, customIntent);
if (a != null) {
r.createdConfig = new Configuration(mConfiguration);
Bundle oldState = r.state;
// 調用acitivity生命周期的onResume(),并將acitivity界面繪制,顯示出來
handleResumeActivity(r.token, false, r.isForward,
!r.activity.mFinished && !r.startsNotResumed);
....
} else {
// If there was an error, for any reason, tell the activity
// manager to stop us.
try {
ActivityManagerNative.getDefault()
.finishActivity(r.token, Activity.RESULT_CANCELED, null, false);
} catch (RemoteException ex) {
// Ignore
}
}
}
S25: ActivityThread.performLaunchActivity()
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
// 先是獲取當前要啟動的acitivity的一些信息,主要是packageInfo和component
ActivityInfo aInfo = r.activityInfo;
if (r.packageInfo == null) {
r.packageInfo = getPackageInfo(aInfo.applicationInfo, r.compatInfo,
Context.CONTEXT_INCLUDE_CODE);
}
ComponentName component = r.intent.getComponent();
if (component == null) {
component = r.intent.resolveActivity(
mInitialApplication.getPackageManager());
r.intent.setComponent(component);
}
if (r.activityInfo.targetActivity != null) {
component = new ComponentName(r.activityInfo.packageName,
r.activityInfo.targetActivity);
}
Activity activity = null;
try {
java.lang.ClassLoader cl = r.packageInfo.getClassLoader();
// 通過反射生成acitivity對象先
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 {
// 生成當前APP的Application對象,并調用其onCreate()
Application app = r.packageInfo.makeApplication(false, mInstrumentation);
if (activity != null) {
// 為了當前acitivity生成一個Context對象
Context appContext = createBaseContextForActivity(r, activity);
CharSequence title = r.activityInfo.loadLabel(appContext.getPackageManager());
Configuration config = new Configuration(mCompatConfiguration);
// 為當前acitivity初始化設置一些必要的參數
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);
if (customIntent != null) {
activity.mIntent = customIntent;
}
r.lastNonConfigurationInstances = null;
activity.mStartedActivity = false;
int theme = r.activityInfo.getThemeResource();
if (theme != 0) {
activity.setTheme(theme);
}
activity.mCalled = false;
// acitivity生命周期的onCreate()在此調用
if (r.isPersistable()) {
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
} else {
mInstrumentation.callActivityOnCreate(activity, r.state);
}
// 如果沒有調用父類的onCreate()方法則,activity.mCalled == false,拋出異常!
if (!activity.mCalled) {
throw new SuperNotCalledException(
"Activity " + r.intent.getComponent().toShortString() +
" did not call through to super.onCreate()");
}
r.activity = activity;
r.stopped = true;
if (!r.activity.mFinished) {
activity.performStart();
r.stopped = false;
}
if (!r.activity.mFinished) {
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);
}
}
if (!r.activity.mFinished) {
activity.mCalled = false;
// 看情況是否需要調用onRestoreInstanceState()方法做一些恢復數據操作
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()");
}
}
}
// 還沒有顯示出來,所以這里先設置為true
r.paused = true;
// 保存當前acitivity信息到該進程的ActivityThread對象中,下面需要取出來用到
mActivities.put(r.token, r);
} catch ....
}
S26: Activity.attach()
final void attach(Context context, ActivityThread aThread,
Instrumentation instr, IBinder token, int ident,
Application application, Intent intent, ActivityInfo info,
CharSequence title, Activity parent, String id,
NonConfigurationInstances lastNonConfigurationInstances,
Configuration config, String referrer, IVoiceInteractor voiceInteractor) {
// 賦值上一步為當前acitivity生成的Context對象,實際是ContextIml對象
attachBaseContext(context);
mFragments.attachHost(null /*parent*/);
// 為當前acitivity設置Window對象
mWindow = new PhoneWindow(this);
// 把當前acitivity對象設置到Window作為通知回調
mWindow.setCallback(this);
mWindow.setOnWindowDismissedCallback(this);
// 這個在XML中直接寫Framgent時候返回調用acitivity中的生成view的方法
mWindow.getLayoutInflater().setPrivateFactory(this);
// 設置輸入法模式
if (info.softInputMode != WindowManager.LayoutParams.SOFT_INPUT_STATE_UNSPECIFIED) {
mWindow.setSoftInputMode(info.softInputMode);
}
if (info.uiOptions != 0) {
mWindow.setUiOptions(info.uiOptions);
}
// 這個當然是主線程啦
mUiThread = Thread.currentThread();
// 保存該應用程序進程的AcitivityThread進程入口對象信息
mMainThread = aThread;
mInstrumentation = instr;
mToken = token;
mIdent = ident;
mApplication = application;
mIntent = intent;
mReferrer = referrer;
mComponent = intent.getComponent();
mActivityInfo = info;
mTitle = title;
mParent = parent;
mEmbeddedID = id;
mLastNonConfigurationInstances = lastNonConfigurationInstances;
if (voiceInteractor != null) {
if (lastNonConfigurationInstances != null) {
mVoiceInteractor = lastNonConfigurationInstances.voiceInteractor;
} else {
mVoiceInteractor = new VoiceInteractor(voiceInteractor, this, this,
Looper.myLooper());
}
}
// 為該acitivity的窗口Window設置WindowManager對象,實際是WindowManagerImpl對象
mWindow.setWindowManager(
(WindowManager)context.getSystemService(Context.WINDOW_SERVICE),
mToken, mComponent.flattenToString(),
(info.flags & ActivityInfo.FLAG_HARDWARE_ACCELERATED) != 0);
if (mParent != null) {
mWindow.setContainer(mParent.getWindow());
}
mWindowManager = mWindow.getWindowManager();
mCurrentConfig = config;
}
主要為acitivity,賦值Context,設置window等
S27: ActivityThread.handleResumeActivity()
final void handleResumeActivity(IBinder token,
boolean clearHide, boolean isForward, boolean reallyResume) {
// 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
// 主要調用了生命周期的onResume()方法
ActivityClientRecord r = performResumeActivity(token, clearHide);
if (r != null) {
final Activity a = r.activity;
if (localLOGV) Slog.v(
TAG, "Resume " + r + " started activity: " +
a.mStartedActivity + ", hideForNow: " + r.hideForNow
+ ", finished: " + a.mFinished);
final int forwardBit = isForward ?
WindowManager.LayoutParams.SOFT_INPUT_IS_FORWARD_NAVIGATION : 0;
// If the window hasn't yet been added to the window manager,
// and this guy didn't finish itself or start another activity,
// then go ahead and add the window.
// 注釋很清楚了...這里為true
boolean willBeVisible = !a.mStartedActivity;
if (!willBeVisible) {
try {
willBeVisible = ActivityManagerNative.getDefault().willActivityBeVisible(
a.getActivityToken());
} catch (RemoteException e) {
}
}
if (r.window == null && !a.mFinished && willBeVisible) {
// 在上一布已經為activity設置了Widnow等
r.window = r.activity.getWindow();
View decor = r.window.getDecorView();
decor.setVisibility(View.INVISIBLE);
ViewManager wm = a.getWindowManager();
WindowManager.LayoutParams l = r.window.getAttributes();
a.mDecor = decor;
l.type = WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
l.softInputMode |= forwardBit;
if (a.mVisibleFromClient) {
a.mWindowAdded = true;
// 核心方法,這里走下去就是acitivity視圖頂層管理對象ViewRootImpl測量,繪制,顯示了
wm.addView(decor, l);
}
}
....
}
至此,從Launcher點擊APP圖標然后在新進程中啟動主acitivity的過程的源碼已經分析完畢.其實還有acitivity中的視圖View繪制和顯示機制,以及事件屏幕事件分發,以后再分析.
來自:http://www.jianshu.com/p/6a1c606934eb