Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 21d46e38 authored by Vishnu Nair's avatar Vishnu Nair
Browse files

WMS AnrController: Don't hold WMS lock when calling into AMS

Change-Id: I20e543b0c89809cf16566744b1ad5ce83d0f2a2c
Test: atest AnrTests
Bug: 239907039
parent 14e28a7e
Loading
Loading
Loading
Loading
+21 −17
Original line number Diff line number Diff line
@@ -70,6 +70,9 @@ class AnrController {
            preDumpIfLockTooSlow();
            final ActivityRecord activity;
            timeoutRecord.mLatencyTracker.waitingOnGlobalLockStarted();
            boolean blamePendingFocusRequest = false;
            IBinder focusToken = null;
            WindowState targetWindowState = null;
            synchronized (mService.mGlobalLock) {
                timeoutRecord.mLatencyTracker.waitingOnGlobalLockEnded();
                activity = ActivityRecord.forTokenLocked(applicationHandle.token);
@@ -82,35 +85,36 @@ class AnrController {
                // App is unresponsive, but we are actively trying to give focus to a window.
                // Blame the window if possible since the window may not belong to the app.
                DisplayContent display = mService.mRoot.getDisplayContent(activity.getDisplayId());
                IBinder focusToken =
                        display == null ? null : display.getInputMonitor().mInputFocus;
                if (display != null) {
                    focusToken = display.getInputMonitor().mInputFocus;
                }
                InputTarget focusTarget = mService.getInputTargetFromToken(focusToken);

                if (focusTarget != null) {
                    // Check if we have a recent focus request, newer than the dispatch timeout,
                    // then ignore the focus request.
                    WindowState targetWindowState = focusTarget.getWindowState();
                    boolean requestIsValid = SystemClock.uptimeMillis()
                    targetWindowState = focusTarget.getWindowState();
                    blamePendingFocusRequest = SystemClock.uptimeMillis()
                            - display.getInputMonitor().mInputFocusRequestTimeMillis
                            >= getInputDispatchingTimeoutMillisLocked(
                                    targetWindowState.getActivityRecord());

                    if (requestIsValid) {
                        if (notifyWindowUnresponsive(focusToken, timeoutRecord)) {
                            Slog.i(TAG_WM, "Blamed " + focusTarget.getWindowState().getName()
                                    + " using pending focus request. Focused activity: "
                                    + activity.getName());
                            return;
                        }
                    }
                }

                if (!blamePendingFocusRequest) {
                    Slog.i(TAG_WM, "ANR in " + activity.getName() + ".  Reason: "
                            + timeoutRecord.mReason);
                    dumpAnrStateLocked(activity, null /* windowState */, timeoutRecord.mReason);
                    mUnresponsiveAppByDisplay.put(activity.getDisplayId(), activity);
                }
            }

            if (blamePendingFocusRequest && notifyWindowUnresponsive(focusToken, timeoutRecord)) {
                Slog.i(TAG_WM, "Blamed " + targetWindowState.getName()
                        + " using pending focus request. Focused activity: "
                        + activity.getName());
            } else {
                activity.inputDispatchingTimedOut(timeoutRecord, INVALID_PID);
            }
        } finally {
            Trace.traceEnd(Trace.TRACE_TAG_ACTIVITY_MANAGER);
        }