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

Commit 95289da7 authored by Joe Bolinger's avatar Joe Bolinger
Browse files

Move ALS auth logging triggers to wakefullness events.

These were orignally tied to pointer up/down events, but change I4a217ef4a068c8b2cae0f345856912028f9a9525 removed these events entirely on many devices and left these triggers unreliable.

Bug: 243836005
Test: atest FingerprintAuthenticationClientTest BiometricContextProviderTest AuthControllerTest
Test: manual (verify on lockscreen via adb shell dumpsys sensorservice | grep -i Biometric)
Change-Id: I2db34ca561850eb1eddcc65c08c617a46dd3d845
parent 09970117
Loading
Loading
Loading
Loading
+4 −1
Original line number Diff line number Diff line
@@ -23,5 +23,8 @@ package android.hardware.biometrics;
 * @hide
 */
oneway interface IBiometricContextListener {
    void onDozeChanged(boolean isDozing);
    // Called when doze or awake (screen on) status changes.
    // These may be called while the device is still transitioning to the new state
    // (i.e. about to become awake or enter doze)
    void onDozeChanged(boolean isDozing, boolean isAwake);
}
+23 −5
Original line number Diff line number Diff line
@@ -19,6 +19,9 @@ package com.android.systemui.biometrics;
import static android.hardware.biometrics.BiometricAuthenticator.TYPE_FACE;
import static android.hardware.biometrics.BiometricAuthenticator.TYPE_FINGERPRINT;

import static com.android.systemui.keyguard.WakefulnessLifecycle.WAKEFULNESS_AWAKE;
import static com.android.systemui.keyguard.WakefulnessLifecycle.WAKEFULNESS_GOING_TO_SLEEP;

import android.annotation.NonNull;
import android.annotation.Nullable;
import android.app.ActivityManager;
@@ -599,7 +602,6 @@ public class AuthController extends CoreStartable implements CommandQueue.Callba
            @Background DelayableExecutor bgExecutor) {
        super(context);
        mExecution = execution;
        mWakefulnessLifecycle = wakefulnessLifecycle;
        mUserManager = userManager;
        mLockPatternUtils = lockPatternUtils;
        mHandler = handler;
@@ -625,11 +627,24 @@ public class AuthController extends CoreStartable implements CommandQueue.Callba
                    return Unit.INSTANCE;
                });

        mWakefulnessLifecycle = wakefulnessLifecycle;
        mWakefulnessLifecycle.addObserver(new WakefulnessLifecycle.Observer() {
            @Override
            public void onFinishedWakingUp() {
                notifyDozeChanged(mStatusBarStateController.isDozing(), WAKEFULNESS_AWAKE);
            }

            @Override
            public void onStartedGoingToSleep() {
                notifyDozeChanged(mStatusBarStateController.isDozing(), WAKEFULNESS_GOING_TO_SLEEP);
            }
        });

        mStatusBarStateController = statusBarStateController;
        mStatusBarStateController.addCallback(new StatusBarStateController.StateListener() {
            @Override
            public void onDozingChanged(boolean isDozing) {
                notifyDozeChanged(isDozing);
                notifyDozeChanged(isDozing, wakefulnessLifecycle.getWakefulness());
            }
        });

