Loading services/core/java/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManager.java +16 −8 Original line number Diff line number Diff line Loading @@ -232,9 +232,6 @@ public class RecoverableKeyStoreManager { throw new ServiceSpecificException(ERROR_INVALID_CERTIFICATE, e.getMessage()); } boolean wasInitialized = mDatabase.getRecoveryServiceCertPath(userId, uid, rootCertificateAlias) != null; // Save the chosen and validated certificate into database try { Log.d(TAG, "Saving the randomly chosen endpoint certificate to database"); Loading @@ -242,9 +239,11 @@ public class RecoverableKeyStoreManager { certPath) > 0) { mDatabase.setRecoveryServiceCertSerial(userId, uid, rootCertificateAlias, newSerial); if (wasInitialized) { Log.i(TAG, "This is a certificate change. Snapshot pending."); if (mDatabase.getSnapshotVersion(userId, uid) != null) { mDatabase.setShouldCreateSnapshot(userId, uid, true); Log.i(TAG, "This is a certificate change. Snapshot must be updated"); } else { Log.i(TAG, "This is a certificate change. Snapshot didn't exist"); } mDatabase.setCounterId(userId, uid, new SecureRandom().nextLong()); } Loading Loading @@ -350,8 +349,12 @@ public class RecoverableKeyStoreManager { return; } Log.i(TAG, "Updated server params. Snapshot pending."); if (mDatabase.getSnapshotVersion(userId, uid) != null) { mDatabase.setShouldCreateSnapshot(userId, uid, true); Log.i(TAG, "Updated server params. Snapshot must be updated"); } else { Log.i(TAG, "Updated server params. Snapshot didn't exist"); } } /** Loading Loading @@ -407,7 +410,12 @@ public class RecoverableKeyStoreManager { } Log.i(TAG, "Updated secret types. Snapshot pending."); if (mDatabase.getSnapshotVersion(userId, uid) != null) { mDatabase.setShouldCreateSnapshot(userId, uid, true); Log.i(TAG, "Updated secret types. Snapshot must be updated"); } else { Log.i(TAG, "Updated secret types. Snapshot didn't exist"); } } /** Loading services/core/java/com/android/server/locksettings/recoverablekeystore/storage/RecoverableKeyStoreDb.java +12 −3 Original line number Diff line number Diff line Loading @@ -789,11 +789,20 @@ public class RecoverableKeyStoreDb { } /** * Updates the snapshot version. * Updates a flag indicating that a new snapshot should be created. * It will be {@code false} until the first application key is added. * After that, the flag will be set to true, if one of the following values is updated: * <ul> * <li> List of application keys * <li> Server params. * <li> Lock-screen secret. * <li> Lock-screen secret type. * <li> Trusted hardware certificate. * </ul> * * @param userId The userId of the profile the application is running under. * @param uid The uid of the application. * @param pending The server parameters. * @param pending Should create snapshot flag. * @return The primary key of the inserted row, or -1 if failed. * * @hide Loading @@ -809,7 +818,7 @@ public class RecoverableKeyStoreDb { * * @param userId The userId of the profile the application is running under. * @param uid The uid of the application who initialized the local recovery components. * @return snapshot outdated flag. * @return should create snapshot flag * * @hide */ Loading services/tests/servicestests/src/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManagerTest.java +57 −7 Original line number Diff line number Diff line Loading @@ -301,6 +301,33 @@ public class RecoverableKeyStoreManagerTest { assertThat(mRecoverableKeyStoreDb.getRecoveryServicePublicKey(userId, uid)).isNull(); } @Test public void initRecoveryService_updatesShouldCreatesnapshotOnCertUpdate() throws Exception { int uid = Binder.getCallingUid(); int userId = UserHandle.getCallingUserId(); long certSerial = 1000L; mRecoverableKeyStoreDb.setShouldCreateSnapshot(userId, uid, false); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial)); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial + 1)); // Since there were no recoverable keys, new snapshot will not be created. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial + 2)); // Since there were a recoverable key, new serial number triggers snapshot creation assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); } @Test public void initRecoveryService_triesToFilterRootAlias() throws Exception { int uid = Binder.getCallingUid(); Loading Loading @@ -405,7 +432,8 @@ public class RecoverableKeyStoreManagerTest { assertThat(mRecoverableKeyStoreDb.getRecoveryServiceCertSerial(userId, uid, DEFAULT_ROOT_CERT_ALIAS)).isEqualTo(certSerial + 1); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); // There were no keys. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); } @Test Loading Loading @@ -479,10 +507,12 @@ public class RecoverableKeyStoreManagerTest { mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial)); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial)); // If the second update succeeds, getShouldCreateSnapshot() will return true. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); } Loading Loading @@ -935,7 +965,6 @@ public class RecoverableKeyStoreManagerTest { assertThat(recoveredKeys).hasSize(1); assertThat(recoveredKeys).containsKey(TEST_ALIAS); // TODO(76083050) Test the grant mechanism for the keys. } @Test Loading Loading @@ -974,7 +1003,6 @@ public class RecoverableKeyStoreManagerTest { assertThat(recoveredKeys).hasSize(1); assertThat(recoveredKeys).containsKey(TEST_ALIAS2); // TODO(76083050) Test the grant mechanism for the keys. } @Test Loading Loading @@ -1016,6 +1044,9 @@ public class RecoverableKeyStoreManagerTest { byte[] serverParams = new byte[] { 1 }; mRecoverableKeyStoreManager.setServerParams(serverParams); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setServerParams(serverParams); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); Loading @@ -1027,6 +1058,9 @@ public class RecoverableKeyStoreManagerTest { int userId = UserHandle.getCallingUserId(); mRecoverableKeyStoreManager.setServerParams(new byte[] { 1 }); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setServerParams(new byte[] { 2 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); Loading Loading @@ -1059,6 +1093,7 @@ public class RecoverableKeyStoreManagerTest { mRecoverableKeyStoreManager.setRecoverySecretTypes(secretTypes); // There were no keys. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); } Loading @@ -1070,6 +1105,9 @@ public class RecoverableKeyStoreManagerTest { int[] secretTypes = new int[] { 101 }; mRecoverableKeyStoreManager.setRecoverySecretTypes(secretTypes); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setRecoverySecretTypes(secretTypes); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); Loading @@ -1081,6 +1119,11 @@ public class RecoverableKeyStoreManagerTest { int userId = UserHandle.getCallingUserId(); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 101 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 102 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); Loading @@ -1102,9 +1145,8 @@ public class RecoverableKeyStoreManagerTest { int userId = UserHandle.getCallingUserId(); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 1 }); mRecoverableKeyStoreManager.generateKey(TEST_ALIAS); // Pretend that key was synced mRecoverableKeyStoreDb.setShouldCreateSnapshot(userId, uid, false); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 2 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); Loading Loading @@ -1175,6 +1217,14 @@ public class RecoverableKeyStoreManagerTest { return bytes; } private void generateKeyAndSimulateSync(int userId, int uid, int snapshotVersion) throws Exception{ mRecoverableKeyStoreManager.generateKey(TEST_ALIAS); // Simulate key sync. mRecoverableKeyStoreDb.setSnapshotVersion(userId, uid, snapshotVersion); mRecoverableKeyStoreDb.setShouldCreateSnapshot(userId, uid, false); } private AndroidKeyStoreSecretKey generateAndroidKeyStoreKey() throws Exception { KeyGenerator keyGenerator = KeyGenerator.getInstance( KEY_ALGORITHM, Loading Loading
services/core/java/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManager.java +16 −8 Original line number Diff line number Diff line Loading @@ -232,9 +232,6 @@ public class RecoverableKeyStoreManager { throw new ServiceSpecificException(ERROR_INVALID_CERTIFICATE, e.getMessage()); } boolean wasInitialized = mDatabase.getRecoveryServiceCertPath(userId, uid, rootCertificateAlias) != null; // Save the chosen and validated certificate into database try { Log.d(TAG, "Saving the randomly chosen endpoint certificate to database"); Loading @@ -242,9 +239,11 @@ public class RecoverableKeyStoreManager { certPath) > 0) { mDatabase.setRecoveryServiceCertSerial(userId, uid, rootCertificateAlias, newSerial); if (wasInitialized) { Log.i(TAG, "This is a certificate change. Snapshot pending."); if (mDatabase.getSnapshotVersion(userId, uid) != null) { mDatabase.setShouldCreateSnapshot(userId, uid, true); Log.i(TAG, "This is a certificate change. Snapshot must be updated"); } else { Log.i(TAG, "This is a certificate change. Snapshot didn't exist"); } mDatabase.setCounterId(userId, uid, new SecureRandom().nextLong()); } Loading Loading @@ -350,8 +349,12 @@ public class RecoverableKeyStoreManager { return; } Log.i(TAG, "Updated server params. Snapshot pending."); if (mDatabase.getSnapshotVersion(userId, uid) != null) { mDatabase.setShouldCreateSnapshot(userId, uid, true); Log.i(TAG, "Updated server params. Snapshot must be updated"); } else { Log.i(TAG, "Updated server params. Snapshot didn't exist"); } } /** Loading Loading @@ -407,7 +410,12 @@ public class RecoverableKeyStoreManager { } Log.i(TAG, "Updated secret types. Snapshot pending."); if (mDatabase.getSnapshotVersion(userId, uid) != null) { mDatabase.setShouldCreateSnapshot(userId, uid, true); Log.i(TAG, "Updated secret types. Snapshot must be updated"); } else { Log.i(TAG, "Updated secret types. Snapshot didn't exist"); } } /** Loading
services/core/java/com/android/server/locksettings/recoverablekeystore/storage/RecoverableKeyStoreDb.java +12 −3 Original line number Diff line number Diff line Loading @@ -789,11 +789,20 @@ public class RecoverableKeyStoreDb { } /** * Updates the snapshot version. * Updates a flag indicating that a new snapshot should be created. * It will be {@code false} until the first application key is added. * After that, the flag will be set to true, if one of the following values is updated: * <ul> * <li> List of application keys * <li> Server params. * <li> Lock-screen secret. * <li> Lock-screen secret type. * <li> Trusted hardware certificate. * </ul> * * @param userId The userId of the profile the application is running under. * @param uid The uid of the application. * @param pending The server parameters. * @param pending Should create snapshot flag. * @return The primary key of the inserted row, or -1 if failed. * * @hide Loading @@ -809,7 +818,7 @@ public class RecoverableKeyStoreDb { * * @param userId The userId of the profile the application is running under. * @param uid The uid of the application who initialized the local recovery components. * @return snapshot outdated flag. * @return should create snapshot flag * * @hide */ Loading
services/tests/servicestests/src/com/android/server/locksettings/recoverablekeystore/RecoverableKeyStoreManagerTest.java +57 −7 Original line number Diff line number Diff line Loading @@ -301,6 +301,33 @@ public class RecoverableKeyStoreManagerTest { assertThat(mRecoverableKeyStoreDb.getRecoveryServicePublicKey(userId, uid)).isNull(); } @Test public void initRecoveryService_updatesShouldCreatesnapshotOnCertUpdate() throws Exception { int uid = Binder.getCallingUid(); int userId = UserHandle.getCallingUserId(); long certSerial = 1000L; mRecoverableKeyStoreDb.setShouldCreateSnapshot(userId, uid, false); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial)); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial + 1)); // Since there were no recoverable keys, new snapshot will not be created. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial + 2)); // Since there were a recoverable key, new serial number triggers snapshot creation assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); } @Test public void initRecoveryService_triesToFilterRootAlias() throws Exception { int uid = Binder.getCallingUid(); Loading Loading @@ -405,7 +432,8 @@ public class RecoverableKeyStoreManagerTest { assertThat(mRecoverableKeyStoreDb.getRecoveryServiceCertSerial(userId, uid, DEFAULT_ROOT_CERT_ALIAS)).isEqualTo(certSerial + 1); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); // There were no keys. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); } @Test Loading Loading @@ -479,10 +507,12 @@ public class RecoverableKeyStoreManagerTest { mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial)); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.initRecoveryService(ROOT_CERTIFICATE_ALIAS, TestData.getCertXmlWithSerial(certSerial)); // If the second update succeeds, getShouldCreateSnapshot() will return true. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); } Loading Loading @@ -935,7 +965,6 @@ public class RecoverableKeyStoreManagerTest { assertThat(recoveredKeys).hasSize(1); assertThat(recoveredKeys).containsKey(TEST_ALIAS); // TODO(76083050) Test the grant mechanism for the keys. } @Test Loading Loading @@ -974,7 +1003,6 @@ public class RecoverableKeyStoreManagerTest { assertThat(recoveredKeys).hasSize(1); assertThat(recoveredKeys).containsKey(TEST_ALIAS2); // TODO(76083050) Test the grant mechanism for the keys. } @Test Loading Loading @@ -1016,6 +1044,9 @@ public class RecoverableKeyStoreManagerTest { byte[] serverParams = new byte[] { 1 }; mRecoverableKeyStoreManager.setServerParams(serverParams); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setServerParams(serverParams); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); Loading @@ -1027,6 +1058,9 @@ public class RecoverableKeyStoreManagerTest { int userId = UserHandle.getCallingUserId(); mRecoverableKeyStoreManager.setServerParams(new byte[] { 1 }); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setServerParams(new byte[] { 2 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); Loading Loading @@ -1059,6 +1093,7 @@ public class RecoverableKeyStoreManagerTest { mRecoverableKeyStoreManager.setRecoverySecretTypes(secretTypes); // There were no keys. assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); } Loading @@ -1070,6 +1105,9 @@ public class RecoverableKeyStoreManagerTest { int[] secretTypes = new int[] { 101 }; mRecoverableKeyStoreManager.setRecoverySecretTypes(secretTypes); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setRecoverySecretTypes(secretTypes); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); Loading @@ -1081,6 +1119,11 @@ public class RecoverableKeyStoreManagerTest { int userId = UserHandle.getCallingUserId(); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 101 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isFalse(); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 102 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); Loading @@ -1102,9 +1145,8 @@ public class RecoverableKeyStoreManagerTest { int userId = UserHandle.getCallingUserId(); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 1 }); mRecoverableKeyStoreManager.generateKey(TEST_ALIAS); // Pretend that key was synced mRecoverableKeyStoreDb.setShouldCreateSnapshot(userId, uid, false); generateKeyAndSimulateSync(userId, uid, 10); mRecoverableKeyStoreManager.setRecoverySecretTypes(new int[] { 2 }); assertThat(mRecoverableKeyStoreDb.getShouldCreateSnapshot(userId, uid)).isTrue(); Loading Loading @@ -1175,6 +1217,14 @@ public class RecoverableKeyStoreManagerTest { return bytes; } private void generateKeyAndSimulateSync(int userId, int uid, int snapshotVersion) throws Exception{ mRecoverableKeyStoreManager.generateKey(TEST_ALIAS); // Simulate key sync. mRecoverableKeyStoreDb.setSnapshotVersion(userId, uid, snapshotVersion); mRecoverableKeyStoreDb.setShouldCreateSnapshot(userId, uid, false); } private AndroidKeyStoreSecretKey generateAndroidKeyStoreKey() throws Exception { KeyGenerator keyGenerator = KeyGenerator.getInstance( KEY_ALGORITHM, Loading