Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit e8fde5d9 authored by Jorim Jaggi's avatar Jorim Jaggi
Browse files

Improve initial unlock delay (1/2)

When checking for the credentials, we add a new callback
onEarlyVerified which gets called as soon as we know that the
credential was correct.

In KeyguardUpdateMonitor, we track the unlocked state of the user,
and if it's still locked, we slow down all the transitions to allow
for a more gradual unlock experience.

Bug: 29007436

Change-Id: I406d228f9f3e41e07fe3292a61df175a7f579e4d
parent 6ac6ceb2
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -343,6 +343,7 @@ LOCAL_SRC_FILES += \
	core/java/com/android/internal/view/IInputMethodManager.aidl \
	core/java/com/android/internal/view/IInputMethodSession.aidl \
	core/java/com/android/internal/view/IInputSessionCallback.aidl \
	core/java/com/android/internal/widget/ICheckCredentialProgressCallback.aidl \
	core/java/com/android/internal/widget/ILockSettings.aidl \
	core/java/com/android/internal/widget/IRemoteViewsFactory.aidl \
	core/java/com/android/internal/widget/IRemoteViewsAdapterConnection.aidl \
+22 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2016 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.android.internal.widget;

/** {@hide} */
oneway interface ICheckCredentialProgressCallback {
    void onCredentialVerified();
}
+5 −2
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@
package com.android.internal.widget;

import android.app.trust.IStrongAuthTracker;
import com.android.internal.widget.ICheckCredentialProgressCallback;
import com.android.internal.widget.VerifyCredentialResponse;

/** {@hide} */
@@ -29,10 +30,12 @@ interface ILockSettings {
    String getString(in String key, in String defaultValue, in int userId);
    void setLockPattern(in String pattern, in String savedPattern, int userId);
    void resetKeyStore(int userId);
    VerifyCredentialResponse checkPattern(in String pattern, int userId);
    VerifyCredentialResponse checkPattern(in String pattern, int userId,
            in ICheckCredentialProgressCallback progressCallback);
    VerifyCredentialResponse verifyPattern(in String pattern, long challenge, int userId);
    void setLockPassword(in String password, in String savedPassword, int userId);
    VerifyCredentialResponse checkPassword(in String password, int userId);
    VerifyCredentialResponse checkPassword(in String password, int userId,
            in ICheckCredentialProgressCallback progressCallback);
    VerifyCredentialResponse verifyPassword(in String password, long challenge, int userId);
    VerifyCredentialResponse verifyTiedProfileChallenge(String password, boolean isPattern, long challenge, int userId);
    boolean checkVoldPassword(int userId);
+9 −2
Original line number Diff line number Diff line
@@ -14,6 +14,13 @@ public final class LockPatternChecker {
     * Interface for a callback to be invoked after security check.
     */
    public interface OnCheckCallback {

        /**
         * Invoked as soon as possible we know that the credentials match. This will be called
         * earlier than {@link #onChecked} but only if the credentials match.
         */
        default void onEarlyMatched() {}

        /**
         * Invoked when a security check is finished.
         *
@@ -92,7 +99,7 @@ public final class LockPatternChecker {
            @Override
            protected Boolean doInBackground(Void... args) {
                try {
                    return utils.checkPattern(pattern, userId);
                    return utils.checkPattern(pattern, userId, callback::onEarlyMatched);
                } catch (RequestThrottledException ex) {
                    mThrottleTimeout = ex.getTimeoutMs();
                    return false;
@@ -199,7 +206,7 @@ public final class LockPatternChecker {
            @Override
            protected Boolean doInBackground(Void... args) {
                try {
                    return utils.checkPassword(password, userId);
                    return utils.checkPassword(password, userId, callback::onEarlyMatched);
                } catch (RequestThrottledException ex) {
                    mThrottleTimeout = ex.getTimeoutMs();
                    return false;
+56 −3
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@
package com.android.internal.widget;

import android.annotation.IntDef;
import android.annotation.Nullable;
import android.app.admin.DevicePolicyManager;
import android.app.trust.IStrongAuthTracker;
import android.app.trust.TrustManager;
@@ -32,7 +33,6 @@ import android.os.Message;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.os.SystemClock;
import android.os.SystemProperties;
import android.os.UserHandle;
import android.os.UserManager;
import android.os.storage.IMountService;
@@ -149,6 +149,7 @@ public class LockPatternUtils {
    private DevicePolicyManager mDevicePolicyManager;
    private ILockSettings mLockSettingsService;
    private UserManager mUserManager;
    private final Handler mHandler = new Handler();

    /**
     * Use {@link TrustManager#isTrustUsuallyManaged(int)}.
@@ -341,10 +342,23 @@ public class LockPatternUtils {
     */
    public boolean checkPattern(List<LockPatternView.Cell> pattern, int userId)
            throws RequestThrottledException {
        return checkPattern(pattern, userId, null /* progressCallback */);
    }

    /**
     * Check to see if a pattern matches the saved pattern.  If no pattern exists,
     * always returns true.
     * @param pattern The pattern to check.
     * @return Whether the pattern matches the stored one.
     */
    public boolean checkPattern(List<LockPatternView.Cell> pattern, int userId,
            @Nullable CheckCredentialProgressCallback progressCallback)
            throws RequestThrottledException {
        throwIfCalledOnMainThread();
        try {
            VerifyCredentialResponse response =
                    getLockSettings().checkPattern(patternToString(pattern), userId);
                    getLockSettings().checkPattern(patternToString(pattern), userId,
                            wrapCallback(progressCallback));

            if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
                return true;
@@ -423,10 +437,22 @@ public class LockPatternUtils {
     * @return Whether the password matches the stored one.
     */
    public boolean checkPassword(String password, int userId) throws RequestThrottledException {
        return checkPassword(password, userId, null /* progressCallback */);
    }

    /**
     * Check to see if a password matches the saved password.  If no password exists,
     * always returns true.
     * @param password The password to check.
     * @return Whether the password matches the stored one.
     */
    public boolean checkPassword(String password, int userId,
            @Nullable CheckCredentialProgressCallback progressCallback)
            throws RequestThrottledException {
        throwIfCalledOnMainThread();
        try {
            VerifyCredentialResponse response =
                    getLockSettings().checkPassword(password, userId);
                    getLockSettings().checkPassword(password, userId, wrapCallback(progressCallback));
            if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_OK) {
                return true;
            } else if (response.getResponseCode() == VerifyCredentialResponse.RESPONSE_RETRY) {
@@ -1475,6 +1501,33 @@ public class LockPatternUtils {
        return (getStrongAuthForUser(userId) & ~StrongAuthTracker.ALLOWING_FINGERPRINT) == 0;
    }

    private ICheckCredentialProgressCallback wrapCallback(
            final CheckCredentialProgressCallback callback) {
        if (callback == null) {
            return null;
        } else {
            return new ICheckCredentialProgressCallback.Stub() {

                @Override
                public void onCredentialVerified() throws RemoteException {
                    mHandler.post(callback::onEarlyMatched);
                }
            };
        }
    }

    /**
     * Callback to be notified about progress when checking credentials.
     */
    public interface CheckCredentialProgressCallback {

        /**
         * Called as soon as possible when we know that the credentials match but the user hasn't
         * been fully unlocked.
         */
        void onEarlyMatched();
    }

    /**
     * Tracks the global strong authentication state.
     */
Loading