【安卓】App启动流程-源码分析

前言

一、App启动源码流程分析

App启动流程的入口是通过Launcher的startActivity,通过手机桌面图标点击跳转,如下类:

\frameworks\base\core\java\android\app\LauncherActivity.java

    @Override

protected void onListItemClick(ListView l, View v, int position, long id) {

Intent intent = intentForPosition(position);

startActivity(intent);

}

startActivity是如何实现的?

\frameworks\base\core\java\android\app\Activity.java

该类最终执行到Instrumentation的execStartActivity方法,查看注释分析如下:

public class Activity extends ContextThemeWrapper

implements LayoutInflater.Factory2,

Window.Callback, KeyEvent.Callback,

OnCreateContextMenuListener, ComponentCallbacks2,

Window.OnWindowDismissedCallback {

//1、首先执行该方法

@Override

public void startActivity(Intent intent) {

this.startActivity(intent, null);

}

//2、跳转至该方法

@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.

//3、最终判断执行该方法,继续分析startActivityForResult

startActivityForResult(intent, -1);

}

}

//4、跳转至该方法

public void startActivityForResult(Intent intent, int requestCode) {

startActivityForResult(intent, requestCode, null);

}

//5、跳转至此,该方法有点长,只分析重点

public void startActivityForResult(Intent intent, int requestCode, @Nullable Bundle options) {

if (mParent == null) {

//6、执行这里execStartActivity,继续看Instrumentation的execStartActivity方法

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());

}

if (requestCode >= 0) {

// If this start is requesting a result, we can avoid making

// the activity visible until the result is received. Setting

// this code during onCreate(Bundle savedInstanceState) or onResume() will keep the

// activity hidden during this time, to avoid flickering.

// This can only be done when a result is requested because

// that guarantees we will get information back when the

// activity is finished, no matter what happens to it.

mStartedActivity = true;

}

cancelInputsAndStartExitTransition(options);

// TODO Consider clearing/flushing other event sources and events for child windows.

} else {

if (options != null) {

mParent.startActivityFromChild(this, intent, requestCode, options);

} else {

// Note we want to go through this method for compatibility with

// existing applications that may have overridden it.

mParent.startActivityFromChild(this, intent, requestCode);

}

}

}

}

分析:

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) {

//执行该方法

attachBaseContext(context);

mFragments.attachHost(null /*parent*/);

mWindow = new PhoneWindow(this);

mWindow.setCallback(this);

mWindow.setOnWindowDismissedCallback(this);

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();

//1、mMainThread变量的定义

mMainThread = aThread;

//2、mInstrumentation变量的定义

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());

}

}

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;

}

分析:

==继续分析如上Activity.java类最终执行到Instrumentation的execStartActivity方法==

\frameworks\base\core\java\android\app\Instrumentation.java

public class Instrumentation {

public ActivityResult execStartActivity(

Context who, IBinder contextThread, IBinder token, Activity target,

Intent intent, int requestCode, Bundle options) {

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;

}

}

}

}

//1、看重点,这里又出现了startActivity调用者ActivityManagerNative.getDefault()是什么呢?

//2、通过源码分析getDefault 的定义会发现getDefault 方法返回的是一个IActivityManager类型的对象

//3、IActivityManager是一个接口,真实返回的其实是一个ActivityManagerService

//4、该类继承自ActivityManagerNative,而ActivityManagerNative 则实现了IActivityManager 接口

//5、同时还继承了Binder ,很显然ActivityManagerService 是一个Binder 对象

try {

intent.migrateExtraStreamToClipData();

intent.prepareToLeaveProcess();

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;

}

}

\frameworks\base\services\core\java\com\android\server\am\ActivityManagerService.java

进入该方法之后又会调用该类的startActivityAsUser 方法。

public final class ActivityManagerService extends ActivityManagerNative

implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback {

@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);

}

}

\frameworks\base\services\core\java\com\android\server\am\ActivityStack.java

