Loading packages/SystemUI/src/com/android/keyguard/FaceAuthReason.kt +10 −1 Original line number Diff line number Diff line Loading @@ -48,11 +48,13 @@ import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_INIT import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_OCCLUSION_CHANGED import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_RESET import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_VISIBILITY_CHANGED import com.android.keyguard.InternalFaceAuthReasons.NON_STRONG_BIOMETRIC_ALLOWED_CHANGED import com.android.keyguard.InternalFaceAuthReasons.OCCLUDING_APP_REQUESTED import com.android.keyguard.InternalFaceAuthReasons.PRIMARY_BOUNCER_SHOWN import com.android.keyguard.InternalFaceAuthReasons.PRIMARY_BOUNCER_SHOWN_OR_WILL_BE_SHOWN import com.android.keyguard.InternalFaceAuthReasons.RETRY_AFTER_HW_UNAVAILABLE import com.android.keyguard.InternalFaceAuthReasons.STARTED_WAKING_UP import com.android.keyguard.InternalFaceAuthReasons.STRONG_AUTH_ALLOWED_CHANGED import com.android.keyguard.InternalFaceAuthReasons.TRUST_DISABLED import com.android.keyguard.InternalFaceAuthReasons.TRUST_ENABLED import com.android.keyguard.InternalFaceAuthReasons.USER_SWITCHING Loading Loading @@ -121,6 +123,9 @@ private object InternalFaceAuthReasons { const val FACE_AUTHENTICATED = "Face auth started/stopped because face is authenticated" const val BIOMETRIC_ENABLED = "Face auth started/stopped because biometric is enabled on keyguard" const val STRONG_AUTH_ALLOWED_CHANGED = "Face auth stopped because strong auth allowed changed" const val NON_STRONG_BIOMETRIC_ALLOWED_CHANGED = "Face auth stopped because non strong biometric allowed changed" } /** Loading Loading @@ -204,7 +209,11 @@ constructor(private val id: Int, val reason: String, var extraInfo: Int = 0) : @UiEvent(doc = FACE_AUTHENTICATED) FACE_AUTH_UPDATED_ON_FACE_AUTHENTICATED(1187, FACE_AUTHENTICATED), @UiEvent(doc = BIOMETRIC_ENABLED) FACE_AUTH_UPDATED_BIOMETRIC_ENABLED_ON_KEYGUARD(1188, BIOMETRIC_ENABLED); FACE_AUTH_UPDATED_BIOMETRIC_ENABLED_ON_KEYGUARD(1188, BIOMETRIC_ENABLED), @UiEvent(doc = STRONG_AUTH_ALLOWED_CHANGED) FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED(1255, STRONG_AUTH_ALLOWED_CHANGED), @UiEvent(doc = NON_STRONG_BIOMETRIC_ALLOWED_CHANGED) FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED(1256, NON_STRONG_BIOMETRIC_ALLOWED_CHANGED); override fun getId(): Int = this.id Loading packages/SystemUI/src/com/android/keyguard/KeyguardListenModel.kt +4 −5 Original line number Diff line number Diff line Loading @@ -53,17 +53,17 @@ data class KeyguardFaceListenModel( val biometricSettingEnabledForUser: Boolean, val bouncerFullyShown: Boolean, val faceAndFpNotAuthenticated: Boolean, val faceAuthAllowed: Boolean, val faceDisabled: Boolean, val faceLockedOut: Boolean, val fpLockedOut: Boolean, val goingToSleep: Boolean, val keyguardAwake: Boolean, val keyguardGoingAway: Boolean, val listeningForFaceAssistant: Boolean, val occludingAppRequestingFaceAuth: Boolean, val primaryUser: Boolean, val scanningAllowedByStrongAuth: Boolean, val secureCameraLaunched: Boolean, val supportsDetect: Boolean, val switchingUser: Boolean, val udfpsBouncerShowing: Boolean, val udfpsFingerDown: Boolean, Loading @@ -79,9 +79,8 @@ data class KeyguardActiveUnlockModel( // keep sorted val awakeKeyguard: Boolean, val authInterruptActive: Boolean, val encryptedOrTimedOut: Boolean, val fpLockout: Boolean, val lockDown: Boolean, val fpLockedOut: Boolean, val primaryAuthRequired: Boolean, val switchingUser: Boolean, val triggerActiveUnlockForAssistant: Boolean, val userCanDismissLockScreen: Boolean Loading packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java +62 −65 Original line number Diff line number Diff line Loading @@ -34,9 +34,9 @@ import static android.os.BatteryManager.BATTERY_STATUS_UNKNOWN; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_BOOT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_LOCKOUT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_TIMEOUT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN; import static com.android.keyguard.FaceAuthReasonKt.apiRequestReasonToUiEvent; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_STOPPED_DREAM_STARTED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_STOPPED_FACE_CANCEL_NOT_RECEIVED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_STOPPED_FINISHED_GOING_TO_SLEEP; Loading Loading @@ -65,6 +65,7 @@ import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_ON_FACE_AUT import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_ON_KEYGUARD_INIT; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_PRIMARY_BOUNCER_SHOWN; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_STARTED_WAKING_UP; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_USER_SWITCHING; import static com.android.systemui.DejankUtils.whitelistIpcs; Loading Loading @@ -170,7 +171,6 @@ import java.util.Map.Entry; import java.util.Set; import java.util.TimeZone; import java.util.concurrent.Executor; import java.util.function.Consumer; import java.util.stream.Collectors; import javax.inject.Inject; Loading Loading @@ -1401,6 +1401,9 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab } } /** * Whether the user locked down the device. This doesn't include device policy manager lockdown. */ public boolean isUserInLockdown(int userId) { return containsFlag(mStrongAuthTracker.getStrongAuthForUser(userId), STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN); Loading Loading @@ -1432,7 +1435,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab return mStrongAuthTracker; } private void notifyStrongAuthStateChanged(int userId) { @VisibleForTesting void notifyStrongAuthAllowedChanged(int userId) { Assert.isMainThread(); for (int i = 0; i < mCallbacks.size(); i++) { KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get(); Loading @@ -1440,6 +1444,15 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab cb.onStrongAuthStateChanged(userId); } } if (userId == getCurrentUser()) { FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED.setExtraInfo( mStrongAuthTracker.getStrongAuthForUser(getCurrentUser())); // Strong auth is only reset when primary auth is used to enter the device, // so we only check whether to stop biometric listening states here updateBiometricListeningState( BIOMETRIC_ACTION_STOP, FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED); } } private void notifyLockedOutStateChanged(BiometricSourceType type) { Loading @@ -1451,8 +1464,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab } } } private void notifyNonStrongBiometricStateChanged(int userId) { @VisibleForTesting void notifyNonStrongBiometricAllowedChanged(int userId) { Assert.isMainThread(); for (int i = 0; i < mCallbacks.size(); i++) { KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get(); Loading @@ -1460,6 +1473,16 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab cb.onNonStrongBiometricAllowedChanged(userId); } } if (userId == getCurrentUser()) { FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED.setExtraInfo( mStrongAuthTracker.isNonStrongBiometricAllowedAfterIdleTimeout( getCurrentUser()) ? -1 : 1); // This is only reset when primary auth is used to enter the device, so we only check // whether to stop biometric listening states here updateBiometricListeningState(BIOMETRIC_ACTION_STOP, FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED); } } private void dispatchErrorMessage(CharSequence message) { Loading Loading @@ -1805,16 +1828,12 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab } } public static class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker { private final Consumer<Integer> mStrongAuthRequiredChangedCallback; private final Consumer<Integer> mNonStrongBiometricAllowedChanged; public StrongAuthTracker(Context context, Consumer<Integer> strongAuthRequiredChangedCallback, Consumer<Integer> nonStrongBiometricAllowedChanged) { /** * Updates callbacks when strong auth requirements change. */ public class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker { public StrongAuthTracker(Context context) { super(context); mStrongAuthRequiredChangedCallback = strongAuthRequiredChangedCallback; mNonStrongBiometricAllowedChanged = nonStrongBiometricAllowedChanged; } public boolean isUnlockingWithBiometricAllowed(boolean isStrongBiometric) { Loading @@ -1830,7 +1849,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab @Override public void onStrongAuthRequiredChanged(int userId) { mStrongAuthRequiredChangedCallback.accept(userId); notifyStrongAuthAllowedChanged(userId); } // TODO(b/247091681): Renaming the inappropriate onIsNonStrongBiometricAllowedChanged Loading @@ -1838,7 +1857,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab // Strong-Auth @Override public void onIsNonStrongBiometricAllowedChanged(int userId) { mNonStrongBiometricAllowedChanged.accept(userId); notifyNonStrongBiometricAllowedChanged(userId); } } Loading Loading @@ -1999,8 +2018,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab mUserTracker = userTracker; mTelephonyListenerManager = telephonyListenerManager; mDeviceProvisioned = isDeviceProvisionedInSettingsDb(); mStrongAuthTracker = new StrongAuthTracker(context, this::notifyStrongAuthStateChanged, this::notifyNonStrongBiometricStateChanged); mStrongAuthTracker = new StrongAuthTracker(context); mBackgroundExecutor = backgroundExecutor; mBroadcastDispatcher = broadcastDispatcher; mInteractionJankMonitor = interactionJankMonitor; Loading Loading @@ -2575,24 +2593,17 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab || !mLockPatternUtils.isSecure(user); // Don't trigger active unlock if fp is locked out final boolean fpLockedout = mFingerprintLockedOut || mFingerprintLockedOutPermanent; final boolean fpLockedOut = mFingerprintLockedOut || mFingerprintLockedOutPermanent; // Don't trigger active unlock if primary auth is required final int strongAuth = mStrongAuthTracker.getStrongAuthForUser(user); final boolean isLockDown = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN); final boolean isEncryptedOrTimedOut = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_BOOT) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_TIMEOUT); final boolean primaryAuthRequired = !isUnlockingWithBiometricAllowed(true); final boolean shouldTriggerActiveUnlock = (mAuthInterruptActive || triggerActiveUnlockForAssistant || awakeKeyguard) && !mSwitchingUser && !userCanDismissLockScreen && !fpLockedout && !isLockDown && !isEncryptedOrTimedOut && !fpLockedOut && !primaryAuthRequired && !mKeyguardGoingAway && !mSecureCameraLaunched; Loading @@ -2604,9 +2615,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab shouldTriggerActiveUnlock, awakeKeyguard, mAuthInterruptActive, isEncryptedOrTimedOut, fpLockedout, isLockDown, fpLockedOut, primaryAuthRequired, mSwitchingUser, triggerActiveUnlockForAssistant, userCanDismissLockScreen)); Loading Loading @@ -2658,7 +2668,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab && !fingerprintDisabledForUser && (!mKeyguardGoingAway || !mDeviceInteractive) && mIsPrimaryUser && biometricEnabledForUser; && biometricEnabledForUser && !isUserInLockdown(user); final boolean strongerAuthRequired = !isUnlockingWithFingerprintAllowed(); final boolean isSideFps = isSfpsSupported() && isSfpsEnrolled(); final boolean shouldListenBouncerState = Loading Loading @@ -2720,14 +2731,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab final boolean awakeKeyguard = isKeyguardVisible() && mDeviceInteractive && !statusBarShadeLocked; final int user = getCurrentUser(); final int strongAuth = mStrongAuthTracker.getStrongAuthForUser(user); final boolean isLockDown = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN); final boolean isEncryptedOrTimedOut = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_BOOT) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_TIMEOUT); final boolean fpLockedOut = isFingerprintLockedOut(); final boolean faceAuthAllowed = isUnlockingWithBiometricAllowed(FACE); final boolean canBypass = mKeyguardBypassController != null && mKeyguardBypassController.canBypass(); // There's no reason to ask the HAL for authentication when the user can dismiss the Loading @@ -2735,20 +2739,15 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab // the lock screen even when TrustAgents are keeping the device unlocked. final boolean userNotTrustedOrDetectionIsNeeded = !getUserHasTrust(user) || canBypass; // Scan even when encrypted or timeout to show a preemptive bouncer when bypassing. // Lock-down mode shouldn't scan, since it is more explicit. boolean strongAuthAllowsScanning = (!isEncryptedOrTimedOut || canBypass && !mPrimaryBouncerFullyShown); // If the device supports face detection (without authentication) and bypass is enabled, // allow face scanning to happen if the device is in lockdown mode. // Otherwise, prevent scanning. final boolean supportsDetectOnly = !mFaceSensorProperties.isEmpty() && canBypass && mFaceSensorProperties.get(0).supportsFaceDetection; if (isLockDown && !supportsDetectOnly) { strongAuthAllowsScanning = false; } // If the device supports face detection (without authentication), if bypass is enabled, // allow face detection to happen even if stronger auth is required. When face is detected, // we show the bouncer. However, if the user manually locked down the device themselves, // never attempt to detect face. final boolean supportsDetect = !mFaceSensorProperties.isEmpty() && mFaceSensorProperties.get(0).supportsFaceDetection && canBypass && !mPrimaryBouncerIsOrWillBeShowing && !isUserInLockdown(user); final boolean faceAuthAllowedOrDetectionIsNeeded = faceAuthAllowed || supportsDetect; // If the face or fp has recently been authenticated do not attempt to authenticate again. final boolean faceAndFpNotAuthenticated = !getUserUnlockedWithBiometric(user); Loading @@ -2769,14 +2768,10 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab || mUdfpsBouncerShowing) && !mSwitchingUser && !faceDisabledForUser && userNotTrustedOrDetectionIsNeeded && !mKeyguardGoingAway && biometricEnabledForUser && strongAuthAllowsScanning && mIsPrimaryUser && faceAuthAllowedOrDetectionIsNeeded && mIsPrimaryUser && (!mSecureCameraLaunched || mOccludingAppRequestingFace) && faceAndFpNotAuthenticated && !mGoingToSleep // We only care about fp locked out state and not face because we still trigger // face auth even when face is locked out to show the user a message that face // unlock was supposed to run but didn't && !fpLockedOut; && !mGoingToSleep; // Aggregate relevant fields for debug logging. maybeLogListenerModelData( Loading @@ -2788,17 +2783,17 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab biometricEnabledForUser, mPrimaryBouncerFullyShown, faceAndFpNotAuthenticated, faceAuthAllowed, faceDisabledForUser, isFaceLockedOut(), fpLockedOut, mGoingToSleep, awakeKeyguard, mKeyguardGoingAway, shouldListenForFaceAssistant, mOccludingAppRequestingFace, mIsPrimaryUser, strongAuthAllowsScanning, mSecureCameraLaunched, supportsDetect, mSwitchingUser, mUdfpsBouncerShowing, isUdfpsFingerDown, Loading Loading @@ -2902,9 +2897,11 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab // This would need to be updated for multi-sensor devices final boolean supportsFaceDetection = !mFaceSensorProperties.isEmpty() && mFaceSensorProperties.get(0).supportsFaceDetection; if (isEncryptedOrLockdown(userId) && supportsFaceDetection) { if (!isUnlockingWithBiometricAllowed(FACE) && supportsFaceDetection) { mLogger.v("startListeningForFace - detect"); mFaceManager.detectFace(mFaceCancelSignal, mFaceDetectionCallback, userId); } else { mLogger.v("startListeningForFace - authenticate"); final boolean isBypassEnabled = mKeyguardBypassController != null && mKeyguardBypassController.isBypassEnabled(); mFaceManager.authenticate(null /* crypto */, mFaceCancelSignal, Loading packages/SystemUI/tests/src/com/android/keyguard/KeyguardListenQueueTest.kt +2 −2 Original line number Diff line number Diff line Loading @@ -87,17 +87,17 @@ private fun faceModel(user: Int) = KeyguardFaceListenModel( biometricSettingEnabledForUser = false, bouncerFullyShown = false, faceAndFpNotAuthenticated = false, faceAuthAllowed = true, faceDisabled = false, faceLockedOut = false, fpLockedOut = false, goingToSleep = false, keyguardAwake = false, keyguardGoingAway = false, listeningForFaceAssistant = false, occludingAppRequestingFaceAuth = false, primaryUser = false, scanningAllowedByStrongAuth = false, secureCameraLaunched = false, supportsDetect = true, switchingUser = false, udfpsBouncerShowing = false, udfpsFingerDown = false, Loading packages/SystemUI/tests/src/com/android/keyguard/KeyguardUpdateMonitorTest.java +195 −68 File changed.Preview size limit exceeded, changes collapsed. Show changes Loading
packages/SystemUI/src/com/android/keyguard/FaceAuthReason.kt +10 −1 Original line number Diff line number Diff line Loading @@ -48,11 +48,13 @@ import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_INIT import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_OCCLUSION_CHANGED import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_RESET import com.android.keyguard.InternalFaceAuthReasons.KEYGUARD_VISIBILITY_CHANGED import com.android.keyguard.InternalFaceAuthReasons.NON_STRONG_BIOMETRIC_ALLOWED_CHANGED import com.android.keyguard.InternalFaceAuthReasons.OCCLUDING_APP_REQUESTED import com.android.keyguard.InternalFaceAuthReasons.PRIMARY_BOUNCER_SHOWN import com.android.keyguard.InternalFaceAuthReasons.PRIMARY_BOUNCER_SHOWN_OR_WILL_BE_SHOWN import com.android.keyguard.InternalFaceAuthReasons.RETRY_AFTER_HW_UNAVAILABLE import com.android.keyguard.InternalFaceAuthReasons.STARTED_WAKING_UP import com.android.keyguard.InternalFaceAuthReasons.STRONG_AUTH_ALLOWED_CHANGED import com.android.keyguard.InternalFaceAuthReasons.TRUST_DISABLED import com.android.keyguard.InternalFaceAuthReasons.TRUST_ENABLED import com.android.keyguard.InternalFaceAuthReasons.USER_SWITCHING Loading Loading @@ -121,6 +123,9 @@ private object InternalFaceAuthReasons { const val FACE_AUTHENTICATED = "Face auth started/stopped because face is authenticated" const val BIOMETRIC_ENABLED = "Face auth started/stopped because biometric is enabled on keyguard" const val STRONG_AUTH_ALLOWED_CHANGED = "Face auth stopped because strong auth allowed changed" const val NON_STRONG_BIOMETRIC_ALLOWED_CHANGED = "Face auth stopped because non strong biometric allowed changed" } /** Loading Loading @@ -204,7 +209,11 @@ constructor(private val id: Int, val reason: String, var extraInfo: Int = 0) : @UiEvent(doc = FACE_AUTHENTICATED) FACE_AUTH_UPDATED_ON_FACE_AUTHENTICATED(1187, FACE_AUTHENTICATED), @UiEvent(doc = BIOMETRIC_ENABLED) FACE_AUTH_UPDATED_BIOMETRIC_ENABLED_ON_KEYGUARD(1188, BIOMETRIC_ENABLED); FACE_AUTH_UPDATED_BIOMETRIC_ENABLED_ON_KEYGUARD(1188, BIOMETRIC_ENABLED), @UiEvent(doc = STRONG_AUTH_ALLOWED_CHANGED) FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED(1255, STRONG_AUTH_ALLOWED_CHANGED), @UiEvent(doc = NON_STRONG_BIOMETRIC_ALLOWED_CHANGED) FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED(1256, NON_STRONG_BIOMETRIC_ALLOWED_CHANGED); override fun getId(): Int = this.id Loading
packages/SystemUI/src/com/android/keyguard/KeyguardListenModel.kt +4 −5 Original line number Diff line number Diff line Loading @@ -53,17 +53,17 @@ data class KeyguardFaceListenModel( val biometricSettingEnabledForUser: Boolean, val bouncerFullyShown: Boolean, val faceAndFpNotAuthenticated: Boolean, val faceAuthAllowed: Boolean, val faceDisabled: Boolean, val faceLockedOut: Boolean, val fpLockedOut: Boolean, val goingToSleep: Boolean, val keyguardAwake: Boolean, val keyguardGoingAway: Boolean, val listeningForFaceAssistant: Boolean, val occludingAppRequestingFaceAuth: Boolean, val primaryUser: Boolean, val scanningAllowedByStrongAuth: Boolean, val secureCameraLaunched: Boolean, val supportsDetect: Boolean, val switchingUser: Boolean, val udfpsBouncerShowing: Boolean, val udfpsFingerDown: Boolean, Loading @@ -79,9 +79,8 @@ data class KeyguardActiveUnlockModel( // keep sorted val awakeKeyguard: Boolean, val authInterruptActive: Boolean, val encryptedOrTimedOut: Boolean, val fpLockout: Boolean, val lockDown: Boolean, val fpLockedOut: Boolean, val primaryAuthRequired: Boolean, val switchingUser: Boolean, val triggerActiveUnlockForAssistant: Boolean, val userCanDismissLockScreen: Boolean Loading
packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java +62 −65 Original line number Diff line number Diff line Loading @@ -34,9 +34,9 @@ import static android.os.BatteryManager.BATTERY_STATUS_UNKNOWN; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_BOOT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_LOCKOUT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_TIMEOUT; import static com.android.internal.widget.LockPatternUtils.StrongAuthTracker.STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN; import static com.android.keyguard.FaceAuthReasonKt.apiRequestReasonToUiEvent; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_STOPPED_DREAM_STARTED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_STOPPED_FACE_CANCEL_NOT_RECEIVED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_STOPPED_FINISHED_GOING_TO_SLEEP; Loading Loading @@ -65,6 +65,7 @@ import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_ON_FACE_AUT import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_ON_KEYGUARD_INIT; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_PRIMARY_BOUNCER_SHOWN; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_STARTED_WAKING_UP; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED; import static com.android.keyguard.FaceAuthUiEvent.FACE_AUTH_UPDATED_USER_SWITCHING; import static com.android.systemui.DejankUtils.whitelistIpcs; Loading Loading @@ -170,7 +171,6 @@ import java.util.Map.Entry; import java.util.Set; import java.util.TimeZone; import java.util.concurrent.Executor; import java.util.function.Consumer; import java.util.stream.Collectors; import javax.inject.Inject; Loading Loading @@ -1401,6 +1401,9 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab } } /** * Whether the user locked down the device. This doesn't include device policy manager lockdown. */ public boolean isUserInLockdown(int userId) { return containsFlag(mStrongAuthTracker.getStrongAuthForUser(userId), STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN); Loading Loading @@ -1432,7 +1435,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab return mStrongAuthTracker; } private void notifyStrongAuthStateChanged(int userId) { @VisibleForTesting void notifyStrongAuthAllowedChanged(int userId) { Assert.isMainThread(); for (int i = 0; i < mCallbacks.size(); i++) { KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get(); Loading @@ -1440,6 +1444,15 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab cb.onStrongAuthStateChanged(userId); } } if (userId == getCurrentUser()) { FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED.setExtraInfo( mStrongAuthTracker.getStrongAuthForUser(getCurrentUser())); // Strong auth is only reset when primary auth is used to enter the device, // so we only check whether to stop biometric listening states here updateBiometricListeningState( BIOMETRIC_ACTION_STOP, FACE_AUTH_UPDATED_STRONG_AUTH_CHANGED); } } private void notifyLockedOutStateChanged(BiometricSourceType type) { Loading @@ -1451,8 +1464,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab } } } private void notifyNonStrongBiometricStateChanged(int userId) { @VisibleForTesting void notifyNonStrongBiometricAllowedChanged(int userId) { Assert.isMainThread(); for (int i = 0; i < mCallbacks.size(); i++) { KeyguardUpdateMonitorCallback cb = mCallbacks.get(i).get(); Loading @@ -1460,6 +1473,16 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab cb.onNonStrongBiometricAllowedChanged(userId); } } if (userId == getCurrentUser()) { FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED.setExtraInfo( mStrongAuthTracker.isNonStrongBiometricAllowedAfterIdleTimeout( getCurrentUser()) ? -1 : 1); // This is only reset when primary auth is used to enter the device, so we only check // whether to stop biometric listening states here updateBiometricListeningState(BIOMETRIC_ACTION_STOP, FACE_AUTH_NON_STRONG_BIOMETRIC_ALLOWED_CHANGED); } } private void dispatchErrorMessage(CharSequence message) { Loading Loading @@ -1805,16 +1828,12 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab } } public static class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker { private final Consumer<Integer> mStrongAuthRequiredChangedCallback; private final Consumer<Integer> mNonStrongBiometricAllowedChanged; public StrongAuthTracker(Context context, Consumer<Integer> strongAuthRequiredChangedCallback, Consumer<Integer> nonStrongBiometricAllowedChanged) { /** * Updates callbacks when strong auth requirements change. */ public class StrongAuthTracker extends LockPatternUtils.StrongAuthTracker { public StrongAuthTracker(Context context) { super(context); mStrongAuthRequiredChangedCallback = strongAuthRequiredChangedCallback; mNonStrongBiometricAllowedChanged = nonStrongBiometricAllowedChanged; } public boolean isUnlockingWithBiometricAllowed(boolean isStrongBiometric) { Loading @@ -1830,7 +1849,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab @Override public void onStrongAuthRequiredChanged(int userId) { mStrongAuthRequiredChangedCallback.accept(userId); notifyStrongAuthAllowedChanged(userId); } // TODO(b/247091681): Renaming the inappropriate onIsNonStrongBiometricAllowedChanged Loading @@ -1838,7 +1857,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab // Strong-Auth @Override public void onIsNonStrongBiometricAllowedChanged(int userId) { mNonStrongBiometricAllowedChanged.accept(userId); notifyNonStrongBiometricAllowedChanged(userId); } } Loading Loading @@ -1999,8 +2018,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab mUserTracker = userTracker; mTelephonyListenerManager = telephonyListenerManager; mDeviceProvisioned = isDeviceProvisionedInSettingsDb(); mStrongAuthTracker = new StrongAuthTracker(context, this::notifyStrongAuthStateChanged, this::notifyNonStrongBiometricStateChanged); mStrongAuthTracker = new StrongAuthTracker(context); mBackgroundExecutor = backgroundExecutor; mBroadcastDispatcher = broadcastDispatcher; mInteractionJankMonitor = interactionJankMonitor; Loading Loading @@ -2575,24 +2593,17 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab || !mLockPatternUtils.isSecure(user); // Don't trigger active unlock if fp is locked out final boolean fpLockedout = mFingerprintLockedOut || mFingerprintLockedOutPermanent; final boolean fpLockedOut = mFingerprintLockedOut || mFingerprintLockedOutPermanent; // Don't trigger active unlock if primary auth is required final int strongAuth = mStrongAuthTracker.getStrongAuthForUser(user); final boolean isLockDown = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN); final boolean isEncryptedOrTimedOut = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_BOOT) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_TIMEOUT); final boolean primaryAuthRequired = !isUnlockingWithBiometricAllowed(true); final boolean shouldTriggerActiveUnlock = (mAuthInterruptActive || triggerActiveUnlockForAssistant || awakeKeyguard) && !mSwitchingUser && !userCanDismissLockScreen && !fpLockedout && !isLockDown && !isEncryptedOrTimedOut && !fpLockedOut && !primaryAuthRequired && !mKeyguardGoingAway && !mSecureCameraLaunched; Loading @@ -2604,9 +2615,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab shouldTriggerActiveUnlock, awakeKeyguard, mAuthInterruptActive, isEncryptedOrTimedOut, fpLockedout, isLockDown, fpLockedOut, primaryAuthRequired, mSwitchingUser, triggerActiveUnlockForAssistant, userCanDismissLockScreen)); Loading Loading @@ -2658,7 +2668,8 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab && !fingerprintDisabledForUser && (!mKeyguardGoingAway || !mDeviceInteractive) && mIsPrimaryUser && biometricEnabledForUser; && biometricEnabledForUser && !isUserInLockdown(user); final boolean strongerAuthRequired = !isUnlockingWithFingerprintAllowed(); final boolean isSideFps = isSfpsSupported() && isSfpsEnrolled(); final boolean shouldListenBouncerState = Loading Loading @@ -2720,14 +2731,7 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab final boolean awakeKeyguard = isKeyguardVisible() && mDeviceInteractive && !statusBarShadeLocked; final int user = getCurrentUser(); final int strongAuth = mStrongAuthTracker.getStrongAuthForUser(user); final boolean isLockDown = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_DPM_LOCK_NOW) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_USER_LOCKDOWN); final boolean isEncryptedOrTimedOut = containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_BOOT) || containsFlag(strongAuth, STRONG_AUTH_REQUIRED_AFTER_TIMEOUT); final boolean fpLockedOut = isFingerprintLockedOut(); final boolean faceAuthAllowed = isUnlockingWithBiometricAllowed(FACE); final boolean canBypass = mKeyguardBypassController != null && mKeyguardBypassController.canBypass(); // There's no reason to ask the HAL for authentication when the user can dismiss the Loading @@ -2735,20 +2739,15 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab // the lock screen even when TrustAgents are keeping the device unlocked. final boolean userNotTrustedOrDetectionIsNeeded = !getUserHasTrust(user) || canBypass; // Scan even when encrypted or timeout to show a preemptive bouncer when bypassing. // Lock-down mode shouldn't scan, since it is more explicit. boolean strongAuthAllowsScanning = (!isEncryptedOrTimedOut || canBypass && !mPrimaryBouncerFullyShown); // If the device supports face detection (without authentication) and bypass is enabled, // allow face scanning to happen if the device is in lockdown mode. // Otherwise, prevent scanning. final boolean supportsDetectOnly = !mFaceSensorProperties.isEmpty() && canBypass && mFaceSensorProperties.get(0).supportsFaceDetection; if (isLockDown && !supportsDetectOnly) { strongAuthAllowsScanning = false; } // If the device supports face detection (without authentication), if bypass is enabled, // allow face detection to happen even if stronger auth is required. When face is detected, // we show the bouncer. However, if the user manually locked down the device themselves, // never attempt to detect face. final boolean supportsDetect = !mFaceSensorProperties.isEmpty() && mFaceSensorProperties.get(0).supportsFaceDetection && canBypass && !mPrimaryBouncerIsOrWillBeShowing && !isUserInLockdown(user); final boolean faceAuthAllowedOrDetectionIsNeeded = faceAuthAllowed || supportsDetect; // If the face or fp has recently been authenticated do not attempt to authenticate again. final boolean faceAndFpNotAuthenticated = !getUserUnlockedWithBiometric(user); Loading @@ -2769,14 +2768,10 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab || mUdfpsBouncerShowing) && !mSwitchingUser && !faceDisabledForUser && userNotTrustedOrDetectionIsNeeded && !mKeyguardGoingAway && biometricEnabledForUser && strongAuthAllowsScanning && mIsPrimaryUser && faceAuthAllowedOrDetectionIsNeeded && mIsPrimaryUser && (!mSecureCameraLaunched || mOccludingAppRequestingFace) && faceAndFpNotAuthenticated && !mGoingToSleep // We only care about fp locked out state and not face because we still trigger // face auth even when face is locked out to show the user a message that face // unlock was supposed to run but didn't && !fpLockedOut; && !mGoingToSleep; // Aggregate relevant fields for debug logging. maybeLogListenerModelData( Loading @@ -2788,17 +2783,17 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab biometricEnabledForUser, mPrimaryBouncerFullyShown, faceAndFpNotAuthenticated, faceAuthAllowed, faceDisabledForUser, isFaceLockedOut(), fpLockedOut, mGoingToSleep, awakeKeyguard, mKeyguardGoingAway, shouldListenForFaceAssistant, mOccludingAppRequestingFace, mIsPrimaryUser, strongAuthAllowsScanning, mSecureCameraLaunched, supportsDetect, mSwitchingUser, mUdfpsBouncerShowing, isUdfpsFingerDown, Loading Loading @@ -2902,9 +2897,11 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener, Dumpab // This would need to be updated for multi-sensor devices final boolean supportsFaceDetection = !mFaceSensorProperties.isEmpty() && mFaceSensorProperties.get(0).supportsFaceDetection; if (isEncryptedOrLockdown(userId) && supportsFaceDetection) { if (!isUnlockingWithBiometricAllowed(FACE) && supportsFaceDetection) { mLogger.v("startListeningForFace - detect"); mFaceManager.detectFace(mFaceCancelSignal, mFaceDetectionCallback, userId); } else { mLogger.v("startListeningForFace - authenticate"); final boolean isBypassEnabled = mKeyguardBypassController != null && mKeyguardBypassController.isBypassEnabled(); mFaceManager.authenticate(null /* crypto */, mFaceCancelSignal, Loading
packages/SystemUI/tests/src/com/android/keyguard/KeyguardListenQueueTest.kt +2 −2 Original line number Diff line number Diff line Loading @@ -87,17 +87,17 @@ private fun faceModel(user: Int) = KeyguardFaceListenModel( biometricSettingEnabledForUser = false, bouncerFullyShown = false, faceAndFpNotAuthenticated = false, faceAuthAllowed = true, faceDisabled = false, faceLockedOut = false, fpLockedOut = false, goingToSleep = false, keyguardAwake = false, keyguardGoingAway = false, listeningForFaceAssistant = false, occludingAppRequestingFaceAuth = false, primaryUser = false, scanningAllowedByStrongAuth = false, secureCameraLaunched = false, supportsDetect = true, switchingUser = false, udfpsBouncerShowing = false, udfpsFingerDown = false, Loading
packages/SystemUI/tests/src/com/android/keyguard/KeyguardUpdateMonitorTest.java +195 −68 File changed.Preview size limit exceeded, changes collapsed. Show changes