Merge "Do not call into ActivityManager when holding mSpManager lock" into oc-dr1-dev
This commit is contained in:
committed by
Android (Google) Code Review
commit
23ed7d7699
@@ -142,6 +142,7 @@ public class LockSettingsService extends ILockSettings.Stub {
|
|||||||
private static final int SYNTHETIC_PASSWORD_ENABLED_BY_DEFAULT = 1;
|
private static final int SYNTHETIC_PASSWORD_ENABLED_BY_DEFAULT = 1;
|
||||||
|
|
||||||
// Order of holding lock: mSeparateChallengeLock -> mSpManager -> this
|
// Order of holding lock: mSeparateChallengeLock -> mSpManager -> this
|
||||||
|
// Do not call into ActivityManager while holding mSpManager lock.
|
||||||
private final Object mSeparateChallengeLock = new Object();
|
private final Object mSeparateChallengeLock = new Object();
|
||||||
|
|
||||||
private final DeviceProvisionedObserver mDeviceProvisionedObserver =
|
private final DeviceProvisionedObserver mDeviceProvisionedObserver =
|
||||||
@@ -1434,16 +1435,14 @@ public class LockSettingsService extends ILockSettings.Stub {
|
|||||||
Slog.e(TAG, "FRP credential can only be verified prior to provisioning.");
|
Slog.e(TAG, "FRP credential can only be verified prior to provisioning.");
|
||||||
return VerifyCredentialResponse.ERROR;
|
return VerifyCredentialResponse.ERROR;
|
||||||
}
|
}
|
||||||
synchronized (mSpManager) {
|
VerifyCredentialResponse response = null;
|
||||||
if (isSyntheticPasswordBasedCredentialLocked(userId)) {
|
response = spBasedDoVerifyCredential(credential, credentialType, hasChallenge, challenge,
|
||||||
VerifyCredentialResponse response = spBasedDoVerifyCredentialLocked(credential,
|
userId, progressCallback);
|
||||||
credentialType, hasChallenge, challenge, userId, progressCallback);
|
// The user employs synthetic password based credential.
|
||||||
if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
|
if (response != null) {
|
||||||
mStrongAuth.reportSuccessfulStrongAuthUnlock(userId);
|
return response;
|
||||||
}
|
|
||||||
return response;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
final CredentialHash storedHash;
|
final CredentialHash storedHash;
|
||||||
if (userId == USER_FRP) {
|
if (userId == USER_FRP) {
|
||||||
PersistentData data = mStorage.readPersistentDataBlock();
|
PersistentData data = mStorage.readPersistentDataBlock();
|
||||||
@@ -1472,7 +1471,7 @@ public class LockSettingsService extends ILockSettings.Stub {
|
|||||||
credentialToVerify = credential;
|
credentialToVerify = credential;
|
||||||
}
|
}
|
||||||
|
|
||||||
VerifyCredentialResponse response = verifyCredential(userId, storedHash, credentialToVerify,
|
response = verifyCredential(userId, storedHash, credentialToVerify,
|
||||||
hasChallenge, challenge, progressCallback);
|
hasChallenge, challenge, progressCallback);
|
||||||
|
|
||||||
if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
|
if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
|
||||||
@@ -1995,33 +1994,46 @@ public class LockSettingsService extends ILockSettings.Stub {
|
|||||||
setLong(SYNTHETIC_PASSWORD_ENABLED_KEY, 1, UserHandle.USER_SYSTEM);
|
setLong(SYNTHETIC_PASSWORD_ENABLED_KEY, 1, UserHandle.USER_SYSTEM);
|
||||||
}
|
}
|
||||||
|
|
||||||
private VerifyCredentialResponse spBasedDoVerifyCredentialLocked(String userCredential, int
|
private VerifyCredentialResponse spBasedDoVerifyCredential(String userCredential, int
|
||||||
credentialType, boolean hasChallenge, long challenge, int userId,
|
credentialType, boolean hasChallenge, long challenge, int userId,
|
||||||
ICheckCredentialProgressCallback progressCallback) throws RemoteException {
|
ICheckCredentialProgressCallback progressCallback) throws RemoteException {
|
||||||
if (DEBUG) Slog.d(TAG, "spBasedDoVerifyCredentialLocked: user=" + userId);
|
if (DEBUG) Slog.d(TAG, "spBasedDoVerifyCredential: user=" + userId);
|
||||||
if (credentialType == LockPatternUtils.CREDENTIAL_TYPE_NONE) {
|
if (credentialType == LockPatternUtils.CREDENTIAL_TYPE_NONE) {
|
||||||
userCredential = null;
|
userCredential = null;
|
||||||
}
|
}
|
||||||
if (userId == USER_FRP) {
|
|
||||||
return mSpManager.verifyFrpCredential(getGateKeeperService(),
|
final AuthenticationResult authResult;
|
||||||
userCredential, credentialType, progressCallback);
|
VerifyCredentialResponse response;
|
||||||
|
synchronized (mSpManager) {
|
||||||
|
if (!isSyntheticPasswordBasedCredentialLocked(userId)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (userId == USER_FRP) {
|
||||||
|
return mSpManager.verifyFrpCredential(getGateKeeperService(),
|
||||||
|
userCredential, credentialType, progressCallback);
|
||||||
|
}
|
||||||
|
|
||||||
|
long handle = getSyntheticPasswordHandleLocked(userId);
|
||||||
|
authResult = mSpManager.unwrapPasswordBasedSyntheticPassword(
|
||||||
|
getGateKeeperService(), handle, userCredential, userId);
|
||||||
|
|
||||||
|
response = authResult.gkResponse;
|
||||||
|
// credential has matched
|
||||||
|
if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
|
||||||
|
// perform verifyChallenge with synthetic password which generates the real GK auth
|
||||||
|
// token and response for the current user
|
||||||
|
response = mSpManager.verifyChallenge(getGateKeeperService(), authResult.authToken,
|
||||||
|
challenge, userId);
|
||||||
|
if (response.getResponseCode() != VerifyCredentialResponse.RESPONSE_OK) {
|
||||||
|
// This shouldn't really happen: the unwrapping of SP succeeds, but SP doesn't
|
||||||
|
// match the recorded GK password handle.
|
||||||
|
Slog.wtf(TAG, "verifyChallenge with SP failed.");
|
||||||
|
return VerifyCredentialResponse.ERROR;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
long handle = getSyntheticPasswordHandleLocked(userId);
|
|
||||||
AuthenticationResult authResult = mSpManager.unwrapPasswordBasedSyntheticPassword(
|
|
||||||
getGateKeeperService(), handle, userCredential, userId);
|
|
||||||
|
|
||||||
VerifyCredentialResponse response = authResult.gkResponse;
|
|
||||||
if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
|
if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
|
||||||
// credential has matched
|
|
||||||
// perform verifyChallenge with synthetic password which generates the real auth
|
|
||||||
// token for the current user
|
|
||||||
response = mSpManager.verifyChallenge(getGateKeeperService(), authResult.authToken,
|
|
||||||
challenge, userId);
|
|
||||||
if (response.getResponseCode() != VerifyCredentialResponse.RESPONSE_OK) {
|
|
||||||
Slog.wtf(TAG, "verifyChallenge with SP failed.");
|
|
||||||
return VerifyCredentialResponse.ERROR;
|
|
||||||
}
|
|
||||||
if (progressCallback != null) {
|
if (progressCallback != null) {
|
||||||
progressCallback.onCredentialVerified();
|
progressCallback.onCredentialVerified();
|
||||||
}
|
}
|
||||||
@@ -2032,12 +2044,14 @@ public class LockSettingsService extends ILockSettings.Stub {
|
|||||||
Slog.i(TAG, "Unlocking user " + userId + " with secret only, length " + secret.length);
|
Slog.i(TAG, "Unlocking user " + userId + " with secret only, length " + secret.length);
|
||||||
unlockUser(userId, null, secret);
|
unlockUser(userId, null, secret);
|
||||||
|
|
||||||
|
activateEscrowTokens(authResult.authToken, userId);
|
||||||
|
|
||||||
if (isManagedProfileWithSeparatedLock(userId)) {
|
if (isManagedProfileWithSeparatedLock(userId)) {
|
||||||
TrustManager trustManager =
|
TrustManager trustManager =
|
||||||
(TrustManager) mContext.getSystemService(Context.TRUST_SERVICE);
|
(TrustManager) mContext.getSystemService(Context.TRUST_SERVICE);
|
||||||
trustManager.setDeviceLockedForUser(userId, false);
|
trustManager.setDeviceLockedForUser(userId, false);
|
||||||
}
|
}
|
||||||
activateEscrowTokens(authResult.authToken, userId);
|
mStrongAuth.reportSuccessfulStrongAuthUnlock(userId);
|
||||||
} else if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_RETRY) {
|
} else if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_RETRY) {
|
||||||
if (response.getTimeout() > 0) {
|
if (response.getTimeout() > 0) {
|
||||||
requireStrongAuth(STRONG_AUTH_REQUIRED_AFTER_LOCKOUT, userId);
|
requireStrongAuth(STRONG_AUTH_REQUIRED_AFTER_LOCKOUT, userId);
|
||||||
@@ -2184,8 +2198,8 @@ public class LockSettingsService extends ILockSettings.Stub {
|
|||||||
|
|
||||||
private void activateEscrowTokens(AuthenticationToken auth, int userId) throws RemoteException {
|
private void activateEscrowTokens(AuthenticationToken auth, int userId) throws RemoteException {
|
||||||
if (DEBUG) Slog.d(TAG, "activateEscrowTokens: user=" + userId);
|
if (DEBUG) Slog.d(TAG, "activateEscrowTokens: user=" + userId);
|
||||||
disableEscrowTokenOnNonManagedDevicesIfNeeded(userId);
|
|
||||||
synchronized (mSpManager) {
|
synchronized (mSpManager) {
|
||||||
|
disableEscrowTokenOnNonManagedDevicesIfNeeded(userId);
|
||||||
for (long handle : mSpManager.getPendingTokensForUser(userId)) {
|
for (long handle : mSpManager.getPendingTokensForUser(userId)) {
|
||||||
Slog.i(TAG, String.format("activateEscrowTokens: %x %d ", handle, userId));
|
Slog.i(TAG, String.format("activateEscrowTokens: %x %d ", handle, userId));
|
||||||
mSpManager.activateTokenBasedSyntheticPassword(handle, auth, userId);
|
mSpManager.activateTokenBasedSyntheticPassword(handle, auth, userId);
|
||||||
|
|||||||
Reference in New Issue
Block a user