Track Keymaster changes.

* MAC length is now specified as a parameters to the begin operation
  instead of as a parameter at key generation/import time.
* KM_TAG_MAC_LENGTH is now in bits instead of in bytes.

Change-Id: I752fe232d11d3ac39a575a48948215d84ded8fb9
This commit is contained in:
Alex Klyubin
2015-04-30 10:50:45 -07:00
parent 403ac2d64f
commit 7ea5090264
4 changed files with 15 additions and 30 deletions

View File

@@ -486,16 +486,6 @@ public class AndroidKeyStore extends KeyStoreSpi {
}
}
args.addInts(KeymasterDefs.KM_TAG_DIGEST, keymasterDigests);
if (keymasterDigests.length > 0) {
// TODO: Remove MAC length constraint once Keymaster API no longer requires it.
// This code will blow up if mode than one digest is specified.
int digestOutputSizeBytes =
KeymasterUtils.getDigestOutputSizeBytes(keymasterDigests[0]);
if (digestOutputSizeBytes != -1) {
// TODO: Switch to bits instead of bytes, once this is fixed in Keymaster
args.addInt(KeymasterDefs.KM_TAG_MAC_LENGTH, digestOutputSizeBytes);
}
}
if (keymasterAlgorithm == KeymasterDefs.KM_ALGORITHM_HMAC) {
if (keymasterDigests.length == 0) {
throw new KeyStoreException("At least one digest algorithm must be specified"

View File

@@ -67,7 +67,7 @@ public abstract class KeyStoreHmacSpi extends MacSpi implements KeyStoreCryptoOp
private final KeyStore mKeyStore = KeyStore.getInstance();
private final int mKeymasterDigest;
private final int mMacSizeBytes;
private final int mMacSizeBits;
// Fields below are populated by engineInit and should be preserved after engineDoFinal.
private KeyStoreSecretKey mKey;
@@ -79,12 +79,12 @@ public abstract class KeyStoreHmacSpi extends MacSpi implements KeyStoreCryptoOp
protected KeyStoreHmacSpi(int keymasterDigest) {
mKeymasterDigest = keymasterDigest;
mMacSizeBytes = KeymasterUtils.getDigestOutputSizeBytes(keymasterDigest);
mMacSizeBits = KeymasterUtils.getDigestOutputSizeBits(keymasterDigest);
}
@Override
protected int engineGetMacLength() {
return mMacSizeBytes;
return (mMacSizeBits + 7) / 8;
}
@Override
@@ -158,14 +158,16 @@ public abstract class KeyStoreHmacSpi extends MacSpi implements KeyStoreCryptoOp
KeymasterArguments keymasterArgs = new KeymasterArguments();
keymasterArgs.addInt(KeymasterDefs.KM_TAG_ALGORITHM, KeymasterDefs.KM_ALGORITHM_HMAC);
keymasterArgs.addInt(KeymasterDefs.KM_TAG_DIGEST, mKeymasterDigest);
keymasterArgs.addInt(KeymasterDefs.KM_TAG_MAC_LENGTH, mMacSizeBits);
KeymasterArguments keymasterOutputArgs = new KeymasterArguments();
OperationResult opResult = mKeyStore.begin(
mKey.getAlias(),
KeymasterDefs.KM_PURPOSE_SIGN,
true,
keymasterArgs,
null,
new KeymasterArguments());
null, // no additional entropy needed for HMAC because it's deterministic
keymasterOutputArgs);
if (opResult == null) {
throw new KeyStoreConnectException();
} else if ((opResult.resultCode != KeyStore.NO_ERROR)

View File

@@ -45,7 +45,7 @@ public abstract class KeyStoreKeyGeneratorSpi extends KeyGeneratorSpi {
protected HmacBase(int keymasterDigest) {
super(KeymasterDefs.KM_ALGORITHM_HMAC,
keymasterDigest,
KeymasterUtils.getDigestOutputSizeBytes(keymasterDigest) * 8);
KeymasterUtils.getDigestOutputSizeBits(keymasterDigest));
}
}
@@ -120,13 +120,6 @@ public abstract class KeyStoreKeyGeneratorSpi extends KeyGeneratorSpi {
args.addInt(KeymasterDefs.KM_TAG_ALGORITHM, mKeymasterAlgorithm);
if (mKeymasterDigest != -1) {
args.addInt(KeymasterDefs.KM_TAG_DIGEST, mKeymasterDigest);
int digestOutputSizeBytes =
KeymasterUtils.getDigestOutputSizeBytes(mKeymasterDigest);
if (digestOutputSizeBytes != -1) {
// TODO: Remove MAC length constraint once Keymaster API no longer requires it.
// TODO: Switch to bits instead of bytes, once this is fixed in Keymaster
args.addInt(KeymasterDefs.KM_TAG_MAC_LENGTH, digestOutputSizeBytes);
}
}
if (mKeymasterAlgorithm == KeymasterDefs.KM_ALGORITHM_HMAC) {
if (mKeymasterDigest == -1) {

View File

@@ -179,22 +179,22 @@ public abstract class KeymasterUtils {
return result;
}
public static int getDigestOutputSizeBytes(int keymasterDigest) {
public static int getDigestOutputSizeBits(int keymasterDigest) {
switch (keymasterDigest) {
case KeymasterDefs.KM_DIGEST_NONE:
return -1;
case KeymasterDefs.KM_DIGEST_MD5:
return 128 / 8;
return 128;
case KeymasterDefs.KM_DIGEST_SHA1:
return 160 / 8;
return 160;
case KeymasterDefs.KM_DIGEST_SHA_2_224:
return 224 / 8;
return 224;
case KeymasterDefs.KM_DIGEST_SHA_2_256:
return 256 / 8;
return 256;
case KeymasterDefs.KM_DIGEST_SHA_2_384:
return 384 / 8;
return 384;
case KeymasterDefs.KM_DIGEST_SHA_2_512:
return 512 / 8;
return 512;
default:
throw new IllegalArgumentException("Unknown digest: " + keymasterDigest);
}