| /* |
| * Copyright (C) 2018 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.server.wm; |
| |
| import static android.os.Process.FIRST_APPLICATION_UID; |
| import static android.os.Process.NFC_UID; |
| import static android.os.Process.SYSTEM_UID; |
| import static android.os.UserHandle.USER_ALL; |
| import static android.os.UserHandle.USER_SYSTEM; |
| |
| import static com.android.dx.mockito.inline.extended.ExtendedMockito.mock; |
| |
| import static org.hamcrest.Matchers.containsString; |
| import static org.junit.Assert.assertFalse; |
| import static org.junit.Assert.assertThat; |
| import static org.junit.Assert.assertTrue; |
| import static org.junit.Assert.fail; |
| |
| import android.os.Binder; |
| import android.os.Handler; |
| import android.os.IBinder; |
| import android.os.UserHandle; |
| import android.platform.test.annotations.Presubmit; |
| import android.util.SparseBooleanArray; |
| |
| import com.android.server.wm.LockTaskController.LockTaskToken; |
| |
| import org.junit.Before; |
| import org.junit.Test; |
| |
| import java.lang.reflect.Constructor; |
| |
| @Presubmit |
| public class KeyguardDisableHandlerTest { |
| |
| private KeyguardDisableHandler mKeyguardDisable; |
| |
| private boolean mKeyguardEnabled; |
| private SparseBooleanArray mKeyguardSecure = new SparseBooleanArray(); |
| private SparseBooleanArray mDpmRequiresPassword = new SparseBooleanArray(); |
| |
| @Before |
| public void setUp() throws Exception { |
| mKeyguardEnabled = true; |
| |
| mKeyguardDisable = new KeyguardDisableHandler(new KeyguardDisableHandler.Injector() { |
| @Override |
| public boolean dpmRequiresPassword(int userId) { |
| return mDpmRequiresPassword.get(userId); |
| } |
| |
| @Override |
| public boolean isKeyguardSecure(int userId) { |
| return mKeyguardSecure.get(userId); |
| } |
| |
| @Override |
| public int getProfileParentId(int userId) { |
| return userId; |
| } |
| |
| @Override |
| public void enableKeyguard(boolean enabled) { |
| mKeyguardEnabled = enabled; |
| } |
| }, mock(Handler.class)) { |
| @Override |
| public void disableKeyguard(IBinder token, String tag, int callingUid, int userId) { |
| super.disableKeyguard(token, tag, callingUid, userId); |
| // In the actual code, the update is posted to the handler thread. Eagerly update |
| // here to simplify the test. |
| updateKeyguardEnabled(userId); |
| } |
| |
| @Override |
| public void reenableKeyguard(IBinder token, int callingUid, int userId) { |
| super.reenableKeyguard(token, callingUid, userId); |
| // In the actual code, the update is posted to the handler thread. Eagerly update |
| // here to simplify the test. |
| updateKeyguardEnabled(userId); |
| } |
| }; |
| } |
| |
| @Test |
| public void starts_enabled() { |
| assertTrue(mKeyguardEnabled); |
| mKeyguardDisable.updateKeyguardEnabled(USER_ALL); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromApp_disables() { |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", FIRST_APPLICATION_UID, USER_SYSTEM); |
| assertFalse(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromApp_secondaryUser_disables() { |
| mKeyguardDisable.setCurrentUser(1); |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", |
| UserHandle.getUid(1, FIRST_APPLICATION_UID), 1); |
| assertFalse(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromSystem_LockTask_disables() { |
| mKeyguardDisable.disableKeyguard(createLockTaskToken(), "Tag", SYSTEM_UID, USER_SYSTEM); |
| assertFalse(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromSystem_genericToken_fails() { |
| try { |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", SYSTEM_UID, USER_SYSTEM); |
| fail("Expected exception not thrown"); |
| } catch (UnsupportedOperationException e) { |
| assertThat(e.getMessage(), containsString("Only apps can use the KeyguardLock API")); |
| } |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromNonApp_genericToken_fails() { |
| try { |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", NFC_UID, USER_SYSTEM); |
| fail("Expected exception not thrown"); |
| } catch (UnsupportedOperationException e) { |
| assertThat(e.getMessage(), containsString("Only apps can use the KeyguardLock API")); |
| } |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromApp_secure_staysEnabled() { |
| configureIsSecure(true, USER_SYSTEM); |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", FIRST_APPLICATION_UID, USER_SYSTEM); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromApp_dpmRequiresPassword_staysEnabled() { |
| configureDpmRequiresPassword(true, USER_SYSTEM); |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", FIRST_APPLICATION_UID, USER_SYSTEM); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromSystem_LockTask_secure_disables() { |
| configureIsSecure(true, USER_SYSTEM); |
| mKeyguardDisable.disableKeyguard(createLockTaskToken(), "Tag", SYSTEM_UID, USER_SYSTEM); |
| assertFalse(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromSystem_LockTask_requiresDpm_staysEnabled() { |
| configureDpmRequiresPassword(true, USER_SYSTEM); |
| mKeyguardDisable.disableKeyguard(createLockTaskToken(), "Tag", SYSTEM_UID, USER_SYSTEM); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromApp_thenSecure_reenables() { |
| mKeyguardDisable.disableKeyguard(new Binder(), "Tag", FIRST_APPLICATION_UID, USER_SYSTEM); |
| configureIsSecure(true, USER_SYSTEM); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void disable_fromSystem_LockTask_thenRequiresDpm_reenables() { |
| mKeyguardDisable.disableKeyguard(createLockTaskToken(), "Tag", SYSTEM_UID, USER_SYSTEM); |
| configureDpmRequiresPassword(true, USER_SYSTEM); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void user_switch_to_enabledUser_applies_enabled() { |
| mKeyguardDisable.disableKeyguard(createLockTaskToken(), "Tag", SYSTEM_UID, USER_SYSTEM); |
| assertFalse("test setup failed", mKeyguardEnabled); |
| mKeyguardDisable.setCurrentUser(1); |
| assertTrue(mKeyguardEnabled); |
| } |
| |
| @Test |
| public void user_switch_to_disabledUser_applies_disabled() { |
| mKeyguardDisable.disableKeyguard(createLockTaskToken(), "Tag", |
| SYSTEM_UID, 1); |
| assertTrue("test setup failed", mKeyguardEnabled); |
| mKeyguardDisable.setCurrentUser(1); |
| assertFalse(mKeyguardEnabled); |
| } |
| |
| private void configureIsSecure(boolean secure, int userId) { |
| mKeyguardSecure.put(userId, secure); |
| mKeyguardDisable.updateKeyguardEnabled(userId); |
| } |
| |
| private void configureDpmRequiresPassword(boolean requiresPassword, int userId) { |
| mDpmRequiresPassword.put(userId, requiresPassword); |
| mKeyguardDisable.updateKeyguardEnabled(userId); |
| } |
| |
| private LockTaskToken createLockTaskToken() { |
| try { |
| final Constructor<LockTaskToken> constructor = |
| LockTaskToken.class.getDeclaredConstructor(); |
| constructor.setAccessible(true); |
| return constructor.newInstance(); |
| } catch (Exception e) { |
| throw new RuntimeException(e); |
| } |
| } |
| } |