Loading services/core/java/com/android/server/wm/ActivityRecord.java +153 −21 Original line number Diff line number Diff line Loading @@ -379,6 +379,27 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A @VisibleForTesting static final int Z_BOOST_BASE = 800570000; static final int INVALID_PID = -1; // How long we wait until giving up on the last activity to pause. This // is short because it directly impacts the responsiveness of starting the // next activity. private static final int PAUSE_TIMEOUT = 500; // Ticks during which we check progress while waiting for an app to launch. private static final int LAUNCH_TICK = 500; // How long we wait for the activity to tell us it has stopped before // giving up. This is a good amount of time because we really need this // from the application in order to get its saved state. Once the stop // is complete we may start destroying client resources triggering // crashes if the UI thread was hung. We put this timeout one second behind // the ANR timeout so these situations will generate ANR instead of // Surface lost or other errors. private static final int STOP_TIMEOUT = 11 * 1000; // How long we wait until giving up on an activity telling us it has // finished destroying itself. private static final int DESTROY_TIMEOUT = 10 * 1000; final ActivityTaskManagerService mAtmService; final ActivityInfo info; // activity info provided by developer in AndroidManifest // Non-null only for application tokens. Loading Loading @@ -681,6 +702,55 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A // Token for targeting this activity for assist purposes. final Binder assistToken = new Binder(); private final Runnable mPauseTimeoutRunnable = new Runnable() { @Override public void run() { // We don't at this point know if the activity is fullscreen, // so we need to be conservative and assume it isn't. Slog.w(TAG, "Activity pause timeout for " + ActivityRecord.this); synchronized (mAtmService.mGlobalLock) { if (hasProcess()) { mAtmService.logAppTooSlow(app, pauseTime, "pausing " + ActivityRecord.this); } activityPaused(true); } } }; private final Runnable mLaunchTickRunnable = new Runnable() { @Override public void run() { synchronized (mAtmService.mGlobalLock) { if (continueLaunchTicking()) { mAtmService.logAppTooSlow( app, launchTickTime, "launching " + ActivityRecord.this); } } } }; private final Runnable mDestroyTimeoutRunnable = new Runnable() { @Override public void run() { synchronized (mAtmService.mGlobalLock) { Slog.w(TAG, "Activity destroy timeout for " + ActivityRecord.this); destroyed("destroyTimeout"); } } }; private final Runnable mStopTimeoutRunnable = new Runnable() { @Override public void run() { synchronized (mAtmService.mGlobalLock) { Slog.w(TAG, "Activity stop timeout for " + ActivityRecord.this); if (isInHistory()) { activityStopped(null /*icicle*/, null /*persistentState*/, null /*description*/); } } } }; private static String startingWindowStateToString(int state) { switch (state) { case STARTING_WINDOW_NOT_SHOWN: Loading Loading @@ -2684,11 +2754,6 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A EventLogTags.writeWmDestroyActivity(mUserId, System.identityHashCode(this), task.mTaskId, shortComponentName, reason); final ActivityStack stack = getActivityStack(); if (hasProcess() && !stack.inLruList(this)) { Slog.w(TAG, "Activity " + this + " being finished, but not in LRU list"); } boolean removedFromHistory = false; cleanUp(false /* cleanServices */, false /* setState */); Loading Loading @@ -2735,7 +2800,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } setState(DESTROYING, "destroyActivityLocked. finishing and not skipping destroy"); stack.scheduleDestroyTimeoutForActivity(this); mAtmService.mH.postDelayed(mDestroyTimeoutRunnable, DESTROY_TIMEOUT); } else { if (DEBUG_STATES) { Slog.v(TAG_STATES, "Moving to DESTROYED: " + this + " (destroy skipped)"); Loading Loading @@ -2785,8 +2850,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } takeFromHistory(); final ActivityStack stack = getActivityStack(); stack.removeTimeoutsForActivity(this); removeTimeouts(); if (DEBUG_STATES) { Slog.v(TAG_STATES, "Moving to DESTROYED: " + this + " (removed from history)"); } Loading Loading @@ -2814,7 +2878,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A * AND finished. */ void destroyed(String reason) { getActivityStack().removeDestroyTimeoutForActivity(this); removeDestroyTimeout(); if (DEBUG_CONTAINERS) Slog.d(TAG_CONTAINERS, "activityDestroyedLocked: r=" + this); Loading Loading @@ -2872,7 +2936,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } // Get rid of any pending idle timeouts. stack.removeTimeoutsForActivity(this); removeTimeouts(); // Clean-up activities are no longer relaunching (e.g. app process died). Notify window // manager so it can update its bookkeeping. clearRelaunching(); Loading Loading @@ -4737,6 +4801,73 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } } void activityPaused(boolean timeout) { if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Activity paused: token=" + appToken + ", timeout=" + timeout); final ActivityStack stack = getStack(); if (stack != null) { removePauseTimeout(); if (stack.mPausingActivity == this) { if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to PAUSED: " + this + (timeout ? " (due to timeout)" : " (pause complete)")); mAtmService.deferWindowLayout(); try { stack.completePauseLocked(true /* resumeNext */, null /* resumingActivity */); } finally { mAtmService.continueWindowLayout(); } return; } else { EventLogTags.writeWmFailedToPause(mUserId, System.identityHashCode(this), shortComponentName, stack.mPausingActivity != null ? stack.mPausingActivity.shortComponentName : "(none)"); if (isState(PAUSING)) { setState(PAUSED, "activityPausedLocked"); if (finishing) { if (DEBUG_PAUSE) Slog.v(TAG, "Executing finish of failed to pause activity: " + this); completeFinishing("activityPausedLocked"); } } } } mRootActivityContainer.ensureActivitiesVisible(null, 0, !PRESERVE_WINDOWS); } /** * Schedule a pause timeout in case the app doesn't respond. We don't give it much time because * this directly impacts the responsiveness seen by the user. */ void schedulePauseTimeout() { pauseTime = SystemClock.uptimeMillis(); mAtmService.mH.postDelayed(mPauseTimeoutRunnable, PAUSE_TIMEOUT); if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Waiting for pause to complete..."); } private void removePauseTimeout() { mAtmService.mH.removeCallbacks(mPauseTimeoutRunnable); } private void removeDestroyTimeout() { mAtmService.mH.removeCallbacks(mDestroyTimeoutRunnable); } private void removeStopTimeout() { mAtmService.mH.removeCallbacks(mStopTimeoutRunnable); } void removeTimeouts() { mStackSupervisor.removeIdleTimeoutForActivity(this); removePauseTimeout(); removeStopTimeout(); removeDestroyTimeout(); finishLaunchTickingLocked(); } void stopIfPossible() { if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, "Stopping: " + this); final ActivityStack stack = getActivityStack(); Loading Loading @@ -4783,7 +4914,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A if (stack.shouldSleepOrShutDownActivities()) { setSleeping(true); } stack.scheduleStopTimeoutForActivity(this); mAtmService.mH.postDelayed(mStopTimeoutRunnable, STOP_TIMEOUT); } catch (Exception e) { // Maybe just ignore exceptions here... if the process has crashed, our death // notification will clean things up. Loading @@ -4798,13 +4929,13 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } } final void activityStoppedLocked(Bundle newIcicle, PersistableBundle newPersistentState, void activityStopped(Bundle newIcicle, PersistableBundle newPersistentState, CharSequence description) { final ActivityStack stack = getActivityStack(); final boolean isStopping = mState == STOPPING; if (!isStopping && mState != RESTARTING_PROCESS) { Slog.i(TAG, "Activity reported stop, but no longer stopping: " + this); stack.removeStopTimeoutForActivity(this); removeStopTimeout(); return; } if (newPersistentState != null) { Loading @@ -4822,7 +4953,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A if (DEBUG_SAVED_STATE) Slog.i(TAG_SAVED_STATE, "Saving icicle of " + this + ": " + mIcicle); if (!stopped) { if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to STOPPED: " + this + " (stop complete)"); stack.removeStopTimeoutForActivity(this); removeStopTimeout(); stopped = true; if (isStopping) { setState(STOPPED, "activityStoppedLocked"); Loading Loading @@ -4877,11 +5008,11 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } if (launchTickTime == 0) { launchTickTime = SystemClock.uptimeMillis(); continueLaunchTickingLocked(); continueLaunchTicking(); } } boolean continueLaunchTickingLocked() { private boolean continueLaunchTicking() { if (launchTickTime == 0) { return false; } Loading @@ -4892,10 +5023,14 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } stack.removeLaunchTickMessages(); stack.scheduleLaunchTickForActivity(this); mAtmService.mH.postDelayed(mLaunchTickRunnable, LAUNCH_TICK); return true; } void removeLaunchTickRunnable() { mAtmService.mH.removeCallbacks(mLaunchTickRunnable); } void finishLaunchTickingLocked() { launchTickTime = 0; final ActivityStack stack = getActivityStack(); Loading Loading @@ -7017,10 +7152,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A newIntents = null; mAtmService.getAppWarningsLocked().onResumeActivity(this); } else { final ActivityStack stack = getActivityStack(); if (stack != null) { stack.removePauseTimeoutForActivity(this); } removePauseTimeout(); setState(PAUSED, "relaunchActivityLocked"); } Loading services/core/java/com/android/server/wm/ActivityStack.java +61 −317 File changed.Preview size limit exceeded, changes collapsed. Show changes services/core/java/com/android/server/wm/ActivityStackSupervisor.java +27 −5 Original line number Diff line number Diff line Loading @@ -52,7 +52,9 @@ import static android.view.WindowManager.TRANSIT_DOCK_TASK_FROM_RECENTS; import static com.android.server.wm.ActivityStack.ActivityState.PAUSED; import static com.android.server.wm.ActivityStack.ActivityState.PAUSING; import static com.android.server.wm.ActivityStack.TAG_CLEANUP; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_ALL; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_CLEANUP; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_IDLE; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_PAUSE; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_RECENTS; Loading Loading @@ -956,9 +958,6 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { } r.launchFailed = false; if (stack.updateLruList(r)) { Slog.w(TAG, "Activity " + r + " being launched, but already in LRU list"); } // TODO(lifecycler): Resume or pause requests are done as part of launch transaction, // so updating the state should be done accordingly. Loading Loading @@ -2162,7 +2161,7 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { if (!processPausingActivities && s.isState(PAUSING)) { // Defer processing pausing activities in this iteration and reschedule // a delayed idle to reprocess it again removeTimeoutsForActivityLocked(idleActivity); removeIdleTimeoutForActivity(idleActivity); scheduleIdleTimeoutLocked(idleActivity); continue; } Loading @@ -2181,6 +2180,29 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { return stops; } void removeHistoryRecords(WindowProcessController app) { removeHistoryRecords(mStoppingActivities, app, "mStoppingActivities"); removeHistoryRecords(mGoingToSleepActivities, app, "mGoingToSleepActivities"); removeHistoryRecords(mFinishingActivities, app, "mFinishingActivities"); } private void removeHistoryRecords(ArrayList<ActivityRecord> list, WindowProcessController app, String listName) { int i = list.size(); if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, "Removing app " + this + " from list " + listName + " with " + i + " entries"); while (i > 0) { i--; ActivityRecord r = list.get(i); if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, "Record #" + i + " " + r); if (r.app == app) { if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, "---> REMOVING this entry!"); list.remove(i); r.removeTimeouts(); } } } public void dump(PrintWriter pw, String prefix) { pw.println(); pw.println("ActivityStackSupervisor state:"); Loading Loading @@ -2371,7 +2393,7 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { scheduleTopResumedActivityStateIfNeeded(); } void removeTimeoutsForActivityLocked(ActivityRecord r) { void removeIdleTimeoutForActivity(ActivityRecord r) { if (DEBUG_IDLE) Slog.d(TAG_IDLE, "removeTimeoutsForActivity: Callers=" + Debug.getCallers(4)); mHandler.removeMessages(IDLE_TIMEOUT_MSG, r); Loading services/core/java/com/android/server/wm/ActivityTaskManagerService.java +6 −6 Original line number Diff line number Diff line Loading @@ -306,7 +306,7 @@ import java.util.Set; public class ActivityTaskManagerService extends IActivityTaskManager.Stub { private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityTaskManagerService" : TAG_ATM; private static final String TAG_STACK = TAG + POSTFIX_STACK; private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE; private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS; private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY; Loading Loading @@ -1730,9 +1730,9 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub { final long origId = Binder.clearCallingIdentity(); synchronized (mGlobalLock) { Trace.traceBegin(TRACE_TAG_WINDOW_MANAGER, "activityPaused"); ActivityStack stack = ActivityRecord.getStackLocked(token); if (stack != null) { stack.activityPausedLocked(token, false); final ActivityRecord r = ActivityRecord.forTokenLocked(token); if (r != null) { r.activityPaused(false); } Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER); } Loading Loading @@ -1765,7 +1765,7 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub { restartingName = r.app.mName; restartingUid = r.app.mUid; } r.activityStoppedLocked(icicle, persistentState, description); r.activityStopped(icicle, persistentState, description); } Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER); } Loading Loading @@ -7304,7 +7304,7 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub { @Override public void scheduleDestroyAllActivities(String reason) { synchronized (mGlobalLock) { mRootActivityContainer.scheduleDestroyAllActivities(null, reason); mRootActivityContainer.scheduleDestroyAllActivities(reason); } } Loading services/core/java/com/android/server/wm/RootActivityContainer.java +38 −9 Original line number Diff line number Diff line Loading @@ -54,6 +54,7 @@ import static com.android.server.wm.ActivityStackSupervisor.printThisActivity; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_RECENTS; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_STACK; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_STATES; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_SWITCH; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_TASKS; import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_RECENTS; import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_RELEASE; Loading @@ -62,6 +63,7 @@ import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_TASKS import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_ATM; import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_WITH_CLASS_NAME; import static com.android.server.wm.ActivityTaskManagerService.ANIMATE; import static com.android.server.wm.ActivityTaskManagerService.TAG_SWITCH; import static com.android.server.wm.Task.REPARENT_LEAVE_STACK_IN_PLACE; import static com.android.server.wm.Task.REPARENT_MOVE_STACK_TO_FRONT; Loading Loading @@ -205,6 +207,28 @@ class RootActivityContainer extends RootWindowContainer private boolean mTmpBoolean; private RemoteException mTmpRemoteException; private String mDestroyAllActivitiesReason; private final Runnable mDestroyAllActivitiesRunnable = new Runnable() { @Override public void run() { synchronized (mService.mGlobalLock) { try { mStackSupervisor.beginDeferResume(); final PooledConsumer c = PooledLambda.obtainConsumer( RootActivityContainer::destroyActivity, RootActivityContainer.this, PooledLambda.__(ActivityRecord.class)); forAllActivities(c); c.recycle(); } finally { mStackSupervisor.endDeferResume(); resumeFocusedStacksTopActivities(); } } } }; private final FindTaskResult mTmpFindTaskResult = new FindTaskResult(); static class FindTaskResult implements Function<Task, Boolean> { ActivityRecord mRecord; Loading Loading @@ -1653,14 +1677,19 @@ class RootActivityContainer extends RootWindowContainer } } void scheduleDestroyAllActivities(WindowProcessController app, String reason) { for (int displayNdx = getChildCount() - 1; displayNdx >= 0; --displayNdx) { final DisplayContent display = getChildAt(displayNdx); for (int stackNdx = display.getStackCount() - 1; stackNdx >= 0; --stackNdx) { final ActivityStack stack = display.getStackAt(stackNdx); stack.scheduleDestroyActivities(app, reason); } void scheduleDestroyAllActivities(String reason) { mDestroyAllActivitiesReason = reason; mService.mH.post(mDestroyAllActivitiesRunnable); } private void destroyActivity(ActivityRecord r) { if (r.finishing || !r.isDestroyable()) return; if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Destroying " + r + " in state " + r.getState() + " resumed=" + r.getStack().mResumedActivity + " pausing=" + r.getStack().mPausingActivity + " for reason " + mDestroyAllActivitiesReason); r.destroyImmediately(true /* removeFromTask */, mDestroyAllActivitiesReason); } // Tries to put all activity stacks to sleep. Returns true if all stacks were Loading Loading @@ -2059,7 +2088,7 @@ class RootActivityContainer extends RootWindowContainer final DisplayContent display = getChildAt(displayNdx); for (int stackNdx = display.getStackCount() - 1; stackNdx >= 0; --stackNdx) { final ActivityStack stack = display.getStackAt(stackNdx); hasVisibleActivities |= stack.handleAppDiedLocked(app); hasVisibleActivities |= stack.handleAppDied(app); } } return hasVisibleActivities; Loading Loading
services/core/java/com/android/server/wm/ActivityRecord.java +153 −21 Original line number Diff line number Diff line Loading @@ -379,6 +379,27 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A @VisibleForTesting static final int Z_BOOST_BASE = 800570000; static final int INVALID_PID = -1; // How long we wait until giving up on the last activity to pause. This // is short because it directly impacts the responsiveness of starting the // next activity. private static final int PAUSE_TIMEOUT = 500; // Ticks during which we check progress while waiting for an app to launch. private static final int LAUNCH_TICK = 500; // How long we wait for the activity to tell us it has stopped before // giving up. This is a good amount of time because we really need this // from the application in order to get its saved state. Once the stop // is complete we may start destroying client resources triggering // crashes if the UI thread was hung. We put this timeout one second behind // the ANR timeout so these situations will generate ANR instead of // Surface lost or other errors. private static final int STOP_TIMEOUT = 11 * 1000; // How long we wait until giving up on an activity telling us it has // finished destroying itself. private static final int DESTROY_TIMEOUT = 10 * 1000; final ActivityTaskManagerService mAtmService; final ActivityInfo info; // activity info provided by developer in AndroidManifest // Non-null only for application tokens. Loading Loading @@ -681,6 +702,55 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A // Token for targeting this activity for assist purposes. final Binder assistToken = new Binder(); private final Runnable mPauseTimeoutRunnable = new Runnable() { @Override public void run() { // We don't at this point know if the activity is fullscreen, // so we need to be conservative and assume it isn't. Slog.w(TAG, "Activity pause timeout for " + ActivityRecord.this); synchronized (mAtmService.mGlobalLock) { if (hasProcess()) { mAtmService.logAppTooSlow(app, pauseTime, "pausing " + ActivityRecord.this); } activityPaused(true); } } }; private final Runnable mLaunchTickRunnable = new Runnable() { @Override public void run() { synchronized (mAtmService.mGlobalLock) { if (continueLaunchTicking()) { mAtmService.logAppTooSlow( app, launchTickTime, "launching " + ActivityRecord.this); } } } }; private final Runnable mDestroyTimeoutRunnable = new Runnable() { @Override public void run() { synchronized (mAtmService.mGlobalLock) { Slog.w(TAG, "Activity destroy timeout for " + ActivityRecord.this); destroyed("destroyTimeout"); } } }; private final Runnable mStopTimeoutRunnable = new Runnable() { @Override public void run() { synchronized (mAtmService.mGlobalLock) { Slog.w(TAG, "Activity stop timeout for " + ActivityRecord.this); if (isInHistory()) { activityStopped(null /*icicle*/, null /*persistentState*/, null /*description*/); } } } }; private static String startingWindowStateToString(int state) { switch (state) { case STARTING_WINDOW_NOT_SHOWN: Loading Loading @@ -2684,11 +2754,6 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A EventLogTags.writeWmDestroyActivity(mUserId, System.identityHashCode(this), task.mTaskId, shortComponentName, reason); final ActivityStack stack = getActivityStack(); if (hasProcess() && !stack.inLruList(this)) { Slog.w(TAG, "Activity " + this + " being finished, but not in LRU list"); } boolean removedFromHistory = false; cleanUp(false /* cleanServices */, false /* setState */); Loading Loading @@ -2735,7 +2800,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } setState(DESTROYING, "destroyActivityLocked. finishing and not skipping destroy"); stack.scheduleDestroyTimeoutForActivity(this); mAtmService.mH.postDelayed(mDestroyTimeoutRunnable, DESTROY_TIMEOUT); } else { if (DEBUG_STATES) { Slog.v(TAG_STATES, "Moving to DESTROYED: " + this + " (destroy skipped)"); Loading Loading @@ -2785,8 +2850,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } takeFromHistory(); final ActivityStack stack = getActivityStack(); stack.removeTimeoutsForActivity(this); removeTimeouts(); if (DEBUG_STATES) { Slog.v(TAG_STATES, "Moving to DESTROYED: " + this + " (removed from history)"); } Loading Loading @@ -2814,7 +2878,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A * AND finished. */ void destroyed(String reason) { getActivityStack().removeDestroyTimeoutForActivity(this); removeDestroyTimeout(); if (DEBUG_CONTAINERS) Slog.d(TAG_CONTAINERS, "activityDestroyedLocked: r=" + this); Loading Loading @@ -2872,7 +2936,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } // Get rid of any pending idle timeouts. stack.removeTimeoutsForActivity(this); removeTimeouts(); // Clean-up activities are no longer relaunching (e.g. app process died). Notify window // manager so it can update its bookkeeping. clearRelaunching(); Loading Loading @@ -4737,6 +4801,73 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } } void activityPaused(boolean timeout) { if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Activity paused: token=" + appToken + ", timeout=" + timeout); final ActivityStack stack = getStack(); if (stack != null) { removePauseTimeout(); if (stack.mPausingActivity == this) { if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to PAUSED: " + this + (timeout ? " (due to timeout)" : " (pause complete)")); mAtmService.deferWindowLayout(); try { stack.completePauseLocked(true /* resumeNext */, null /* resumingActivity */); } finally { mAtmService.continueWindowLayout(); } return; } else { EventLogTags.writeWmFailedToPause(mUserId, System.identityHashCode(this), shortComponentName, stack.mPausingActivity != null ? stack.mPausingActivity.shortComponentName : "(none)"); if (isState(PAUSING)) { setState(PAUSED, "activityPausedLocked"); if (finishing) { if (DEBUG_PAUSE) Slog.v(TAG, "Executing finish of failed to pause activity: " + this); completeFinishing("activityPausedLocked"); } } } } mRootActivityContainer.ensureActivitiesVisible(null, 0, !PRESERVE_WINDOWS); } /** * Schedule a pause timeout in case the app doesn't respond. We don't give it much time because * this directly impacts the responsiveness seen by the user. */ void schedulePauseTimeout() { pauseTime = SystemClock.uptimeMillis(); mAtmService.mH.postDelayed(mPauseTimeoutRunnable, PAUSE_TIMEOUT); if (DEBUG_PAUSE) Slog.v(TAG_PAUSE, "Waiting for pause to complete..."); } private void removePauseTimeout() { mAtmService.mH.removeCallbacks(mPauseTimeoutRunnable); } private void removeDestroyTimeout() { mAtmService.mH.removeCallbacks(mDestroyTimeoutRunnable); } private void removeStopTimeout() { mAtmService.mH.removeCallbacks(mStopTimeoutRunnable); } void removeTimeouts() { mStackSupervisor.removeIdleTimeoutForActivity(this); removePauseTimeout(); removeStopTimeout(); removeDestroyTimeout(); finishLaunchTickingLocked(); } void stopIfPossible() { if (DEBUG_SWITCH) Slog.d(TAG_SWITCH, "Stopping: " + this); final ActivityStack stack = getActivityStack(); Loading Loading @@ -4783,7 +4914,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A if (stack.shouldSleepOrShutDownActivities()) { setSleeping(true); } stack.scheduleStopTimeoutForActivity(this); mAtmService.mH.postDelayed(mStopTimeoutRunnable, STOP_TIMEOUT); } catch (Exception e) { // Maybe just ignore exceptions here... if the process has crashed, our death // notification will clean things up. Loading @@ -4798,13 +4929,13 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } } final void activityStoppedLocked(Bundle newIcicle, PersistableBundle newPersistentState, void activityStopped(Bundle newIcicle, PersistableBundle newPersistentState, CharSequence description) { final ActivityStack stack = getActivityStack(); final boolean isStopping = mState == STOPPING; if (!isStopping && mState != RESTARTING_PROCESS) { Slog.i(TAG, "Activity reported stop, but no longer stopping: " + this); stack.removeStopTimeoutForActivity(this); removeStopTimeout(); return; } if (newPersistentState != null) { Loading @@ -4822,7 +4953,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A if (DEBUG_SAVED_STATE) Slog.i(TAG_SAVED_STATE, "Saving icicle of " + this + ": " + mIcicle); if (!stopped) { if (DEBUG_STATES) Slog.v(TAG_STATES, "Moving to STOPPED: " + this + " (stop complete)"); stack.removeStopTimeoutForActivity(this); removeStopTimeout(); stopped = true; if (isStopping) { setState(STOPPED, "activityStoppedLocked"); Loading Loading @@ -4877,11 +5008,11 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } if (launchTickTime == 0) { launchTickTime = SystemClock.uptimeMillis(); continueLaunchTickingLocked(); continueLaunchTicking(); } } boolean continueLaunchTickingLocked() { private boolean continueLaunchTicking() { if (launchTickTime == 0) { return false; } Loading @@ -4892,10 +5023,14 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A } stack.removeLaunchTickMessages(); stack.scheduleLaunchTickForActivity(this); mAtmService.mH.postDelayed(mLaunchTickRunnable, LAUNCH_TICK); return true; } void removeLaunchTickRunnable() { mAtmService.mH.removeCallbacks(mLaunchTickRunnable); } void finishLaunchTickingLocked() { launchTickTime = 0; final ActivityStack stack = getActivityStack(); Loading Loading @@ -7017,10 +7152,7 @@ final class ActivityRecord extends WindowToken implements WindowManagerService.A newIntents = null; mAtmService.getAppWarningsLocked().onResumeActivity(this); } else { final ActivityStack stack = getActivityStack(); if (stack != null) { stack.removePauseTimeoutForActivity(this); } removePauseTimeout(); setState(PAUSED, "relaunchActivityLocked"); } Loading
services/core/java/com/android/server/wm/ActivityStack.java +61 −317 File changed.Preview size limit exceeded, changes collapsed. Show changes
services/core/java/com/android/server/wm/ActivityStackSupervisor.java +27 −5 Original line number Diff line number Diff line Loading @@ -52,7 +52,9 @@ import static android.view.WindowManager.TRANSIT_DOCK_TASK_FROM_RECENTS; import static com.android.server.wm.ActivityStack.ActivityState.PAUSED; import static com.android.server.wm.ActivityStack.ActivityState.PAUSING; import static com.android.server.wm.ActivityStack.TAG_CLEANUP; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_ALL; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_CLEANUP; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_IDLE; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_PAUSE; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_RECENTS; Loading Loading @@ -956,9 +958,6 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { } r.launchFailed = false; if (stack.updateLruList(r)) { Slog.w(TAG, "Activity " + r + " being launched, but already in LRU list"); } // TODO(lifecycler): Resume or pause requests are done as part of launch transaction, // so updating the state should be done accordingly. Loading Loading @@ -2162,7 +2161,7 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { if (!processPausingActivities && s.isState(PAUSING)) { // Defer processing pausing activities in this iteration and reschedule // a delayed idle to reprocess it again removeTimeoutsForActivityLocked(idleActivity); removeIdleTimeoutForActivity(idleActivity); scheduleIdleTimeoutLocked(idleActivity); continue; } Loading @@ -2181,6 +2180,29 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { return stops; } void removeHistoryRecords(WindowProcessController app) { removeHistoryRecords(mStoppingActivities, app, "mStoppingActivities"); removeHistoryRecords(mGoingToSleepActivities, app, "mGoingToSleepActivities"); removeHistoryRecords(mFinishingActivities, app, "mFinishingActivities"); } private void removeHistoryRecords(ArrayList<ActivityRecord> list, WindowProcessController app, String listName) { int i = list.size(); if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, "Removing app " + this + " from list " + listName + " with " + i + " entries"); while (i > 0) { i--; ActivityRecord r = list.get(i); if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, "Record #" + i + " " + r); if (r.app == app) { if (DEBUG_CLEANUP) Slog.v(TAG_CLEANUP, "---> REMOVING this entry!"); list.remove(i); r.removeTimeouts(); } } } public void dump(PrintWriter pw, String prefix) { pw.println(); pw.println("ActivityStackSupervisor state:"); Loading Loading @@ -2371,7 +2393,7 @@ public class ActivityStackSupervisor implements RecentTasks.Callbacks { scheduleTopResumedActivityStateIfNeeded(); } void removeTimeoutsForActivityLocked(ActivityRecord r) { void removeIdleTimeoutForActivity(ActivityRecord r) { if (DEBUG_IDLE) Slog.d(TAG_IDLE, "removeTimeoutsForActivity: Callers=" + Debug.getCallers(4)); mHandler.removeMessages(IDLE_TIMEOUT_MSG, r); Loading
services/core/java/com/android/server/wm/ActivityTaskManagerService.java +6 −6 Original line number Diff line number Diff line Loading @@ -306,7 +306,7 @@ import java.util.Set; public class ActivityTaskManagerService extends IActivityTaskManager.Stub { private static final String TAG = TAG_WITH_CLASS_NAME ? "ActivityTaskManagerService" : TAG_ATM; private static final String TAG_STACK = TAG + POSTFIX_STACK; private static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; static final String TAG_SWITCH = TAG + POSTFIX_SWITCH; private static final String TAG_IMMERSIVE = TAG + POSTFIX_IMMERSIVE; private static final String TAG_FOCUS = TAG + POSTFIX_FOCUS; private static final String TAG_VISIBILITY = TAG + POSTFIX_VISIBILITY; Loading Loading @@ -1730,9 +1730,9 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub { final long origId = Binder.clearCallingIdentity(); synchronized (mGlobalLock) { Trace.traceBegin(TRACE_TAG_WINDOW_MANAGER, "activityPaused"); ActivityStack stack = ActivityRecord.getStackLocked(token); if (stack != null) { stack.activityPausedLocked(token, false); final ActivityRecord r = ActivityRecord.forTokenLocked(token); if (r != null) { r.activityPaused(false); } Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER); } Loading Loading @@ -1765,7 +1765,7 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub { restartingName = r.app.mName; restartingUid = r.app.mUid; } r.activityStoppedLocked(icicle, persistentState, description); r.activityStopped(icicle, persistentState, description); } Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER); } Loading Loading @@ -7304,7 +7304,7 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub { @Override public void scheduleDestroyAllActivities(String reason) { synchronized (mGlobalLock) { mRootActivityContainer.scheduleDestroyAllActivities(null, reason); mRootActivityContainer.scheduleDestroyAllActivities(reason); } } Loading
services/core/java/com/android/server/wm/RootActivityContainer.java +38 −9 Original line number Diff line number Diff line Loading @@ -54,6 +54,7 @@ import static com.android.server.wm.ActivityStackSupervisor.printThisActivity; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_RECENTS; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_STACK; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_STATES; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_SWITCH; import static com.android.server.wm.ActivityTaskManagerDebugConfig.DEBUG_TASKS; import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_RECENTS; import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_RELEASE; Loading @@ -62,6 +63,7 @@ import static com.android.server.wm.ActivityTaskManagerDebugConfig.POSTFIX_TASKS import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_ATM; import static com.android.server.wm.ActivityTaskManagerDebugConfig.TAG_WITH_CLASS_NAME; import static com.android.server.wm.ActivityTaskManagerService.ANIMATE; import static com.android.server.wm.ActivityTaskManagerService.TAG_SWITCH; import static com.android.server.wm.Task.REPARENT_LEAVE_STACK_IN_PLACE; import static com.android.server.wm.Task.REPARENT_MOVE_STACK_TO_FRONT; Loading Loading @@ -205,6 +207,28 @@ class RootActivityContainer extends RootWindowContainer private boolean mTmpBoolean; private RemoteException mTmpRemoteException; private String mDestroyAllActivitiesReason; private final Runnable mDestroyAllActivitiesRunnable = new Runnable() { @Override public void run() { synchronized (mService.mGlobalLock) { try { mStackSupervisor.beginDeferResume(); final PooledConsumer c = PooledLambda.obtainConsumer( RootActivityContainer::destroyActivity, RootActivityContainer.this, PooledLambda.__(ActivityRecord.class)); forAllActivities(c); c.recycle(); } finally { mStackSupervisor.endDeferResume(); resumeFocusedStacksTopActivities(); } } } }; private final FindTaskResult mTmpFindTaskResult = new FindTaskResult(); static class FindTaskResult implements Function<Task, Boolean> { ActivityRecord mRecord; Loading Loading @@ -1653,14 +1677,19 @@ class RootActivityContainer extends RootWindowContainer } } void scheduleDestroyAllActivities(WindowProcessController app, String reason) { for (int displayNdx = getChildCount() - 1; displayNdx >= 0; --displayNdx) { final DisplayContent display = getChildAt(displayNdx); for (int stackNdx = display.getStackCount() - 1; stackNdx >= 0; --stackNdx) { final ActivityStack stack = display.getStackAt(stackNdx); stack.scheduleDestroyActivities(app, reason); } void scheduleDestroyAllActivities(String reason) { mDestroyAllActivitiesReason = reason; mService.mH.post(mDestroyAllActivitiesRunnable); } private void destroyActivity(ActivityRecord r) { if (r.finishing || !r.isDestroyable()) return; if (DEBUG_SWITCH) Slog.v(TAG_SWITCH, "Destroying " + r + " in state " + r.getState() + " resumed=" + r.getStack().mResumedActivity + " pausing=" + r.getStack().mPausingActivity + " for reason " + mDestroyAllActivitiesReason); r.destroyImmediately(true /* removeFromTask */, mDestroyAllActivitiesReason); } // Tries to put all activity stacks to sleep. Returns true if all stacks were Loading Loading @@ -2059,7 +2088,7 @@ class RootActivityContainer extends RootWindowContainer final DisplayContent display = getChildAt(displayNdx); for (int stackNdx = display.getStackCount() - 1; stackNdx >= 0; --stackNdx) { final ActivityStack stack = display.getStackAt(stackNdx); hasVisibleActivities |= stack.handleAppDiedLocked(app); hasVisibleActivities |= stack.handleAppDied(app); } } return hasVisibleActivities; Loading