Search in sources :

Example 6 with GateKeeperResponse

use of android.service.gatekeeper.GateKeeperResponse in project android_frameworks_base by crdroidandroid.

the class LockSettingsService method verifyCredential.

private VerifyCredentialResponse verifyCredential(int userId, CredentialHash storedHash, String credential, boolean hasChallenge, long challenge, CredentialUtil credentialUtil, ICheckCredentialProgressCallback progressCallback) throws RemoteException {
    if ((storedHash == null || storedHash.hash.length == 0) && TextUtils.isEmpty(credential)) {
        // don't need to pass empty credentials to GateKeeper
        return VerifyCredentialResponse.OK;
    }
    if (TextUtils.isEmpty(credential)) {
        return VerifyCredentialResponse.ERROR;
    }
    if (storedHash.version == CredentialHash.VERSION_LEGACY) {
        byte[] hash = credentialUtil.toHash(credential, userId);
        if (Arrays.equals(hash, storedHash.hash)) {
            unlockKeystore(credentialUtil.adjustForKeystore(credential), userId);
            // Users with legacy credentials don't have credential-backed
            // FBE keys, so just pass through a fake token/secret
            Slog.i(TAG, "Unlocking user with fake token: " + userId);
            final byte[] fakeToken = String.valueOf(userId).getBytes();
            unlockUser(userId, fakeToken, fakeToken);
            // migrate credential to GateKeeper
            credentialUtil.setCredential(credential, null, userId);
            if (!hasChallenge) {
                notifyActivePasswordMetricsAvailable(credential, userId);
                return VerifyCredentialResponse.OK;
            }
        // Fall through to get the auth token. Technically this should never happen,
        // as a user that had a legacy credential would have to unlock their device
        // before getting to a flow with a challenge, but supporting for consistency.
        } else {
            return VerifyCredentialResponse.ERROR;
        }
    }
    VerifyCredentialResponse response;
    boolean shouldReEnroll = false;
    GateKeeperResponse gateKeeperResponse = getGateKeeperService().verifyChallenge(userId, challenge, storedHash.hash, credential.getBytes());
    int responseCode = gateKeeperResponse.getResponseCode();
    if (responseCode == GateKeeperResponse.RESPONSE_RETRY) {
        response = new VerifyCredentialResponse(gateKeeperResponse.getTimeout());
    } else if (responseCode == GateKeeperResponse.RESPONSE_OK) {
        byte[] token = gateKeeperResponse.getPayload();
        if (token == null) {
            // something's wrong if there's no payload with a challenge
            Slog.e(TAG, "verifyChallenge response had no associated payload");
            response = VerifyCredentialResponse.ERROR;
        } else {
            shouldReEnroll = gateKeeperResponse.getShouldReEnroll();
            response = new VerifyCredentialResponse(token);
        }
    } else {
        response = VerifyCredentialResponse.ERROR;
    }
    if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
        if (progressCallback != null) {
            progressCallback.onCredentialVerified();
        }
        notifyActivePasswordMetricsAvailable(credential, userId);
        unlockKeystore(credential, userId);
        Slog.i(TAG, "Unlocking user " + userId + " with token length " + response.getPayload().length);
        unlockUser(userId, response.getPayload(), secretFromCredential(credential));
        if (isManagedProfileWithSeparatedLock(userId)) {
            TrustManager trustManager = (TrustManager) mContext.getSystemService(Context.TRUST_SERVICE);
            trustManager.setDeviceLockedForUser(userId, false);
        }
        if (shouldReEnroll) {
            credentialUtil.setCredential(credential, credential, userId);
        }
    } else if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_RETRY) {
        if (response.getTimeout() > 0) {
            requireStrongAuth(STRONG_AUTH_REQUIRED_AFTER_LOCKOUT, userId);
        }
    }
    return response;
}
Also used : VerifyCredentialResponse(com.android.internal.widget.VerifyCredentialResponse) GateKeeperResponse(android.service.gatekeeper.GateKeeperResponse) TrustManager(android.app.trust.TrustManager)

Example 7 with GateKeeperResponse

use of android.service.gatekeeper.GateKeeperResponse in project android_frameworks_base by AOSPA.

the class LockSettingsService method enrollCredential.

private byte[] enrollCredential(byte[] enrolledHandle, String enrolledCredential, String toEnroll, int userId) throws RemoteException {
    checkWritePermission(userId);
    byte[] enrolledCredentialBytes = enrolledCredential == null ? null : enrolledCredential.getBytes();
    byte[] toEnrollBytes = toEnroll == null ? null : toEnroll.getBytes();
    GateKeeperResponse response = getGateKeeperService().enroll(userId, enrolledHandle, enrolledCredentialBytes, toEnrollBytes);
    if (response == null) {
        return null;
    }
    byte[] hash = response.getPayload();
    if (hash != null) {
        setKeystorePassword(toEnroll, userId);
    } else {
        // Should not happen
        Slog.e(TAG, "Throttled while enrolling a password");
    }
    return hash;
}
Also used : GateKeeperResponse(android.service.gatekeeper.GateKeeperResponse)

