Activity启动流程 ,基于Android 10

Posted by roger on November 24, 2019

Activity启动流程 ,基于Android 10

先上一张图

核心类

Activity:界面展示等ui操作 ActivityThread:应用的主线程,入口

Instrumentation 负责调用Activity和Application生命周期。

ActivityTaskManagerService(ATMS):负责管理activity ActivityManagerService(AMS):之前版本负责管理activity,与ATMS同一个父类

ActivityTaskManagerInternal ActivityTaskManagerService对外提供的一个抽象类,真正的实现在ActivityTaskManagerService#LocalService

ActivityStarter:负责启动模式,启动Flag相关处理

ActivityStack:负责管理单独栈activity和其状态,即具体启动的执行等

ActivityStackSupervisor:与ActivityStack类似,但设计window相关的操作

ClientTransactionItem:执行具体activity生命周期的抽象类,子类:LaunchActivityItem等

ClientTransaction:处理相关的信息和生命周期状态

TransactionExecutor 主要作用是执行ClientTransaction

ClientLifecycleManager 生命周期的管理调用

1.启动

  1. Activity

    • -> startActivity -> startActivityForResult() ->
  2. mInstrumentation.execStartActivity()

    最终会调用ActivityTaskManager#getService得到IActivityTaskManager,这里是一个IPC的调用,IActivityTaskManager的服务端是ActivityTaskManagerService,所以ActivityTaskManager.getService().startActivity最终调用的是ActivityTaskManagerService#startActivity

  3. getActivityStartController得到的是ActivityStartController。通过ActivityStartController#obtainStarter得到的是ActivityStarter。最终会调用ActivityStarter#execute

    ActivityStarter

    • 最后会调用startActivityUnchecked(),会根据启动标志位和Activity启动模式来决定如何启动一个Activity

    RootActivityContainer

    -> mRootActivityContainer.resumeFocusedStacksTopActivities()

    ActivityStack

    -> focusedStack.resumeTopActivityUncheckedLocked(target, targetOptions);

    -> resumeTopActivityInnerLocked()

    • 会判断是否有Activity处于Resume状态,如果有的话会让这个Activity执行Pausing过程,即会调用startPausingLocked进行暂停, 然后再执行startSpecificActivityLocked方法启动要启动的Activity

    1.栈顶的Activity执行onPause方法退出

    -> startPausingLocked()

    在ActivityStack.startPausingLocked()方法中通过ClientLifecycleManager的scheduleTransaction方法把PausingActivityItem事件加入到执行计划中,开始栈顶的pausing过程

    mService.getLifecycleManager().scheduleTransaction(prev.app.getThread(),
                            prev.appToken, PauseActivityItem.obtain(prev.finishing, userLeaving,
                                    prev.configChangeFlags, pauseImmediately));
    

    ClientLifecycleManager#scheduleTransaction

    然后在在内部调用ClientTransaction.schedule方法,直接跳转到ApplicationThread中的scheduleTransaction方法

    然后在ClientTransactionHandler.scheduleTransaction方法中 调用了sendMessage方法 ,这个方法是一个抽象方法,其实现在ClientTransactionHandler派生类的ActivityThread中,ActivityThread.sendMessage方法会把消息发送给内部名字叫H的Handler。

最后调用的是ActivityThread中的方法。我们看下ActivityThread#handlePauseActivity。

然后调用performResumeActivity()方法,

所以最终会调用到Instrumentation#callActivityOnPause ,我们看到了熟悉的onPause()

### Activity的创建

我们回到上面的ActivityStack#startPausingLocked执行之后。会调用mStackSupervisor.startSpecificActivityLocked(next, true, true)

如果进程和线程存在,则会直接调用realStartActivityLocked。如果不存在则会调用mService.mH.sendMessage(msg)。mH就是我们上面提到的ActivityThread的内部类H。

ActivityStackSupervisor.startSpecificActivityLocked()

如果进程和线程存在,则会直接调用realStartActivityLocked。如果不存在则会调用mService.mH.sendMessage(msg)。mH就是我们上面提到的ActivityThread的内部类H。

