5/n: Add invalidation plumbing in fingerprint/face providers

A subsequent CL will initiate the invalidation, e.g. create an
InvalidationRequesterClient when enroll finishes.

Bug: 159667191
Test: Presubmit
Change-Id: I80338fc3cec4b441ea4eef6359fd36969ce04277
diff --git a/services/core/java/com/android/server/biometrics/sensors/InvalidationClient.java b/services/core/java/com/android/server/biometrics/sensors/InvalidationClient.java
index fe946cb..cdd0abf 100644
--- a/services/core/java/com/android/server/biometrics/sensors/InvalidationClient.java
+++ b/services/core/java/com/android/server/biometrics/sensors/InvalidationClient.java
@@ -20,6 +20,9 @@
 import android.content.Context;
 import android.hardware.biometrics.BiometricAuthenticator;
 import android.hardware.biometrics.BiometricsProtoEnums;
+import android.hardware.biometrics.IInvalidationCallback;
+import android.os.RemoteException;
+import android.util.Slog;
 
 import java.util.Map;
 
@@ -30,22 +33,29 @@
 public abstract class InvalidationClient<S extends BiometricAuthenticator.Identifier, T>
         extends ClientMonitor<T> {
 
-    private final BiometricUtils<S> mUtils;
-    private final Map<Integer, Long> mAuthenticatorIds;
+    private static final String TAG = "InvalidationClient";
+
+    @NonNull private final Map<Integer, Long> mAuthenticatorIds;
+    @NonNull private final IInvalidationCallback mInvalidationCallback;
 
     public InvalidationClient(@NonNull Context context, @NonNull LazyDaemon<T> lazyDaemon,
-            int userId, int sensorId, @NonNull BiometricUtils<S> utils,
-            @NonNull Map<Integer, Long> authenticatorIds) {
+            int userId, int sensorId, @NonNull Map<Integer, Long> authenticatorIds,
+            @NonNull IInvalidationCallback callback) {
         super(context, lazyDaemon, null /* token */, null /* listener */, userId,
                 context.getOpPackageName(), 0 /* cookie */, sensorId,
                 BiometricsProtoEnums.MODALITY_UNKNOWN, BiometricsProtoEnums.ACTION_UNKNOWN,
                 BiometricsProtoEnums.CLIENT_UNKNOWN);
-        mUtils = utils;
         mAuthenticatorIds = authenticatorIds;
+        mInvalidationCallback = callback;
     }
 
     public void onAuthenticatorIdInvalidated(long newAuthenticatorId) {
         mAuthenticatorIds.put(getTargetUserId(), newAuthenticatorId);
+        try {
+            mInvalidationCallback.onCompleted();
+        } catch (RemoteException e) {
+            Slog.e(TAG, "Remote exception", e);
+        }
         mCallback.onClientFinished(this, true /* success */);
     }
 
diff --git a/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceInvalidationClient.java b/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceInvalidationClient.java
index 9c6438e..855ee1d 100644
--- a/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceInvalidationClient.java
+++ b/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceInvalidationClient.java
@@ -18,13 +18,13 @@
 
 import android.annotation.NonNull;
 import android.content.Context;
+import android.hardware.biometrics.IInvalidationCallback;
 import android.hardware.biometrics.face.ISession;
 import android.hardware.face.Face;
 import android.os.RemoteException;
 import android.util.Slog;
 
 import com.android.server.biometrics.sensors.InvalidationClient;
-import com.android.server.biometrics.sensors.face.FaceUtils;
 
 import java.util.Map;
 
@@ -33,8 +33,8 @@
 
     public FaceInvalidationClient(@NonNull Context context,
             @NonNull LazyDaemon<ISession> lazyDaemon, int userId, int sensorId,
-            @NonNull FaceUtils utils, @NonNull Map<Integer, Long> authenticatorIds) {
-        super(context, lazyDaemon, userId, sensorId, utils, authenticatorIds);
+            @NonNull Map<Integer, Long> authenticatorIds, @NonNull IInvalidationCallback callback) {
+        super(context, lazyDaemon, userId, sensorId, authenticatorIds, callback);
     }
 
     @Override
diff --git a/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceProvider.java b/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceProvider.java
index cec1cb8..e90cc24 100644
--- a/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceProvider.java
+++ b/services/core/java/com/android/server/biometrics/sensors/face/aidl/FaceProvider.java
@@ -20,10 +20,10 @@
 import android.annotation.Nullable;
 import android.app.ActivityManager;
 import android.app.ActivityTaskManager;
-import android.app.IActivityTaskManager;
 import android.app.TaskStackListener;
 import android.content.Context;
 import android.content.pm.UserInfo;
+import android.hardware.biometrics.IInvalidationCallback;
 import android.hardware.biometrics.ITestSession;
 import android.hardware.biometrics.face.IFace;
 import android.hardware.biometrics.face.SensorProps;
@@ -269,6 +269,32 @@
     }
 
     @Override
+    public void scheduleInvalidateAuthenticatorId(int sensorId, int userId,
+            @NonNull IInvalidationCallback callback) {
+        mHandler.post(() -> {
+            final IFace daemon = getHalInstance();
+            if (daemon == null) {
+                Slog.e(getTag(), "Null daemon during scheduleInvalidateAuthenticatorId: "
+                        + sensorId);
+                return;
+            }
+
+            try {
+                if (!mSensors.get(sensorId).hasSessionForUser(userId)) {
+                    createNewSessionWithoutHandler(daemon, sensorId, userId);
+                }
+
+                final FaceInvalidationClient client = new FaceInvalidationClient(mContext,
+                        mSensors.get(sensorId).getLazySession(), userId, sensorId,
+                        mSensors.get(sensorId).getAuthenticatorIds(), callback);
+                mSensors.get(sensorId).getScheduler().scheduleClientMonitor(client);
+            } catch (RemoteException e) {
+                Slog.e(getTag(), "Remote exception", e);
+            }
+        });
+    }
+
+    @Override
     public int getLockoutModeForUser(int sensorId, int userId) {
         return mSensors.get(sensorId).getLockoutCache().getLockoutModeForUser(userId);
     }