@@ -738,13 +753,16 @@ public class AuthController extends CoreStartable implements CommandQueue.Callba
    @Override
    public void setBiometicContextListener(IBiometricContextListener listener) {
        mBiometricContextListener = listener;
        notifyDozeChanged(mStatusBarStateController.isDozing());
        notifyDozeChanged(mStatusBarStateController.isDozing(),
                mWakefulnessLifecycle.getWakefulness());
    }

    private void notifyDozeChanged(boolean isDozing) {
    private void notifyDozeChanged(boolean isDozing,
            @WakefulnessLifecycle.Wakefulness int wakefullness) {
        if (mBiometricContextListener != null) {
            try {
                mBiometricContextListener.onDozeChanged(isDozing);
                final boolean isAwake = wakefullness == WAKEFULNESS_AWAKE;
                mBiometricContextListener.onDozeChanged(isDozing, isAwake);
            } catch (RemoteException e) {
                Log.w(TAG, "failed to notify initial doze state");
            }
+36 −9
Original line number Diff line number Diff line
@@ -20,6 +20,8 @@ import static android.hardware.biometrics.BiometricAuthenticator.TYPE_FINGERPRIN
import static android.hardware.biometrics.BiometricManager.Authenticators;
import static android.hardware.biometrics.BiometricManager.BIOMETRIC_MULTI_SENSOR_FINGERPRINT_AND_FACE;

import static com.android.systemui.keyguard.WakefulnessLifecycle.WAKEFULNESS_AWAKE;

import static com.google.common.truth.Truth.assertThat;

import static junit.framework.Assert.assertEquals;
@@ -157,13 +159,15 @@ public class AuthControllerTest extends SysuiTestCase {
    @Mock
    private InteractionJankMonitor mInteractionJankMonitor;
    @Captor
    ArgumentCaptor<IFingerprintAuthenticatorsRegisteredCallback> mFpAuthenticatorsRegisteredCaptor;
    private ArgumentCaptor<IFingerprintAuthenticatorsRegisteredCallback> mFpAuthenticatorsRegisteredCaptor;
    @Captor
    private ArgumentCaptor<IFaceAuthenticatorsRegisteredCallback> mFaceAuthenticatorsRegisteredCaptor;
    @Captor
    ArgumentCaptor<IFaceAuthenticatorsRegisteredCallback> mFaceAuthenticatorsRegisteredCaptor;
    private ArgumentCaptor<BiometricStateListener> mBiometricStateCaptor;
    @Captor
    ArgumentCaptor<BiometricStateListener> mBiometricStateCaptor;
    private ArgumentCaptor<StatusBarStateController.StateListener> mStatusBarStateListenerCaptor;
    @Captor
    ArgumentCaptor<StatusBarStateController.StateListener> mStatusBarStateListenerCaptor;
    private ArgumentCaptor<WakefulnessLifecycle.Observer> mWakefullnessObserverCaptor;

    private TestableContext mContextSpy;
    private Execution mExecution;
@@ -242,7 +246,9 @@ public class AuthControllerTest extends SysuiTestCase {
                mFaceAuthenticatorsRegisteredCaptor.capture());

        when(mStatusBarStateController.isDozing()).thenReturn(false);
        when(mWakefulnessLifecycle.getWakefulness()).thenReturn(WAKEFULNESS_AWAKE);
        verify(mStatusBarStateController).addCallback(mStatusBarStateListenerCaptor.capture());
        verify(mWakefulnessLifecycle).addObserver(mWakefullnessObserverCaptor.capture());

        mFpAuthenticatorsRegisteredCaptor.getValue().onAllAuthenticatorsRegistered(fpProps);
        mFaceAuthenticatorsRegisteredCaptor.getValue().onAllAuthenticatorsRegistered(faceProps);
@@ -759,16 +765,37 @@ public class AuthControllerTest extends SysuiTestCase {
    }

    @Test
    public void testForwardsDozeEvent() throws RemoteException {
    public void testForwardsDozeEvents() throws RemoteException {
        when(mStatusBarStateController.isDozing()).thenReturn(true);
        when(mWakefulnessLifecycle.getWakefulness()).thenReturn(WAKEFULNESS_AWAKE);
        mAuthController.setBiometicContextListener(mContextListener);

        mStatusBarStateListenerCaptor.getValue().onDozingChanged(false);
        mStatusBarStateListenerCaptor.getValue().onDozingChanged(true);
        mStatusBarStateListenerCaptor.getValue().onDozingChanged(false);

        InOrder order = inOrder(mContextListener);
        order.verify(mContextListener, times(2)).onDozeChanged(eq(true), eq(true));
        order.verify(mContextListener).onDozeChanged(eq(false), eq(true));
        order.verifyNoMoreInteractions();
    }

    @Test
    public void testForwardsWakeEvents() throws RemoteException {
        when(mStatusBarStateController.isDozing()).thenReturn(false);
        when(mWakefulnessLifecycle.getWakefulness()).thenReturn(WAKEFULNESS_AWAKE);
        mAuthController.setBiometicContextListener(mContextListener);

        mWakefullnessObserverCaptor.getValue().onStartedGoingToSleep();
        mWakefullnessObserverCaptor.getValue().onFinishedGoingToSleep();
        mWakefullnessObserverCaptor.getValue().onStartedWakingUp();
        mWakefullnessObserverCaptor.getValue().onFinishedWakingUp();
        mWakefullnessObserverCaptor.getValue().onPostFinishedWakingUp();

        InOrder order = inOrder(mContextListener);
        // invoked twice since the initial state is false
        order.verify(mContextListener, times(2)).onDozeChanged(eq(false));
        order.verify(mContextListener).onDozeChanged(eq(true));
        order.verify(mContextListener).onDozeChanged(eq(false), eq(true));
        order.verify(mContextListener).onDozeChanged(eq(false), eq(false));
        order.verify(mContextListener).onDozeChanged(eq(false), eq(true));
        order.verifyNoMoreInteractions();
    }

    // Helpers
+3 −0
Original line number Diff line number Diff line
@@ -46,6 +46,9 @@ public interface BiometricContext {
    /** If the display is in AOD. */
    boolean isAod();

    /** If the device is awake or is becoming awake. */
    boolean isAwake();

    /**
     * Subscribe to context changes.
     *
+21 −6
Original line number Diff line number Diff line
@@ -43,7 +43,7 @@ import java.util.function.Consumer;
/**
 * A default provider for {@link BiometricContext}.
 */
class BiometricContextProvider implements BiometricContext {
final class BiometricContextProvider implements BiometricContext {

    private static final String TAG = "BiometricContextProvider";

@@ -76,7 +76,8 @@ class BiometricContextProvider implements BiometricContext {
    private final Map<Integer, InstanceId> mSession = new ConcurrentHashMap<>();

    private final AmbientDisplayConfiguration mAmbientDisplayConfiguration;
    private boolean mIsDozing = false;
    private boolean mIsAod = false;
    private boolean mIsAwake = false;

    @VisibleForTesting
    BiometricContextProvider(@NonNull AmbientDisplayConfiguration ambientDisplayConfiguration,
@@ -85,10 +86,15 @@ class BiometricContextProvider implements BiometricContext {
        try {
            service.setBiometicContextListener(new IBiometricContextListener.Stub() {
                @Override
                public void onDozeChanged(boolean isDozing) {
                    mIsDozing = isDozing;
                public void onDozeChanged(boolean isDozing, boolean isAwake) {
                    isDozing = isDozing && isAodEnabled();
                    final boolean changed = (mIsAod != isDozing) || (mIsAwake != isAwake);
                    if (changed) {
                        mIsAod = isDozing;
                        mIsAwake = isAwake;
                        notifyChanged();
                    }
                }

                private void notifyChanged() {
                    if (handler != null) {
@@ -97,6 +103,10 @@ class BiometricContextProvider implements BiometricContext {
                        notifySubscribers();
                    }
                }

                private boolean isAodEnabled() {
                    return mAmbientDisplayConfiguration.alwaysOnEnabled(UserHandle.USER_CURRENT);
                }
            });
            service.registerSessionListener(SESSION_TYPES, new ISessionListener.Stub() {
                @Override
@@ -161,7 +171,12 @@ class BiometricContextProvider implements BiometricContext {

    @Override
    public boolean isAod() {
        return mIsDozing && mAmbientDisplayConfiguration.alwaysOnEnabled(UserHandle.USER_CURRENT);
        return mIsAod;
    }

    @Override
    public boolean isAwake() {
        return mIsAwake;
    }

    @Override
Loading