2.创建新的进程

\platform_frameworks_base-master\services\core\java\com\android\server\wm\ActivityStackSupervisor.java
final Message msg = PooledLambda.obtainMessage(
                    ActivityManagerInternal::startProcess, mService.mAmInternal, r.processName,
                    r.info.applicationInfo, knownToBeDead, "activity", r.intent.getComponent());
            mService.mH.sendMessage(msg);

通过ActivityManagerInternal::startProcess

ActivityManagerInternal的实现类ActivityManagerService#LocalService

之后会调用ActivityManagerService.LocalService.startProcessLocked方法,经过多次跳转最终会通过Process.start方法来为应用创建进程。

经过一步步调用,可以发现其最终调用了Zygote并通过socket通信的方式让Zygote进程fork出一个新的进程,并根据传递的”android.app.ActivityThread”字符串,反射出该对象并执行ActivityThread的main方法对其进行初始化。

Activity所在应用主线程初始化

  • ActivityThread.main
  • ActivityThread.attach

在ActivityThread.main方法中对ActivityThread进行了初始化,创建了主线程的Looper对象并调用Looper.loop()方法启动Looper,把自定义Handler类H的对象作为主线程的handler。接下来跳转到ActivityThread.attach方法

在ActivityThread.attach方法中,首先会通过ActivityManagerService为这个应用绑定一个Application,然后添加一个垃圾回收观察者,每当系统触发垃圾回收的时候就会在run方法里面去计算应用使用了多少内存,如果超过总量的四分之三就会尝试释放内存。最后,为根View添加config回调接收config变化相关的信息。

final IActivityManager mgr = ActivityManager.getService();
    try {
         mgr.attachApplication(mAppThread, startSeq);
        } catch (RemoteException ex) {
          throw ex.rethrowFromSystemServer();
    }

进入AMS的attachApplication,即通知系统进程引用启动,这里主要是线程启动,然后调用attachApplicationLocked()

thread.bindApplication(processName, appInfo, providers,
                        instr2.mClass,
                        profilerInfo, instr2.mArguments,
                        instr2.mWatcher,
                        instr2.mUiAutomationConnection, testMode,
                        mBinderTransactionTrackingEnabled, enableTrackAllocation,
                        isRestrictedBackupMode || !normalMode, app.isPersistent(),
                        new Configuration(app.getWindowProcessController().getConfiguration()),
                        app.compat, getCommonServicesLocked(app.isolated),
                        mCoreSettingsObserver.getCoreSettingsLocked(),
                        buildSerial, autofillOptions, contentCaptureOptions,
                        disabledCompatChanges);
                    .....
         // See if the top visible activity is waiting to run in this process...
        if (normalMode) {
            try {
                didSomething = mAtmInternal.attachApplication(app.getWindowProcessController());
            } catch (Exception e) {
                Slog.wtf(TAG, "Exception thrown launching activities in " + app, e);
                badApp = true;
            }
        }
  • 配置应用相关的属性
  • thread.bindApplcation
  • mAtmInternal.attachApplication(app.getWindowProcessController());

其中thread.bindApplicaion,即ActivityThread.ApplicationThread.bindApplication

ActivityThread.bindApplication()

sendMessage(H.BIND_APPLICATION, data);

//在ActivityThread.H handleMessage

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;

在handleBindApplication完成application初始化,

if (!data.restrictedBackupMode) {
                if (!ArrayUtils.isEmpty(data.providers)) {
                    installContentProviders(app, data.providers);
                }
            }
mInstrumentation.callApplicationOnCreate(app);

这里可以看的ContentProvider先于application.onCreate方法,

-接下来启动Activity

 didSomething = mAtmInternal.attachApplication(app.getWindowProcessController());

class LocalService extends ActivityTaskManagerInternal

  • 调用ATMS.localService.attachApplication
 public boolean attachApplication(WindowProcessController wpc) throws RemoteException {
            synchronized (mGlobalLockWithoutBoost) {
                return mRootActivityContainer.attachApplication(wpc);
            }
        }

