• Activity 的销毁流程


    销毁 Activity 时序图 Activity -> ATMS

    销毁 Activity 时序图 ATMS -> ActivityThread -> Activity

    // frameworks/base/core/java/android/app/Activity.java
    public void finish() {
        finish(DONT_FINISH_TASK_WITH_ACTIVITY); // 1
    }
    
    @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.R, trackingBug = 170729553)
    private void finish(int finishTask) {
        if (mParent == null) {
            int resultCode;
            Intent resultData;
            synchronized (this) {
                resultCode = mResultCode;
                resultData = mResultData;
            }
            if (false) Log.v(TAG, "Finishing self: token=" + mToken);
            if (resultData != null) {
                resultData.prepareToLeaveProcess(this);
            }
            if (ActivityClient.getInstance().finishActivity(mToken, resultCode, resultData,
                    finishTask)) { // 2
                mFinished = true;
            }
        } else {
            mParent.finishFromChild(this);
        }
    
        getAutofillClientController().onActivityFinish(mIntent);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    // frameworks/base/core/java/android/app/ActivityClient.java
    public static ActivityClient getInstance() {
        return sInstance.get();
    }
    
    public boolean finishActivity(IBinder token, int resultCode, Intent resultData,
            int finishTask) {
        try {
            return getActivityClientController().finishActivity(token, resultCode, resultData,
                    finishTask); // 3
        } catch (RemoteException e) {
            throw e.rethrowFromSystemServer();
        }
    }
    
    private static IActivityClientController getActivityClientController() {
        final IActivityClientController controller = INTERFACE_SINGLETON.mKnownInstance;
        return controller != null ? controller : INTERFACE_SINGLETON.get();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    // frameworks/base/core/java/android/app/IActivityClientController.aidl
    interface IActivityClientController {
    		boolean finishActivity(in IBinder token, int code, in Intent data, int finishTask);
    }
    
    • 1
    • 2
    • 3
    • 4
    // frameworks/base/services/core/java/com/android/server/wm/ActivityClientController.java
    class ActivityClientController extends IActivityClientController.Stub {
        @Override
        public boolean finishActivity(IBinder token, int resultCode, Intent resultData,
                int finishTask) {
            ...
    
            final ActivityRecord r;
            synchronized (mGlobalLock) {
                r = ActivityRecord.isInRootTaskLocked(token);
                if (r == null) {
                    return true;
                }
            }
    
            ...
    
            synchronized (mGlobalLock) {
                ...
                try {
                    final boolean res;
                    final boolean finishWithRootActivity =
                            finishTask == Activity.FINISH_TASK_WITH_ROOT_ACTIVITY;
                    if (finishTask == Activity.FINISH_TASK_WITH_ACTIVITY
                            || (finishWithRootActivity && r == rootR)) {
                        mTaskSupervisor.removeTask(tr, false /*killProcess*/,
                                finishWithRootActivity, "finish-activity");
                        res = true;
                        r.mRelaunchReason = RELAUNCH_REASON_NONE;
                    } else {
                        r.finishIfPossible(resultCode, resultData, resultGrants, "app-request",
                                true /* oomAdj */); // 1
                        res = r.finishing;
                        if (!res) {
                            Slog.i(TAG, "Failed to finish by app-request");
                        }
                    }
                    return res;
                } finally {
                    Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER);
                    Binder.restoreCallingIdentity(origId);
                }
            }
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    // frameworks/base/services/core/java/com/android/server/wm/ActivityRecord.java
    final ActivityTaskManagerService mAtmService;
    @FinishRequest int finishIfPossible(int resultCode, Intent resultData,
            NeededUriGrants resultGrants, String reason, boolean oomAdj) {
       	...
    
        mAtmService.deferWindowLayout();
        try {
            ...
    
            finishActivityResults(resultCode, resultData, resultGrants); // 1
    
            final boolean endTask = task.getTopNonFinishingActivity() == null
                    && !task.isClearingToReuseTask();
            mTransitionController.requestCloseTransitionIfNeeded(endTask ? task : this);
      			
      			...
    
            return FINISH_RESULT_REQUESTED;
        } finally {
            mAtmService.continueWindowLayout();
        }
    }
    
    private void finishActivityResults(int resultCode, Intent resultData,
            NeededUriGrants resultGrants) {
        if (resultTo != null) {
            ...
            if (mForceSendResultForMediaProjection || resultTo.isState(RESUMED)) {
                final ActivityRecord resultToActivity = resultTo; // 1
                mAtmService.mH.post(() -> {
                    synchronized (mAtmService.mGlobalLock) {
                        resultToActivity.sendResult(this.getUid(), resultWho, requestCode,
                                resultCode, resultData, resultGrants,
                                mForceSendResultForMediaProjection); // 2
                    }
                });
            } else {
                resultTo.addResultLocked(this, resultWho, requestCode, resultCode, resultData);
            }
            resultTo = null;
        } else if (DEBUG_RESULTS) {
            Slog.v(TAG_RESULTS, "No result destination from " + this);
        }
    
        ...
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    // frameworks/base/services/core/java/com/android/server/wm/ActivityRecord.java
    final ActivityTaskManagerService mAtmService;
    
    void sendResult(int callingUid, String resultWho, int requestCode, int resultCode,
            Intent data, NeededUriGrants dataGrants, boolean forceSendForMediaProjection) {
        ...
    
        if (forceSendForMediaProjection && attachedToProcess() && 
            		isState(STARTED, PAUSING, PAUSED, STOPPING, STOPPED)) {
            final ClientTransaction transaction = 
              ClientTransaction.obtain(app.getThread(), token);
          
            transaction.addCallback(ActivityResultItem.obtain(
                    List.of(new ResultInfo(resultWho, requestCode, resultCode, data))));
            ActivityLifecycleItem lifecycleItem = getLifecycleItemForCurrentStateForResult();
            if (lifecycleItem != null) {
                transaction.setLifecycleStateRequest(lifecycleItem);
            } else {
                Slog.w(TAG, "Unable to get the lifecycle item for state " + mState
                        + " so couldn't immediately send result");
            }
            try {
                mAtmService.getLifecycleManager().scheduleTransaction(transaction); // 1
            } catch (RemoteException e) {
                Slog.w(TAG, "Exception thrown sending result to " + this, e);
            }
        }
    
        addResultLocked(null /* from */, resultWho, requestCode, resultCode, data);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    // frameworks/base/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
    ClientLifecycleManager getLifecycleManager() {
        return mLifecycleManager;
    }
    
    • 1
    • 2
    • 3
    • 4
    // frameworks/base/services/core/java/com/android/server/wm/ClientLifecycleManager.java
    class ClientLifecycleManager {
        void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
            final IApplicationThread client = transaction.getClient();
            transaction.schedule(); // 1
            if (!(client instanceof Binder)) {
                transaction.recycle();
            }
        }
     
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    // frameworks/base/core/java/android/app/servertransaction/ClientTransaction.java
    private IApplicationThread mClient;
    public void schedule() throws RemoteException {
        mClient.scheduleTransaction(this);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    // 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);
      }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    // frameworks/base/core/java/android/app/ClientTransactionHandler.java
    public abstract class ClientTransactionHandler {
    
        // Schedule phase related logic and handlers.
    
        /** Prepare and schedule transaction for execution. */
        void scheduleTransaction(ClientTransaction transaction) {
            transaction.preExecute(this);
            sendMessage(ActivityThread.H.EXECUTE_TRANSACTION, transaction);
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    // frameworks/base/core/java/android/app/ActivityThread.java
    final H mH = new H();
    
    private final TransactionExecutor mTransactionExecutor = new TransactionExecutor(this);
    
    private void sendMessage(int what, Object obj, int arg1, int arg2, boolean async) {
        ...
        Message msg = Message.obtain();
        msg.what = what;
        msg.obj = obj;
        msg.arg1 = arg1;
        msg.arg2 = arg2;
        if (async) {
            msg.setAsynchronous(true);
        }
        mH.sendMessage(msg); // 1
    }
    
    
    class H extends Handler {
      public void handleMessage(Message msg) {
        ...
        case EXECUTE_TRANSACTION:
            final ClientTransaction transaction = (ClientTransaction) msg.obj;
            mTransactionExecutor.execute(transaction); // 2
            if (isSystem()) {
                transaction.recycle();
            }
            break;
        ...
    	}
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    // frameworks/base/core/java/android/app/servertransaction/TransactionExecutor.java
    public void execute(ClientTransaction transaction) {
        if (DEBUG_RESOLVER) Slog.d(TAG, tId(transaction) + "Start resolving transaction");
    
        final IBinder token = transaction.getActivityToken();
        if (token != null) {
            final Map<IBinder, ClientTransactionItem> activitiesToBeDestroyed =
                    mTransactionHandler.getActivitiesToBeDestroyed();
            final ClientTransactionItem destroyItem = activitiesToBeDestroyed.get(token);
            if (destroyItem != null) {
                if (transaction.getLifecycleStateRequest() == destroyItem) {
                    activitiesToBeDestroyed.remove(token);
                }
                if (mTransactionHandler.getActivityClient(token) == null) {
                    Slog.w(TAG, tId(transaction) + "Skip pre-destroyed transaction:\n"
                            + transactionToString(transaction, mTransactionHandler));
                    return;
                }
            }
        }
    
        if (DEBUG_RESOLVER) Slog.d(TAG, transactionToString(transaction, mTransactionHandler));
    
        executeCallbacks(transaction); // 1
    
        executeLifecycleState(transaction);
        mPendingActions.clear();
        if (DEBUG_RESOLVER) Slog.d(TAG, tId(transaction) + "End resolving transaction");
    }
    
    /** Cycle through all states requested by callbacks and execute them at proper times. */
    @VisibleForTesting
    public void executeCallbacks(ClientTransaction transaction) {
        final List<ClientTransactionItem> callbacks = transaction.getCallbacks();
        if (callbacks == null || callbacks.isEmpty()) {
            // No callbacks to execute, return early.
            return;
        }
        if (DEBUG_RESOLVER) Slog.d(TAG, tId(transaction) + "Resolving callbacks in transaction");
    
        final IBinder token = transaction.getActivityToken(); // 2
        ActivityClientRecord r = mTransactionHandler.getActivityClient(token);
    
        final ActivityLifecycleItem finalStateRequest = transaction.getLifecycleStateRequest();
        final int finalState = finalStateRequest != null ? finalStateRequest.getTargetState()
                : UNDEFINED;
        final int lastCallbackRequestingState = lastCallbackRequestingState(transaction);
    
        final int size = callbacks.size();
        for (int i = 0; i < size; ++i) {
            final ClientTransactionItem item = callbacks.get(i);
            if (DEBUG_RESOLVER) Slog.d(TAG, tId(transaction) + "Resolving callback: " + item);
            final int postExecutionState = item.getPostExecutionState();
    
            if (item.shouldHaveDefinedPreExecutionState()) {
                final int closestPreExecutionState = mHelper.getClosestPreExecutionState(r,
                        item.getPostExecutionState());
                if (closestPreExecutionState != UNDEFINED) {
                    cycleToPath(r, closestPreExecutionState, transaction);
                }
            }
    
            item.execute(mTransactionHandler, token, mPendingActions); // 3
            item.postExecute(mTransactionHandler, token, mPendingActions);
            if (r == null) {
                // Launch activity request will create an activity record.
                r = mTransactionHandler.getActivityClient(token);
            }
    
            if (postExecutionState != UNDEFINED && r != null) {
                final boolean shouldExcludeLastTransition =
                        i == lastCallbackRequestingState && finalState == postExecutionState;
                cycleToPath(r, postExecutionState, shouldExcludeLastTransition, transaction);
            }
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    // frameworks/base/core/java/android/app/servertransaction/DestroyActivityItem.java
    public class DestroyActivityItem extends ActivityLifecycleItem {
        @Override
        public void execute(ClientTransactionHandler client, ActivityClientRecord r,
            PendingTransactionActions pendingActions) {
            Trace.traceBegin(TRACE_TAG_ACTIVITY_MANAGER, "activityDestroy");
            client.handleDestroyActivity(r, mFinished, mConfigChanges,
                    false /* getNonConfigInstance */, "DestroyActivityItem");
            Trace.traceEnd(TRACE_TAG_ACTIVITY_MANAGER);
        }
    }
    
    // frameworks/base/core/java/android/app/ClientTransactionHandler.java
    public abstract class ClientTransactionHandler {
        /** Destroy the activity. */
        public abstract void handleDestroyActivity(@NonNull ActivityClientRecord r, 
            boolean finishing, int configChanges, boolean getNonConfigInstance, String reason);
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    // frameworks/base/core/java/android/app/ActivityThread.java
    @Override
    public void handleDestroyActivity(ActivityClientRecord r, boolean finishing, 
                                      int configChanges, boolean getNonConfigInstance, 
                                      String reason) {
        performDestroyActivity(r, finishing, configChanges, getNonConfigInstance, reason); // 1
        ...
    }
    
    /** Core implementation of activity destroy call. */
    void performDestroyActivity(ActivityClientRecord r, boolean finishing,
            int configChanges, boolean getNonConfigInstance, String reason) {
        Class<? extends Activity> activityClass;
        if (localLOGV) Slog.v(TAG, "Performing finish of " + r);
        activityClass = r.activity.getClass();
        r.activity.mConfigChangeFlags |= configChanges;
        if (finishing) {
            r.activity.mFinished = true;
        }
    
        performPauseActivityIfNeeded(r, "destroy");
    
        if (!r.stopped) {
            callActivityOnStop(r, false /* saveState */, "destroy");
        }
        ...
        try {
            r.activity.mCalled = false;
            mInstrumentation.callActivityOnDestroy(r.activity); // 2
            ...
        } catch (SuperNotCalledException e) {
            throw e;
        } catch (Exception e) {
            ...
        }
        r.setState(ON_DESTROY);
        ...
    }
    
    // frameworks/base/core/java/android/app/Instrumentation.java
    public void callActivityOnDestroy(Activity activity) {
        activity.performDestroy();
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    // frameworks/base/core/java/android/app/Activity.java
    final void performDestroy() {
        ...
        dispatchActivityPreDestroyed();
        mDestroyed = true;
        mWindow.destroy();
        mFragments.dispatchDestroy();
        onDestroy(); // 1
        ...
        dispatchActivityPostDestroyed();
        Trace.traceEnd(Trace.TRACE_TAG_WINDOW_MANAGER);
    }
    
    @CallSuper
    protected void onDestroy() {
        if (DEBUG_LIFECYCLE) Slog.v(TAG, "onDestroy " + this);
        mCalled = true;
    
        getAutofillClientController().onActivityDestroyed();
    
        // 2 dismiss any dialogs we are managing. 关闭所有被管理的 dialog
        if (mManagedDialogs != null) {
            final int numDialogs = mManagedDialogs.size();
            for (int i = 0; i < numDialogs; i++) {
                final ManagedDialog md = mManagedDialogs.valueAt(i);
                if (md.mDialog.isShowing()) {
                    md.mDialog.dismiss();
                }
            }
            mManagedDialogs = null;
        }
    
        // 3 close any cursors we are managing. 关闭所有被管理的 Cursor
        synchronized (mManagedCursors) {
            int numCursors = mManagedCursors.size();
            for (int i = 0; i < numCursors; i++) {
                ManagedCursor c = mManagedCursors.get(i);
                if (c != null) {
                    c.mCursor.close();
                }
            }
            mManagedCursors.clear();
        }
    
        // 4 Close any open search dialog 关闭系统搜索服务的弹窗
        if (mSearchManager != null) {
            mSearchManager.stopSearch();
        }
    
        if (mActionBar != null) {
            mActionBar.onDestroy();
        }
    
        // 5 发送 Destroyed 事件,执行所有注册的 ActivityLifecycleCallbacks 的 onActivityDestroyed 回调
        dispatchActivityDestroyed();
    		// 内容捕获服务
        notifyContentCaptureManagerIfNeeded(CONTENT_CAPTURE_STOP);
    
        if (mUiTranslationController != null) {
            mUiTranslationController.onActivityDestroyed();
        }
        if (mDefaultBackCallback != null) {
            getOnBackInvokedDispatcher().unregisterOnBackInvokedCallback(mDefaultBackCallback);
            mDefaultBackCallback = null;
        }
        if (mCallbacksController != null) {
            mCallbacksController.clearCallbacks();
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69

    至此,Activity 整个销毁流程就结束了。

  • 相关阅读:
    【优化调度】粒子群算法求解水火电调度优化问题【含Matlab源码 1181期】
    powershell和cmd对比
    微服务架构学习与思考(10):微服务网关和开源 API 网关01-以 Nginx 为基础的 API 网关详细介绍
    问题2:为什么4级中断处理完成之后会经过用户程序之后再回到1中断处理程序处理呢
    零基础Linux_12(进程)笔试选择题:冯诺依曼结构+操作系统+进程
    c++提高篇——模板(下)
    uni-app小程序开发使用uView,u-model传入富文本内容过长,真机上无法滚动
    刷题 BFS 广度优先算法 : 大胖子走迷宫 (python, java)
    ShardingSphere-proxy-5.0.0部署之分表实现(一)
    C#值类型设置为null
  • 原文地址:https://blog.csdn.net/xingyu19911016/article/details/132668021