Loading services/core/java/com/android/server/locksettings/LockSettingsService.java +9 −0 Original line number Diff line number Diff line Loading @@ -2537,6 +2537,7 @@ public class LockSettingsService extends ILockSettings.Stub { * Returns a fixed pseudorandom byte string derived from the user's synthetic password. * This is used to salt the password history hash to protect the hash against offline * bruteforcing, since rederiving this value requires a successful authentication. * If user is a managed profile with unified challenge, currentCredential is ignored. */ @Override public byte[] getHashFactor(String currentCredential, int userId) throws RemoteException { Loading @@ -2544,6 +2545,14 @@ public class LockSettingsService extends ILockSettings.Stub { if (TextUtils.isEmpty(currentCredential)) { currentCredential = null; } if (isManagedProfileWithUnifiedLock(userId)) { try { currentCredential = getDecryptedPasswordForTiedProfile(userId); } catch (Exception e) { Slog.e(TAG, "Failed to get work profile credential", e); return null; } } synchronized (mSpManager) { if (!isSyntheticPasswordBasedCredentialLocked(userId)) { Slog.w(TAG, "Synthetic password not enabled"); Loading services/tests/servicestests/src/com/android/server/locksettings/SyntheticPasswordTests.java +33 −0 Original line number Diff line number Diff line Loading @@ -448,6 +448,39 @@ public class SyntheticPasswordTests extends BaseLockSettingsServiceTests { assertTrue(mLocalService.isEscrowTokenActive(handle, PRIMARY_USER_ID)); } public void testgetHashFactorPrimaryUser() throws RemoteException { final String password = "password"; mService.setLockCredential(password, LockPatternUtils.CREDENTIAL_TYPE_PASSWORD, null, PASSWORD_QUALITY_ALPHABETIC, PRIMARY_USER_ID); final byte[] hashFactor = mService.getHashFactor(password, PRIMARY_USER_ID); assertNotNull(hashFactor); mService.setLockCredential(null, LockPatternUtils.CREDENTIAL_TYPE_NONE, password, PASSWORD_QUALITY_UNSPECIFIED, PRIMARY_USER_ID); final byte[] newHashFactor = mService.getHashFactor(null, PRIMARY_USER_ID); assertNotNull(newHashFactor); // Hash factor should never change after password change/removal assertArrayEquals(hashFactor, newHashFactor); } public void testgetHashFactorManagedProfileUnifiedChallenge() throws RemoteException { final String pattern = "1236"; mService.setLockCredential(pattern, LockPatternUtils.CREDENTIAL_TYPE_PATTERN, null, PASSWORD_QUALITY_SOMETHING, PRIMARY_USER_ID); mService.setSeparateProfileChallengeEnabled(MANAGED_PROFILE_USER_ID, false, null); assertNotNull(mService.getHashFactor(null, MANAGED_PROFILE_USER_ID)); } public void testgetHashFactorManagedProfileSeparateChallenge() throws RemoteException { final String primaryPassword = "primary"; final String profilePassword = "profile"; mService.setLockCredential(primaryPassword, LockPatternUtils.CREDENTIAL_TYPE_PASSWORD, null, PASSWORD_QUALITY_ALPHABETIC, PRIMARY_USER_ID); mService.setLockCredential(profilePassword, LockPatternUtils.CREDENTIAL_TYPE_PASSWORD, null, PASSWORD_QUALITY_ALPHABETIC, MANAGED_PROFILE_USER_ID); assertNotNull(mService.getHashFactor(profilePassword, MANAGED_PROFILE_USER_ID)); } public void testPasswordData_serializeDeserialize() { PasswordData data = new PasswordData(); data.scryptN = 11; Loading Loading
services/core/java/com/android/server/locksettings/LockSettingsService.java +9 −0 Original line number Diff line number Diff line Loading @@ -2537,6 +2537,7 @@ public class LockSettingsService extends ILockSettings.Stub { * Returns a fixed pseudorandom byte string derived from the user's synthetic password. * This is used to salt the password history hash to protect the hash against offline * bruteforcing, since rederiving this value requires a successful authentication. * If user is a managed profile with unified challenge, currentCredential is ignored. */ @Override public byte[] getHashFactor(String currentCredential, int userId) throws RemoteException { Loading @@ -2544,6 +2545,14 @@ public class LockSettingsService extends ILockSettings.Stub { if (TextUtils.isEmpty(currentCredential)) { currentCredential = null; } if (isManagedProfileWithUnifiedLock(userId)) { try { currentCredential = getDecryptedPasswordForTiedProfile(userId); } catch (Exception e) { Slog.e(TAG, "Failed to get work profile credential", e); return null; } } synchronized (mSpManager) { if (!isSyntheticPasswordBasedCredentialLocked(userId)) { Slog.w(TAG, "Synthetic password not enabled"); Loading
services/tests/servicestests/src/com/android/server/locksettings/SyntheticPasswordTests.java +33 −0 Original line number Diff line number Diff line Loading @@ -448,6 +448,39 @@ public class SyntheticPasswordTests extends BaseLockSettingsServiceTests { assertTrue(mLocalService.isEscrowTokenActive(handle, PRIMARY_USER_ID)); } public void testgetHashFactorPrimaryUser() throws RemoteException { final String password = "password"; mService.setLockCredential(password, LockPatternUtils.CREDENTIAL_TYPE_PASSWORD, null, PASSWORD_QUALITY_ALPHABETIC, PRIMARY_USER_ID); final byte[] hashFactor = mService.getHashFactor(password, PRIMARY_USER_ID); assertNotNull(hashFactor); mService.setLockCredential(null, LockPatternUtils.CREDENTIAL_TYPE_NONE, password, PASSWORD_QUALITY_UNSPECIFIED, PRIMARY_USER_ID); final byte[] newHashFactor = mService.getHashFactor(null, PRIMARY_USER_ID); assertNotNull(newHashFactor); // Hash factor should never change after password change/removal assertArrayEquals(hashFactor, newHashFactor); } public void testgetHashFactorManagedProfileUnifiedChallenge() throws RemoteException { final String pattern = "1236"; mService.setLockCredential(pattern, LockPatternUtils.CREDENTIAL_TYPE_PATTERN, null, PASSWORD_QUALITY_SOMETHING, PRIMARY_USER_ID); mService.setSeparateProfileChallengeEnabled(MANAGED_PROFILE_USER_ID, false, null); assertNotNull(mService.getHashFactor(null, MANAGED_PROFILE_USER_ID)); } public void testgetHashFactorManagedProfileSeparateChallenge() throws RemoteException { final String primaryPassword = "primary"; final String profilePassword = "profile"; mService.setLockCredential(primaryPassword, LockPatternUtils.CREDENTIAL_TYPE_PASSWORD, null, PASSWORD_QUALITY_ALPHABETIC, PRIMARY_USER_ID); mService.setLockCredential(profilePassword, LockPatternUtils.CREDENTIAL_TYPE_PASSWORD, null, PASSWORD_QUALITY_ALPHABETIC, MANAGED_PROFILE_USER_ID); assertNotNull(mService.getHashFactor(profilePassword, MANAGED_PROFILE_USER_ID)); } public void testPasswordData_serializeDeserialize() { PasswordData data = new PasswordData(); data.scryptN = 11; Loading