Example 8 with GateKeeperResponse

use of android.service.gatekeeper.GateKeeperResponse in project android_frameworks_base by AOSPA.

the class LockSettingsService method verifyCredential.

private VerifyCredentialResponse verifyCredential(int userId, CredentialHash storedHash, String credential, boolean hasChallenge, long challenge, CredentialUtil credentialUtil, ICheckCredentialProgressCallback progressCallback) throws RemoteException {
    if ((storedHash == null || storedHash.hash.length == 0) && TextUtils.isEmpty(credential)) {
        // don't need to pass empty credentials to GateKeeper
        return VerifyCredentialResponse.OK;
    }
    if (TextUtils.isEmpty(credential)) {
        return VerifyCredentialResponse.ERROR;
    }
    if (storedHash.version == CredentialHash.VERSION_LEGACY) {
        byte[] hash = credentialUtil.toHash(credential, userId);
        if (Arrays.equals(hash, storedHash.hash)) {
            unlockKeystore(credentialUtil.adjustForKeystore(credential), userId);
            // Users with legacy credentials don't have credential-backed
            // FBE keys, so just pass through a fake token/secret
            Slog.i(TAG, "Unlocking user with fake token: " + userId);
            final byte[] fakeToken = String.valueOf(userId).getBytes();
            unlockUser(userId, fakeToken, fakeToken);
            // migrate credential to GateKeeper
            credentialUtil.setCredential(credential, null, userId);
            if (!hasChallenge) {
                notifyActivePasswordMetricsAvailable(credential, userId);
                return VerifyCredentialResponse.OK;
            }
        // Fall through to get the auth token. Technically this should never happen,
        // as a user that had a legacy credential would have to unlock their device
        // before getting to a flow with a challenge, but supporting for consistency.
        } else {
            return VerifyCredentialResponse.ERROR;
        }
    }
    VerifyCredentialResponse response;
    boolean shouldReEnroll = false;
    GateKeeperResponse gateKeeperResponse = getGateKeeperService().verifyChallenge(userId, challenge, storedHash.hash, credential.getBytes());
    int responseCode = gateKeeperResponse.getResponseCode();
    if (responseCode == GateKeeperResponse.RESPONSE_RETRY) {
        response = new VerifyCredentialResponse(gateKeeperResponse.getTimeout());
    } else if (responseCode == GateKeeperResponse.RESPONSE_OK) {
        byte[] token = gateKeeperResponse.getPayload();
        if (token == null) {
            // something's wrong if there's no payload with a challenge
            Slog.e(TAG, "verifyChallenge response had no associated payload");
            response = VerifyCredentialResponse.ERROR;
        } else {
            shouldReEnroll = gateKeeperResponse.getShouldReEnroll();
            response = new VerifyCredentialResponse(token);
        }
    } else {
        response = VerifyCredentialResponse.ERROR;
    }
    if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
        if (progressCallback != null) {
            progressCallback.onCredentialVerified();
        }
        notifyActivePasswordMetricsAvailable(credential, userId);
        unlockKeystore(credential, userId);
        Slog.i(TAG, "Unlocking user " + userId + " with token length " + response.getPayload().length);
        unlockUser(userId, response.getPayload(), secretFromCredential(credential));
        if (isManagedProfileWithSeparatedLock(userId)) {
            TrustManager trustManager = (TrustManager) mContext.getSystemService(Context.TRUST_SERVICE);
            trustManager.setDeviceLockedForUser(userId, false);
        }
        if (shouldReEnroll) {
            credentialUtil.setCredential(credential, credential, userId);
        }
    } else if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_RETRY) {
        if (response.getTimeout() > 0) {
            requireStrongAuth(STRONG_AUTH_REQUIRED_AFTER_LOCKOUT, userId);
        }
    }
    return response;
}
Also used : VerifyCredentialResponse(com.android.internal.widget.VerifyCredentialResponse) GateKeeperResponse(android.service.gatekeeper.GateKeeperResponse) TrustManager(android.app.trust.TrustManager)

Example 9 with GateKeeperResponse

use of android.service.gatekeeper.GateKeeperResponse in project android_frameworks_base by DirtyUnicorns.

the class LockSettingsService method verifyCredential.