最后调用ActivityStack.realStartActivityLocked

clientTransaction.addCallback(LaunchActivityItem.obtain(new Intent(r.intent),
mService.getLifecycleManager().scheduleTransaction(clientTransaction);

后续流程基本与pasue和resume类似

3.直接调用realStartActivityLocked()方法

在ActivityStackSupervisor.realStartActivityLocked()方法中为ClientTransaction对象添加LaunchActivityItem的callback,然后设置当前的生命周期状态,最后调用ClientLifeMananger.scheduleTransaction方法执行

然后,之前一样,

ApplicationThread是一个ActivityThread中的内部类

ClientTransaction.schedule方法的mClient是一个IApplicationThread类型,ActivityThread的内部类ApplicationThread派生这个接口类并实现了对应的方法。所以直接跳转到ApplicationThread中的scheduleTransaction方法。ActivityThread类中并没有定义scheduleTransaction方法,所以调用的是他父类ClientTransactionHandler的scheduleTransaction方法。

    frameworks/base/core/java/android/app/ActivityThread.java
    private class ApplicationThread extends IApplicationThread.Stub {
        ...
        @Override
        public void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
            ActivityThread.this.scheduleTransaction(transaction);
        }
    }

    frameworks/base/core/java/android/app/ClientTransactionHandler.java
    void scheduleTransaction(ClientTransaction transaction) {
        transaction.preExecute(this);
        sendMessage(ActivityThread.H.EXECUTE_TRANSACTION, transaction);
    }

在ClientTransactionHandler.scheduleTransaction方法中调用了sendMessage方法,这个方法是一个抽象方法,其实现在ClientTransactionHandler派生类的ActivityThread中,ActivityThread.sendMessage方法会把消息发送给内部名字叫H的Handler。

    frameworks/base/core/java/android/app/ActivityThread.java
    void sendMessage(int what, Object obj) {
        sendMessage(what, obj, 0, 0, false);
    }

    private void sendMessage(int what, Object obj, int arg1) {
        sendMessage(what, obj, arg1, 0, false);
    }

    private void sendMessage(int what, Object obj, int arg1, int arg2) {
        sendMessage(what, obj, arg1, arg2, 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);
        }
        mH.sendMessage(msg);
    }

    public void handleMessage(Message msg) {
        ...
        case EXECUTE_TRANSACTION:
            final ClientTransaction transaction = (ClientTransaction) msg.obj;
            mTransactionExecutor.execute(transaction);
            ...
            break;
        ...
    }

Handler H的实例接收到EXECUTE_TRANSACTION消息后调用TransactionExecutor.execute方法切换Activity状态。TransactionExecutor.execute方法里面先执行Callbacks,然后改变Activity当前的生命周期状态。然后执行executeLifecycleState方法。

executeCallbacks(transaction);
executeLifecycleState(transaction);

在executeLifecycleState方法里面,会先去调用TransactionExecutor.cycleToPath执行当前生命周期状态之前的状态,然后执行ActivityLifecycleItem.execute方法。所以executeLifecycleState方法里调用的execute方法其实是LaunchActivityItem.execute方法。

frameworks\base\core\java\android\app\servertransaction\TransactionExecutor.java
cycleToPath(r, lifecycleItem.getTargetState(), true /* excludeLastState */, transaction);

        // Execute the final transition with proper parameters.
        lifecycleItem.execute(mTransactionHandler, token, mPendingActions);
        lifecycleItem.postExecute(mTransactionHandler, token, mPendingActions);

然后

    frameworks/base/core/java/android/app/servertransaction/LaunchActivityItem.java
    public void execute(ClientTransactionHandler client, IBinder token,
            PendingTransactionActions pendingActions) {
        ...
        client.handleLaunchActivity(r, pendingActions, null /* customIntent */);
    }

进入了ActivityThread#handleLaunchActivity方法

