Add biometric strength reset and fix CTS tests on multi sensor devices (mostly)
Tests can still fail due to flakiness in cleanup (main cause seems to be stale enrollments). Fix: 187250205 Test: atest CtsBiometricsTestCases Change-Id: I3e379322277cde984f5a0112d38db60b9c6e360d
This commit is contained in:
@@ -23,7 +23,6 @@ import android.annotation.Nullable;
|
||||
import android.annotation.RequiresPermission;
|
||||
import android.annotation.TestApi;
|
||||
import android.content.Context;
|
||||
import android.hardware.fingerprint.FingerprintManager;
|
||||
import android.os.RemoteException;
|
||||
import android.util.ArraySet;
|
||||
import android.util.Log;
|
||||
@@ -248,6 +247,12 @@ public class BiometricTestSession implements AutoCloseable {
|
||||
}
|
||||
}
|
||||
|
||||
if (!mUsersCleaningUp.isEmpty()) {
|
||||
// TODO(b/186600837): this seems common on multi sensor devices
|
||||
Log.e(getTag(), "Cleanup not finished before shutdown - pending: "
|
||||
+ mUsersCleaningUp.size());
|
||||
}
|
||||
|
||||
// Disable the test HAL after the sensor becomes idle.
|
||||
setTestHalEnabled(false);
|
||||
}
|
||||
|
||||
@@ -481,14 +481,24 @@ public class AuthController extends SystemUI implements CommandQueue.Callbacks,
|
||||
*/
|
||||
@Override
|
||||
public void onBiometricAuthenticated() {
|
||||
mCurrentDialog.onAuthenticationSucceeded();
|
||||
if (DEBUG) Log.d(TAG, "onBiometricAuthenticated: ");
|
||||
|
||||
if (mCurrentDialog != null) {
|
||||
mCurrentDialog.onAuthenticationSucceeded();
|
||||
} else {
|
||||
Log.w(TAG, "onBiometricAuthenticated callback but dialog gone");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onBiometricHelp(String message) {
|
||||
if (DEBUG) Log.d(TAG, "onBiometricHelp: " + message);
|
||||
|
||||
mCurrentDialog.onHelp(message);
|
||||
if (mCurrentDialog != null) {
|
||||
mCurrentDialog.onHelp(message);
|
||||
} else {
|
||||
Log.w(TAG, "onBiometricHelp callback but dialog gone");
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@@ -527,19 +537,23 @@ public class AuthController extends SystemUI implements CommandQueue.Callbacks,
|
||||
final boolean isSoftError = (error == BiometricConstants.BIOMETRIC_PAUSED_REJECTED
|
||||
|| error == BiometricConstants.BIOMETRIC_ERROR_TIMEOUT);
|
||||
|
||||
if (mCurrentDialog.isAllowDeviceCredentials() && isLockout) {
|
||||
if (DEBUG) Log.d(TAG, "onBiometricError, lockout");
|
||||
mCurrentDialog.animateToCredentialUI();
|
||||
} else if (isSoftError) {
|
||||
final String errorMessage = (error == BiometricConstants.BIOMETRIC_PAUSED_REJECTED)
|
||||
? mContext.getString(R.string.biometric_not_recognized)
|
||||
: getErrorString(modality, error, vendorCode);
|
||||
if (DEBUG) Log.d(TAG, "onBiometricError, soft error: " + errorMessage);
|
||||
mCurrentDialog.onAuthenticationFailed(errorMessage);
|
||||
if (mCurrentDialog != null) {
|
||||
if (mCurrentDialog.isAllowDeviceCredentials() && isLockout) {
|
||||
if (DEBUG) Log.d(TAG, "onBiometricError, lockout");
|
||||
mCurrentDialog.animateToCredentialUI();
|
||||
} else if (isSoftError) {
|
||||
final String errorMessage = (error == BiometricConstants.BIOMETRIC_PAUSED_REJECTED)
|
||||
? mContext.getString(R.string.biometric_not_recognized)
|
||||
: getErrorString(modality, error, vendorCode);
|
||||
if (DEBUG) Log.d(TAG, "onBiometricError, soft error: " + errorMessage);
|
||||
mCurrentDialog.onAuthenticationFailed(errorMessage);
|
||||
} else {
|
||||
final String errorMessage = getErrorString(modality, error, vendorCode);
|
||||
if (DEBUG) Log.d(TAG, "onBiometricError, hard error: " + errorMessage);
|
||||
mCurrentDialog.onError(errorMessage);
|
||||
}
|
||||
} else {
|
||||
final String errorMessage = getErrorString(modality, error, vendorCode);
|
||||
if (DEBUG) Log.d(TAG, "onBiometricError, hard error: " + errorMessage);
|
||||
mCurrentDialog.onError(errorMessage);
|
||||
Log.w(TAG, "onBiometricError callback but dialog is gone");
|
||||
}
|
||||
|
||||
onCancelUdfps();
|
||||
|
||||
@@ -48,16 +48,9 @@ public class BiometricStrengthController {
|
||||
*/
|
||||
private static final String KEY_BIOMETRIC_STRENGTHS = "biometric_strengths";
|
||||
|
||||
/**
|
||||
* Default (no-op) value of the flag KEY_BIOMETRIC_STRENGTHS
|
||||
*/
|
||||
public static final String DEFAULT_BIOMETRIC_STRENGTHS = null;
|
||||
|
||||
private DeviceConfig.OnPropertiesChangedListener mDeviceConfigListener = properties -> {
|
||||
for (String name : properties.getKeyset()) {
|
||||
if (KEY_BIOMETRIC_STRENGTHS.equals(name)) {
|
||||
updateStrengths();
|
||||
}
|
||||
if (properties.getKeyset().contains(KEY_BIOMETRIC_STRENGTHS)) {
|
||||
updateStrengths();
|
||||
}
|
||||
};
|
||||
|
||||
@@ -75,7 +68,17 @@ public class BiometricStrengthController {
|
||||
* has been changed.
|
||||
*/
|
||||
public void updateStrengths() {
|
||||
final Map<Integer, Integer> idToStrength = getIdToStrengthMap();
|
||||
final String newValue = DeviceConfig.getString(DeviceConfig.NAMESPACE_BIOMETRICS,
|
||||
KEY_BIOMETRIC_STRENGTHS, "null");
|
||||
if ("null".equals(newValue) || newValue.isEmpty()) {
|
||||
revertStrengths();
|
||||
} else {
|
||||
updateStrengths(newValue);
|
||||
}
|
||||
}
|
||||
|
||||
private void updateStrengths(String flags) {
|
||||
final Map<Integer, Integer> idToStrength = getIdToStrengthMap(flags);
|
||||
if (idToStrength == null) {
|
||||
return;
|
||||
}
|
||||
@@ -91,12 +94,18 @@ public class BiometricStrengthController {
|
||||
}
|
||||
}
|
||||
|
||||
private void revertStrengths() {
|
||||
for (BiometricSensor sensor : mService.mSensors) {
|
||||
Slog.d(TAG, "updateStrengths: revert sensorId=" + sensor.id + " to oemStrength="
|
||||
+ sensor.oemStrength);
|
||||
sensor.updateStrength(sensor.oemStrength);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @return a map of <ID, Strength>
|
||||
*/
|
||||
private Map<Integer, Integer> getIdToStrengthMap() {
|
||||
final String flags = DeviceConfig.getString(DeviceConfig.NAMESPACE_BIOMETRICS,
|
||||
KEY_BIOMETRIC_STRENGTHS, DEFAULT_BIOMETRIC_STRENGTHS);
|
||||
private static Map<Integer, Integer> getIdToStrengthMap(String flags) {
|
||||
if (flags == null || flags.isEmpty()) {
|
||||
Slog.d(TAG, "Flags are null or empty");
|
||||
return null;
|
||||
|
||||
@@ -82,7 +82,20 @@ public abstract class BaseClientMonitor extends LoggableMonitor
|
||||
private final int mCookie;
|
||||
boolean mAlreadyDone;
|
||||
|
||||
@NonNull protected Callback mCallback;
|
||||
// Use an empty callback by default since delayed operations can receive events
|
||||
// before they are started and cause NPE in subclasses that access this field directly.
|
||||
@NonNull protected Callback mCallback = new Callback() {
|
||||
@Override
|
||||
public void onClientStarted(@NonNull BaseClientMonitor clientMonitor) {
|
||||
Slog.e(TAG, "mCallback onClientStarted: called before set (should not happen)");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onClientFinished(@NonNull BaseClientMonitor clientMonitor,
|
||||
boolean success) {
|
||||
Slog.e(TAG, "mCallback onClientFinished: called before set (should not happen)");
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @return A ClientMonitorEnum constant defined in biometrics.proto
|
||||
|
||||
Reference in New Issue
Block a user