summaryrefslogtreecommitdiffstats
path: root/keystore/java/android
diff options
context:
space:
mode:
Diffstat (limited to 'keystore/java/android')
-rw-r--r--keystore/java/android/security/AndroidKeyStore.java4
-rw-r--r--keystore/java/android/security/KeyChain.java56
-rw-r--r--keystore/java/android/security/KeyGeneratorSpec.java38
-rw-r--r--keystore/java/android/security/KeyPairGeneratorSpec.java44
-rw-r--r--keystore/java/android/security/KeyStore.java3
-rw-r--r--keystore/java/android/security/KeyStoreKeyConstraints.java9
-rw-r--r--keystore/java/android/security/KeyStoreKeyGeneratorSpi.java4
-rw-r--r--keystore/java/android/security/KeyStoreKeySpec.java17
-rw-r--r--keystore/java/android/security/KeyStoreParameter.java38
-rw-r--r--keystore/java/android/security/KeyStoreSecretKeyFactorySpi.java6
-rw-r--r--keystore/java/android/security/NewFingerprintEnrolledException.java41
11 files changed, 249 insertions, 11 deletions
diff --git a/keystore/java/android/security/AndroidKeyStore.java b/keystore/java/android/security/AndroidKeyStore.java
index 55a8b4f..c5b6a68 100644
--- a/keystore/java/android/security/AndroidKeyStore.java
+++ b/keystore/java/android/security/AndroidKeyStore.java
@@ -542,6 +542,10 @@ public class AndroidKeyStore extends KeyStoreSpi {
KeyStoreKeyConstraints.UserAuthenticator.allToKeymaster(
params.getUserAuthenticators()));
}
+ if (params.isInvalidatedOnNewFingerprintEnrolled()) {
+ // TODO: Add the invalidate on fingerprint enrolled constraint once Keymaster supports
+ // that.
+ }
if (params.getUserAuthenticationValidityDurationSeconds() != -1) {
args.addInt(KeymasterDefs.KM_TAG_AUTH_TIMEOUT,
params.getUserAuthenticationValidityDurationSeconds());
diff --git a/keystore/java/android/security/KeyChain.java b/keystore/java/android/security/KeyChain.java
index dfa41e8..e9c24dd 100644
--- a/keystore/java/android/security/KeyChain.java
+++ b/keystore/java/android/security/KeyChain.java
@@ -127,6 +127,12 @@ public final class KeyChain {
* Extra for use with {@link #ACTION_CHOOSER}
* @hide Also used by KeyChainActivity implementation
*/
+ public static final String EXTRA_URL = "url";
+
+ /**
+ * Extra for use with {@link #ACTION_CHOOSER}
+ * @hide Also used by KeyChainActivity implementation
+ */
public static final String EXTRA_ALIAS = "alias";
/**
@@ -224,6 +230,51 @@ public final class KeyChain {
* selected alias or null will be returned via the
* KeyChainAliasCallback callback.
*
+ * <p>The device or profile owner can intercept this before the activity
+ * is shown, to pick a specific private key alias.
+ *
+ * <p>{@code keyTypes} and {@code issuers} may be used to
+ * highlight suggested choices to the user, although to cope with
+ * sometimes erroneous values provided by servers, the user may be
+ * able to override these suggestions.
+ *
+ * <p>{@code host} and {@code port} may be used to give the user
+ * more context about the server requesting the credentials.
+ *
+ * <p>{@code alias} allows the chooser to preselect an existing
+ * alias which will still be subject to user confirmation.
+ *
+ * @param activity The {@link Activity} context to use for
+ * launching the new sub-Activity to prompt the user to select
+ * a private key; used only to call startActivity(); must not
+ * be null.
+ * @param response Callback to invoke when the request completes;
+ * must not be null
+ * @param keyTypes The acceptable types of asymmetric keys such as
+ * "RSA" or "DSA", or a null array.
+ * @param issuers The acceptable certificate issuers for the
+ * certificate matching the private key, or null.
+ * @param host The host name of the server requesting the
+ * certificate, or null if unavailable.
+ * @param port The port number of the server requesting the
+ * certificate, or -1 if unavailable.
+ * @param alias The alias to preselect if available, or null if
+ * unavailable.
+ */
+ public static void choosePrivateKeyAlias(Activity activity, KeyChainAliasCallback response,
+ String[] keyTypes, Principal[] issuers, String host, int port, String alias) {
+ choosePrivateKeyAlias(activity, response, keyTypes, issuers, host, port, null, alias);
+ }
+
+ /**
+ * Launches an {@code Activity} for the user to select the alias
+ * for a private key and certificate pair for authentication. The
+ * selected alias or null will be returned via the
+ * KeyChainAliasCallback callback.
+ *
+ * <p>The device or profile owner can intercept this before the activity
+ * is shown, to pick a specific private key alias.</p>
+ *
* <p>{@code keyTypes} and {@code issuers} may be used to
* highlight suggested choices to the user, although to cope with
* sometimes erroneous values provided by servers, the user may be
@@ -249,12 +300,14 @@ public final class KeyChain {
* certificate, or null if unavailable.
* @param port The port number of the server requesting the
* certificate, or -1 if unavailable.
+ * @param url The full url the server is requesting the certificate
+ * for, or null if unavailable.
* @param alias The alias to preselect if available, or null if
* unavailable.
*/
public static void choosePrivateKeyAlias(Activity activity, KeyChainAliasCallback response,
String[] keyTypes, Principal[] issuers,
- String host, int port,
+ String host, int port, String url,
String alias) {
/*
* TODO currently keyTypes, issuers are unused. They are meant
@@ -283,6 +336,7 @@ public final class KeyChain {
intent.putExtra(EXTRA_RESPONSE, new AliasResponse(response));
intent.putExtra(EXTRA_HOST, host);
intent.putExtra(EXTRA_PORT, port);
+ intent.putExtra(EXTRA_URL, url);
intent.putExtra(EXTRA_ALIAS, alias);
// the PendingIntent is used to get calling package name
intent.putExtra(EXTRA_SENDER, PendingIntent.getActivity(activity, 0, new Intent(), 0));
diff --git a/keystore/java/android/security/KeyGeneratorSpec.java b/keystore/java/android/security/KeyGeneratorSpec.java
index 5bed2e1..29b1209 100644
--- a/keystore/java/android/security/KeyGeneratorSpec.java
+++ b/keystore/java/android/security/KeyGeneratorSpec.java
@@ -55,6 +55,7 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
private final boolean mRandomizedEncryptionRequired;
private final @KeyStoreKeyConstraints.UserAuthenticatorEnum int mUserAuthenticators;
private final int mUserAuthenticationValidityDurationSeconds;
+ private final boolean mInvalidatedOnNewFingerprintEnrolled;
private KeyGeneratorSpec(
Context context,
@@ -69,7 +70,8 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
@KeyStoreKeyConstraints.BlockModeEnum int blockModes,
boolean randomizedEncryptionRequired,
@KeyStoreKeyConstraints.UserAuthenticatorEnum int userAuthenticators,
- int userAuthenticationValidityDurationSeconds) {
+ int userAuthenticationValidityDurationSeconds,
+ boolean invalidatedOnNewFingerprintEnrolled) {
if (context == null) {
throw new IllegalArgumentException("context == null");
} else if (TextUtils.isEmpty(keyStoreAlias)) {
@@ -93,6 +95,7 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
mRandomizedEncryptionRequired = randomizedEncryptionRequired;
mUserAuthenticators = userAuthenticators;
mUserAuthenticationValidityDurationSeconds = userAuthenticationValidityDurationSeconds;
+ mInvalidatedOnNewFingerprintEnrolled = invalidatedOnNewFingerprintEnrolled;
}
/**
@@ -207,6 +210,19 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
}
/**
+ * Returns {@code true} if this key must be permanently invalidated once a new fingerprint is
+ * enrolled. This constraint only has effect if fingerprint reader is one of the user
+ * authenticators protecting access to this key.
+ *
+ * @see #getUserAuthenticators()
+ *
+ * @hide
+ */
+ public boolean isInvalidatedOnNewFingerprintEnrolled() {
+ return mInvalidatedOnNewFingerprintEnrolled;
+ }
+
+ /**
* Returns {@code true} if the key must be encrypted in the {@link java.security.KeyStore}.
*/
public boolean isEncryptionRequired() {
@@ -227,6 +243,7 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
private boolean mRandomizedEncryptionRequired = true;
private @KeyStoreKeyConstraints.UserAuthenticatorEnum int mUserAuthenticators;
private int mUserAuthenticationValidityDurationSeconds = -1;
+ private boolean mInvalidatedOnNewFingerprintEnrolled;
/**
* Creates a new instance of the {@code Builder} with the given {@code context}. The
@@ -434,6 +451,22 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
}
/**
+ * Sets whether this key must be invalidated (permanently) once a new fingerprint is
+ * enrolled. This only has effect if fingerprint reader is one of the user authenticators
+ * protecting access to the key.
+ *
+ * <p>By default, enrolling a new fingerprint does not invalidate the key.
+ *
+ * @see #setUserAuthenticators(Set)
+ *
+ * @hide
+ */
+ public Builder setInvalidatedOnNewFingerprintEnrolled(boolean invalidated) {
+ mInvalidatedOnNewFingerprintEnrolled = invalidated;
+ return this;
+ }
+
+ /**
* Builds a new instance instance of {@code KeyGeneratorSpec}.
*
* @throws IllegalArgumentException if a required field is missing or violates a constraint.
@@ -451,7 +484,8 @@ public class KeyGeneratorSpec implements AlgorithmParameterSpec {
mBlockModes,
mRandomizedEncryptionRequired,
mUserAuthenticators,
- mUserAuthenticationValidityDurationSeconds);
+ mUserAuthenticationValidityDurationSeconds,
+ mInvalidatedOnNewFingerprintEnrolled);
}
}
}
diff --git a/keystore/java/android/security/KeyPairGeneratorSpec.java b/keystore/java/android/security/KeyPairGeneratorSpec.java
index 8945701..1c7e2ce 100644
--- a/keystore/java/android/security/KeyPairGeneratorSpec.java
+++ b/keystore/java/android/security/KeyPairGeneratorSpec.java
@@ -92,6 +92,8 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
private final int mUserAuthenticationValidityDurationSeconds;
+ private final boolean mInvalidatedOnNewFingerprintEnrolled;
+
/**
* Parameter specification for the "{@code AndroidKeyPairGenerator}"
* instance of the {@link java.security.KeyPairGenerator} API. The
@@ -136,7 +138,8 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
@KeyStoreKeyConstraints.BlockModeEnum int blockModes,
boolean randomizedEncryptionRequired,
@KeyStoreKeyConstraints.UserAuthenticatorEnum int userAuthenticators,
- int userAuthenticationValidityDurationSeconds) {
+ int userAuthenticationValidityDurationSeconds,
+ boolean invalidatedOnNewFingerprintEnrolled) {
if (context == null) {
throw new IllegalArgumentException("context == null");
} else if (TextUtils.isEmpty(keyStoreAlias)) {
@@ -177,6 +180,7 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
mRandomizedEncryptionRequired = randomizedEncryptionRequired;
mUserAuthenticators = userAuthenticators;
mUserAuthenticationValidityDurationSeconds = userAuthenticationValidityDurationSeconds;
+ mInvalidatedOnNewFingerprintEnrolled = invalidatedOnNewFingerprintEnrolled;
}
/**
@@ -186,6 +190,7 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
public KeyPairGeneratorSpec(Context context, String keyStoreAlias, String keyType, int keySize,
AlgorithmParameterSpec spec, X500Principal subjectDN, BigInteger serialNumber,
Date startDate, Date endDate, int flags) {
+
this(context,
keyStoreAlias,
keyType,
@@ -205,7 +210,8 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
0,
true,
0,
- -1);
+ -1,
+ false);
}
/**
@@ -411,6 +417,19 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
}
/**
+ * Returns {@code true} if this key must be permanently invalidated once a new fingerprint is
+ * enrolled. This constraint only has effect if fingerprint reader is one of the user
+ * authenticators protecting access to this key.
+ *
+ * @see #getUserAuthenticators()
+ *
+ * @hide
+ */
+ public boolean isInvalidatedOnNewFingerprintEnrolled() {
+ return mInvalidatedOnNewFingerprintEnrolled;
+ }
+
+ /**
* Builder class for {@link KeyPairGeneratorSpec} objects.
* <p>
* This will build a parameter spec for use with the <a href="{@docRoot}
@@ -472,6 +491,8 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
private int mUserAuthenticationValidityDurationSeconds = -1;
+ private boolean mInvalidatedOnNewFingerprintEnrolled;
+
/**
* Creates a new instance of the {@code Builder} with the given
* {@code context}. The {@code context} passed in may be used to pop up
@@ -779,6 +800,22 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
}
/**
+ * Sets whether this key must be invalidated (permanently) once a new fingerprint is
+ * enrolled. This only has effect if fingerprint reader is one of the user authenticators
+ * protecting access to the key.
+ *
+ * <p>By default, enrolling a new fingerprint does not invalidate the key.
+ *
+ * @see #setUserAuthenticators(Set)
+ *
+ * @hide
+ */
+ public Builder setInvalidatedOnNewFingerprintEnrolled(boolean invalidated) {
+ mInvalidatedOnNewFingerprintEnrolled = invalidated;
+ return this;
+ }
+
+ /**
* Builds the instance of the {@code KeyPairGeneratorSpec}.
*
* @throws IllegalArgumentException if a required field is missing
@@ -804,7 +841,8 @@ public final class KeyPairGeneratorSpec implements AlgorithmParameterSpec {
mBlockModes,
mRandomizedEncryptionRequired,
mUserAuthenticators,
- mUserAuthenticationValidityDurationSeconds);
+ mUserAuthenticationValidityDurationSeconds,
+ mInvalidatedOnNewFingerprintEnrolled);
}
}
}
diff --git a/keystore/java/android/security/KeyStore.java b/keystore/java/android/security/KeyStore.java
index 84a664e..5af0527 100644
--- a/keystore/java/android/security/KeyStore.java
+++ b/keystore/java/android/security/KeyStore.java
@@ -552,6 +552,9 @@ public class KeyStore {
return new KeyNotYetValidException();
case KeymasterDefs.KM_ERROR_KEY_USER_NOT_AUTHENTICATED:
return new UserNotAuthenticatedException();
+ // TODO: Handle TBD Keymaster error code "invalid key: new fingerprint enrolled"
+ // case KeymasterDefs.KM_ERROR_TBD
+ // return new NewFingerprintEnrolledException();
default:
return new CryptoOperationException("Crypto operation failed", e);
}
diff --git a/keystore/java/android/security/KeyStoreKeyConstraints.java b/keystore/java/android/security/KeyStoreKeyConstraints.java
index cde27f9..e61092f 100644
--- a/keystore/java/android/security/KeyStoreKeyConstraints.java
+++ b/keystore/java/android/security/KeyStoreKeyConstraints.java
@@ -829,6 +829,9 @@ public abstract class KeyStoreKeyConstraints {
/** Lock screen. */
public static final int LOCK_SCREEN = 1 << 0;
+ /** Fingerprint reader/sensor. */
+ public static final int FINGERPRINT_READER = 1 << 1;
+
/**
* @hide
*/
@@ -836,6 +839,8 @@ public abstract class KeyStoreKeyConstraints {
switch (userAuthenticator) {
case LOCK_SCREEN:
return KeymasterDefs.HW_AUTH_PASSWORD;
+ case FINGERPRINT_READER:
+ return KeymasterDefs.HW_AUTH_FINGERPRINT;
default:
throw new IllegalArgumentException(
"Unknown user authenticator: " + userAuthenticator);
@@ -849,6 +854,8 @@ public abstract class KeyStoreKeyConstraints {
switch (userAuthenticator) {
case KeymasterDefs.HW_AUTH_PASSWORD:
return LOCK_SCREEN;
+ case FINGERPRINT_READER:
+ return FINGERPRINT_READER;
default:
throw new IllegalArgumentException(
"Unknown user authenticator: " + userAuthenticator);
@@ -894,6 +901,8 @@ public abstract class KeyStoreKeyConstraints {
switch (userAuthenticator) {
case LOCK_SCREEN:
return "LOCK_SCREEN";
+ case FINGERPRINT_READER:
+ return "FINGERPRINT_READER";
default:
throw new IllegalArgumentException(
"Unknown user authenticator: " + userAuthenticator);
diff --git a/keystore/java/android/security/KeyStoreKeyGeneratorSpi.java b/keystore/java/android/security/KeyStoreKeyGeneratorSpi.java
index a500786..b39d16d 100644
--- a/keystore/java/android/security/KeyStoreKeyGeneratorSpi.java
+++ b/keystore/java/android/security/KeyStoreKeyGeneratorSpi.java
@@ -171,6 +171,10 @@ public abstract class KeyStoreKeyGeneratorSpi extends KeyGeneratorSpi {
KeyStoreKeyConstraints.UserAuthenticator.allToKeymaster(
spec.getUserAuthenticators()));
}
+ if (spec.isInvalidatedOnNewFingerprintEnrolled()) {
+ // TODO: Add the invalidate on fingerprint enrolled constraint once Keymaster supports
+ // that.
+ }
if (spec.getUserAuthenticationValidityDurationSeconds() != -1) {
args.addInt(KeymasterDefs.KM_TAG_AUTH_TIMEOUT,
spec.getUserAuthenticationValidityDurationSeconds());
diff --git a/keystore/java/android/security/KeyStoreKeySpec.java b/keystore/java/android/security/KeyStoreKeySpec.java
index df4c958..256d9b3 100644
--- a/keystore/java/android/security/KeyStoreKeySpec.java
+++ b/keystore/java/android/security/KeyStoreKeySpec.java
@@ -40,7 +40,7 @@ public class KeyStoreKeySpec implements KeySpec {
private final @KeyStoreKeyConstraints.UserAuthenticatorEnum int mUserAuthenticators;
private final @KeyStoreKeyConstraints.UserAuthenticatorEnum int mTeeEnforcedUserAuthenticators;
private final int mUserAuthenticationValidityDurationSeconds;
-
+ private final boolean mInvalidatedOnNewFingerprintEnrolled;
/**
* @hide
@@ -58,7 +58,8 @@ public class KeyStoreKeySpec implements KeySpec {
@KeyStoreKeyConstraints.BlockModeEnum int blockModes,
@KeyStoreKeyConstraints.UserAuthenticatorEnum int userAuthenticators,
@KeyStoreKeyConstraints.UserAuthenticatorEnum int teeEnforcedUserAuthenticators,
- int userAuthenticationValidityDurationSeconds) {
+ int userAuthenticationValidityDurationSeconds,
+ boolean invalidatedOnNewFingerprintEnrolled) {
mKeystoreAlias = keystoreKeyAlias;
mOrigin = origin;
mKeySize = keySize;
@@ -73,6 +74,7 @@ public class KeyStoreKeySpec implements KeySpec {
mUserAuthenticators = userAuthenticators;
mTeeEnforcedUserAuthenticators = teeEnforcedUserAuthenticators;
mUserAuthenticationValidityDurationSeconds = userAuthenticationValidityDurationSeconds;
+ mInvalidatedOnNewFingerprintEnrolled = invalidatedOnNewFingerprintEnrolled;
}
/**
@@ -187,4 +189,15 @@ public class KeyStoreKeySpec implements KeySpec {
public int getUserAuthenticationValidityDurationSeconds() {
return mUserAuthenticationValidityDurationSeconds;
}
+
+ /**
+ * Returns {@code true} if this key will be permanently invalidated once a new fingerprint is
+ * enrolled. This constraint only has effect if fingerprint reader is one of the user
+ * authenticators protecting access to this key.
+ *
+ * @see #getUserAuthenticators()
+ */
+ public boolean isInvalidatedOnNewFingerprintEnrolled() {
+ return mInvalidatedOnNewFingerprintEnrolled;
+ }
}
diff --git a/keystore/java/android/security/KeyStoreParameter.java b/keystore/java/android/security/KeyStoreParameter.java
index c9b7c36..ff63a25 100644
--- a/keystore/java/android/security/KeyStoreParameter.java
+++ b/keystore/java/android/security/KeyStoreParameter.java
@@ -57,6 +57,7 @@ public final class KeyStoreParameter implements ProtectionParameter {
private final boolean mRandomizedEncryptionRequired;
private final @KeyStoreKeyConstraints.UserAuthenticatorEnum int mUserAuthenticators;
private final int mUserAuthenticationValidityDurationSeconds;
+ private final boolean mInvalidatedOnNewFingerprintEnrolled;
private KeyStoreParameter(int flags,
Date keyValidityStart,
@@ -68,7 +69,8 @@ public final class KeyStoreParameter implements ProtectionParameter {
@KeyStoreKeyConstraints.BlockModeEnum int blockModes,
boolean randomizedEncryptionRequired,
@KeyStoreKeyConstraints.UserAuthenticatorEnum int userAuthenticators,
- int userAuthenticationValidityDurationSeconds) {
+ int userAuthenticationValidityDurationSeconds,
+ boolean invalidatedOnNewFingerprintEnrolled) {
if ((userAuthenticationValidityDurationSeconds < 0)
&& (userAuthenticationValidityDurationSeconds != -1)) {
throw new IllegalArgumentException(
@@ -86,6 +88,7 @@ public final class KeyStoreParameter implements ProtectionParameter {
mRandomizedEncryptionRequired = randomizedEncryptionRequired;
mUserAuthenticators = userAuthenticators;
mUserAuthenticationValidityDurationSeconds = userAuthenticationValidityDurationSeconds;
+ mInvalidatedOnNewFingerprintEnrolled = invalidatedOnNewFingerprintEnrolled;
}
/**
@@ -230,6 +233,19 @@ public final class KeyStoreParameter implements ProtectionParameter {
}
/**
+ * Returns {@code true} if this key must be permanently invalidated once a new fingerprint is
+ * enrolled. This constraint only has effect if fingerprint reader is one of the user
+ * authenticators protecting access to this key.
+ *
+ * @see #getUserAuthenticators()
+ *
+ * @hide
+ */
+ public boolean isInvalidatedOnNewFingerprintEnrolled() {
+ return mInvalidatedOnNewFingerprintEnrolled;
+ }
+
+ /**
* Builder class for {@link KeyStoreParameter} objects.
* <p>
* This will build protection parameters for use with the
@@ -258,6 +274,7 @@ public final class KeyStoreParameter implements ProtectionParameter {
private boolean mRandomizedEncryptionRequired = true;
private @KeyStoreKeyConstraints.UserAuthenticatorEnum int mUserAuthenticators;
private int mUserAuthenticationValidityDurationSeconds = -1;
+ private boolean mInvalidatedOnNewFingerprintEnrolled;
/**
* Creates a new instance of the {@code Builder} with the given
@@ -480,6 +497,22 @@ public final class KeyStoreParameter implements ProtectionParameter {
}
/**
+ * Sets whether this key must be invalidated (permanently) whenever a new fingerprint is
+ * enrolled. This only has effect if fingerprint reader is one of the user authenticators
+ * protecting access to the key.
+ *
+ * <p>By default, enrolling a new fingerprint does not invalidate the key.
+ *
+ * @see #setUserAuthenticators(Set)
+ *
+ * @hide
+ */
+ public Builder setInvalidatedOnNewFingerprintEnrolled(boolean invalidated) {
+ mInvalidatedOnNewFingerprintEnrolled = invalidated;
+ return this;
+ }
+
+ /**
* Builds the instance of the {@code KeyStoreParameter}.
*
* @throws IllegalArgumentException if a required field is missing
@@ -496,7 +529,8 @@ public final class KeyStoreParameter implements ProtectionParameter {
mBlockModes,
mRandomizedEncryptionRequired,
mUserAuthenticators,
- mUserAuthenticationValidityDurationSeconds);
+ mUserAuthenticationValidityDurationSeconds,
+ mInvalidatedOnNewFingerprintEnrolled);
}
}
}
diff --git a/keystore/java/android/security/KeyStoreSecretKeyFactorySpi.java b/keystore/java/android/security/KeyStoreSecretKeyFactorySpi.java
index 09f0b00..8bf228a 100644
--- a/keystore/java/android/security/KeyStoreSecretKeyFactorySpi.java
+++ b/keystore/java/android/security/KeyStoreSecretKeyFactorySpi.java
@@ -143,6 +143,9 @@ public class KeyStoreSecretKeyFactorySpi extends SecretKeyFactorySpi {
Integer userAuthenticationValidityDurationSeconds =
KeymasterUtils.getInt(keyCharacteristics, KeymasterDefs.KM_TAG_AUTH_TIMEOUT);
+ // TODO: Populate the value below from key characteristics once Keymaster is ready.
+ boolean invalidatedOnNewFingerprintEnrolled = false;
+
return new KeyStoreKeySpec(entryAlias,
origin,
keySize,
@@ -157,7 +160,8 @@ public class KeyStoreSecretKeyFactorySpi extends SecretKeyFactorySpi {
userAuthenticators,
teeEnforcedUserAuthenticators,
((userAuthenticationValidityDurationSeconds != null)
- ? userAuthenticationValidityDurationSeconds : -1));
+ ? userAuthenticationValidityDurationSeconds : -1),
+ invalidatedOnNewFingerprintEnrolled);
}
@Override
diff --git a/keystore/java/android/security/NewFingerprintEnrolledException.java b/keystore/java/android/security/NewFingerprintEnrolledException.java
new file mode 100644
index 0000000..6da4a2a
--- /dev/null
+++ b/keystore/java/android/security/NewFingerprintEnrolledException.java
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2015 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.security;
+
+/**
+ * Indicates that a cryptographic operation could not be performed because the key used by the
+ * operation is permanently invalid because a new fingerprint was enrolled.
+ *
+ * @hide
+ */
+public class NewFingerprintEnrolledException extends CryptoOperationException {
+
+ /**
+ * Constructs a new {@code NewFingerprintEnrolledException} without detail message and cause.
+ */
+ public NewFingerprintEnrolledException() {
+ super("Invalid key: new fingerprint enrolled");
+ }
+
+ /**
+ * Constructs a new {@code NewFingerprintEnrolledException} with the provided detail message and
+ * no cause.
+ */
+ public NewFingerprintEnrolledException(String message) {
+ super(message);
+ }
+}