private VerifyCredentialResponse verifyCredential(int userId, CredentialHash storedHash, String credential, boolean hasChallenge, long challenge, CredentialUtil credentialUtil, ICheckCredentialProgressCallback progressCallback) throws RemoteException {
    if ((storedHash == null || storedHash.hash.length == 0) && TextUtils.isEmpty(credential)) {
        // don't need to pass empty credentials to GateKeeper
        return VerifyCredentialResponse.OK;
    }
    if (TextUtils.isEmpty(credential)) {
        return VerifyCredentialResponse.ERROR;
    }
    if (storedHash.version == CredentialHash.VERSION_LEGACY) {
        byte[] hash = credentialUtil.toHash(credential, userId);
        if (Arrays.equals(hash, storedHash.hash)) {
            unlockKeystore(credentialUtil.adjustForKeystore(credential), userId);
            // Users with legacy credentials don't have credential-backed
            // FBE keys, so just pass through a fake token/secret
            Slog.i(TAG, "Unlocking user with fake token: " + userId);
            final byte[] fakeToken = String.valueOf(userId).getBytes();
            unlockUser(userId, fakeToken, fakeToken);
            // migrate credential to GateKeeper
            credentialUtil.setCredential(credential, null, userId);
            if (!hasChallenge) {
                notifyActivePasswordMetricsAvailable(credential, userId);
                return VerifyCredentialResponse.OK;
            }
        // Fall through to get the auth token. Technically this should never happen,
        // as a user that had a legacy credential would have to unlock their device
        // before getting to a flow with a challenge, but supporting for consistency.
        } else {
            return VerifyCredentialResponse.ERROR;
        }
    }
    VerifyCredentialResponse response;
    boolean shouldReEnroll = false;
    GateKeeperResponse gateKeeperResponse = getGateKeeperService().verifyChallenge(userId, challenge, storedHash.hash, credential.getBytes());
    int responseCode = gateKeeperResponse.getResponseCode();
    if (responseCode == GateKeeperResponse.RESPONSE_RETRY) {
        response = new VerifyCredentialResponse(gateKeeperResponse.getTimeout());
    } else if (responseCode == GateKeeperResponse.RESPONSE_OK) {
        byte[] token = gateKeeperResponse.getPayload();
        if (token == null) {
            // something's wrong if there's no payload with a challenge
            Slog.e(TAG, "verifyChallenge response had no associated payload");
            response = VerifyCredentialResponse.ERROR;
        } else {
            shouldReEnroll = gateKeeperResponse.getShouldReEnroll();
            response = new VerifyCredentialResponse(token);
        }
    } else {
        response = VerifyCredentialResponse.ERROR;
    }
    if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
        if (progressCallback != null) {
            progressCallback.onCredentialVerified();
        }
        notifyActivePasswordMetricsAvailable(credential, userId);
        unlockKeystore(credential, userId);
        Slog.i(TAG, "Unlocking user " + userId + " with token length " + response.getPayload().length);
        unlockUser(userId, response.getPayload(), secretFromCredential(credential));
        if (isManagedProfileWithSeparatedLock(userId)) {
            TrustManager trustManager = (TrustManager) mContext.getSystemService(Context.TRUST_SERVICE);
            trustManager.setDeviceLockedForUser(userId, false);
        }
        if (shouldReEnroll) {
            credentialUtil.setCredential(credential, credential, userId);
        }
    } else if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_RETRY) {
        if (response.getTimeout() > 0) {
            requireStrongAuth(STRONG_AUTH_REQUIRED_AFTER_LOCKOUT, userId);
        }
    }
    return response;
}
Also used : VerifyCredentialResponse(com.android.internal.widget.VerifyCredentialResponse) GateKeeperResponse(android.service.gatekeeper.GateKeeperResponse) TrustManager(android.app.trust.TrustManager)

Example 10 with GateKeeperResponse

use of android.service.gatekeeper.GateKeeperResponse in project android_frameworks_base by DirtyUnicorns.

the class LockSettingsService method enrollCredential.

private byte[] enrollCredential(byte[] enrolledHandle, String enrolledCredential, String toEnroll, int userId) throws RemoteException {
    checkWritePermission(userId);
    byte[] enrolledCredentialBytes = enrolledCredential == null ? null : enrolledCredential.getBytes();
    byte[] toEnrollBytes = toEnroll == null ? null : toEnroll.getBytes();
    GateKeeperResponse response = getGateKeeperService().enroll(userId, enrolledHandle, enrolledCredentialBytes, toEnrollBytes);
    if (response == null) {
        return null;
    }
    byte[] hash = response.getPayload();
    if (hash != null) {
        setKeystorePassword(toEnroll, userId);
    } else {
        // Should not happen
        Slog.e(TAG, "Throttled while enrolling a password");
    }
    return hash;
}
Also used : GateKeeperResponse(android.service.gatekeeper.GateKeeperResponse)

Aggregations

GateKeeperResponse (android.service.gatekeeper.GateKeeperResponse)10 TrustManager (android.app.trust.TrustManager)5 VerifyCredentialResponse (com.android.internal.widget.VerifyCredentialResponse)5