private void handleLaunchActivity(ActivityClientRecord r, Intent customIntent, String reason) {
    ...
    // Make sure we are running with the most recent config.
    handleConfigurationChanged(null, null);

    // Initialize before creating the activity //初始化WindowManagerGlobal
    WindowManagerGlobal.initialize();

    //1. 启动一个Activity,涉及到创建Activity对象,最终返回Activity对象
    Activity a = Activity a = performLaunchActivity(r, customIntent);

    if (a != null) {
        r.createdConfig = new Configuration(mConfiguration);
        reportSizeConfigurations(r);
        Bundle oldState = r.state;
	//2. Activity 进入onResume方法
        handleResumeActivity(r.token, false, r.isForward,
                !r.activity.mFinished && !r.startsNotResumed, r.lastProcessedSeq, reason);

        if (!r.activity.mFinished && r.startsNotResumed) {
	    //3. 如果没能在前台显示,就进入onPuse方法
            performPauseActivityIfNeeded(r, reason);

        }
    } else {
        // If there was an error, for any reason, tell the activity manager to stop us.
	//4. activity启动失败,则通知AMS finish掉这个Activity
        try {
            ActivityManagerNative.getDefault()
                .finishActivity(r.token, Activity.RESULT_CANCELED, null,
                        Activity.DONT_FINISH_TASK_WITH_ACTIVITY);
        } catch (RemoteException ex) {
            throw ex.rethrowFromSystemServer();
        }
    }
}

经过上面代码一步步的跳转,执行到ActivityThread.performLaunchActivity方法。在ActivityThread.performLaunchActivity方法中首先对Activity的ComponentName、ContextImpl、Activity以及Application对象进行了初始化并相互关联,然后设置Activity主题,最后调用Instrumentation.callActivityOnCreate方法。

ActivityThread#perfomLaunchActivity

private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {

	//1 创建Activity对象
	activity = mInstrumentation.newActivity(
                cl, component.getClassName(), r.intent);

	//2 调用Activity的attach方法
	activity.attach(appContext, this, getInstrumentation(), r.token,
                    r.ident, app, r.intent, r.activityInfo, title, r.parent,
                    r.embeddedID, r.lastNonConfigurationInstances, config,
                    r.referrer, r.voiceInteractor, window);

	//3.回调onCreate
	mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);

}

分析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,
        Window window) {
	//1、回调 attachBaseContext
    attachBaseContext(context);

	//2、创建PhoneWindow
    mWindow = new PhoneWindow(this, window);
    mWindow.setWindowControllerCallback(this);
    mWindow.setCallback(this);
    mWindow.setOnWindowDismissedCallback(this);
    ...
    
    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;

attach方法主要关注两点: 1.会调用attachBaseContext 方法; 2.创建PhoneWindow,赋值给mWindow

从Instrumentation.callActivityOnCreate方法继续追踪,跳转到Activity.performCreate方法,在这里我们看到了Activity.onCreate方法。

\core\java\android\app\Activity.java
final void performCreate(Bundle icicle, PersistableBundle persistentState) {
        dispatchActivityPreCreated(icicle);
        mCanEnterPictureInPicture = true;
        restoreHasCurrentPermissionRequest(icicle);
        if (persistentState != null) {
            onCreate(icicle, persistentState);
        } else {
            onCreate(icicle);
        }
        writeEventLog(LOG_AM_ON_CREATE_CALLED, "performCreate");
        mActivityTransitionState.readState(icicle);

        mVisibleFromClient = !mWindow.getWindowStyle().getBoolean(
                com.android.internal.R.styleable.Window_windowNoDisplay, false);
        mFragments.dispatchActivityCreated();
        mActivityTransitionState.setEnterActivityOptions(this, getActivityOptions());
        dispatchActivityPostCreated(icicle);
    }

至此,我们就基本分析了Activity的启动流程

总结

Activity启动流程,Android 9和Android 10有很多变化,自己参考了许多文章,感谢那些博客,让自己分析源码有了思路。如果有什么写的不对或者不好的地方,欢迎大家批评指正。