diff --git a/services/core/java/com/android/server/biometrics/sensors/face/aidl/Sensor.java b/services/core/java/com/android/server/biometrics/sensors/face/aidl/Sensor.java
index 2cf729c..32f12e6 100644
--- a/services/core/java/com/android/server/biometrics/sensors/face/aidl/Sensor.java
+++ b/services/core/java/com/android/server/biometrics/sensors/face/aidl/Sensor.java
@@ -376,7 +376,17 @@
 
         @Override
         public void onAuthenticatorIdInvalidated(long newAuthenticatorId) {
-            // TODO(b/159667191)
+            mHandler.post(() -> {
+                final ClientMonitor<?> client = mScheduler.getCurrentClient();
+                if (!(client instanceof FaceInvalidationClient)) {
+                    Slog.e(mTag, "onAuthenticatorIdInvalidated for wrong consumer: "
+                            + Utils.getClientName(client));
+                    return;
+                }
+
+                final FaceInvalidationClient invalidationClient = (FaceInvalidationClient) client;
+                invalidationClient.onAuthenticatorIdInvalidated(newAuthenticatorId);
+            });
         }
 
     }
diff --git a/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintInvalidationClient.java b/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintInvalidationClient.java
index 3d07334..80d1a0f 100644
--- a/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintInvalidationClient.java
+++ b/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintInvalidationClient.java
@@ -18,13 +18,13 @@
 
 import android.annotation.NonNull;
 import android.content.Context;
+import android.hardware.biometrics.IInvalidationCallback;
 import android.hardware.biometrics.fingerprint.ISession;
 import android.hardware.fingerprint.Fingerprint;
 import android.os.RemoteException;
 import android.util.Slog;
 
 import com.android.server.biometrics.sensors.InvalidationClient;
-import com.android.server.biometrics.sensors.fingerprint.FingerprintUtils;
 
 import java.util.Map;
 
@@ -33,8 +33,8 @@
 
     public FingerprintInvalidationClient(@NonNull Context context,
             @NonNull LazyDaemon<ISession> lazyDaemon, int userId, int sensorId,
-            @NonNull FingerprintUtils utils, @NonNull Map<Integer, Long> authenticatorIds) {
-        super(context, lazyDaemon, userId, sensorId, utils, authenticatorIds);
+            @NonNull Map<Integer, Long> authenticatorIds, @NonNull IInvalidationCallback callback) {
+        super(context, lazyDaemon, userId, sensorId, authenticatorIds, callback);
     }
 
     @Override
diff --git a/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintProvider.java b/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintProvider.java
index a03deba..adf4659 100644
--- a/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintProvider.java
+++ b/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/FingerprintProvider.java
@@ -23,6 +23,7 @@
 import android.app.TaskStackListener;
 import android.content.Context;
 import android.content.pm.UserInfo;
+import android.hardware.biometrics.IInvalidationCallback;
 import android.hardware.biometrics.ITestSession;
 import android.hardware.biometrics.fingerprint.IFingerprint;
 import android.hardware.biometrics.fingerprint.SensorProps;
@@ -542,6 +543,33 @@
     }
 
     @Override
+    public void scheduleInvalidateAuthenticatorId(int sensorId, int userId,
+            @NonNull IInvalidationCallback callback) {
+        mHandler.post(() -> {
+            final IFingerprint daemon = getHalInstance();
+            if (daemon == null) {
+                Slog.e(getTag(), "Null daemon during scheduleInvalidateAuthenticatorId: "
+                        + sensorId);
+                return;
+            }
+
+            try {
+                if (!mSensors.get(sensorId).hasSessionForUser(userId)) {
+                    createNewSessionWithoutHandler(daemon, sensorId, userId);
+                }
+
+                final FingerprintInvalidationClient client =
+                        new FingerprintInvalidationClient(mContext,
+                                mSensors.get(sensorId).getLazySession(), userId, sensorId,
+                                mSensors.get(sensorId).getAuthenticatorIds(), callback);
+                mSensors.get(sensorId).getScheduler().scheduleClientMonitor(client);
+            } catch (RemoteException e) {
+                Slog.e(getTag(), "Remote exception", e);
+            }
+        });
+    }
+
+    @Override
     public int getLockoutModeForUser(int sensorId, int userId) {
         return mSensors.get(sensorId).getLockoutCache().getLockoutModeForUser(userId);
     }
diff --git a/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/Sensor.java b/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/Sensor.java
index 5fefe98..a27ac420 100644
--- a/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/Sensor.java
+++ b/services/core/java/com/android/server/biometrics/sensors/fingerprint/aidl/Sensor.java
@@ -389,7 +389,18 @@
 
         @Override
         public void onAuthenticatorIdInvalidated(long newAuthenticatorId) {
-            // TODO(159667191)
+            mHandler.post(() -> {
+                final ClientMonitor<?> client = mScheduler.getCurrentClient();
+                if (!(client instanceof FingerprintInvalidationClient)) {
+                    Slog.e(mTag, "onAuthenticatorIdInvalidated for wrong consumer: "
+                            + Utils.getClientName(client));
+                    return;
+                }
+
+                final FingerprintInvalidationClient invalidationClient =
+                        (FingerprintInvalidationClient) client;
+                invalidationClient.onAuthenticatorIdInvalidated(newAuthenticatorId);
+            });
         }
     }