final class ActivityStack {

final void startActivityLocked(ActivityRecord r, boolean newTask,

boolean doResume, boolean keepCurTransition, Bundle options) {

//省略...

if (!isHomeStack() || numActivities() > 0) {

//1、注意:这里有个开始启动前启动了一个预览的window

// We want to show the starting preview window if we are

// switching to a new task, or the next activity's process is

// not currently running.

boolean showStartingIcon = newTask;

ProcessRecord proc = r.app;

if (proc == null) {

proc = mService.mProcessNames.get(r.processName, r.info.applicationInfo.uid);

}

if (proc == null || proc.thread == null) {

showStartingIcon = true;

}

if (DEBUG_TRANSITION) Slog.v(TAG_TRANSITION,

"Prepare open transition: starting " + r);

if ((r.intent.getFlags() & Intent.FLAG_ACTIVITY_NO_ANIMATION) != 0) {

mWindowManager.prepareAppTransition(AppTransition.TRANSIT_NONE, keepCurTransition);

mNoAnimActivities.add(r);

} else {

mWindowManager.prepareAppTransition(newTask

? r.mLaunchTaskBehind

? AppTransition.TRANSIT_TASK_OPEN_BEHIND

: AppTransition.TRANSIT_TASK_OPEN

: AppTransition.TRANSIT_ACTIVITY_OPEN, keepCurTransition);

mNoAnimActivities.remove(r);

}

mWindowManager.addAppToken(task.mActivities.indexOf(r),

r.appToken, r.task.taskId, mStackId, r.info.screenOrientation, r.fullscreen,

(r.info.flags & ActivityInfo.FLAG_SHOW_FOR_ALL_USERS) != 0, r.userId,

r.info.configChanges, task.voiceSession != null, r.mLaunchTaskBehind);

boolean doShow = true;

//省略...

if (r.mLaunchTaskBehind) {

// Don't do a starting window for mLaunchTaskBehind. More importantly make sure we

// tell WindowManager that r is visible even though it is at the back of the stack.

mWindowManager.setAppVisibility(r.appToken, true);

ensureActivitiesVisibleLocked(null, 0);

} else if (SHOW_APP_STARTING_PREVIEW && doShow) {

// Figure out if we are transitioning from another activity that is

// "has the same starting icon" as the next one. This allows the

// window manager to keep the previous window it had previously

// created, if it still had one.

ActivityRecord prev = mResumedActivity;

if (prev != null) {

// We don't want to reuse the previous starting preview if:

// (1) The current activity is in a different task.

if (prev.task != r.task) {

prev = null;

}

// (2) The current activity is already displayed.

else if (prev.nowVisible) {

prev = null;

}

}

//2、mWindowManager.setAppStartingWindow();

mWindowManager.setAppStartingWindow(

r.appToken, r.packageName, r.theme,

mService.compatibilityInfoForPackageLocked(

r.info.applicationInfo), r.nonLocalizedLabel,

r.labelRes, r.icon, r.logo, r.windowFlags,

prev != null ? prev.appToken : null, showStartingIcon);

r.mStartingWindowShown = true;

}

} else {

// If this is the first activity, don't do any fancy animations,

// because there is nothing for it to animate on top of.

mWindowManager.addAppToken(task.mActivities.indexOf(r), r.appToken,

r.task.taskId, mStackId, r.info.screenOrientation, r.fullscreen,

(r.info.flags & ActivityInfo.FLAG_SHOW_FOR_ALL_USERS) != 0, r.userId,

r.info.configChanges, task.voiceSession != null, r.mLaunchTaskBehind);

ActivityOptions.abort(options);

options = null;

}

if (VALIDATE_TOKENS) {

validateAppTokensLocked();

}

//代码又从ActivityStack回到了mStackSupervisor中

if (doResume) {

mStackSupervisor.resumeTopActivitiesLocked(this, r, options);

}

}

}

分析:

==接着继续走启动流程业务:==

\frameworks\base\services\core\java\com\android\server\am\ActivityStackSupervisor.java

==新进程的创建:==

这个startSpecificActivityLocked()进行了一波进程是否存在的判断,接着会调用ActivityManagerService的startProcessLocked()开始进程的创建

public final class ActivityStackSupervisor implements DisplayListener {

void startSpecificActivityLocked(ActivityRecord r,

boolean andResume, boolean checkConfig) {

// Is this activity's application already running?

ProcessRecord app = mService.getProcessRecordLocked(r.processName,

r.info.applicationInfo.uid, true);

r.task.stack.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.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.

}

//APP还未创建才会走到这里,通过ActivityManagerService开启进程

mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,

"activity", r.intent.getComponent(), false, false, true);

}

}

ActivityManagerService的startProcessLocked()这个进程创建的过程也凹凸起伏的:

\frameworks\base\services\core\java\com\android\server\am\ActivityManagerService.java

    // Start the process.  It will either succeed and return a result containing

// the PID of the new process, or else throw a RuntimeException.

boolean isActivityProcess = (entryPoint == null);

if (entryPoint == null) entryPoint = "android.app.ActivityThread";

Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " +

app.processName);

checkTime(startTime, "startProcess: asking zygote to start proc");

//Process.start()完成了ActivityThread的创建

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);

checkTime(startTime, "startProcess: returned from zygote!");

Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);

Process.start()完成了ActivityThread的创建,之后就会执行ActivityThread的main()方法

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 {

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);

}

}

\frameworks\base\core\java\android\app\ActivityThread.java

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>");

//1、Looper终于在此闪亮登场

Looper.prepareMainLooper();

//2、thread.attach(false);方法执行

ActivityThread thread = new ActivityThread();

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");

}

private void attach(boolean system) {

sCurrentActivityThread = this;

mSystemThread = system;

if (!system) {

ViewRootImpl.addFirstDrawHandler(new Runnable() {

@Override

public void run() {

ensureJitEnabled();

}

});

android.ddm.DdmHandleAppName.setAppName("<pre-initialized>",

UserHandle.myUserId());

RuntimeInit.setApplicationObject(mAppThread.asBinder());

final IActivityManager mgr = ActivityManagerNative.getDefault();

try {

//mgr是IActivityManager,也就是说这里通过AIDL调用了ActivityManagerService的attachApplication(mAppThread)

mgr.attachApplication(mAppThread);

} catch (RemoteException ex) {

// Ignore

}

}

分析main函数整体流程:

分析attach流程:

代码如下:

public final void attachApplication(IApplicationThread thread) {

synchronized (this) {

int callingPid = Binder.getCallingPid();

final long origId = Binder.clearCallingIdentity();

attachApplicationLocked(thread, callingPid);

Binder.restoreCallingIdentity(origId);

}

}

private final boolean attachApplicationLocked(IApplicationThread thread,

int pid) {

...

try {

...

thread.bindApplication(processName, appInfo, providers, app.instrumentationClass,

profilerInfo, app.instrumentationArguments, app.instrumentationWatcher,

app.instrumentationUiAutomationConnection, testMode,

mBinderTransactionTrackingEnabled, enableTrackAllocation,

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) {

...

}

...

// 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;

}

\frameworks\base\core\java\android\app\ActivityThread.java

public final void bindApplication(String processName, ApplicationInfo appInfo,

List<ProviderInfo> providers, ComponentName instrumentationName,

ProfilerInfo profilerInfo, Bundle instrumentationArgs,

IInstrumentationWatcher instrumentationWatcher,

IUiAutomationConnection instrumentationUiConnection, int debugMode,

boolean enableBinderTracking, boolean trackAllocation,

boolean isRestrictedBackupMode, boolean persistent, Configuration config,

CompatibilityInfo compatInfo, Map<String, IBinder> services, Bundle coreSettings) {

if (services != null) {

// Setup the service cache in the ServiceManager

ServiceManager.initServiceCache(services);

}

setCoreSettings(coreSettings);

AppBindData data = new AppBindData();

data.processName = processName;

data.appInfo = appInfo;

data.providers = providers;

data.instrumentationName = instrumentationName;

data.instrumentationArgs = instrumentationArgs;

data.instrumentationWatcher = instrumentationWatcher;

data.instrumentationUiAutomationConnection = instrumentationUiConnection;

data.debugMode = debugMode;

data.enableBinderTracking = enableBinderTracking;

data.trackAllocation = trackAllocation;

data.restrictedBackupMode = isRestrictedBackupMode;

data.persistent = persistent;

data.config = config;

data.compatInfo = compatInfo;

data.initProfilerInfo = profilerInfo;

sendMessage(H.BIND_APPLICATION, data);

}

bindApplication分析:

case BIND_APPLICATION:

Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "bindApplication");

AppBindData data = (AppBindData)msg.obj;

handleBindApplication(data);

Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);

break;

private void handleBindApplication(AppBindData data) {

...

// Continue loading instrumentation.

if (ii != null) {

...

mInstrumentation.init(this, instrContext, appContext, component,

data.instrumentationWatcher, data.instrumentationUiAutomationConnection);

if (mProfiler.profileFile != null && !ii.handleProfiling

&& mProfiler.profileFd == null) {

mProfiler.handlingProfiling = true;

final File file = new File(mProfiler.profileFile);

file.getParentFile().mkdirs();

Debug.startMethodTracing(file.toString(), 8 * 1024 * 1024);

}

} else {

mInstrumentation = new Instrumentation();

}

...

try {

// If the app is being launched for full backup or restore, bring it up in

// a restricted environment with the base application class.

//1、这里makeApplication

Application app = data.info.makeApplication(data.restrictedBackupMode, null);

mInitialApplication = app;

...

// Do this after providers, since instrumentation tests generally start their

// test thread at this point, and we don't want that racing.

try {

mInstrumentation.onCreate(data.instrumentationArgs);

}

catch (Exception e) {

...

}

//2、Application的onCreate()执行

try {

mInstrumentation.callApplicationOnCreate(app);

} catch (Exception e) {

...

}

} finally {

StrictMode.setThreadPolicy(savedPolicy);

}

}

