Loading services/core/java/com/android/server/am/ActivityManagerService.java +7 −2 Original line number Diff line number Diff line Loading @@ -6694,6 +6694,10 @@ public class ActivityManagerService extends IActivityManager.Stub @Override public void appNotResponding(final String reason) { appNotResponding(reason, /*isContinuousAnr*/ false); } public void appNotResponding(final String reason, boolean isContinuousAnr) { TimeoutRecord timeoutRecord = TimeoutRecord.forApp("App requested: " + reason); final int callingPid = Binder.getCallingPid(); Loading @@ -6706,7 +6710,7 @@ public class ActivityManagerService extends IActivityManager.Stub } mAnrHelper.appNotResponding(app, null, app.info, null, null, false, timeoutRecord); timeoutRecord, isContinuousAnr); } } Loading Loading @@ -18401,7 +18405,8 @@ public class ActivityManagerService extends IActivityManager.Stub } } mAnrHelper.appNotResponding(proc, activityShortComponentName, aInfo, parentShortComponentName, parentProcess, aboveSystem, timeoutRecord); parentShortComponentName, parentProcess, aboveSystem, timeoutRecord, /*isContinuousAnr*/ true); } return true; services/core/java/com/android/server/am/AnrHelper.java +9 −5 Original line number Diff line number Diff line Loading @@ -96,13 +96,13 @@ class AnrHelper { void appNotResponding(ProcessRecord anrProcess, TimeoutRecord timeoutRecord) { appNotResponding(anrProcess, null /* activityShortComponentName */, null /* aInfo */, null /* parentShortComponentName */, null /* parentProcess */, false /* aboveSystem */, timeoutRecord); false /* aboveSystem */, timeoutRecord, /*isContinuousAnr*/ false); } void appNotResponding(ProcessRecord anrProcess, String activityShortComponentName, ApplicationInfo aInfo, String parentShortComponentName, WindowProcessController parentProcess, boolean aboveSystem, TimeoutRecord timeoutRecord) { TimeoutRecord timeoutRecord, boolean isContinuousAnr) { try { timeoutRecord.mLatencyTracker.appNotRespondingStarted(); final int incomingPid = anrProcess.mPid; Loading Loading @@ -132,7 +132,7 @@ class AnrHelper { timeoutRecord.mLatencyTracker.anrRecordPlacingOnQueueWithSize(mAnrRecords.size()); mAnrRecords.add(new AnrRecord(anrProcess, activityShortComponentName, aInfo, parentShortComponentName, parentProcess, aboveSystem, mAuxiliaryTaskExecutor, timeoutRecord)); mAuxiliaryTaskExecutor, timeoutRecord, isContinuousAnr)); } startAnrConsumerIfNeeded(); } finally { Loading Loading @@ -230,10 +230,12 @@ class AnrHelper { final boolean mAboveSystem; final ExecutorService mAuxiliaryTaskExecutor; final long mTimestamp = SystemClock.uptimeMillis(); final boolean mIsContinuousAnr; AnrRecord(ProcessRecord anrProcess, String activityShortComponentName, ApplicationInfo aInfo, String parentShortComponentName, WindowProcessController parentProcess, boolean aboveSystem, ExecutorService auxiliaryTaskExecutor, TimeoutRecord timeoutRecord) { ExecutorService auxiliaryTaskExecutor, TimeoutRecord timeoutRecord, boolean isContinuousAnr) { mApp = anrProcess; mPid = anrProcess.mPid; mActivityShortComponentName = activityShortComponentName; Loading @@ -243,6 +245,7 @@ class AnrHelper { mParentProcess = parentProcess; mAboveSystem = aboveSystem; mAuxiliaryTaskExecutor = auxiliaryTaskExecutor; mIsContinuousAnr = isContinuousAnr; } void appNotResponding(boolean onlyDumpSelf) { Loading @@ -250,7 +253,8 @@ class AnrHelper { mTimeoutRecord.mLatencyTracker.anrProcessingStarted(); mApp.mErrorState.appNotResponding(mActivityShortComponentName, mAppInfo, mParentShortComponentName, mParentProcess, mAboveSystem, mTimeoutRecord, mAuxiliaryTaskExecutor, onlyDumpSelf); mTimeoutRecord, mAuxiliaryTaskExecutor, onlyDumpSelf, mIsContinuousAnr); } finally { mTimeoutRecord.mLatencyTracker.anrProcessingEnded(); } Loading services/core/java/com/android/server/am/AppNotRespondingDialog.java +12 −3 Original line number Diff line number Diff line Loading @@ -169,9 +169,11 @@ final class AppNotRespondingDialog extends BaseErrorDialog implements View.OnCli errState.getDialogController().clearAnrDialogs(); } mService.mServices.scheduleServiceTimeoutLocked(app); if (mData.isContinuousAnr) { // If the app remains unresponsive, show the dialog again after a delay. mService.mInternal.rescheduleAnrDialog(mData); } } break; } Loading @@ -197,10 +199,17 @@ final class AppNotRespondingDialog extends BaseErrorDialog implements View.OnCli final ApplicationInfo aInfo; final boolean aboveSystem; Data(ProcessRecord proc, ApplicationInfo aInfo, boolean aboveSystem) { // If true, then even if the user presses "WAIT" on the ANR dialog, // we'll show it again until the app start responding again. // (we only use it for input dispatch ANRs) final boolean isContinuousAnr; Data(ProcessRecord proc, ApplicationInfo aInfo, boolean aboveSystem, boolean isContinuousAnr) { this.proc = proc; this.aInfo = aInfo; this.aboveSystem = aboveSystem; this.isContinuousAnr = isContinuousAnr; } } } services/core/java/com/android/server/am/ProcessErrorStateRecord.java +4 −2 Original line number Diff line number Diff line Loading @@ -263,7 +263,8 @@ class ProcessErrorStateRecord { void appNotResponding(String activityShortComponentName, ApplicationInfo aInfo, String parentShortComponentName, WindowProcessController parentProcess, boolean aboveSystem, TimeoutRecord timeoutRecord, ExecutorService auxiliaryTaskExecutor, boolean onlyDumpSelf) { ExecutorService auxiliaryTaskExecutor, boolean onlyDumpSelf, boolean isContinuousAnr) { String annotation = timeoutRecord.mReason; AnrLatencyTracker latencyTracker = timeoutRecord.mLatencyTracker; Future<?> updateCpuStatsNowFirstCall = null; Loading Loading @@ -630,7 +631,8 @@ class ProcessErrorStateRecord { // Bring up the infamous App Not Responding dialog Message msg = Message.obtain(); msg.what = ActivityManagerService.SHOW_NOT_RESPONDING_UI_MSG; msg.obj = new AppNotRespondingDialog.Data(mApp, aInfo, aboveSystem); msg.obj = new AppNotRespondingDialog.Data(mApp, aInfo, aboveSystem, isContinuousAnr); mService.mUiHandler.sendMessageDelayed(msg, anrDialogDelayMs); } Loading services/tests/servicestests/src/com/android/server/am/AnrHelperTest.java +7 −5 Original line number Diff line number Diff line Loading @@ -119,12 +119,13 @@ public class AnrHelperTest { final TimeoutRecord timeoutRecord = TimeoutRecord.forInputDispatchWindowUnresponsive( annotation); mAnrHelper.appNotResponding(mAnrApp, activityShortComponentName, appInfo, parentShortComponentName, parentProcess, aboveSystem, timeoutRecord); parentShortComponentName, parentProcess, aboveSystem, timeoutRecord, /*isContinuousAnr*/ false); verify(mAnrApp.mErrorState, timeout(TIMEOUT_MS)).appNotResponding( eq(activityShortComponentName), eq(appInfo), eq(parentShortComponentName), eq(parentProcess), eq(aboveSystem), eq(timeoutRecord), eq(mExecutorService), eq(false) /* onlyDumpSelf */); eq(false) /* onlyDumpSelf */, eq(false) /*isContinuousAnr*/); } @Test Loading @@ -137,13 +138,14 @@ public class AnrHelperTest { processingLatch.await(); return null; }).when(mAnrApp.mErrorState).appNotResponding(anyString(), any(), any(), any(), anyBoolean(), any(), any(), anyBoolean()); anyBoolean(), any(), any(), anyBoolean(), anyBoolean()); final ApplicationInfo appInfo = new ApplicationInfo(); final TimeoutRecord timeoutRecord = TimeoutRecord.forInputDispatchWindowUnresponsive( "annotation"); final Runnable reportAnr = () -> mAnrHelper.appNotResponding(mAnrApp, "activityShortComponentName", appInfo, "parentShortComponentName", null /* parentProcess */, false /* aboveSystem */, timeoutRecord); null /* parentProcess */, false /* aboveSystem */, timeoutRecord, false /*isContinuousAnr*/); reportAnr.run(); // This should be skipped because the pid is pending in queue. reportAnr.run(); Loading @@ -160,6 +162,6 @@ public class AnrHelperTest { // There is only one ANR reported. verify(mAnrApp.mErrorState, timeout(TIMEOUT_MS).only()).appNotResponding( anyString(), any(), any(), any(), anyBoolean(), any(), eq(mExecutorService), anyBoolean()); anyBoolean(), anyBoolean()); } } Loading
services/core/java/com/android/server/am/ActivityManagerService.java +7 −2 Original line number Diff line number Diff line Loading @@ -6694,6 +6694,10 @@ public class ActivityManagerService extends IActivityManager.Stub @Override public void appNotResponding(final String reason) { appNotResponding(reason, /*isContinuousAnr*/ false); } public void appNotResponding(final String reason, boolean isContinuousAnr) { TimeoutRecord timeoutRecord = TimeoutRecord.forApp("App requested: " + reason); final int callingPid = Binder.getCallingPid(); Loading @@ -6706,7 +6710,7 @@ public class ActivityManagerService extends IActivityManager.Stub } mAnrHelper.appNotResponding(app, null, app.info, null, null, false, timeoutRecord); timeoutRecord, isContinuousAnr); } } Loading Loading @@ -18401,7 +18405,8 @@ public class ActivityManagerService extends IActivityManager.Stub } } mAnrHelper.appNotResponding(proc, activityShortComponentName, aInfo, parentShortComponentName, parentProcess, aboveSystem, timeoutRecord); parentShortComponentName, parentProcess, aboveSystem, timeoutRecord, /*isContinuousAnr*/ true); } return true;
services/core/java/com/android/server/am/AnrHelper.java +9 −5 Original line number Diff line number Diff line Loading @@ -96,13 +96,13 @@ class AnrHelper { void appNotResponding(ProcessRecord anrProcess, TimeoutRecord timeoutRecord) { appNotResponding(anrProcess, null /* activityShortComponentName */, null /* aInfo */, null /* parentShortComponentName */, null /* parentProcess */, false /* aboveSystem */, timeoutRecord); false /* aboveSystem */, timeoutRecord, /*isContinuousAnr*/ false); } void appNotResponding(ProcessRecord anrProcess, String activityShortComponentName, ApplicationInfo aInfo, String parentShortComponentName, WindowProcessController parentProcess, boolean aboveSystem, TimeoutRecord timeoutRecord) { TimeoutRecord timeoutRecord, boolean isContinuousAnr) { try { timeoutRecord.mLatencyTracker.appNotRespondingStarted(); final int incomingPid = anrProcess.mPid; Loading Loading @@ -132,7 +132,7 @@ class AnrHelper { timeoutRecord.mLatencyTracker.anrRecordPlacingOnQueueWithSize(mAnrRecords.size()); mAnrRecords.add(new AnrRecord(anrProcess, activityShortComponentName, aInfo, parentShortComponentName, parentProcess, aboveSystem, mAuxiliaryTaskExecutor, timeoutRecord)); mAuxiliaryTaskExecutor, timeoutRecord, isContinuousAnr)); } startAnrConsumerIfNeeded(); } finally { Loading Loading @@ -230,10 +230,12 @@ class AnrHelper { final boolean mAboveSystem; final ExecutorService mAuxiliaryTaskExecutor; final long mTimestamp = SystemClock.uptimeMillis(); final boolean mIsContinuousAnr; AnrRecord(ProcessRecord anrProcess, String activityShortComponentName, ApplicationInfo aInfo, String parentShortComponentName, WindowProcessController parentProcess, boolean aboveSystem, ExecutorService auxiliaryTaskExecutor, TimeoutRecord timeoutRecord) { ExecutorService auxiliaryTaskExecutor, TimeoutRecord timeoutRecord, boolean isContinuousAnr) { mApp = anrProcess; mPid = anrProcess.mPid; mActivityShortComponentName = activityShortComponentName; Loading @@ -243,6 +245,7 @@ class AnrHelper { mParentProcess = parentProcess; mAboveSystem = aboveSystem; mAuxiliaryTaskExecutor = auxiliaryTaskExecutor; mIsContinuousAnr = isContinuousAnr; } void appNotResponding(boolean onlyDumpSelf) { Loading @@ -250,7 +253,8 @@ class AnrHelper { mTimeoutRecord.mLatencyTracker.anrProcessingStarted(); mApp.mErrorState.appNotResponding(mActivityShortComponentName, mAppInfo, mParentShortComponentName, mParentProcess, mAboveSystem, mTimeoutRecord, mAuxiliaryTaskExecutor, onlyDumpSelf); mTimeoutRecord, mAuxiliaryTaskExecutor, onlyDumpSelf, mIsContinuousAnr); } finally { mTimeoutRecord.mLatencyTracker.anrProcessingEnded(); } Loading
services/core/java/com/android/server/am/AppNotRespondingDialog.java +12 −3 Original line number Diff line number Diff line Loading @@ -169,9 +169,11 @@ final class AppNotRespondingDialog extends BaseErrorDialog implements View.OnCli errState.getDialogController().clearAnrDialogs(); } mService.mServices.scheduleServiceTimeoutLocked(app); if (mData.isContinuousAnr) { // If the app remains unresponsive, show the dialog again after a delay. mService.mInternal.rescheduleAnrDialog(mData); } } break; } Loading @@ -197,10 +199,17 @@ final class AppNotRespondingDialog extends BaseErrorDialog implements View.OnCli final ApplicationInfo aInfo; final boolean aboveSystem; Data(ProcessRecord proc, ApplicationInfo aInfo, boolean aboveSystem) { // If true, then even if the user presses "WAIT" on the ANR dialog, // we'll show it again until the app start responding again. // (we only use it for input dispatch ANRs) final boolean isContinuousAnr; Data(ProcessRecord proc, ApplicationInfo aInfo, boolean aboveSystem, boolean isContinuousAnr) { this.proc = proc; this.aInfo = aInfo; this.aboveSystem = aboveSystem; this.isContinuousAnr = isContinuousAnr; } } }
services/core/java/com/android/server/am/ProcessErrorStateRecord.java +4 −2 Original line number Diff line number Diff line Loading @@ -263,7 +263,8 @@ class ProcessErrorStateRecord { void appNotResponding(String activityShortComponentName, ApplicationInfo aInfo, String parentShortComponentName, WindowProcessController parentProcess, boolean aboveSystem, TimeoutRecord timeoutRecord, ExecutorService auxiliaryTaskExecutor, boolean onlyDumpSelf) { ExecutorService auxiliaryTaskExecutor, boolean onlyDumpSelf, boolean isContinuousAnr) { String annotation = timeoutRecord.mReason; AnrLatencyTracker latencyTracker = timeoutRecord.mLatencyTracker; Future<?> updateCpuStatsNowFirstCall = null; Loading Loading @@ -630,7 +631,8 @@ class ProcessErrorStateRecord { // Bring up the infamous App Not Responding dialog Message msg = Message.obtain(); msg.what = ActivityManagerService.SHOW_NOT_RESPONDING_UI_MSG; msg.obj = new AppNotRespondingDialog.Data(mApp, aInfo, aboveSystem); msg.obj = new AppNotRespondingDialog.Data(mApp, aInfo, aboveSystem, isContinuousAnr); mService.mUiHandler.sendMessageDelayed(msg, anrDialogDelayMs); } Loading
services/tests/servicestests/src/com/android/server/am/AnrHelperTest.java +7 −5 Original line number Diff line number Diff line Loading @@ -119,12 +119,13 @@ public class AnrHelperTest { final TimeoutRecord timeoutRecord = TimeoutRecord.forInputDispatchWindowUnresponsive( annotation); mAnrHelper.appNotResponding(mAnrApp, activityShortComponentName, appInfo, parentShortComponentName, parentProcess, aboveSystem, timeoutRecord); parentShortComponentName, parentProcess, aboveSystem, timeoutRecord, /*isContinuousAnr*/ false); verify(mAnrApp.mErrorState, timeout(TIMEOUT_MS)).appNotResponding( eq(activityShortComponentName), eq(appInfo), eq(parentShortComponentName), eq(parentProcess), eq(aboveSystem), eq(timeoutRecord), eq(mExecutorService), eq(false) /* onlyDumpSelf */); eq(false) /* onlyDumpSelf */, eq(false) /*isContinuousAnr*/); } @Test Loading @@ -137,13 +138,14 @@ public class AnrHelperTest { processingLatch.await(); return null; }).when(mAnrApp.mErrorState).appNotResponding(anyString(), any(), any(), any(), anyBoolean(), any(), any(), anyBoolean()); anyBoolean(), any(), any(), anyBoolean(), anyBoolean()); final ApplicationInfo appInfo = new ApplicationInfo(); final TimeoutRecord timeoutRecord = TimeoutRecord.forInputDispatchWindowUnresponsive( "annotation"); final Runnable reportAnr = () -> mAnrHelper.appNotResponding(mAnrApp, "activityShortComponentName", appInfo, "parentShortComponentName", null /* parentProcess */, false /* aboveSystem */, timeoutRecord); null /* parentProcess */, false /* aboveSystem */, timeoutRecord, false /*isContinuousAnr*/); reportAnr.run(); // This should be skipped because the pid is pending in queue. reportAnr.run(); Loading @@ -160,6 +162,6 @@ public class AnrHelperTest { // There is only one ANR reported. verify(mAnrApp.mErrorState, timeout(TIMEOUT_MS).only()).appNotResponding( anyString(), any(), any(), any(), anyBoolean(), any(), eq(mExecutorService), anyBoolean()); anyBoolean(), anyBoolean()); } }