diff options
author | Bryce Lee <brycelee@google.com> | 2023-07-27 17:32:51 -0700 |
---|---|---|
committer | Android Build Coastguard Worker <android-build-coastguard-worker@google.com> | 2023-08-11 06:46:13 +0000 |
commit | 01b1b256babba19a4e9050287b9af246393ef364 (patch) | |
tree | dbdc470b26c48695d20b62d49914164937099e15 | |
parent | e7e2a56ab04a3ced9cd818a9f7a529124c655962 (diff) | |
download | base-01b1b256babba19a4e9050287b9af246393ef364.tar.gz |
Check for non-interactive dreams when wake and unlocking.
BiometricUnlockController coordinates with KeyguardViewMediator for
ordering the wake and unlock actions, necessary for non-doze/aod dreams.
Currently, the StatusBarStateController is consulted for the doze state.
However, this value can be out of sync with the current state. This
change instead checks the dream interactivity through PowerManager,
which provides a consistent signal for this state. This change also
ensures BiometricUnlockController and KeyguardViewMediator are in sync
on this state with biometricUnlockController informing
KeyguardViewMediator of the dream state in onWakingAndUnlocking, rather
than KeyguardViewMediator calculating this later in handleHide(). This
prevents inconsistencies from state changes between these two method
invocations.
This changelist also improves the logging around wake and unlock in
KeyguardViewMediator.
Test: atest KeyguardViewMediatorTest#testWakeAndUnlockingOverNonInteractiveDream_noWakeByKeyguardViewMediator
Fixes: 293159518
Fixes: 293464892
(cherry picked from https://googleplex-android-review.googlesource.com/q/commit:51de9458ec0fab7dc8947fdf50a6b0a30a927a39)
Merged-In: Iaffbb53b29578c0575a7737c8aacdc8ca547b426
Change-Id: Iaffbb53b29578c0575a7737c8aacdc8ca547b426
4 files changed, 116 insertions, 14 deletions
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java index 505be0867fe4..1a06b0184bc5 100644 --- a/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java +++ b/packages/SystemUI/src/com/android/systemui/keyguard/KeyguardViewMediator.java @@ -99,6 +99,7 @@ import android.view.WindowManagerPolicyConstants; import android.view.animation.Animation; import android.view.animation.AnimationUtils; +import androidx.annotation.IntDef; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.annotation.VisibleForTesting; @@ -167,6 +168,8 @@ import com.android.wm.shell.keyguard.KeyguardTransitions; import dagger.Lazy; import java.io.PrintWriter; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; import java.util.ArrayList; import java.util.Arrays; import java.util.Objects; @@ -251,6 +254,22 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, private static final int SYSTEM_READY = 18; private static final int CANCEL_KEYGUARD_EXIT_ANIM = 19; + /** Enum for reasons behind updating wakeAndUnlock state. */ + @Retention(RetentionPolicy.SOURCE) + @IntDef( + value = { + WakeAndUnlockUpdateReason.HIDE, + WakeAndUnlockUpdateReason.SHOW, + WakeAndUnlockUpdateReason.FULFILL, + WakeAndUnlockUpdateReason.WAKE_AND_UNLOCK, + }) + @interface WakeAndUnlockUpdateReason { + int HIDE = 0; + int SHOW = 1; + int FULFILL = 2; + int WAKE_AND_UNLOCK = 3; + } + /** * The default amount of time we stay awake (used for all key input) */ @@ -812,7 +831,7 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, // dreaming. It's time to wake up. if (mUnlockingAndWakingFromDream) { Log.d(TAG, "waking from dream after unlock"); - mUnlockingAndWakingFromDream = false; + setUnlockAndWakeFromDream(false, WakeAndUnlockUpdateReason.FULFILL); if (mKeyguardStateController.isShowing()) { Log.d(TAG, "keyguard showing after keyguardGone, dismiss"); @@ -2654,7 +2673,7 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, mKeyguardExitAnimationRunner = null; mWakeAndUnlocking = false; - mUnlockingAndWakingFromDream = false; + setUnlockAndWakeFromDream(false, WakeAndUnlockUpdateReason.SHOW); setPendingLock(false); // Force if we we're showing in the middle of hiding, to ensure we end up in the correct @@ -2760,6 +2779,51 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, tryKeyguardDone(); }; + private void setUnlockAndWakeFromDream(boolean updatedValue, + @WakeAndUnlockUpdateReason int reason) { + if (updatedValue == mUnlockingAndWakingFromDream) { + return; + } + + final String reasonDescription; + + switch(reason) { + case WakeAndUnlockUpdateReason.FULFILL: + reasonDescription = "fulfilling existing request"; + break; + case WakeAndUnlockUpdateReason.HIDE: + reasonDescription = "hiding keyguard"; + break; + case WakeAndUnlockUpdateReason.SHOW: + reasonDescription = "showing keyguard"; + break; + case WakeAndUnlockUpdateReason.WAKE_AND_UNLOCK: + reasonDescription = "waking to unlock"; + break; + default: + throw new IllegalStateException("Unexpected value: " + reason); + } + + final boolean unsetUnfulfilled = !updatedValue + && reason != WakeAndUnlockUpdateReason.FULFILL; + + mUnlockingAndWakingFromDream = updatedValue; + + final String description; + + if (unsetUnfulfilled) { + description = "Interrupting request to wake and unlock"; + } else if (mUnlockingAndWakingFromDream) { + description = "Initiating request to wake and unlock"; + } else { + description = "Fulfilling request to wake and unlock"; + } + + Log.d(TAG, String.format( + "Updating waking and unlocking request to %b. description:[%s]. reason:[%s]", + mUnlockingAndWakingFromDream, description, reasonDescription)); + } + /** * Handle message sent by {@link #hideLocked()} * @see #HIDE @@ -2779,8 +2843,11 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, mHiding = true; - mUnlockingAndWakingFromDream = mStatusBarStateController.isDreaming() - && !mStatusBarStateController.isDozing(); + // If waking and unlocking, waking from dream has been set properly. + if (!mWakeAndUnlocking) { + setUnlockAndWakeFromDream(mStatusBarStateController.isDreaming() + && mPM.isInteractive(), WakeAndUnlockUpdateReason.HIDE); + } if ((mShowing && !mOccluded) || mUnlockingAndWakingFromDream) { if (mUnlockingAndWakingFromDream) { @@ -3282,9 +3349,14 @@ public class KeyguardViewMediator implements CoreStartable, Dumpable, } } - public void onWakeAndUnlocking() { + /** + * Informs the keyguard view mediator that the device is waking and unlocking. + * @param fromDream Whether waking and unlocking is happening over an interactive dream. + */ + public void onWakeAndUnlocking(boolean fromDream) { Trace.beginSection("KeyguardViewMediator#onWakeAndUnlocking"); mWakeAndUnlocking = true; + setUnlockAndWakeFromDream(fromDream, WakeAndUnlockUpdateReason.WAKE_AND_UNLOCK); mKeyguardViewControllerLazy.get().notifyKeyguardAuthenticated(/* primaryAuth */ false); userActivity(); diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java index ccb51898a333..ed11711f66c6 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/BiometricUnlockController.java @@ -463,7 +463,7 @@ public class BiometricUnlockController extends KeyguardUpdateMonitorCallback imp }; final boolean wakingFromDream = mMode == MODE_WAKE_AND_UNLOCK_FROM_DREAM - && !mStatusBarStateController.isDozing(); + && mPowerManager.isInteractive(); if (mMode != MODE_NONE && !wakingFromDream) { wakeUp.run(); @@ -501,7 +501,7 @@ public class BiometricUnlockController extends KeyguardUpdateMonitorCallback imp // later to awaken. } mNotificationShadeWindowController.setNotificationShadeFocusable(false); - mKeyguardViewMediator.onWakeAndUnlocking(); + mKeyguardViewMediator.onWakeAndUnlocking(wakingFromDream); Trace.endSection(); break; case MODE_ONLY_WAKE: diff --git a/packages/SystemUI/tests/src/com/android/systemui/keyguard/KeyguardViewMediatorTest.java b/packages/SystemUI/tests/src/com/android/systemui/keyguard/KeyguardViewMediatorTest.java index 2fc3cf6af6b1..34ea91b94414 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/keyguard/KeyguardViewMediatorTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/keyguard/KeyguardViewMediatorTest.java @@ -243,7 +243,7 @@ public class KeyguardViewMediatorTest extends SysuiTestCase { TestableLooper.get(this).processAllMessages(); mViewMediator.onStartedGoingToSleep(OFF_BECAUSE_OF_USER); - mViewMediator.onWakeAndUnlocking(); + mViewMediator.onWakeAndUnlocking(false); mViewMediator.onStartedWakingUp(OFF_BECAUSE_OF_USER, false); TestableLooper.get(this).processAllMessages(); @@ -596,14 +596,14 @@ public class KeyguardViewMediatorTest extends SysuiTestCase { @Test public void testWakeAndUnlocking() { - mViewMediator.onWakeAndUnlocking(); + mViewMediator.onWakeAndUnlocking(false); verify(mStatusBarKeyguardViewManager).notifyKeyguardAuthenticated(anyBoolean()); } @Test public void testWakeAndUnlockingOverDream() { // Send signal to wake - mViewMediator.onWakeAndUnlocking(); + mViewMediator.onWakeAndUnlocking(true); // Ensure not woken up yet verify(mPowerManager, never()).wakeUp(anyLong(), anyInt(), anyString()); @@ -632,7 +632,7 @@ public class KeyguardViewMediatorTest extends SysuiTestCase { @Test public void testWakeAndUnlockingOverDream_signalAuthenticateIfStillShowing() { // Send signal to wake - mViewMediator.onWakeAndUnlocking(); + mViewMediator.onWakeAndUnlocking(true); // Ensure not woken up yet verify(mPowerManager, never()).wakeUp(anyLong(), anyInt(), anyString()); @@ -662,6 +662,35 @@ public class KeyguardViewMediatorTest extends SysuiTestCase { } @Test + public void testWakeAndUnlockingOverNonInteractiveDream_noWakeByKeyguardViewMediator() { + // Send signal to wake + mViewMediator.onWakeAndUnlocking(false); + + // Ensure not woken up yet + verify(mPowerManager, never()).wakeUp(anyLong(), anyInt(), anyString()); + + // Verify keyguard told of authentication + verify(mStatusBarKeyguardViewManager).notifyKeyguardAuthenticated(anyBoolean()); + mViewMediator.mViewMediatorCallback.keyguardDonePending(true, + mUpdateMonitor.getCurrentUser()); + mViewMediator.mViewMediatorCallback.readyForKeyguardDone(); + final ArgumentCaptor<Runnable> animationRunnableCaptor = + ArgumentCaptor.forClass(Runnable.class); + verify(mStatusBarKeyguardViewManager).startPreHideAnimation( + animationRunnableCaptor.capture()); + + when(mStatusBarStateController.isDreaming()).thenReturn(true); + when(mStatusBarStateController.isDozing()).thenReturn(false); + animationRunnableCaptor.getValue().run(); + + when(mKeyguardStateController.isShowing()).thenReturn(false); + mViewMediator.mViewMediatorCallback.keyguardGone(); + + // Verify not woken up. + verify(mPowerManager, never()).wakeUp(anyLong(), anyInt(), anyString()); + } + + @Test @TestableLooper.RunWithLooper(setAsMainLooper = true) public void testDoKeyguardWhileInteractive_resets() { mViewMediator.setShowingLocked(true); diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java index 4f8de3eacf7a..7acf398955fb 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/phone/BiometricsUnlockControllerTest.java @@ -186,7 +186,7 @@ public class BiometricsUnlockControllerTest extends SysuiTestCase { mBiometricUnlockController.onBiometricAuthenticated(UserHandle.USER_CURRENT, BiometricSourceType.FINGERPRINT, true /* isStrongBiometric */); - verify(mKeyguardViewMediator).onWakeAndUnlocking(); + verify(mKeyguardViewMediator).onWakeAndUnlocking(false); assertThat(mBiometricUnlockController.getMode()) .isEqualTo(BiometricUnlockController.MODE_WAKE_AND_UNLOCK_PULSING); } @@ -204,7 +204,7 @@ public class BiometricsUnlockControllerTest extends SysuiTestCase { mBiometricUnlockController.onBiometricAuthenticated(UserHandle.USER_CURRENT, BiometricSourceType.FINGERPRINT, true /* isStrongBiometric */); - verify(mKeyguardViewMediator).onWakeAndUnlocking(); + verify(mKeyguardViewMediator).onWakeAndUnlocking(false); assertThat(mBiometricUnlockController.getMode()) .isEqualTo(MODE_WAKE_AND_UNLOCK); } @@ -553,8 +553,9 @@ public class BiometricsUnlockControllerTest extends SysuiTestCase { when(mWakefulnessLifecycle.getLastWakeReason()) .thenReturn(PowerManager.WAKE_REASON_POWER_BUTTON); givenDreamingLocked(); + when(mPowerManager.isInteractive()).thenReturn(true); mBiometricUnlockController.startWakeAndUnlock(BiometricSourceType.FINGERPRINT, true); - verify(mKeyguardViewMediator).onWakeAndUnlocking(); + verify(mKeyguardViewMediator).onWakeAndUnlocking(true); // Ensure that the power hasn't been told to wake up yet. verify(mPowerManager, never()).wakeUp(anyLong(), anyInt(), anyString()); } |