Application中在onCreate()方法里去初始化各种全局的变量数据是推荐的做法,但是如果你想把初始化的时间点提前到极致,也可以去重写attachBaseContext()方法

public class CustomApplication extends Application {

@Override

protected void attachBaseContext(Context base) {

// 在这里调用Context的方法会崩溃

super.attachBaseContext(base);

// 在这里可以正常调用Context的方法

}

}

【安卓】App启动流程-源码分析

继续分析:

LAUNCH_ACTIVITY接收如下分支:

case LAUNCH_ACTIVITY: {

Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "activityStart");

final ActivityClientRecord r = (ActivityClientRecord) msg.obj;

r.packageInfo = getPackageInfoNoCheck(

r.activityInfo.applicationInfo, r.compatInfo);

//1、调用handleLaunchActivity()方法

handleLaunchActivity(r, null);

Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);

} break;

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;

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

WindowManagerGlobal.initialize();

//2、Activity 终于被创建了,调用了performLaunchActivity方法创建Activity

Activity a = performLaunchActivity(r, customIntent);

//如果Activity 被创建成功的话,会调用handleResumeActivity

//然后会调用到performResumeActivity,

//然后会调用到Activity 的performResume方法

//最终调用到activity.onResume()生命周期方法

if (a != null) {

r.createdConfig = new Configuration(mConfiguration);

Bundle oldState = r.state;

handleResumeActivity(r.token, false, r.isForward,

!r.activity.mFinished && !r.startsNotResumed);

if (!r.activity.mFinished && r.startsNotResumed) {

// The activity manager actually wants this one to start out

// paused, because it needs to be visible but isn't in the

// foreground. We accomplish this by going through the

// normal startup (because activities expect to go through

// onResume() the first time they run, before their window

// is displayed), and then pausing it. However, in this case

// we do -not- need to do the full pause cycle (of freezing

// and such) because the activity manager assumes it can just

// retain the current state it has.

try {

r.activity.mCalled = false;

mInstrumentation.callActivityOnPause(r.activity);

// We need to keep around the original state, in case

// we need to be created again. But we only do this

// for pre-Honeycomb apps, which always save their state

// when pausing, so we can not have them save their state

// when restarting from a paused state. For HC and later,

// we want to (and can) let the state be saved as the normal

// part of stopping the activity.

if (r.isPreHoneycomb()) {

r.state = oldState;

}

if (!r.activity.mCalled) {

throw new SuperNotCalledException(

"Activity " + r.intent.getComponent().toShortString() +

" 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 "

+ r.intent.getComponent().toShortString()

+ ": " + e.toString(), e);

}

}

r.paused = true;

}

} 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

}

}

}

接着看一下performLaunchActivity做了什么?

里面调用了Activity 的onCreate 和 onStart 等生命周期方法,包括Theme等的设置

    private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {

// System.out.println("##### [" + System.currentTimeMillis() + "] ActivityThread.performLaunchActivity(" + r + ")");

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();

//1、mInstrumentation通过newActivity调用了ActivityActivity 的onCreate 和 onStart等生命周期方法

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 {

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) {

Context appContext = createBaseContextForActivity(r, activity);

CharSequence title = r.activityInfo.loadLabel(appContext.getPackageManager());

Configuration config = new Configuration(mCompatConfiguration);

if (DEBUG_CONFIGURATION) Slog.v(TAG, "Launching activity "

+ r.activityInfo.name + " with config " + config);

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;

//Activity的Theme主题的设置

int theme = r.activityInfo.getThemeResource();

if (theme != 0) {

activity.setTheme(theme);

}

activity.mCalled = false;

if (r.isPersistable()) {

mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);

} else {

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;

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;

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()");

}

}

}

r.paused = true;

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;

}

Application以及Activity的启动流程图如下:

【安卓】App启动流程-源码分析


关注我的技术公众号

【安卓】App启动流程-源码分析

以上是 【安卓】App启动流程-源码分析 的全部内容, 来源链接: utcz.com/a/104865.html

回到顶部