DevicePolicyManagerTest.java revision dafec11e698daf054730cfb04db64f3e31a0c9ff
1/* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16package com.android.server.devicepolicy; 17 18import android.Manifest.permission; 19import android.app.Activity; 20import android.app.admin.DeviceAdminReceiver; 21import android.app.admin.DevicePolicyManager; 22import android.app.admin.DevicePolicyManagerInternal; 23import android.content.BroadcastReceiver; 24import android.content.ComponentName; 25import android.content.pm.ApplicationInfo; 26import android.content.pm.PackageInfo; 27import android.content.pm.PackageManager; 28import android.net.wifi.WifiInfo; 29import android.os.Build.VERSION_CODES; 30import android.os.Build; 31import android.os.Bundle; 32import android.os.Process; 33import android.os.UserHandle; 34import android.os.UserManager; 35import android.test.MoreAsserts; 36import android.test.suitebuilder.annotation.SmallTest; 37import android.util.ArraySet; 38import android.util.Pair; 39 40import com.android.server.LocalServices; 41import com.android.server.SystemService; 42 43import org.mockito.ArgumentCaptor; 44import org.mockito.invocation.InvocationOnMock; 45import org.mockito.stubbing.Answer; 46 47import java.util.ArrayList; 48import java.util.Arrays; 49import java.util.HashMap; 50import java.util.List; 51import java.util.Map; 52import java.util.Set; 53 54import static org.mockito.Matchers.any; 55import static org.mockito.Matchers.anyInt; 56import static org.mockito.Matchers.anyString; 57import static org.mockito.Matchers.eq; 58import static org.mockito.Matchers.isNull; 59import static org.mockito.Mockito.doAnswer; 60import static org.mockito.Mockito.doReturn; 61import static org.mockito.Mockito.reset; 62import static org.mockito.Mockito.times; 63import static org.mockito.Mockito.verify; 64import static org.mockito.Mockito.when; 65 66/** 67 * Tests for DevicePolicyManager( and DevicePolicyManagerService). 68 * 69 m FrameworksServicesTests && 70 adb install \ 71 -r ${ANDROID_PRODUCT_OUT}/data/app/FrameworksServicesTests/FrameworksServicesTests.apk && 72 adb shell am instrument -e class com.android.server.devicepolicy.DevicePolicyManagerTest \ 73 -w com.android.frameworks.servicestests/android.support.test.runner.AndroidJUnitRunner 74 75 (mmma frameworks/base/services/tests/servicestests/ for non-ninja build) 76 */ 77@SmallTest 78public class DevicePolicyManagerTest extends DpmTestBase { 79 private static final List<String> OWNER_SETUP_PERMISSIONS = Arrays.asList( 80 permission.MANAGE_DEVICE_ADMINS, permission.MANAGE_PROFILE_AND_DEVICE_OWNERS, 81 permission.MANAGE_USERS, permission.INTERACT_ACROSS_USERS_FULL); 82 83 private DpmMockContext mContext; 84 public DevicePolicyManager dpm; 85 public DevicePolicyManagerServiceTestable dpms; 86 87 @Override 88 protected void setUp() throws Exception { 89 super.setUp(); 90 91 mContext = getContext(); 92 93 when(mContext.packageManager.hasSystemFeature(eq(PackageManager.FEATURE_DEVICE_ADMIN))) 94 .thenReturn(true); 95 96 // By default, pretend all users are running and unlocked. 97 when(mContext.userManager.isUserUnlocked(anyInt())).thenReturn(true); 98 99 initializeDpms(); 100 101 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID); 102 setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID); 103 setUpPackageManagerForAdmin(admin3, DpmMockContext.CALLER_UID); 104 setUpPackageManagerForAdmin(adminNoPerm, DpmMockContext.CALLER_UID); 105 106 setUpUserManager(); 107 } 108 109 private void initializeDpms() { 110 // Need clearCallingIdentity() to pass permission checks. 111 final long ident = mContext.binder.clearCallingIdentity(); 112 try { 113 LocalServices.removeServiceForTest(DevicePolicyManagerInternal.class); 114 115 dpms = new DevicePolicyManagerServiceTestable(mContext, dataDir); 116 117 dpms.systemReady(SystemService.PHASE_LOCK_SETTINGS_READY); 118 dpms.systemReady(SystemService.PHASE_BOOT_COMPLETED); 119 120 dpm = new DevicePolicyManagerTestable(mContext, dpms); 121 } finally { 122 mContext.binder.restoreCallingIdentity(ident); 123 } 124 } 125 126 private void setUpUserManager() { 127 // Emulate UserManager.set/getApplicationRestriction(). 128 final Map<Pair<String, UserHandle>, Bundle> appRestrictions = new HashMap<>(); 129 130 // UM.setApplicationRestrictions() will save to appRestrictions. 131 doAnswer(new Answer<Void>() { 132 @Override 133 public Void answer(InvocationOnMock invocation) throws Throwable { 134 String pkg = (String) invocation.getArguments()[0]; 135 Bundle bundle = (Bundle) invocation.getArguments()[1]; 136 UserHandle user = (UserHandle) invocation.getArguments()[2]; 137 138 appRestrictions.put(Pair.create(pkg, user), bundle); 139 140 return null; 141 } 142 }).when(mContext.userManager).setApplicationRestrictions( 143 anyString(), any(Bundle.class), any(UserHandle.class)); 144 145 // UM.getApplicationRestrictions() will read from appRestrictions. 146 doAnswer(new Answer<Bundle>() { 147 @Override 148 public Bundle answer(InvocationOnMock invocation) throws Throwable { 149 String pkg = (String) invocation.getArguments()[0]; 150 UserHandle user = (UserHandle) invocation.getArguments()[1]; 151 152 return appRestrictions.get(Pair.create(pkg, user)); 153 } 154 }).when(mContext.userManager).getApplicationRestrictions( 155 anyString(), any(UserHandle.class)); 156 157 // Add the first secondary user. 158 mContext.addUser(DpmMockContext.CALLER_USER_HANDLE, 0); 159 } 160 161 private void setAsProfileOwner(ComponentName admin) { 162 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 163 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 164 165 // PO needs to be an DA. 166 dpm.setActiveAdmin(admin, /* replace =*/ false); 167 168 // Fire! 169 assertTrue(dpm.setProfileOwner(admin, "owner-name", DpmMockContext.CALLER_USER_HANDLE)); 170 171 // Check 172 assertEquals(admin, dpm.getProfileOwnerAsUser(DpmMockContext.CALLER_USER_HANDLE)); 173 } 174 175 public void testHasNoFeature() throws Exception { 176 when(mContext.packageManager.hasSystemFeature(eq(PackageManager.FEATURE_DEVICE_ADMIN))) 177 .thenReturn(false); 178 179 LocalServices.removeServiceForTest(DevicePolicyManagerInternal.class); 180 new DevicePolicyManagerServiceTestable(mContext, dataDir); 181 182 // If the device has no DPMS feature, it shouldn't register the local service. 183 assertNull(LocalServices.getService(DevicePolicyManagerInternal.class)); 184 } 185 186 /** 187 * Caller doesn't have proper permissions. 188 */ 189 public void testSetActiveAdmin_SecurityException() { 190 // 1. Failure cases. 191 192 // Caller doesn't have MANAGE_DEVICE_ADMINS. 193 try { 194 dpm.setActiveAdmin(admin1, false); 195 fail("Didn't throw SecurityException"); 196 } catch (SecurityException expected) { 197 } 198 199 // Caller has MANAGE_DEVICE_ADMINS, but for different user. 200 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 201 try { 202 dpm.setActiveAdmin(admin1, false, DpmMockContext.CALLER_USER_HANDLE + 1); 203 fail("Didn't throw SecurityException"); 204 } catch (SecurityException expected) { 205 } 206 } 207 208 /** 209 * Test for: 210 * {@link DevicePolicyManager#setActiveAdmin} 211 * with replace=false and replace=true 212 * {@link DevicePolicyManager#isAdminActive} 213 * {@link DevicePolicyManager#isAdminActiveAsUser} 214 * {@link DevicePolicyManager#getActiveAdmins} 215 * {@link DevicePolicyManager#getActiveAdminsAsUser} 216 */ 217 public void testSetActiveAdmin() throws Exception { 218 // 1. Make sure the caller has proper permissions. 219 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 220 221 // 2. Call the API. 222 dpm.setActiveAdmin(admin1, /* replace =*/ false); 223 224 // 3. Verify internal calls. 225 226 // Check if the boradcast is sent. 227 verify(mContext.spiedContext).sendBroadcastAsUser( 228 MockUtils.checkIntentAction( 229 DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED), 230 MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE)); 231 verify(mContext.spiedContext).sendBroadcastAsUser( 232 MockUtils.checkIntentAction( 233 DeviceAdminReceiver.ACTION_DEVICE_ADMIN_ENABLED), 234 MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE)); 235 236 verify(mContext.ipackageManager, times(1)).setApplicationEnabledSetting( 237 eq(admin1.getPackageName()), 238 eq(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT), 239 eq(PackageManager.DONT_KILL_APP), 240 eq(DpmMockContext.CALLER_USER_HANDLE), 241 anyString()); 242 243 // TODO Verify other calls too. 244 245 // Make sure it's active admin1. 246 assertTrue(dpm.isAdminActive(admin1)); 247 assertFalse(dpm.isAdminActive(admin2)); 248 assertFalse(dpm.isAdminActive(admin3)); 249 250 // But not admin1 for a different user. 251 252 // For this to work, caller needs android.permission.INTERACT_ACROSS_USERS_FULL. 253 // (Because we're checking a different user's status from CALLER_USER_HANDLE.) 254 mContext.callerPermissions.add("android.permission.INTERACT_ACROSS_USERS_FULL"); 255 256 assertFalse(dpm.isAdminActiveAsUser(admin1, DpmMockContext.CALLER_USER_HANDLE + 1)); 257 assertFalse(dpm.isAdminActiveAsUser(admin2, DpmMockContext.CALLER_USER_HANDLE + 1)); 258 259 mContext.callerPermissions.remove("android.permission.INTERACT_ACROSS_USERS_FULL"); 260 261 // Next, add one more admin. 262 // Before doing so, update the application info, now it's enabled. 263 setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID, 264 PackageManager.COMPONENT_ENABLED_STATE_ENABLED); 265 266 dpm.setActiveAdmin(admin2, /* replace =*/ false); 267 268 // Now we have two admins. 269 assertTrue(dpm.isAdminActive(admin1)); 270 assertTrue(dpm.isAdminActive(admin2)); 271 assertFalse(dpm.isAdminActive(admin3)); 272 273 // Admin2 was already enabled, so setApplicationEnabledSetting() shouldn't have called 274 // again. (times(1) because it was previously called for admin1) 275 verify(mContext.ipackageManager, times(1)).setApplicationEnabledSetting( 276 eq(admin1.getPackageName()), 277 eq(PackageManager.COMPONENT_ENABLED_STATE_DEFAULT), 278 eq(PackageManager.DONT_KILL_APP), 279 eq(DpmMockContext.CALLER_USER_HANDLE), 280 anyString()); 281 282 // 4. Add the same admin1 again without replace, which should throw. 283 try { 284 dpm.setActiveAdmin(admin1, /* replace =*/ false); 285 fail("Didn't throw"); 286 } catch (IllegalArgumentException expected) { 287 } 288 289 // 5. Add the same admin1 again with replace, which should succeed. 290 dpm.setActiveAdmin(admin1, /* replace =*/ true); 291 292 // TODO make sure it's replaced. 293 294 // 6. Test getActiveAdmins() 295 List<ComponentName> admins = dpm.getActiveAdmins(); 296 assertEquals(2, admins.size()); 297 assertEquals(admin1, admins.get(0)); 298 assertEquals(admin2, admins.get(1)); 299 300 // Another user has no admins. 301 mContext.callerPermissions.add("android.permission.INTERACT_ACROSS_USERS_FULL"); 302 303 assertEquals(0, DpmTestUtils.getListSizeAllowingNull( 304 dpm.getActiveAdminsAsUser(DpmMockContext.CALLER_USER_HANDLE + 1))); 305 306 mContext.callerPermissions.remove("android.permission.INTERACT_ACROSS_USERS_FULL"); 307 } 308 309 public void testSetActiveAdmin_multiUsers() throws Exception { 310 311 final int ANOTHER_USER_ID = 100; 312 final int ANOTHER_ADMIN_UID = UserHandle.getUid(ANOTHER_USER_ID, 20456); 313 314 mMockContext.addUser(ANOTHER_USER_ID, 0); // Add one more user. 315 316 // Set up pacakge manager for the other user. 317 setUpPackageManagerForAdmin(admin2, ANOTHER_ADMIN_UID); 318 319 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 320 321 dpm.setActiveAdmin(admin1, /* replace =*/ false); 322 323 mMockContext.binder.callingUid = ANOTHER_ADMIN_UID; 324 dpm.setActiveAdmin(admin2, /* replace =*/ false); 325 326 327 mMockContext.binder.callingUid = DpmMockContext.CALLER_UID; 328 assertTrue(dpm.isAdminActive(admin1)); 329 assertFalse(dpm.isAdminActive(admin2)); 330 331 mMockContext.binder.callingUid = ANOTHER_ADMIN_UID; 332 assertFalse(dpm.isAdminActive(admin1)); 333 assertTrue(dpm.isAdminActive(admin2)); 334 } 335 336 /** 337 * Test for: 338 * {@link DevicePolicyManager#setActiveAdmin} 339 * with replace=false 340 */ 341 public void testSetActiveAdmin_twiceWithoutReplace() throws Exception { 342 // 1. Make sure the caller has proper permissions. 343 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 344 345 dpm.setActiveAdmin(admin1, /* replace =*/ false); 346 assertTrue(dpm.isAdminActive(admin1)); 347 348 // Add the same admin1 again without replace, which should throw. 349 try { 350 dpm.setActiveAdmin(admin1, /* replace =*/ false); 351 fail("Didn't throw"); 352 } catch (IllegalArgumentException expected) { 353 } 354 } 355 356 /** 357 * Test for: 358 * {@link DevicePolicyManager#setActiveAdmin} when the admin isn't protected with 359 * BIND_DEVICE_ADMIN. 360 */ 361 public void testSetActiveAdmin_permissionCheck() throws Exception { 362 // 1. Make sure the caller has proper permissions. 363 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 364 365 try { 366 dpm.setActiveAdmin(adminNoPerm, /* replace =*/ false); 367 fail(); 368 } catch (IllegalArgumentException expected) { 369 assertTrue(expected.getMessage().contains(permission.BIND_DEVICE_ADMIN)); 370 } 371 assertFalse(dpm.isAdminActive(adminNoPerm)); 372 373 // Change the target API level to MNC. Now it can be set as DA. 374 setUpPackageManagerForAdmin(adminNoPerm, DpmMockContext.CALLER_UID, null, 375 VERSION_CODES.M); 376 dpm.setActiveAdmin(adminNoPerm, /* replace =*/ false); 377 assertTrue(dpm.isAdminActive(adminNoPerm)); 378 379 // TODO Test the "load from the file" case where DA will still be loaded even without 380 // BIND_DEVICE_ADMIN and target API is N. 381 } 382 383 /** 384 * Test for: 385 * {@link DevicePolicyManager#removeActiveAdmin} 386 */ 387 public void testRemoveActiveAdmin_SecurityException() { 388 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 389 390 // Add admin. 391 392 dpm.setActiveAdmin(admin1, /* replace =*/ false); 393 394 assertTrue(dpm.isAdminActive(admin1)); 395 396 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 397 398 // Directly call the DPMS method with a different userid, which should fail. 399 try { 400 dpms.removeActiveAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE + 1); 401 fail("Didn't throw SecurityException"); 402 } catch (SecurityException expected) { 403 } 404 405 // Try to remove active admin with a different caller userid should fail too, without 406 // having MANAGE_DEVICE_ADMINS. 407 mContext.callerPermissions.clear(); 408 409 // Change the caller, and call into DPMS directly with a different user-id. 410 411 mContext.binder.callingUid = 1234567; 412 try { 413 dpms.removeActiveAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE); 414 fail("Didn't throw SecurityException"); 415 } catch (SecurityException expected) { 416 } 417 } 418 419 /** 420 * {@link DevicePolicyManager#removeActiveAdmin} should fail with the user is not unlocked 421 * (because we can't send the remove broadcast). 422 */ 423 public void testRemoveActiveAdmin_userNotRunningOrLocked() { 424 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 425 426 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 427 428 // Add admin. 429 430 dpm.setActiveAdmin(admin1, /* replace =*/ false); 431 432 assertTrue(dpm.isAdminActive(admin1)); 433 434 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 435 436 // 1. User not unlocked. 437 when(mContext.userManager.isUserUnlocked(eq(DpmMockContext.CALLER_USER_HANDLE))) 438 .thenReturn(false); 439 try { 440 dpm.removeActiveAdmin(admin1); 441 fail("Didn't throw IllegalStateException"); 442 } catch (IllegalStateException expected) { 443 MoreAsserts.assertContainsRegex( 444 "User must be running and unlocked", expected.getMessage()); 445 } 446 447 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 448 449 // 2. User unlocked. 450 when(mContext.userManager.isUserUnlocked(eq(DpmMockContext.CALLER_USER_HANDLE))) 451 .thenReturn(true); 452 453 dpm.removeActiveAdmin(admin1); 454 455 assertTrue(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 456 } 457 458 /** 459 * Test for: 460 * {@link DevicePolicyManager#removeActiveAdmin} 461 */ 462 public void testRemoveActiveAdmin_fromDifferentUserWithINTERACT_ACROSS_USERS_FULL() { 463 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 464 465 // Add admin1. 466 467 dpm.setActiveAdmin(admin1, /* replace =*/ false); 468 469 assertTrue(dpm.isAdminActive(admin1)); 470 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 471 472 // Different user, but should work, because caller has proper permissions. 473 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 474 475 // Change the caller, and call into DPMS directly with a different user-id. 476 mContext.binder.callingUid = 1234567; 477 478 dpms.removeActiveAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE); 479 480 assertTrue(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 481 482 // TODO DO Still can't be removed in this case. 483 } 484 485 /** 486 * Test for: 487 * {@link DevicePolicyManager#removeActiveAdmin} 488 */ 489 public void testRemoveActiveAdmin_sameUserNoMANAGE_DEVICE_ADMINS() { 490 // Need MANAGE_DEVICE_ADMINS for setActiveAdmin. We'll remove it later. 491 mContext.callerPermissions.add(android.Manifest.permission.MANAGE_DEVICE_ADMINS); 492 493 // Add admin1. 494 495 dpm.setActiveAdmin(admin1, /* replace =*/ false); 496 497 assertTrue(dpm.isAdminActive(admin1)); 498 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 499 500 // Broadcast from saveSettingsLocked(). 501 verify(mContext.spiedContext, times(1)).sendBroadcastAsUser( 502 MockUtils.checkIntentAction( 503 DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED), 504 MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE)); 505 506 // Remove. No permissions, but same user, so it'll work. 507 mContext.callerPermissions.clear(); 508 dpm.removeActiveAdmin(admin1); 509 510 final ArgumentCaptor<BroadcastReceiver> brCap = 511 ArgumentCaptor.forClass(BroadcastReceiver.class); 512 513 // Is removing now, but not removed yet. 514 assertTrue(dpm.isAdminActive(admin1)); 515 assertTrue(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 516 517 verify(mContext.spiedContext).sendOrderedBroadcastAsUser( 518 MockUtils.checkIntentAction( 519 DeviceAdminReceiver.ACTION_DEVICE_ADMIN_DISABLED), 520 MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE), 521 isNull(String.class), 522 brCap.capture(), 523 eq(dpms.mHandler), 524 eq(Activity.RESULT_OK), 525 isNull(String.class), 526 isNull(Bundle.class)); 527 528 brCap.getValue().onReceive(mContext, null); 529 530 assertFalse(dpm.isAdminActive(admin1)); 531 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 532 533 // Again broadcast from saveSettingsLocked(). 534 verify(mContext.spiedContext, times(2)).sendBroadcastAsUser( 535 MockUtils.checkIntentAction( 536 DevicePolicyManager.ACTION_DEVICE_POLICY_MANAGER_STATE_CHANGED), 537 MockUtils.checkUserHandle(DpmMockContext.CALLER_USER_HANDLE)); 538 539 // TODO Check other internal calls. 540 } 541 542 /** 543 * Test for: {@link DevicePolicyManager#setDeviceOwner} DO on system user installs 544 * successfully. 545 */ 546 public void testSetDeviceOwner() throws Exception { 547 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 548 mContext.callerPermissions.add(permission.MANAGE_USERS); 549 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 550 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 551 552 // In this test, change the caller user to "system". 553 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 554 555 // Make sure admin1 is installed on system user. 556 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 557 558 // Check various get APIs. 559 checkGetDeviceOwnerInfoApi(dpm, /* hasDeviceOwner =*/ false); 560 561 // DO needs to be an DA. 562 dpm.setActiveAdmin(admin1, /* replace =*/ false); 563 564 // Fire! 565 assertTrue(dpm.setDeviceOwner(admin1, "owner-name")); 566 567 // getDeviceOwnerComponent should return the admin1 component. 568 assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser()); 569 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 570 571 // Check various get APIs. 572 checkGetDeviceOwnerInfoApi(dpm, /* hasDeviceOwner =*/ true); 573 574 // getDeviceOwnerComponent should *NOT* return the admin1 component for other users. 575 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 576 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 577 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 578 579 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 580 581 // Verify internal calls. 582 verify(mContext.iactivityManager, times(1)).updateDeviceOwner( 583 eq(admin1.getPackageName())); 584 585 // TODO We should check if the caller has called clearCallerIdentity(). 586 verify(mContext.ibackupManager, times(1)).setBackupServiceActive( 587 eq(UserHandle.USER_SYSTEM), eq(false)); 588 589 verify(mContext.spiedContext, times(1)).sendBroadcastAsUser( 590 MockUtils.checkIntentAction(DevicePolicyManager.ACTION_DEVICE_OWNER_CHANGED), 591 MockUtils.checkUserHandle(UserHandle.USER_SYSTEM)); 592 593 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 594 595 // Try to set a profile owner on the same user, which should fail. 596 setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_SYSTEM_USER_UID); 597 dpm.setActiveAdmin(admin2, /* refreshing= */ true, UserHandle.USER_SYSTEM); 598 try { 599 dpm.setProfileOwner(admin2, "owner-name", UserHandle.USER_SYSTEM); 600 fail("IllegalStateException not thrown"); 601 } catch (IllegalStateException expected) { 602 assertTrue("Message was: " + expected.getMessage(), 603 expected.getMessage().contains("already has a device owner")); 604 } 605 606 // DO admin can't be deactivated. 607 dpm.removeActiveAdmin(admin1); 608 assertTrue(dpm.isAdminActive(admin1)); 609 610 // TODO Test getDeviceOwnerName() too. To do so, we need to change 611 // DPMS.getApplicationLabel() because Context.createPackageContextAsUser() is not mockable. 612 } 613 614 private void checkGetDeviceOwnerInfoApi(DevicePolicyManager dpm, boolean hasDeviceOwner) { 615 final int origCallingUser = mContext.binder.callingUid; 616 final List origPermissions = new ArrayList(mContext.callerPermissions); 617 mContext.callerPermissions.clear(); 618 619 mContext.callerPermissions.add(permission.MANAGE_USERS); 620 621 mContext.binder.callingUid = Process.SYSTEM_UID; 622 623 // TODO Test getDeviceOwnerName() too. To do so, we need to change 624 // DPMS.getApplicationLabel() because Context.createPackageContextAsUser() is not mockable. 625 if (hasDeviceOwner) { 626 assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName())); 627 assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 628 assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser()); 629 630 assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 631 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 632 assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId()); 633 } else { 634 assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName())); 635 assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 636 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 637 638 assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 639 assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser()); 640 assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId()); 641 } 642 643 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 644 if (hasDeviceOwner) { 645 assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName())); 646 assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 647 assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser()); 648 649 assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 650 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 651 assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId()); 652 } else { 653 assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName())); 654 assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 655 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 656 657 assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 658 assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser()); 659 assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId()); 660 } 661 662 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 663 // Still with MANAGE_USERS. 664 assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName())); 665 assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 666 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 667 668 if (hasDeviceOwner) { 669 assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 670 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 671 assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId()); 672 } else { 673 assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 674 assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser()); 675 assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId()); 676 } 677 678 mContext.binder.callingUid = Process.SYSTEM_UID; 679 mContext.callerPermissions.remove(permission.MANAGE_USERS); 680 // System can still call "OnAnyUser" without MANAGE_USERS. 681 if (hasDeviceOwner) { 682 assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName())); 683 assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 684 assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser()); 685 686 assertTrue(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 687 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 688 assertEquals(UserHandle.USER_SYSTEM, dpm.getDeviceOwnerUserId()); 689 } else { 690 assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName())); 691 assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 692 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 693 694 assertFalse(dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName())); 695 assertEquals(null, dpm.getDeviceOwnerComponentOnAnyUser()); 696 assertEquals(UserHandle.USER_NULL, dpm.getDeviceOwnerUserId()); 697 } 698 699 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 700 // Still no MANAGE_USERS. 701 if (hasDeviceOwner) { 702 assertTrue(dpm.isDeviceOwnerApp(admin1.getPackageName())); 703 assertTrue(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 704 assertEquals(admin1, dpm.getDeviceOwnerComponentOnCallingUser()); 705 } else { 706 assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName())); 707 assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 708 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 709 } 710 711 try { 712 dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()); 713 fail(); 714 } catch (SecurityException expected) { 715 } 716 try { 717 dpm.getDeviceOwnerComponentOnAnyUser(); 718 fail(); 719 } catch (SecurityException expected) { 720 } 721 try { 722 dpm.getDeviceOwnerUserId(); 723 fail(); 724 } catch (SecurityException expected) { 725 } 726 try { 727 dpm.getDeviceOwnerNameOnAnyUser(); 728 fail(); 729 } catch (SecurityException expected) { 730 } 731 732 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 733 // Still no MANAGE_USERS. 734 assertFalse(dpm.isDeviceOwnerApp(admin1.getPackageName())); 735 assertFalse(dpm.isDeviceOwnerAppOnCallingUser(admin1.getPackageName())); 736 assertEquals(null, dpm.getDeviceOwnerComponentOnCallingUser()); 737 738 try { 739 dpm.isDeviceOwnerAppOnAnyUser(admin1.getPackageName()); 740 fail(); 741 } catch (SecurityException expected) { 742 } 743 try { 744 dpm.getDeviceOwnerComponentOnAnyUser(); 745 fail(); 746 } catch (SecurityException expected) { 747 } 748 try { 749 dpm.getDeviceOwnerUserId(); 750 fail(); 751 } catch (SecurityException expected) { 752 } 753 try { 754 dpm.getDeviceOwnerNameOnAnyUser(); 755 fail(); 756 } catch (SecurityException expected) { 757 } 758 759 // Restore. 760 mContext.binder.callingUid = origCallingUser; 761 mContext.callerPermissions.addAll(origPermissions); 762 } 763 764 765 /** 766 * Test for: {@link DevicePolicyManager#setDeviceOwner} Package doesn't exist. 767 */ 768 public void testSetDeviceOwner_noSuchPackage() { 769 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 770 mContext.callerPermissions.add(permission.MANAGE_USERS); 771 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 772 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 773 774 // Call from a process on the system user. 775 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 776 777 try { 778 dpm.setDeviceOwner(new ComponentName("a.b.c", ".def")); 779 fail("Didn't throw IllegalArgumentException"); 780 } catch (IllegalArgumentException expected) { 781 assertTrue("Message was: " + expected.getMessage(), 782 expected.getMessage().contains("Invalid component")); 783 } 784 } 785 786 public void testSetDeviceOwner_failures() throws Exception { 787 // TODO Test more failure cases. Basically test all chacks in enforceCanSetDeviceOwner(). 788 } 789 790 public void testClearDeviceOwner() throws Exception { 791 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 792 mContext.callerPermissions.add(permission.MANAGE_USERS); 793 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 794 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 795 796 // Set admin1 as a DA to the secondary user. 797 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID); 798 799 dpm.setActiveAdmin(admin1, /* replace =*/ false); 800 801 // Set admin 1 as the DO to the system user. 802 803 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 804 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 805 dpm.setActiveAdmin(admin1, /* replace =*/ false); 806 assertTrue(dpm.setDeviceOwner(admin1, "owner-name")); 807 808 // Verify internal calls. 809 verify(mContext.iactivityManager, times(1)).updateDeviceOwner( 810 eq(admin1.getPackageName())); 811 812 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 813 814 dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADD_USER); 815 816 assertTrue(dpm.isAdminActive(admin1)); 817 assertFalse(dpm.isRemovingAdmin(admin1, UserHandle.USER_SYSTEM)); 818 819 // Set up other mocks. 820 when(mContext.userManager.getUserRestrictions()).thenReturn(new Bundle()); 821 822 // Now call clear. 823 doReturn(DpmMockContext.CALLER_SYSTEM_USER_UID).when(mContext.packageManager).getPackageUidAsUser( 824 eq(admin1.getPackageName()), 825 anyInt()); 826 827 // But first pretend the user is locked. Then it should fail. 828 when(mContext.userManager.isUserUnlocked(anyInt())).thenReturn(false); 829 try { 830 dpm.clearDeviceOwnerApp(admin1.getPackageName()); 831 fail("Didn't throw IllegalStateException"); 832 } catch (IllegalStateException expected) { 833 MoreAsserts.assertContainsRegex( 834 "User must be running and unlocked", expected.getMessage()); 835 } 836 837 when(mContext.userManager.isUserUnlocked(anyInt())).thenReturn(true); 838 reset(mContext.userManagerInternal); 839 dpm.clearDeviceOwnerApp(admin1.getPackageName()); 840 841 // Now DO shouldn't be set. 842 assertNull(dpm.getDeviceOwnerComponentOnAnyUser()); 843 844 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 845 eq(UserHandle.USER_SYSTEM), 846 MockUtils.checkUserRestrictions(), 847 MockUtils.checkUserRestrictions() 848 ); 849 850 assertTrue(dpm.isAdminActive(admin1)); 851 assertTrue(dpm.isRemovingAdmin(admin1, UserHandle.USER_SYSTEM)); 852 853 // TODO Check other calls. 854 } 855 856 public void testClearDeviceOwner_fromDifferentUser() throws Exception { 857 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 858 mContext.callerPermissions.add(permission.MANAGE_USERS); 859 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 860 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 861 862 // Set admin1 as a DA to the secondary user. 863 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID); 864 865 dpm.setActiveAdmin(admin1, /* replace =*/ false); 866 867 // Set admin 1 as the DO to the system user. 868 869 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 870 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 871 dpm.setActiveAdmin(admin1, /* replace =*/ false); 872 assertTrue(dpm.setDeviceOwner(admin1, "owner-name")); 873 874 // Verify internal calls. 875 verify(mContext.iactivityManager, times(1)).updateDeviceOwner( 876 eq(admin1.getPackageName())); 877 878 assertEquals(admin1, dpm.getDeviceOwnerComponentOnAnyUser()); 879 880 // Now call clear from the secondary user, which should throw. 881 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 882 883 // Now call clear. 884 doReturn(DpmMockContext.CALLER_UID).when(mContext.packageManager).getPackageUidAsUser( 885 eq(admin1.getPackageName()), 886 anyInt()); 887 try { 888 dpm.clearDeviceOwnerApp(admin1.getPackageName()); 889 fail("Didn't throw"); 890 } catch (SecurityException e) { 891 assertEquals("clearDeviceOwner can only be called by the device owner", e.getMessage()); 892 } 893 894 // DO shouldn't be removed. 895 assertTrue(dpm.isDeviceManaged()); 896 } 897 898 public void testSetProfileOwner() throws Exception { 899 setAsProfileOwner(admin1); 900 901 // PO admin can't be deactivated. 902 dpm.removeActiveAdmin(admin1); 903 assertTrue(dpm.isAdminActive(admin1)); 904 905 // Try setting DO on the same user, which should fail. 906 setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID); 907 dpm.setActiveAdmin(admin2, /* refreshing= */ true, DpmMockContext.CALLER_USER_HANDLE); 908 try { 909 dpm.setDeviceOwner(admin2, "owner-name", DpmMockContext.CALLER_USER_HANDLE); 910 fail("IllegalStateException not thrown"); 911 } catch (IllegalStateException expected) { 912 assertTrue("Message was: " + expected.getMessage(), 913 expected.getMessage().contains("already has a profile owner")); 914 } 915 } 916 917 public void testClearProfileOwner() throws Exception { 918 setAsProfileOwner(admin1); 919 920 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 921 922 assertTrue(dpm.isProfileOwnerApp(admin1.getPackageName())); 923 assertFalse(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 924 925 // First try when the user is locked, which should fail. 926 when(mContext.userManager.isUserUnlocked(anyInt())) 927 .thenReturn(false); 928 try { 929 dpm.clearProfileOwner(admin1); 930 fail("Didn't throw IllegalStateException"); 931 } catch (IllegalStateException expected) { 932 MoreAsserts.assertContainsRegex( 933 "User must be running and unlocked", expected.getMessage()); 934 } 935 // Clear, really. 936 when(mContext.userManager.isUserUnlocked(anyInt())) 937 .thenReturn(true); 938 dpm.clearProfileOwner(admin1); 939 940 // Check 941 assertFalse(dpm.isProfileOwnerApp(admin1.getPackageName())); 942 assertTrue(dpm.isRemovingAdmin(admin1, DpmMockContext.CALLER_USER_HANDLE)); 943 } 944 945 public void testSetProfileOwner_failures() throws Exception { 946 // TODO Test more failure cases. Basically test all chacks in enforceCanSetProfileOwner(). 947 } 948 949 public void testGetDeviceOwnerAdminLocked() throws Exception { 950 checkDeviceOwnerWithMultipleDeviceAdmins(); 951 } 952 953 private void checkDeviceOwnerWithMultipleDeviceAdmins() throws Exception { 954 // In ths test, we use 3 users (system + 2 secondary users), set some device admins to them, 955 // set admin2 on CALLER_USER_HANDLE as DO, then call getDeviceOwnerAdminLocked() to 956 // make sure it gets the right component from the right user. 957 958 final int ANOTHER_USER_ID = 100; 959 final int ANOTHER_ADMIN_UID = UserHandle.getUid(ANOTHER_USER_ID, 456); 960 961 mMockContext.addUser(ANOTHER_USER_ID, 0); // Add one more user. 962 963 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 964 mContext.callerPermissions.add(permission.MANAGE_USERS); 965 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 966 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 967 968 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 969 970 // Make sure the admin packge is installed to each user. 971 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 972 setUpPackageManagerForAdmin(admin3, DpmMockContext.CALLER_SYSTEM_USER_UID); 973 974 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID); 975 setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_UID); 976 977 setUpPackageManagerForAdmin(admin2, ANOTHER_ADMIN_UID); 978 979 980 // Set active admins to the users. 981 dpm.setActiveAdmin(admin1, /* replace =*/ false); 982 dpm.setActiveAdmin(admin3, /* replace =*/ false); 983 984 dpm.setActiveAdmin(admin1, /* replace =*/ false, DpmMockContext.CALLER_USER_HANDLE); 985 dpm.setActiveAdmin(admin2, /* replace =*/ false, DpmMockContext.CALLER_USER_HANDLE); 986 987 dpm.setActiveAdmin(admin2, /* replace =*/ false, ANOTHER_USER_ID); 988 989 // Set DO on the first non-system user. 990 mContext.setUserRunning(DpmMockContext.CALLER_USER_HANDLE, true); 991 assertTrue(dpm.setDeviceOwner(admin2, "owner-name", DpmMockContext.CALLER_USER_HANDLE)); 992 993 assertEquals(admin2, dpms.getDeviceOwnerComponent(/* callingUserOnly =*/ false)); 994 995 // Then check getDeviceOwnerAdminLocked(). 996 assertEquals(admin2, dpms.getDeviceOwnerAdminLocked().info.getComponent()); 997 assertEquals(DpmMockContext.CALLER_UID, dpms.getDeviceOwnerAdminLocked().getUid()); 998 } 999 1000 /** 1001 * This essentially tests 1002 * {@code DevicePolicyManagerService.findOwnerComponentIfNecessaryLocked()}. (which is private.) 1003 * 1004 * We didn't use to persist the DO component class name, but now we do, and the above method 1005 * finds the right component from a package name upon migration. 1006 */ 1007 public void testDeviceOwnerMigration() throws Exception { 1008 checkDeviceOwnerWithMultipleDeviceAdmins(); 1009 1010 // Overwrite the device owner setting and clears the clas name. 1011 dpms.mOwners.setDeviceOwner( 1012 new ComponentName(admin2.getPackageName(), ""), 1013 "owner-name", DpmMockContext.CALLER_USER_HANDLE); 1014 dpms.mOwners.writeDeviceOwner(); 1015 1016 // Make sure the DO component name doesn't have a class name. 1017 assertEquals("", dpms.getDeviceOwnerComponent(/* callingUserOnly =*/ false).getClassName()); 1018 1019 // Then create a new DPMS to have it load the settings from files. 1020 when(mContext.userManager.getUserRestrictions(any(UserHandle.class))) 1021 .thenReturn(new Bundle()); 1022 initializeDpms(); 1023 1024 // Now the DO component name is a full name. 1025 // *BUT* because both admin1 and admin2 belong to the same package, we think admin1 is the 1026 // DO. 1027 assertEquals(admin1, dpms.getDeviceOwnerComponent(/* callingUserOnly =*/ false)); 1028 } 1029 1030 public void testSetGetApplicationRestriction() { 1031 setAsProfileOwner(admin1); 1032 1033 { 1034 Bundle rest = new Bundle(); 1035 rest.putString("KEY_STRING", "Foo1"); 1036 dpm.setApplicationRestrictions(admin1, "pkg1", rest); 1037 } 1038 1039 { 1040 Bundle rest = new Bundle(); 1041 rest.putString("KEY_STRING", "Foo2"); 1042 dpm.setApplicationRestrictions(admin1, "pkg2", rest); 1043 } 1044 1045 { 1046 Bundle returned = dpm.getApplicationRestrictions(admin1, "pkg1"); 1047 assertNotNull(returned); 1048 assertEquals(returned.size(), 1); 1049 assertEquals(returned.get("KEY_STRING"), "Foo1"); 1050 } 1051 1052 { 1053 Bundle returned = dpm.getApplicationRestrictions(admin1, "pkg2"); 1054 assertNotNull(returned); 1055 assertEquals(returned.size(), 1); 1056 assertEquals(returned.get("KEY_STRING"), "Foo2"); 1057 } 1058 1059 dpm.setApplicationRestrictions(admin1, "pkg2", new Bundle()); 1060 assertEquals(0, dpm.getApplicationRestrictions(admin1, "pkg2").size()); 1061 } 1062 1063 public void testApplicationRestrictionsManagingApp() throws Exception { 1064 setAsProfileOwner(admin1); 1065 1066 final String nonExistAppRestrictionsManagerPackage = "com.google.app.restrictions.manager2"; 1067 final String appRestrictionsManagerPackage = "com.google.app.restrictions.manager"; 1068 final int appRestrictionsManagerAppId = 20987; 1069 final int appRestrictionsManagerUid = UserHandle.getUid( 1070 DpmMockContext.CALLER_USER_HANDLE, appRestrictionsManagerAppId); 1071 doReturn(appRestrictionsManagerUid).when(mContext.packageManager).getPackageUidAsUser( 1072 eq(appRestrictionsManagerPackage), 1073 eq(DpmMockContext.CALLER_USER_HANDLE)); 1074 mContext.binder.callingUid = appRestrictionsManagerUid; 1075 1076 final PackageInfo pi = new PackageInfo(); 1077 pi.applicationInfo = new ApplicationInfo(); 1078 pi.applicationInfo.flags = ApplicationInfo.FLAG_HAS_CODE; 1079 doReturn(pi).when(mContext.ipackageManager).getPackageInfo( 1080 eq(appRestrictionsManagerPackage), 1081 anyInt(), 1082 eq(DpmMockContext.CALLER_USER_HANDLE)); 1083 1084 // appRestrictionsManager package shouldn't be able to manage restrictions as the PO hasn't 1085 // delegated that permission yet. 1086 assertFalse(dpm.isCallerApplicationRestrictionsManagingPackage()); 1087 Bundle rest = new Bundle(); 1088 rest.putString("KEY_STRING", "Foo1"); 1089 try { 1090 dpm.setApplicationRestrictions(null, "pkg1", rest); 1091 fail("Didn't throw expected SecurityException"); 1092 } catch (SecurityException expected) { 1093 MoreAsserts.assertContainsRegex( 1094 "caller cannot manage application restrictions", expected.getMessage()); 1095 } 1096 try { 1097 dpm.getApplicationRestrictions(null, "pkg1"); 1098 fail("Didn't throw expected SecurityException"); 1099 } catch (SecurityException expected) { 1100 MoreAsserts.assertContainsRegex( 1101 "caller cannot manage application restrictions", expected.getMessage()); 1102 } 1103 1104 // Check via the profile owner that no restrictions were set. 1105 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 1106 assertEquals(0, dpm.getApplicationRestrictions(admin1, "pkg1").size()); 1107 1108 // Check the API does not allow setting a non-existent package 1109 try { 1110 dpm.setApplicationRestrictionsManagingPackage(admin1, 1111 nonExistAppRestrictionsManagerPackage); 1112 fail("Non-existent app set as app restriction manager."); 1113 } catch (IllegalArgumentException expected) { 1114 MoreAsserts.assertContainsRegex( 1115 "is not installed on the current user", expected.getMessage()); 1116 } 1117 1118 // Let appRestrictionsManagerPackage manage app restrictions 1119 dpm.setApplicationRestrictionsManagingPackage(admin1, appRestrictionsManagerPackage); 1120 assertEquals(appRestrictionsManagerPackage, 1121 dpm.getApplicationRestrictionsManagingPackage(admin1)); 1122 1123 // Now that package should be able to set and retrieve app restrictions. 1124 mContext.binder.callingUid = appRestrictionsManagerUid; 1125 assertTrue(dpm.isCallerApplicationRestrictionsManagingPackage()); 1126 dpm.setApplicationRestrictions(null, "pkg1", rest); 1127 Bundle returned = dpm.getApplicationRestrictions(null, "pkg1"); 1128 assertEquals(1, returned.size(), 1); 1129 assertEquals("Foo1", returned.get("KEY_STRING")); 1130 1131 // The same app running on a separate user shouldn't be able to manage app restrictions. 1132 mContext.binder.callingUid = UserHandle.getUid( 1133 UserHandle.USER_SYSTEM, appRestrictionsManagerAppId); 1134 assertFalse(dpm.isCallerApplicationRestrictionsManagingPackage()); 1135 try { 1136 dpm.setApplicationRestrictions(null, "pkg1", rest); 1137 fail("Didn't throw expected SecurityException"); 1138 } catch (SecurityException expected) { 1139 MoreAsserts.assertContainsRegex( 1140 "caller cannot manage application restrictions", expected.getMessage()); 1141 } 1142 1143 // The DPM is still able to manage app restrictions, even if it allowed another app to do it 1144 // too. 1145 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 1146 assertEquals(returned, dpm.getApplicationRestrictions(admin1, "pkg1")); 1147 dpm.setApplicationRestrictions(admin1, "pkg1", null); 1148 assertEquals(0, dpm.getApplicationRestrictions(admin1, "pkg1").size()); 1149 1150 // Removing the ability for the package to manage app restrictions. 1151 dpm.setApplicationRestrictionsManagingPackage(admin1, null); 1152 assertNull(dpm.getApplicationRestrictionsManagingPackage(admin1)); 1153 mContext.binder.callingUid = appRestrictionsManagerUid; 1154 assertFalse(dpm.isCallerApplicationRestrictionsManagingPackage()); 1155 try { 1156 dpm.setApplicationRestrictions(null, "pkg1", null); 1157 fail("Didn't throw expected SecurityException"); 1158 } catch (SecurityException expected) { 1159 MoreAsserts.assertContainsRegex( 1160 "caller cannot manage application restrictions", expected.getMessage()); 1161 } 1162 } 1163 1164 public void testSetUserRestriction_asDo() throws Exception { 1165 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 1166 mContext.callerPermissions.add(permission.MANAGE_USERS); 1167 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1168 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 1169 1170 // First, set DO. 1171 1172 // Call from a process on the system user. 1173 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1174 1175 // Make sure admin1 is installed on system user. 1176 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 1177 1178 // Call. 1179 dpm.setActiveAdmin(admin1, /* replace =*/ false, UserHandle.USER_SYSTEM); 1180 assertTrue(dpm.setDeviceOwner(admin1, "owner-name", 1181 UserHandle.USER_SYSTEM)); 1182 1183 DpmTestUtils.assertRestrictions( 1184 DpmTestUtils.newRestrictions(), 1185 dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions() 1186 ); 1187 DpmTestUtils.assertRestrictions( 1188 DpmTestUtils.newRestrictions(), 1189 dpm.getUserRestrictions(admin1) 1190 ); 1191 1192 reset(mContext.userManagerInternal); 1193 1194 dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADD_USER); 1195 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1196 eq(UserHandle.USER_SYSTEM), 1197 MockUtils.checkUserRestrictions(), 1198 MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADD_USER) 1199 ); 1200 reset(mContext.userManagerInternal); 1201 1202 dpm.addUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS); 1203 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1204 eq(UserHandle.USER_SYSTEM), 1205 MockUtils.checkUserRestrictions(UserManager.DISALLOW_OUTGOING_CALLS), 1206 MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADD_USER) 1207 ); 1208 reset(mContext.userManagerInternal); 1209 1210 DpmTestUtils.assertRestrictions( 1211 DpmTestUtils.newRestrictions( 1212 UserManager.DISALLOW_ADD_USER, UserManager.DISALLOW_OUTGOING_CALLS), 1213 dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions() 1214 ); 1215 DpmTestUtils.assertRestrictions( 1216 DpmTestUtils.newRestrictions( 1217 UserManager.DISALLOW_ADD_USER, UserManager.DISALLOW_OUTGOING_CALLS), 1218 dpm.getUserRestrictions(admin1) 1219 ); 1220 1221 dpm.clearUserRestriction(admin1, UserManager.DISALLOW_ADD_USER); 1222 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1223 eq(UserHandle.USER_SYSTEM), 1224 MockUtils.checkUserRestrictions(UserManager.DISALLOW_OUTGOING_CALLS), 1225 MockUtils.checkUserRestrictions() 1226 ); 1227 reset(mContext.userManagerInternal); 1228 1229 DpmTestUtils.assertRestrictions( 1230 DpmTestUtils.newRestrictions(UserManager.DISALLOW_OUTGOING_CALLS), 1231 dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions() 1232 ); 1233 DpmTestUtils.assertRestrictions( 1234 DpmTestUtils.newRestrictions(UserManager.DISALLOW_OUTGOING_CALLS), 1235 dpm.getUserRestrictions(admin1) 1236 ); 1237 1238 dpm.clearUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS); 1239 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1240 eq(UserHandle.USER_SYSTEM), 1241 MockUtils.checkUserRestrictions(), 1242 MockUtils.checkUserRestrictions() 1243 ); 1244 reset(mContext.userManagerInternal); 1245 1246 DpmTestUtils.assertRestrictions( 1247 DpmTestUtils.newRestrictions(), 1248 dpms.getDeviceOwnerAdminLocked().ensureUserRestrictions() 1249 ); 1250 DpmTestUtils.assertRestrictions( 1251 DpmTestUtils.newRestrictions(), 1252 dpm.getUserRestrictions(admin1) 1253 ); 1254 1255 // DISALLOW_ADJUST_VOLUME and DISALLOW_UNMUTE_MICROPHONE are PO restrictions, but when 1256 // DO sets them, the scope is global. 1257 dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADJUST_VOLUME); 1258 reset(mContext.userManagerInternal); 1259 dpm.addUserRestriction(admin1, UserManager.DISALLOW_UNMUTE_MICROPHONE); 1260 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1261 eq(UserHandle.USER_SYSTEM), 1262 MockUtils.checkUserRestrictions(), 1263 MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADJUST_VOLUME, 1264 UserManager.DISALLOW_UNMUTE_MICROPHONE) 1265 ); 1266 reset(mContext.userManagerInternal); 1267 1268 dpm.clearUserRestriction(admin1, UserManager.DISALLOW_ADJUST_VOLUME); 1269 dpm.clearUserRestriction(admin1, UserManager.DISALLOW_UNMUTE_MICROPHONE); 1270 1271 1272 // More tests. 1273 dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADD_USER); 1274 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1275 eq(UserHandle.USER_SYSTEM), 1276 MockUtils.checkUserRestrictions(), 1277 MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADD_USER) 1278 ); 1279 reset(mContext.userManagerInternal); 1280 1281 dpm.addUserRestriction(admin1, UserManager.DISALLOW_FUN); 1282 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1283 eq(UserHandle.USER_SYSTEM), 1284 MockUtils.checkUserRestrictions(), 1285 MockUtils.checkUserRestrictions(UserManager.DISALLOW_FUN, 1286 UserManager.DISALLOW_ADD_USER) 1287 ); 1288 reset(mContext.userManagerInternal); 1289 1290 dpm.setCameraDisabled(admin1, true); 1291 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1292 eq(UserHandle.USER_SYSTEM), 1293 // DISALLOW_CAMERA will be applied to both local and global. 1294 MockUtils.checkUserRestrictions(UserManager.DISALLOW_CAMERA), 1295 MockUtils.checkUserRestrictions(UserManager.DISALLOW_FUN, 1296 UserManager.DISALLOW_CAMERA, UserManager.DISALLOW_ADD_USER) 1297 ); 1298 reset(mContext.userManagerInternal); 1299 1300 // Set up another DA and let it disable camera. Now DISALLOW_CAMERA will only be applied 1301 // locally. 1302 dpm.setCameraDisabled(admin1, false); 1303 reset(mContext.userManagerInternal); 1304 1305 setUpPackageManagerForAdmin(admin2, DpmMockContext.CALLER_SYSTEM_USER_UID); 1306 dpm.setActiveAdmin(admin2, /* replace =*/ false, UserHandle.USER_SYSTEM); 1307 dpm.setCameraDisabled(admin2, true); 1308 1309 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1310 eq(UserHandle.USER_SYSTEM), 1311 // DISALLOW_CAMERA will be applied to both local and global. 1312 MockUtils.checkUserRestrictions(UserManager.DISALLOW_CAMERA), 1313 MockUtils.checkUserRestrictions(UserManager.DISALLOW_FUN, 1314 UserManager.DISALLOW_ADD_USER) 1315 ); 1316 reset(mContext.userManagerInternal); 1317 // TODO Make sure restrictions are written to the file. 1318 } 1319 1320 public void testSetUserRestriction_asPo() { 1321 setAsProfileOwner(admin1); 1322 1323 DpmTestUtils.assertRestrictions( 1324 DpmTestUtils.newRestrictions(), 1325 dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE) 1326 .ensureUserRestrictions() 1327 ); 1328 1329 dpm.addUserRestriction(admin1, UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES); 1330 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1331 eq(DpmMockContext.CALLER_USER_HANDLE), 1332 MockUtils.checkUserRestrictions(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES), 1333 isNull(Bundle.class) 1334 ); 1335 reset(mContext.userManagerInternal); 1336 1337 dpm.addUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS); 1338 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1339 eq(DpmMockContext.CALLER_USER_HANDLE), 1340 MockUtils.checkUserRestrictions(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES, 1341 UserManager.DISALLOW_OUTGOING_CALLS), 1342 isNull(Bundle.class) 1343 ); 1344 reset(mContext.userManagerInternal); 1345 1346 DpmTestUtils.assertRestrictions( 1347 DpmTestUtils.newRestrictions( 1348 UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES, 1349 UserManager.DISALLOW_OUTGOING_CALLS 1350 ), 1351 dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE) 1352 .ensureUserRestrictions() 1353 ); 1354 DpmTestUtils.assertRestrictions( 1355 DpmTestUtils.newRestrictions( 1356 UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES, 1357 UserManager.DISALLOW_OUTGOING_CALLS 1358 ), 1359 dpm.getUserRestrictions(admin1) 1360 ); 1361 1362 dpm.clearUserRestriction(admin1, UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES); 1363 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1364 eq(DpmMockContext.CALLER_USER_HANDLE), 1365 MockUtils.checkUserRestrictions(UserManager.DISALLOW_OUTGOING_CALLS), 1366 isNull(Bundle.class) 1367 ); 1368 reset(mContext.userManagerInternal); 1369 1370 DpmTestUtils.assertRestrictions( 1371 DpmTestUtils.newRestrictions( 1372 UserManager.DISALLOW_OUTGOING_CALLS 1373 ), 1374 dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE) 1375 .ensureUserRestrictions() 1376 ); 1377 DpmTestUtils.assertRestrictions( 1378 DpmTestUtils.newRestrictions( 1379 UserManager.DISALLOW_OUTGOING_CALLS 1380 ), 1381 dpm.getUserRestrictions(admin1) 1382 ); 1383 1384 dpm.clearUserRestriction(admin1, UserManager.DISALLOW_OUTGOING_CALLS); 1385 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1386 eq(DpmMockContext.CALLER_USER_HANDLE), 1387 MockUtils.checkUserRestrictions(), 1388 isNull(Bundle.class) 1389 ); 1390 reset(mContext.userManagerInternal); 1391 1392 DpmTestUtils.assertRestrictions( 1393 DpmTestUtils.newRestrictions(), 1394 dpms.getProfileOwnerAdminLocked(DpmMockContext.CALLER_USER_HANDLE) 1395 .ensureUserRestrictions() 1396 ); 1397 DpmTestUtils.assertRestrictions( 1398 DpmTestUtils.newRestrictions(), 1399 dpm.getUserRestrictions(admin1) 1400 ); 1401 1402 // DISALLOW_ADJUST_VOLUME and DISALLOW_UNMUTE_MICROPHONE can be set by PO too, even 1403 // though when DO sets them they'll be applied globally. 1404 dpm.addUserRestriction(admin1, UserManager.DISALLOW_ADJUST_VOLUME); 1405 reset(mContext.userManagerInternal); 1406 dpm.addUserRestriction(admin1, UserManager.DISALLOW_UNMUTE_MICROPHONE); 1407 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1408 eq(DpmMockContext.CALLER_USER_HANDLE), 1409 MockUtils.checkUserRestrictions(UserManager.DISALLOW_ADJUST_VOLUME, 1410 UserManager.DISALLOW_UNMUTE_MICROPHONE), 1411 isNull(Bundle.class) 1412 ); 1413 reset(mContext.userManagerInternal); 1414 1415 dpm.setCameraDisabled(admin1, true); 1416 verify(mContext.userManagerInternal).setDevicePolicyUserRestrictions( 1417 eq(DpmMockContext.CALLER_USER_HANDLE), 1418 MockUtils.checkUserRestrictions(UserManager.DISALLOW_CAMERA, 1419 UserManager.DISALLOW_ADJUST_VOLUME, 1420 UserManager.DISALLOW_UNMUTE_MICROPHONE), 1421 isNull(Bundle.class) 1422 ); 1423 reset(mContext.userManagerInternal); 1424 1425 // TODO Make sure restrictions are written to the file. 1426 } 1427 1428 public void testGetMacAddress() throws Exception { 1429 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 1430 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1431 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 1432 1433 // In this test, change the caller user to "system". 1434 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1435 1436 // Make sure admin1 is installed on system user. 1437 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 1438 1439 // Test 1. Caller doesn't have DO or DA. 1440 try { 1441 dpm.getWifiMacAddress(); 1442 fail(); 1443 } catch (SecurityException e) { 1444 MoreAsserts.assertContainsRegex("No active admin owned", e.getMessage()); 1445 } 1446 1447 // DO needs to be an DA. 1448 dpm.setActiveAdmin(admin1, /* replace =*/ false); 1449 assertTrue(dpm.isAdminActive(admin1)); 1450 1451 // Test 2. Caller has DA, but not DO. 1452 try { 1453 dpm.getWifiMacAddress(); 1454 fail(); 1455 } catch (SecurityException e) { 1456 MoreAsserts.assertContainsRegex("No active admin owned", e.getMessage()); 1457 } 1458 1459 // Test 3. Caller has PO, but not DO. 1460 assertTrue(dpm.setProfileOwner(admin1, null, UserHandle.USER_SYSTEM)); 1461 try { 1462 dpm.getWifiMacAddress(); 1463 fail(); 1464 } catch (SecurityException e) { 1465 MoreAsserts.assertContainsRegex("No active admin owned", e.getMessage()); 1466 } 1467 1468 // Remove PO. 1469 dpm.clearProfileOwner(admin1); 1470 1471 // Test 4, Caller is DO now. 1472 assertTrue(dpm.setDeviceOwner(admin1, null, UserHandle.USER_SYSTEM)); 1473 1474 // 4-1. But no WifiInfo. 1475 assertNull(dpm.getWifiMacAddress()); 1476 1477 // 4-2. Returns WifiInfo, but with the default MAC. 1478 when(mContext.wifiManager.getConnectionInfo()).thenReturn(new WifiInfo()); 1479 assertNull(dpm.getWifiMacAddress()); 1480 1481 // 4-3. With a real MAC address. 1482 final WifiInfo wi = new WifiInfo(); 1483 wi.setMacAddress("11:22:33:44:55:66"); 1484 when(mContext.wifiManager.getConnectionInfo()).thenReturn(wi); 1485 assertEquals("11:22:33:44:55:66", dpm.getWifiMacAddress()); 1486 } 1487 1488 public void testRebootCanOnlyBeCalledByDeviceOwner() throws Exception { 1489 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 1490 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1491 1492 // In this test, change the caller user to "system". 1493 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1494 1495 // Make sure admin1 is installed on system user. 1496 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 1497 1498 // Set admin1 as DA. 1499 dpm.setActiveAdmin(admin1, false); 1500 assertTrue(dpm.isAdminActive(admin1)); 1501 try { 1502 dpm.reboot(admin1); 1503 fail("DA calls DPM.reboot(), did not throw expected SecurityException"); 1504 } catch (SecurityException expected) { 1505 MoreAsserts.assertContainsRegex("does not own the device", expected.getMessage()); 1506 } 1507 1508 // Set admin1 as PO. 1509 assertTrue(dpm.setProfileOwner(admin1, null, UserHandle.USER_SYSTEM)); 1510 try { 1511 dpm.reboot(admin1); 1512 fail("PO calls DPM.reboot(), did not throw expected SecurityException"); 1513 } catch (SecurityException expected) { 1514 MoreAsserts.assertContainsRegex("does not own the device", expected.getMessage()); 1515 } 1516 1517 // Remove PO and add DO. 1518 dpm.clearProfileOwner(admin1); 1519 assertTrue(dpm.setDeviceOwner(admin1, null, UserHandle.USER_SYSTEM)); 1520 1521 dpm.reboot(admin1); 1522 } 1523 1524 public void testSetGetSupportText() { 1525 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 1526 dpm.setActiveAdmin(admin1, true); 1527 dpm.setActiveAdmin(admin2, true); 1528 mContext.callerPermissions.remove(permission.MANAGE_DEVICE_ADMINS); 1529 1530 // Null default support messages. 1531 { 1532 assertNull(dpm.getLongSupportMessage(admin1)); 1533 assertNull(dpm.getShortSupportMessage(admin1)); 1534 mContext.binder.callingUid = DpmMockContext.SYSTEM_UID; 1535 assertNull(dpm.getShortSupportMessageForUser(admin1, 1536 DpmMockContext.CALLER_USER_HANDLE)); 1537 assertNull(dpm.getLongSupportMessageForUser(admin1, 1538 DpmMockContext.CALLER_USER_HANDLE)); 1539 mMockContext.binder.callingUid = DpmMockContext.CALLER_UID; 1540 } 1541 1542 // Only system can call the per user versions. 1543 { 1544 try { 1545 dpm.getShortSupportMessageForUser(admin1, 1546 DpmMockContext.CALLER_USER_HANDLE); 1547 fail("Only system should be able to call getXXXForUser versions"); 1548 } catch (SecurityException expected) { 1549 MoreAsserts.assertContainsRegex("message for user", expected.getMessage()); 1550 } 1551 try { 1552 dpm.getLongSupportMessageForUser(admin1, 1553 DpmMockContext.CALLER_USER_HANDLE); 1554 fail("Only system should be able to call getXXXForUser versions"); 1555 } catch (SecurityException expected) { 1556 MoreAsserts.assertContainsRegex("message for user", expected.getMessage()); 1557 } 1558 } 1559 1560 // Can't set message for admin in another uid. 1561 { 1562 mContext.binder.callingUid = DpmMockContext.CALLER_UID + 1; 1563 try { 1564 dpm.setShortSupportMessage(admin1, "Some text"); 1565 fail("Admins should only be able to change their own support text."); 1566 } catch (SecurityException expected) { 1567 MoreAsserts.assertContainsRegex("is not owned by uid", expected.getMessage()); 1568 } 1569 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 1570 } 1571 1572 // Set/Get short returns what it sets and other admins text isn't changed. 1573 { 1574 final String supportText = "Some text to test with."; 1575 dpm.setShortSupportMessage(admin1, supportText); 1576 assertEquals(supportText, dpm.getShortSupportMessage(admin1)); 1577 assertNull(dpm.getLongSupportMessage(admin1)); 1578 assertNull(dpm.getShortSupportMessage(admin2)); 1579 1580 mContext.binder.callingUid = DpmMockContext.SYSTEM_UID; 1581 assertEquals(supportText, dpm.getShortSupportMessageForUser(admin1, 1582 DpmMockContext.CALLER_USER_HANDLE)); 1583 assertNull(dpm.getShortSupportMessageForUser(admin2, 1584 DpmMockContext.CALLER_USER_HANDLE)); 1585 assertNull(dpm.getLongSupportMessageForUser(admin1, 1586 DpmMockContext.CALLER_USER_HANDLE)); 1587 mMockContext.binder.callingUid = DpmMockContext.CALLER_UID; 1588 1589 dpm.setShortSupportMessage(admin1, null); 1590 assertNull(dpm.getShortSupportMessage(admin1)); 1591 } 1592 1593 // Set/Get long returns what it sets and other admins text isn't changed. 1594 { 1595 final String supportText = "Some text to test with.\nWith more text."; 1596 dpm.setLongSupportMessage(admin1, supportText); 1597 assertEquals(supportText, dpm.getLongSupportMessage(admin1)); 1598 assertNull(dpm.getShortSupportMessage(admin1)); 1599 assertNull(dpm.getLongSupportMessage(admin2)); 1600 1601 mContext.binder.callingUid = DpmMockContext.SYSTEM_UID; 1602 assertEquals(supportText, dpm.getLongSupportMessageForUser(admin1, 1603 DpmMockContext.CALLER_USER_HANDLE)); 1604 assertNull(dpm.getLongSupportMessageForUser(admin2, 1605 DpmMockContext.CALLER_USER_HANDLE)); 1606 assertNull(dpm.getShortSupportMessageForUser(admin1, 1607 DpmMockContext.CALLER_USER_HANDLE)); 1608 mMockContext.binder.callingUid = DpmMockContext.CALLER_UID; 1609 1610 dpm.setLongSupportMessage(admin1, null); 1611 assertNull(dpm.getLongSupportMessage(admin1)); 1612 } 1613 } 1614 1615 /** 1616 * Test for: 1617 * {@link DevicePolicyManager#setAffiliationIds} 1618 * {@link DevicePolicyManager#isAffiliatedUser} 1619 */ 1620 public void testUserAffiliation() throws Exception { 1621 mContext.callerPermissions.add(permission.MANAGE_DEVICE_ADMINS); 1622 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1623 mContext.callerPermissions.add(permission.INTERACT_ACROSS_USERS_FULL); 1624 1625 // Check that the system user is unaffiliated. 1626 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1627 assertFalse(dpm.isAffiliatedUser()); 1628 1629 // Set a device owner on the system user. Check that the system user becomes affiliated. 1630 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 1631 dpm.setActiveAdmin(admin1, /* replace =*/ false); 1632 assertTrue(dpm.setDeviceOwner(admin1, "owner-name")); 1633 assertTrue(dpm.isAffiliatedUser()); 1634 1635 // Install a profile owner whose package name matches the device owner on a test user. Check 1636 // that the test user is unaffiliated. 1637 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 1638 setAsProfileOwner(admin2); 1639 assertFalse(dpm.isAffiliatedUser()); 1640 1641 // Have the profile owner specify a set of affiliation ids. Check that the test user remains 1642 // unaffiliated. 1643 final Set<String> userAffiliationIds = new ArraySet<>(); 1644 userAffiliationIds.add("red"); 1645 userAffiliationIds.add("green"); 1646 userAffiliationIds.add("blue"); 1647 dpm.setAffiliationIds(admin2, userAffiliationIds); 1648 assertFalse(dpm.isAffiliatedUser()); 1649 1650 // Have the device owner specify a set of affiliation ids that do not intersect with those 1651 // specified by the profile owner. Check that the test user remains unaffiliated. 1652 final Set<String> deviceAffiliationIds = new ArraySet<>(); 1653 deviceAffiliationIds.add("cyan"); 1654 deviceAffiliationIds.add("yellow"); 1655 deviceAffiliationIds.add("magenta"); 1656 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1657 dpm.setAffiliationIds(admin1, deviceAffiliationIds); 1658 mContext.binder.callingUid = DpmMockContext.CALLER_UID; 1659 assertFalse(dpm.isAffiliatedUser()); 1660 1661 // Have the profile owner specify a set of affiliation ids that intersect with those 1662 // specified by the device owner. Check that the test user becomes affiliated. 1663 userAffiliationIds.add("yellow"); 1664 dpm.setAffiliationIds(admin2, userAffiliationIds); 1665 assertTrue(dpm.isAffiliatedUser()); 1666 1667 // Change the profile owner to one whose package name does not match the device owner. Check 1668 // that the test user is not affiliated anymore. 1669 dpm.clearProfileOwner(admin2); 1670 final ComponentName admin = new ComponentName("test", "test"); 1671 markPackageAsInstalled(admin.getPackageName(), null, DpmMockContext.CALLER_USER_HANDLE); 1672 assertTrue(dpm.setProfileOwner(admin, "owner-name", DpmMockContext.CALLER_USER_HANDLE)); 1673 assertFalse(dpm.isAffiliatedUser()); 1674 1675 // Check that the system user remains affiliated. 1676 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1677 assertTrue(dpm.isAffiliatedUser()); 1678 } 1679 1680 public void testGetUserProvisioningState_defaultResult() { 1681 assertEquals(DevicePolicyManager.STATE_USER_UNMANAGED, dpm.getUserProvisioningState()); 1682 } 1683 1684 public void testSetUserProvisioningState_permission() throws Exception { 1685 setupProfileOwner(); 1686 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1687 1688 exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE, 1689 DevicePolicyManager.STATE_USER_SETUP_FINALIZED); 1690 } 1691 1692 public void testSetUserProvisioningState_unprivileged() throws Exception { 1693 setupProfileOwner(); 1694 try { 1695 dpm.setUserProvisioningState(DevicePolicyManager.STATE_USER_SETUP_FINALIZED, 1696 DpmMockContext.CALLER_USER_HANDLE); 1697 fail("Expected SecurityException"); 1698 } catch (SecurityException expected) { 1699 } 1700 } 1701 1702 public void testSetUserProvisioningState_noManagement() { 1703 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1704 try { 1705 dpm.setUserProvisioningState(DevicePolicyManager.STATE_USER_SETUP_FINALIZED, 1706 DpmMockContext.CALLER_USER_HANDLE); 1707 fail("IllegalStateException expected"); 1708 } catch (IllegalStateException e) { 1709 MoreAsserts.assertContainsRegex("change provisioning state unless a .* owner is set", 1710 e.getMessage()); 1711 } 1712 assertEquals(DevicePolicyManager.STATE_USER_UNMANAGED, dpm.getUserProvisioningState()); 1713 } 1714 1715 public void testSetUserProvisioningState_deviceOwnerFromSetupWizard() throws Exception { 1716 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1717 setupDeviceOwner(); 1718 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1719 1720 exerciseUserProvisioningTransitions(UserHandle.USER_SYSTEM, 1721 DevicePolicyManager.STATE_USER_SETUP_COMPLETE, 1722 DevicePolicyManager.STATE_USER_SETUP_FINALIZED); 1723 } 1724 1725 public void testSetUserProvisioningState_deviceOwnerFromSetupWizardAlternative() 1726 throws Exception { 1727 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1728 setupDeviceOwner(); 1729 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1730 1731 exerciseUserProvisioningTransitions(UserHandle.USER_SYSTEM, 1732 DevicePolicyManager.STATE_USER_SETUP_INCOMPLETE, 1733 DevicePolicyManager.STATE_USER_SETUP_FINALIZED); 1734 } 1735 1736 public void testSetUserProvisioningState_deviceOwnerWithoutSetupWizard() throws Exception { 1737 mContext.binder.callingUid = DpmMockContext.CALLER_SYSTEM_USER_UID; 1738 setupDeviceOwner(); 1739 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1740 1741 exerciseUserProvisioningTransitions(UserHandle.USER_SYSTEM, 1742 DevicePolicyManager.STATE_USER_SETUP_FINALIZED); 1743 } 1744 1745 public void testSetUserProvisioningState_managedProfileFromSetupWizard_primaryUser() 1746 throws Exception { 1747 setupProfileOwner(); 1748 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1749 1750 exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE, 1751 DevicePolicyManager.STATE_USER_PROFILE_COMPLETE, 1752 DevicePolicyManager.STATE_USER_UNMANAGED); 1753 } 1754 1755 public void testSetUserProvisioningState_managedProfileFromSetupWizard_managedProfile() 1756 throws Exception { 1757 setupProfileOwner(); 1758 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1759 1760 exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE, 1761 DevicePolicyManager.STATE_USER_SETUP_COMPLETE, 1762 DevicePolicyManager.STATE_USER_SETUP_FINALIZED); 1763 } 1764 1765 public void testSetUserProvisioningState_managedProfileWithoutSetupWizard() throws Exception { 1766 setupProfileOwner(); 1767 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1768 1769 exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE, 1770 DevicePolicyManager.STATE_USER_SETUP_FINALIZED); 1771 } 1772 1773 public void testSetUserProvisioningState_illegalTransitionOutOfFinalized1() throws Exception { 1774 setupProfileOwner(); 1775 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1776 1777 try { 1778 exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE, 1779 DevicePolicyManager.STATE_USER_SETUP_FINALIZED, 1780 DevicePolicyManager.STATE_USER_UNMANAGED); 1781 fail("Expected IllegalStateException"); 1782 } catch (IllegalStateException e) { 1783 MoreAsserts.assertContainsRegex("Cannot move to user provisioning state", 1784 e.getMessage()); 1785 } 1786 } 1787 1788 public void testSetUserProvisioningState_illegalTransitionToAnotherInProgressState() 1789 throws Exception { 1790 setupProfileOwner(); 1791 mContext.callerPermissions.add(permission.MANAGE_PROFILE_AND_DEVICE_OWNERS); 1792 1793 try { 1794 exerciseUserProvisioningTransitions(DpmMockContext.CALLER_USER_HANDLE, 1795 DevicePolicyManager.STATE_USER_SETUP_INCOMPLETE, 1796 DevicePolicyManager.STATE_USER_SETUP_COMPLETE); 1797 fail("Expected IllegalStateException"); 1798 } catch (IllegalStateException e) { 1799 MoreAsserts.assertContainsRegex("Cannot move to user provisioning state", 1800 e.getMessage()); 1801 } 1802 } 1803 1804 private void exerciseUserProvisioningTransitions(int userId, int... states) { 1805 assertEquals(DevicePolicyManager.STATE_USER_UNMANAGED, dpm.getUserProvisioningState()); 1806 for (int state : states) { 1807 dpm.setUserProvisioningState(state, userId); 1808 assertEquals(state, dpm.getUserProvisioningState()); 1809 } 1810 } 1811 1812 private void setupProfileOwner() throws Exception { 1813 mContext.callerPermissions.addAll(OWNER_SETUP_PERMISSIONS); 1814 1815 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_UID); 1816 dpm.setActiveAdmin(admin1, false); 1817 assertTrue(dpm.setProfileOwner(admin1, null, DpmMockContext.CALLER_USER_HANDLE)); 1818 1819 mContext.callerPermissions.removeAll(OWNER_SETUP_PERMISSIONS); 1820 } 1821 1822 private void setupDeviceOwner() throws Exception { 1823 mContext.callerPermissions.addAll(OWNER_SETUP_PERMISSIONS); 1824 1825 setUpPackageManagerForAdmin(admin1, DpmMockContext.CALLER_SYSTEM_USER_UID); 1826 dpm.setActiveAdmin(admin1, false); 1827 assertTrue(dpm.setDeviceOwner(admin1, null, UserHandle.USER_SYSTEM)); 1828 1829 mContext.callerPermissions.removeAll(OWNER_SETUP_PERMISSIONS); 1830 } 1831} 1832