1 /* 2 * Copyright (C) 2017 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 */ 16 package com.android.server.notification; 17 18 import static android.content.Context.DEVICE_POLICY_SERVICE; 19 import static android.os.UserManager.USER_TYPE_FULL_SECONDARY; 20 import static android.os.UserManager.USER_TYPE_PROFILE_CLONE; 21 import static android.os.UserManager.USER_TYPE_PROFILE_MANAGED; 22 import static android.service.notification.NotificationListenerService.META_DATA_DEFAULT_AUTOBIND; 23 24 import static com.android.server.notification.ManagedServices.APPROVAL_BY_COMPONENT; 25 import static com.android.server.notification.ManagedServices.APPROVAL_BY_PACKAGE; 26 27 import static com.google.common.truth.Truth.assertThat; 28 29 import static junit.framework.Assert.assertEquals; 30 import static junit.framework.Assert.assertFalse; 31 import static junit.framework.Assert.assertNotNull; 32 import static junit.framework.Assert.assertTrue; 33 34 import static org.mockito.ArgumentMatchers.anyString; 35 import static org.mockito.Matchers.any; 36 import static org.mockito.Matchers.anyInt; 37 import static org.mockito.Matchers.anyLong; 38 import static org.mockito.Matchers.eq; 39 import static org.mockito.Mockito.mock; 40 import static org.mockito.Mockito.never; 41 import static org.mockito.Mockito.spy; 42 import static org.mockito.Mockito.times; 43 import static org.mockito.Mockito.verify; 44 import static org.mockito.Mockito.when; 45 46 import android.app.ActivityManager; 47 import android.app.admin.DevicePolicyManager; 48 import android.content.ComponentName; 49 import android.content.Context; 50 import android.content.Intent; 51 import android.content.ServiceConnection; 52 import android.content.pm.ApplicationInfo; 53 import android.content.pm.IPackageManager; 54 import android.content.pm.PackageManager; 55 import android.content.pm.ResolveInfo; 56 import android.content.pm.ServiceInfo; 57 import android.content.pm.UserInfo; 58 import android.os.Build; 59 import android.os.Bundle; 60 import android.os.IBinder; 61 import android.os.IInterface; 62 import android.os.RemoteException; 63 import android.os.UserHandle; 64 import android.os.UserManager; 65 import android.provider.Settings; 66 import android.text.TextUtils; 67 import android.util.ArrayMap; 68 import android.util.ArraySet; 69 import android.util.IntArray; 70 import android.util.SparseArray; 71 import android.util.Xml; 72 73 import com.android.internal.util.XmlUtils; 74 import com.android.modules.utils.TypedXmlPullParser; 75 import com.android.modules.utils.TypedXmlSerializer; 76 import com.android.server.UiServiceTestCase; 77 78 import com.google.android.collect.Lists; 79 80 import org.junit.Before; 81 import org.junit.Test; 82 import org.mockito.ArgumentCaptor; 83 import org.mockito.Mock; 84 import org.mockito.MockitoAnnotations; 85 import org.mockito.invocation.InvocationOnMock; 86 import org.mockito.stubbing.Answer; 87 88 import java.io.BufferedInputStream; 89 import java.io.BufferedOutputStream; 90 import java.io.ByteArrayInputStream; 91 import java.io.ByteArrayOutputStream; 92 import java.nio.charset.StandardCharsets; 93 import java.util.ArrayList; 94 import java.util.Arrays; 95 import java.util.Collection; 96 import java.util.Collections; 97 import java.util.List; 98 import java.util.Set; 99 import java.util.concurrent.CountDownLatch; 100 101 public class ManagedServicesTest extends UiServiceTestCase { 102 103 @Mock 104 private IPackageManager mIpm; 105 @Mock 106 private PackageManager mPm; 107 @Mock 108 private UserManager mUm; 109 @Mock 110 private ManagedServices.UserProfiles mUserProfiles; 111 @Mock private DevicePolicyManager mDpm; 112 Object mLock = new Object(); 113 114 UserInfo mZero = new UserInfo(0, "zero", 0); 115 UserInfo mTen = new UserInfo(10, "ten", 0); 116 private String mDefaultsString; 117 private String mVersionString; 118 private final Set<ComponentName> mDefaults = new ArraySet(); 119 private ManagedServices mService; 120 private String mUserSetString; 121 122 private static final String SETTING = "setting"; 123 private static final String SECONDARY_SETTING = "secondary_setting"; 124 125 private ArrayMap<Integer, String> mExpectedPrimaryPackages; 126 private ArrayMap<Integer, String> mExpectedPrimaryComponentNames; 127 private ArrayMap<Integer, String> mExpectedSecondaryPackages; 128 private ArrayMap<Integer, String> mExpectedSecondaryComponentNames; 129 130 // type : user : list of approved 131 private ArrayMap<Integer, ArrayMap<Integer, String>> mExpectedPrimary; 132 private ArrayMap<Integer, ArrayMap<Integer, String>> mExpectedSecondary; 133 134 private UserHandle mUser; 135 private String mPkg; 136 137 @Before setUp()138 public void setUp() throws Exception { 139 MockitoAnnotations.initMocks(this); 140 141 mContext.setMockPackageManager(mPm); 142 mContext.addMockSystemService(Context.USER_SERVICE, mUm); 143 mContext.addMockSystemService(DEVICE_POLICY_SERVICE, mDpm); 144 mUser = mContext.getUser(); 145 mPkg = mContext.getPackageName(); 146 147 List<UserInfo> users = new ArrayList<>(); 148 users.add(mZero); 149 users.add(mTen); 150 users.add(new UserInfo(11, "11", 0)); 151 users.add(new UserInfo(12, "12", 0)); 152 users.add(new UserInfo(13, "13", 0)); 153 for (UserInfo user : users) { 154 when(mUm.getUserInfo(eq(user.id))).thenReturn(user); 155 } 156 when(mUm.getUsers()).thenReturn(users); 157 IntArray profileIds = new IntArray(); 158 profileIds.add(0); 159 profileIds.add(11); 160 profileIds.add(10); 161 profileIds.add(12); 162 profileIds.add(13); 163 when(mUserProfiles.getCurrentProfileIds()).thenReturn(profileIds); 164 165 mVersionString = "4"; 166 mExpectedPrimary = new ArrayMap<>(); 167 mExpectedSecondary = new ArrayMap<>(); 168 mExpectedPrimaryPackages = new ArrayMap<>(); 169 mExpectedPrimaryPackages.put(0, "this.is.a.package.name:another.package"); 170 mExpectedPrimaryPackages.put(10, "this.is.another.package"); 171 mExpectedPrimaryPackages.put(11, ""); 172 mExpectedPrimaryPackages.put(12, "bananas!"); 173 mExpectedPrimaryPackages.put(13, "non.user.set.package"); 174 mExpectedPrimaryComponentNames = new ArrayMap<>(); 175 mExpectedPrimaryComponentNames.put(0, "this.is.a.package.name/Ba:another.package/B1"); 176 mExpectedPrimaryComponentNames.put(10, "this.is.another.package/M1"); 177 mExpectedPrimaryComponentNames.put(11, ""); 178 mExpectedPrimaryComponentNames.put(12, "bananas!/Bananas!"); 179 mExpectedPrimaryComponentNames.put(13, "non.user.set.package/M1"); 180 mExpectedPrimary.put(APPROVAL_BY_PACKAGE, mExpectedPrimaryPackages); 181 mExpectedPrimary.put(APPROVAL_BY_COMPONENT, mExpectedPrimaryComponentNames); 182 183 mExpectedSecondaryComponentNames = new ArrayMap<>(); 184 mExpectedSecondaryComponentNames.put(0, "secondary/component.Name"); 185 mExpectedSecondaryComponentNames.put(10, 186 "this.is.another.package/with.Component:component/2:package/component2"); 187 mExpectedSecondaryPackages = new ArrayMap<>(); 188 mExpectedSecondaryPackages.put(0, "secondary"); 189 mExpectedSecondaryPackages.put(10, 190 "this.is.another.package:component:package"); 191 mExpectedSecondary.put(APPROVAL_BY_PACKAGE, mExpectedSecondaryPackages); 192 mExpectedSecondary.put(APPROVAL_BY_COMPONENT, mExpectedSecondaryComponentNames); 193 mService = new TestManagedServices(getContext(), mLock, mUserProfiles, 194 mIpm, APPROVAL_BY_COMPONENT); 195 } 196 197 @Test testBackupAndRestore_migration()198 public void testBackupAndRestore_migration() throws Exception { 199 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 200 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 201 mIpm, approvalLevel); 202 203 for (int userId : mExpectedPrimary.get(approvalLevel).keySet()) { 204 service.onSettingRestored( 205 service.getConfig().secureSettingName, 206 mExpectedPrimary.get(approvalLevel).get(userId), 207 Build.VERSION_CODES.O, userId); 208 } 209 verifyExpectedApprovedEntries(service, true); 210 211 for (int userId : mExpectedSecondary.get(approvalLevel).keySet()) { 212 service.onSettingRestored(service.getConfig().secondarySettingName, 213 mExpectedSecondary.get(approvalLevel).get(userId), Build.VERSION_CODES.O, 214 userId); 215 } 216 verifyExpectedApprovedEntries(service); 217 } 218 } 219 220 @Test testBackupAndRestore_migration_preO()221 public void testBackupAndRestore_migration_preO() throws Exception { 222 ArrayMap<Integer, String> backupPrimaryPackages = new ArrayMap<>(); 223 backupPrimaryPackages.put(0, "backup.0:backup:0a"); 224 backupPrimaryPackages.put(10, "10.backup"); 225 backupPrimaryPackages.put(11, "eleven"); 226 backupPrimaryPackages.put(12, ""); 227 ArrayMap<Integer, String> backupPrimaryComponentNames = new ArrayMap<>(); 228 backupPrimaryComponentNames.put(0, "backup.first/whatever:a/b"); 229 backupPrimaryComponentNames.put(10, "again/M1"); 230 backupPrimaryComponentNames.put(11, "orange/youglad:itisnot/banana"); 231 backupPrimaryComponentNames.put(12, ""); 232 ArrayMap<Integer, ArrayMap<Integer, String>> backupPrimary = new ArrayMap<>(); 233 backupPrimary.put(APPROVAL_BY_PACKAGE, backupPrimaryPackages); 234 backupPrimary.put(APPROVAL_BY_COMPONENT, backupPrimaryComponentNames); 235 236 ArrayMap<Integer, String> backupSecondaryComponentNames = new ArrayMap<>(); 237 backupSecondaryComponentNames.put(0, "secondary.1/component.Name"); 238 backupSecondaryComponentNames.put(10, 239 "this.is.another.package.backup/with.Component:component.backup/2"); 240 ArrayMap<Integer, String> backupSecondaryPackages = new ArrayMap<>(); 241 backupSecondaryPackages.put(0, ""); 242 backupSecondaryPackages.put(10, 243 "this.is.another.package.backup:package.backup"); 244 ArrayMap<Integer, ArrayMap<Integer, String>> backupSecondary = new ArrayMap<>(); 245 backupSecondary.put(APPROVAL_BY_PACKAGE, backupSecondaryPackages); 246 backupSecondary.put(APPROVAL_BY_COMPONENT, backupSecondaryComponentNames); 247 248 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 249 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 250 mIpm, approvalLevel); 251 252 // not an expected flow but a way to get data into the settings 253 for (int userId : mExpectedPrimary.get(approvalLevel).keySet()) { 254 service.onSettingRestored( 255 service.getConfig().secureSettingName, 256 mExpectedPrimary.get(approvalLevel).get(userId), 257 Build.VERSION_CODES.O, userId); 258 } 259 260 for (int userId : mExpectedSecondary.get(approvalLevel).keySet()) { 261 service.onSettingRestored(service.getConfig().secondarySettingName, 262 mExpectedSecondary.get(approvalLevel).get(userId), Build.VERSION_CODES.O, 263 userId); 264 } 265 266 // actual test 267 for (int userId : backupPrimary.get(approvalLevel).keySet()) { 268 service.onSettingRestored( 269 service.getConfig().secureSettingName, 270 backupPrimary.get(approvalLevel).get(userId), 271 Build.VERSION_CODES.N_MR1, userId); 272 } 273 274 for (int userId : backupSecondary.get(approvalLevel).keySet()) { 275 service.onSettingRestored(service.getConfig().secondarySettingName, 276 backupSecondary.get(approvalLevel).get(userId), 277 Build.VERSION_CODES.N_MR1, userId); 278 } 279 // both sets of approved entries should be allowed 280 verifyExpectedApprovedEntries(service); 281 verifyExpectedApprovedEntries(service, backupPrimary.get(approvalLevel)); 282 verifyExpectedApprovedEntries(service, backupSecondary.get(approvalLevel)); 283 } 284 } 285 286 @Test testReadXml_migrationFromSettings()287 public void testReadXml_migrationFromSettings() throws Exception { 288 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 289 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 290 mIpm, approvalLevel); 291 292 // approved services aren't in xml 293 TypedXmlPullParser parser = Xml.newFastPullParser(); 294 parser.setInput(new BufferedInputStream(new ByteArrayInputStream(new byte[]{})), 295 null); 296 writeExpectedValuesToSettings(approvalLevel); 297 298 service.migrateToXml(); 299 300 verifyExpectedApprovedEntries(service); 301 } 302 } 303 304 @Test testReadXml_noLongerMigrateFromSettings()305 public void testReadXml_noLongerMigrateFromSettings() throws Exception { 306 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 307 ManagedServices service = new TestManagedServicesNoSettings(getContext(), mLock, 308 mUserProfiles, mIpm, approvalLevel); 309 310 // approved services aren't in xml 311 TypedXmlPullParser parser = Xml.newFastPullParser(); 312 parser.setInput(new BufferedInputStream(new ByteArrayInputStream(new byte[]{})), 313 null); 314 writeExpectedValuesToSettings(approvalLevel); 315 316 service.migrateToXml(); 317 // No crash? success 318 319 ArrayMap<Integer, String> verifyMap = approvalLevel == APPROVAL_BY_COMPONENT 320 ? mExpectedPrimary.get(service.mApprovalLevel) 321 : mExpectedSecondary.get(service.mApprovalLevel); 322 for (int userId : verifyMap.keySet()) { 323 for (String verifyValue : verifyMap.get(userId).split(":")) { 324 if (!TextUtils.isEmpty(verifyValue)) { 325 assertFalse("service type " + service.mApprovalLevel + ":" 326 + verifyValue + " is allowed for user " + userId, 327 service.isPackageOrComponentAllowed(verifyValue, userId)); 328 } 329 } 330 } 331 } 332 } 333 334 @Test testReadXml()335 public void testReadXml() throws Exception { 336 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 337 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 338 mIpm, approvalLevel); 339 340 loadXml(service); 341 342 verifyExpectedApprovedEntries(service); 343 344 int[] invalidUsers = new int[] {98, 99}; 345 for (int invalidUser : invalidUsers) { 346 assertFalse("service type " + service.mApprovalLevel + ":" 347 + invalidUser + " is allowed for user " + invalidUser, 348 service.isPackageOrComponentAllowed( 349 String.valueOf(invalidUser), invalidUser)); 350 } 351 } 352 } 353 354 @Test testReadXml_appendsListOfApprovedComponents()355 public void testReadXml_appendsListOfApprovedComponents() throws Exception { 356 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 357 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 358 mIpm, approvalLevel); 359 360 String preApprovedPackage = "some.random.package"; 361 String preApprovedComponent = "some.random.package/C1"; 362 363 List<String> packages = new ArrayList<>(); 364 packages.add(preApprovedPackage); 365 addExpectedServices(service, packages, 0); 366 367 service.setPackageOrComponentEnabled(preApprovedComponent, 0, true, true); 368 369 loadXml(service); 370 371 verifyExpectedApprovedEntries(service); 372 373 String verifyValue = (approvalLevel == APPROVAL_BY_COMPONENT) 374 ? preApprovedComponent 375 : preApprovedPackage; 376 assertTrue(service.isPackageOrComponentAllowed(verifyValue, 0)); 377 } 378 } 379 380 /** Test that restore ignores the user id attribute and applies the data to the target user. */ 381 @Test testReadXml_onlyRestoresForTargetUser()382 public void testReadXml_onlyRestoresForTargetUser() throws Exception { 383 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 384 ManagedServices service = 385 new TestManagedServices( 386 getContext(), mLock, mUserProfiles, mIpm, approvalLevel); 387 String testPackage = "user.test.package"; 388 String testComponent = "user.test.component/C1"; 389 String resolvedValue = 390 (approvalLevel == APPROVAL_BY_COMPONENT) ? testComponent : testPackage; 391 TypedXmlPullParser parser = 392 getParserWithEntries(service, getXmlEntry(resolvedValue, 0, true)); 393 394 service.readXml(parser, null, true, 10); 395 396 assertFalse(service.isPackageOrComponentAllowed(resolvedValue, 0)); 397 assertTrue(service.isPackageOrComponentAllowed(resolvedValue, 10)); 398 } 399 } 400 401 /** Test that restore correctly parses the user_set attribute. */ 402 @Test testReadXml_restoresUserSet()403 public void testReadXml_restoresUserSet() throws Exception { 404 mVersionString = "4"; 405 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 406 ManagedServices service = 407 new TestManagedServices( 408 getContext(), mLock, mUserProfiles, mIpm, approvalLevel); 409 String testPackage = "user.test.package"; 410 String testComponent = "user.test.component/C1"; 411 String resolvedValue = 412 (approvalLevel == APPROVAL_BY_COMPONENT) ? testComponent : testPackage; 413 String xmlEntry = getXmlEntry(resolvedValue, 0, true, false); 414 TypedXmlPullParser parser = getParserWithEntries(service, xmlEntry); 415 416 service.readXml(parser, null, true, 0); 417 418 assertFalse("Failed while parsing xml:\n" + xmlEntry, 419 service.isPackageOrComponentUserSet(resolvedValue, 0)); 420 421 xmlEntry = getXmlEntry(resolvedValue, 0, true, true); 422 parser = getParserWithEntries(service, xmlEntry); 423 424 service.readXml(parser, null, true, 0); 425 426 assertTrue("Failed while parsing xml:\n" + xmlEntry, 427 service.isPackageOrComponentUserSet(resolvedValue, 0)); 428 } 429 } 430 431 /** Test that restore ignores the user id attribute and applies the data to the target user. */ 432 @Test testWriteReadXml_writeReadDefaults()433 public void testWriteReadXml_writeReadDefaults() throws Exception { 434 // setup 435 ManagedServices service1 = 436 new TestManagedServices( 437 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 438 ManagedServices service2 = 439 new TestManagedServices( 440 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 441 TypedXmlSerializer serializer = Xml.newFastSerializer(); 442 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 443 BufferedOutputStream outStream = new BufferedOutputStream(baos); 444 serializer.setOutput(outStream, "utf-8"); 445 446 //data setup 447 service1.addDefaultComponentOrPackage("package/class"); 448 serializer.startDocument(null, true); 449 service1.writeXml(serializer, false, 0); 450 serializer.endDocument(); 451 outStream.flush(); 452 453 final TypedXmlPullParser parser = Xml.newFastPullParser(); 454 BufferedInputStream input = new BufferedInputStream( 455 new ByteArrayInputStream(baos.toByteArray())); 456 457 parser.setInput(input, StandardCharsets.UTF_8.name()); 458 XmlUtils.beginDocument(parser, "test"); 459 service2.readXml(parser, null, false, 0); 460 ArraySet<ComponentName> defaults = service2.getDefaultComponents(); 461 462 assertEquals(1, defaults.size()); 463 assertEquals(new ComponentName("package", "class"), defaults.valueAt(0)); 464 } 465 466 @Test resetPackage_enableDefaultsOnly()467 public void resetPackage_enableDefaultsOnly() { 468 // setup 469 ManagedServices service = 470 new TestManagedServices( 471 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 472 service.addApprovedList( 473 "package/not-default:another-package/not-default:package2/default", 474 0, true); 475 service.addDefaultComponentOrPackage("package/default"); 476 service.addDefaultComponentOrPackage("package2/default"); 477 478 ArrayMap<Boolean, ArrayList<ComponentName>> componentsToActivate = 479 service.resetComponents("package", 0); 480 481 assertEquals(1, componentsToActivate.get(true).size()); 482 assertEquals(new ComponentName("package", "default"), 483 componentsToActivate.get(true).get(0)); 484 } 485 486 487 @Test resetPackage_nonDefaultsRemoved()488 public void resetPackage_nonDefaultsRemoved() { 489 // setup 490 ManagedServices service = 491 new TestManagedServices( 492 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 493 service.addApprovedList( 494 "package/not-default:another-package/not-default:package2/default", 495 0, true); 496 service.addDefaultComponentOrPackage("package/default"); 497 service.addDefaultComponentOrPackage("package2/default"); 498 499 ArrayMap<Boolean, ArrayList<ComponentName>> componentsToActivate = 500 service.resetComponents("package", 0); 501 502 assertEquals(1, componentsToActivate.get(true).size()); 503 assertEquals(new ComponentName("package", "not-default"), 504 componentsToActivate.get(false).get(0)); 505 } 506 507 @Test resetPackage_onlyDefaultsOnly()508 public void resetPackage_onlyDefaultsOnly() { 509 // setup 510 ManagedServices service = 511 new TestManagedServices( 512 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 513 service.addApprovedList( 514 "package/not-default:another-package/not-default:package2/default", 515 0, true); 516 service.addDefaultComponentOrPackage("package/default"); 517 service.addDefaultComponentOrPackage("package2/default"); 518 519 assertEquals(3, service.getAllowedComponents(0).size()); 520 521 service.resetComponents("package", 0); 522 523 List<ComponentName> components = service.getAllowedComponents(0); 524 assertEquals(3, components.size()); 525 assertTrue(components.contains(new ComponentName("package", "default"))); 526 } 527 528 @Test resetPackage_affectCurrentUserOnly()529 public void resetPackage_affectCurrentUserOnly() { 530 // setup 531 ManagedServices service = 532 new TestManagedServices( 533 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 534 service.addApprovedList( 535 "package/not-default:another-package/not-default:package2/default", 536 0, true); 537 service.addApprovedList( 538 "package/not-default:another-package/not-default:package2/default", 539 1, true); 540 service.addDefaultComponentOrPackage("package/default"); 541 service.addDefaultComponentOrPackage("package2/default"); 542 543 service.resetComponents("package", 0); 544 545 List<ComponentName> components = service.getAllowedComponents(1); 546 assertEquals(3, components.size()); 547 } 548 549 @Test resetPackage_samePackageMultipleClasses()550 public void resetPackage_samePackageMultipleClasses() { 551 // setup 552 ManagedServices service = 553 new TestManagedServices( 554 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 555 service.addApprovedList( 556 "package/not-default:another-package/not-default:package2/default", 557 0, true); 558 service.addApprovedList( 559 "package/class:another-package/class:package2/class", 560 0, true); 561 service.addDefaultComponentOrPackage("package/default"); 562 service.addDefaultComponentOrPackage("package2/default"); 563 564 service.resetComponents("package", 0); 565 566 List<ComponentName> components = service.getAllowedComponents(0); 567 assertEquals(5, components.size()); 568 assertTrue(components.contains(new ComponentName("package", "default"))); 569 } 570 571 @Test resetPackage_clearsUserSet()572 public void resetPackage_clearsUserSet() { 573 // setup 574 ManagedServices service = 575 new TestManagedServices( 576 getContext(), mLock, mUserProfiles, mIpm, APPROVAL_BY_COMPONENT); 577 String componentName = "package/user-allowed"; 578 service.addApprovedList(componentName, 0, true); 579 580 service.resetComponents("package", 0); 581 582 assertFalse(service.isPackageOrComponentUserSet(componentName, 0)); 583 } 584 585 /** Test that backup only writes packages/components that belong to the target user. */ 586 @Test testWriteXml_onlyBackupsForTargetUser()587 public void testWriteXml_onlyBackupsForTargetUser() throws Exception { 588 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 589 ManagedServices service = 590 new TestManagedServices( 591 getContext(), mLock, mUserProfiles, mIpm, approvalLevel); 592 // Set up components. 593 String testPackage0 = "user0.test.package"; 594 String testComponent0 = "user0.test.component/C1"; 595 String testPackage10 = "user10.test.package"; 596 String testComponent10 = "user10.test.component/C1"; 597 String resolvedValue0 = 598 (approvalLevel == APPROVAL_BY_COMPONENT) ? testComponent0 : testPackage0; 599 String resolvedValue10 = 600 (approvalLevel == APPROVAL_BY_COMPONENT) ? testComponent10 : testPackage10; 601 addExpectedServices( 602 service, Collections.singletonList(service.getPackageName(resolvedValue0)), 0); 603 addExpectedServices( 604 service, 605 Collections.singletonList(service.getPackageName(resolvedValue10)), 606 10); 607 TypedXmlPullParser parser = 608 getParserWithEntries( 609 service, 610 getXmlEntry(resolvedValue0, 0, true), 611 getXmlEntry(resolvedValue10, 10, true)); 612 service.readXml(parser, null, false, UserHandle.USER_ALL); 613 614 // Write backup. 615 TypedXmlSerializer serializer = Xml.newFastSerializer(); 616 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 617 serializer.setOutput(new BufferedOutputStream(baos), "utf-8"); 618 serializer.startDocument(null, true); 619 service.writeXml(serializer, true, 10); 620 serializer.endDocument(); 621 serializer.flush(); 622 623 // Reset values. 624 service.setPackageOrComponentEnabled(resolvedValue0, 0, true, false); 625 service.setPackageOrComponentEnabled(resolvedValue10, 10, true, false); 626 627 // Parse backup via restore. 628 TypedXmlPullParser restoreParser = Xml.newFastPullParser(); 629 restoreParser.setInput( 630 new BufferedInputStream(new ByteArrayInputStream(baos.toByteArray())), null); 631 restoreParser.nextTag(); 632 service.readXml(restoreParser, null, true, 10); 633 634 assertFalse(service.isPackageOrComponentAllowed(resolvedValue0, 0)); 635 assertFalse(service.isPackageOrComponentAllowed(resolvedValue0, 10)); 636 assertTrue(service.isPackageOrComponentAllowed(resolvedValue10, 10)); 637 } 638 } 639 640 @Test testWriteXml_trimsMissingServices()641 public void testWriteXml_trimsMissingServices() throws Exception { 642 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 643 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 644 mIpm, approvalLevel); 645 loadXml(service); 646 647 // remove missing 648 mExpectedPrimaryPackages.put(0, "another.package"); 649 mExpectedPrimaryPackages.remove(12); 650 mExpectedPrimaryComponentNames.put(0, "another.package/B1"); 651 mExpectedPrimaryComponentNames.remove(12); 652 mExpectedSecondaryPackages.put(10, "this.is.another.package:component"); 653 mExpectedSecondaryComponentNames.put( 654 10, "this.is.another.package/with.Component:component/2"); 655 656 for (UserInfo userInfo : mUm.getUsers()) { 657 List<String> entriesExpectedToHaveServices = new ArrayList<>(); 658 if (mExpectedPrimary.get(approvalLevel).containsKey(userInfo.id)) { 659 for (String packageOrComponent : 660 mExpectedPrimary.get(approvalLevel).get(userInfo.id).split(":")) { 661 if (!TextUtils.isEmpty(packageOrComponent)) { 662 entriesExpectedToHaveServices.add( 663 service.getPackageName(packageOrComponent)); 664 } 665 } 666 } 667 if (mExpectedSecondary.get(approvalLevel).containsKey(userInfo.id)) { 668 for (String packageOrComponent : 669 mExpectedSecondary.get(approvalLevel).get(userInfo.id).split(":")) { 670 if (!TextUtils.isEmpty(packageOrComponent)) { 671 entriesExpectedToHaveServices.add( 672 service.getPackageName(packageOrComponent)); 673 } 674 } 675 } 676 addExpectedServices(service, entriesExpectedToHaveServices, userInfo.id); 677 } 678 679 TypedXmlSerializer serializer = Xml.newFastSerializer(); 680 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 681 serializer.setOutput(new BufferedOutputStream(baos), "utf-8"); 682 serializer.startDocument(null, true); 683 for (UserInfo userInfo : mUm.getUsers()) { 684 service.writeXml(serializer, true, userInfo.id); 685 } 686 serializer.endDocument(); 687 serializer.flush(); 688 689 TypedXmlPullParser parser = Xml.newFastPullParser(); 690 parser.setInput(new BufferedInputStream( 691 new ByteArrayInputStream(baos.toByteArray())), null); 692 parser.nextTag(); 693 for (UserInfo userInfo : mUm.getUsers()) { 694 service.readXml(parser, null, true, userInfo.id); 695 } 696 697 verifyExpectedApprovedEntries(service); 698 assertFalse(service.isPackageOrComponentAllowed("this.is.a.package.name", 0)); 699 assertFalse(service.isPackageOrComponentAllowed("bananas!", 12)); 700 assertFalse(service.isPackageOrComponentAllowed("package/component2", 10)); 701 } 702 } 703 704 @Test testWriteXml_writesSetting()705 public void testWriteXml_writesSetting() throws Exception { 706 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 707 ManagedServices service = new TestManagedServicesSettings(getContext(), mLock, 708 mUserProfiles, mIpm, approvalLevel); 709 loadXml(service); 710 711 TypedXmlSerializer serializer = Xml.newFastSerializer(); 712 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 713 serializer.setOutput(new BufferedOutputStream(baos), "utf-8"); 714 serializer.startDocument(null, true); 715 service.writeXml(serializer, false, UserHandle.USER_ALL); 716 serializer.endDocument(); 717 serializer.flush(); 718 719 for (int userId : mUserProfiles.getCurrentProfileIds().toArray()) { 720 List<String> expected = 721 stringToList(mExpectedPrimary.get(approvalLevel).get(userId)); 722 List<String> actual = stringToList(Settings.Secure.getStringForUser( 723 getContext().getContentResolver(), 724 service.getConfig().secureSettingName, userId)); 725 assertContentsInAnyOrder(actual, expected); 726 } 727 } 728 } 729 730 @Test testWriteXml_doesNotWriteSetting()731 public void testWriteXml_doesNotWriteSetting() throws Exception { 732 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 733 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 734 mIpm, approvalLevel); 735 736 for (int userId : mUserProfiles.getCurrentProfileIds().toArray()) { 737 Settings.Secure.putStringForUser( 738 getContext().getContentResolver(), 739 service.getConfig().secureSettingName, null, userId); 740 } 741 loadXml(service); 742 743 TypedXmlSerializer serializer = Xml.newFastSerializer(); 744 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 745 serializer.setOutput(new BufferedOutputStream(baos), "utf-8"); 746 serializer.startDocument(null, true); 747 service.writeXml(serializer, false, UserHandle.USER_ALL); 748 serializer.endDocument(); 749 serializer.flush(); 750 751 for (int userId : mUserProfiles.getCurrentProfileIds().toArray()) { 752 String actual = Settings.Secure.getStringForUser( 753 getContext().getContentResolver(), 754 service.getConfig().secureSettingName, userId); 755 assertTrue(TextUtils.isEmpty(actual)); 756 } 757 } 758 } 759 760 @Test testWriteXml_writesUserSet()761 public void testWriteXml_writesUserSet() throws Exception { 762 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 763 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 764 mIpm, approvalLevel); 765 loadXml(service); 766 767 TypedXmlSerializer serializer = Xml.newFastSerializer(); 768 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 769 serializer.setOutput(new BufferedOutputStream(baos), "utf-8"); 770 serializer.startDocument(null, true); 771 service.writeXml(serializer, false, UserHandle.USER_ALL); 772 serializer.endDocument(); 773 serializer.flush(); 774 775 TypedXmlPullParser parser = Xml.newFastPullParser(); 776 byte[] rawOutput = baos.toByteArray(); 777 parser.setInput(new BufferedInputStream( 778 new ByteArrayInputStream(rawOutput)), null); 779 parser.nextTag(); 780 for (UserInfo userInfo : mUm.getUsers()) { 781 service.readXml(parser, null, true, userInfo.id); 782 } 783 784 String resolvedUserSetComponent = approvalLevel == APPROVAL_BY_PACKAGE 785 ? mExpectedPrimaryPackages.get(10) 786 : mExpectedPrimaryComponentNames.get(10); 787 String resolvedNonUserSetComponent = approvalLevel == APPROVAL_BY_PACKAGE 788 ? mExpectedPrimaryPackages.get(13) 789 : mExpectedPrimaryComponentNames.get(13); 790 791 try { 792 assertFalse(service.isPackageOrComponentUserSet(resolvedNonUserSetComponent, 13)); 793 assertTrue(service.isPackageOrComponentUserSet(resolvedUserSetComponent, 10)); 794 } catch (AssertionError e) { 795 throw new AssertionError( 796 "Assertion failed while parsing xml:\n" + new String(rawOutput), e); 797 } 798 } 799 } 800 801 @Test rebindServices_onlyBindsExactMatchesIfComponent()802 public void rebindServices_onlyBindsExactMatchesIfComponent() throws Exception { 803 // If the primary and secondary lists contain component names, only those components within 804 // the package should be matched 805 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 806 mIpm, 807 ManagedServices.APPROVAL_BY_COMPONENT); 808 809 List<String> packages = new ArrayList<>(); 810 packages.add("package"); 811 packages.add("anotherPackage"); 812 addExpectedServices(service, packages, 0); 813 814 // only 2 components are approved per package 815 mExpectedPrimaryComponentNames.clear(); 816 mExpectedPrimaryComponentNames.put(0, "package/C1:package/C2"); 817 mExpectedSecondaryComponentNames.clear(); 818 mExpectedSecondaryComponentNames.put(0, "anotherPackage/C1:anotherPackage/C2"); 819 820 loadXml(service); 821 822 // verify the 2 components per package are enabled (bound) 823 verifyExpectedBoundEntries(service, true); 824 verifyExpectedBoundEntries(service, false); 825 826 // verify the last component per package is not enabled/we don't try to bind to it 827 for (String pkg : packages) { 828 ComponentName unapprovedAdditionalComponent = 829 ComponentName.unflattenFromString(pkg + "/C3"); 830 assertFalse( 831 service.isComponentEnabledForCurrentProfiles( 832 unapprovedAdditionalComponent)); 833 verify(mIpm, never()).getServiceInfo( 834 eq(unapprovedAdditionalComponent), anyLong(), anyInt()); 835 } 836 } 837 838 @Test rebindServices_bindsEverythingInAPackage()839 public void rebindServices_bindsEverythingInAPackage() throws Exception { 840 // If the primary and secondary lists contain packages, all components within those packages 841 // should be bound 842 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 843 APPROVAL_BY_PACKAGE); 844 845 List<String> packages = new ArrayList<>(); 846 packages.add("package"); 847 packages.add("packagea"); 848 addExpectedServices(service, packages, 0); 849 850 // 2 approved packages 851 mExpectedPrimaryPackages.clear(); 852 mExpectedPrimaryPackages.put(0, "package"); 853 mExpectedSecondaryPackages.clear(); 854 mExpectedSecondaryPackages.put(0, "packagea"); 855 856 loadXml(service); 857 858 // verify the 3 components per package are enabled (bound) 859 verifyExpectedBoundEntries(service, true); 860 verifyExpectedBoundEntries(service, false); 861 } 862 863 @Test reregisterService_checksAppIsApproved_pkg()864 public void reregisterService_checksAppIsApproved_pkg() throws Exception { 865 Context context = mock(Context.class); 866 PackageManager pm = mock(PackageManager.class); 867 ApplicationInfo ai = new ApplicationInfo(); 868 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 869 870 when(context.getPackageName()).thenReturn(mPkg); 871 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 872 when(context.getPackageManager()).thenReturn(pm); 873 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 874 875 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 876 APPROVAL_BY_PACKAGE); 877 ComponentName cn = ComponentName.unflattenFromString("a/a"); 878 879 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 880 Object[] args = invocation.getArguments(); 881 ServiceConnection sc = (ServiceConnection) args[1]; 882 sc.onServiceConnected(cn, mock(IBinder.class)); 883 return true; 884 }); 885 886 service.addApprovedList("a", 0, true); 887 888 service.reregisterService(cn, 0); 889 890 assertTrue(service.isBound(cn, 0)); 891 } 892 893 @Test reregisterService_checksAppIsApproved_pkg_secondary()894 public void reregisterService_checksAppIsApproved_pkg_secondary() throws Exception { 895 Context context = mock(Context.class); 896 PackageManager pm = mock(PackageManager.class); 897 ApplicationInfo ai = new ApplicationInfo(); 898 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 899 900 when(context.getPackageName()).thenReturn(mPkg); 901 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 902 when(context.getPackageManager()).thenReturn(pm); 903 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 904 905 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 906 APPROVAL_BY_PACKAGE); 907 ComponentName cn = ComponentName.unflattenFromString("a/a"); 908 909 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 910 Object[] args = invocation.getArguments(); 911 ServiceConnection sc = (ServiceConnection) args[1]; 912 sc.onServiceConnected(cn, mock(IBinder.class)); 913 return true; 914 }); 915 916 service.addApprovedList("a", 0, false); 917 918 service.reregisterService(cn, 0); 919 920 assertTrue(service.isBound(cn, 0)); 921 } 922 923 @Test reregisterService_checksAppIsApproved_cn()924 public void reregisterService_checksAppIsApproved_cn() throws Exception { 925 Context context = mock(Context.class); 926 PackageManager pm = mock(PackageManager.class); 927 ApplicationInfo ai = new ApplicationInfo(); 928 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 929 930 when(context.getPackageName()).thenReturn(mPkg); 931 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 932 when(context.getPackageManager()).thenReturn(pm); 933 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 934 935 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 936 APPROVAL_BY_COMPONENT); 937 ComponentName cn = ComponentName.unflattenFromString("a/a"); 938 939 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 940 Object[] args = invocation.getArguments(); 941 ServiceConnection sc = (ServiceConnection) args[1]; 942 sc.onServiceConnected(cn, mock(IBinder.class)); 943 return true; 944 }); 945 946 service.addApprovedList("a/a", 0, true); 947 948 service.reregisterService(cn, 0); 949 950 assertTrue(service.isBound(cn, 0)); 951 } 952 953 @Test reregisterService_checksAppIsApproved_cn_secondary()954 public void reregisterService_checksAppIsApproved_cn_secondary() throws Exception { 955 Context context = mock(Context.class); 956 PackageManager pm = mock(PackageManager.class); 957 ApplicationInfo ai = new ApplicationInfo(); 958 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 959 960 when(context.getPackageName()).thenReturn(mPkg); 961 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 962 when(context.getPackageManager()).thenReturn(pm); 963 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 964 965 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 966 APPROVAL_BY_COMPONENT); 967 ComponentName cn = ComponentName.unflattenFromString("a/a"); 968 969 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 970 Object[] args = invocation.getArguments(); 971 ServiceConnection sc = (ServiceConnection) args[1]; 972 sc.onServiceConnected(cn, mock(IBinder.class)); 973 return true; 974 }); 975 976 service.addApprovedList("a/a", 0, false); 977 978 service.reregisterService(cn, 0); 979 980 assertTrue(service.isBound(cn, 0)); 981 } 982 983 @Test reregisterService_checksAppIsNotApproved_cn_secondary()984 public void reregisterService_checksAppIsNotApproved_cn_secondary() throws Exception { 985 Context context = mock(Context.class); 986 PackageManager pm = mock(PackageManager.class); 987 ApplicationInfo ai = new ApplicationInfo(); 988 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 989 990 when(context.getPackageName()).thenReturn(mPkg); 991 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 992 when(context.getPackageManager()).thenReturn(pm); 993 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 994 995 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 996 APPROVAL_BY_COMPONENT); 997 ComponentName cn = ComponentName.unflattenFromString("a/a"); 998 999 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1000 Object[] args = invocation.getArguments(); 1001 ServiceConnection sc = (ServiceConnection) args[1]; 1002 sc.onServiceConnected(cn, mock(IBinder.class)); 1003 return true; 1004 }); 1005 1006 service.addApprovedList("b/b", 0, false); 1007 1008 service.reregisterService(cn, 0); 1009 1010 assertFalse(service.isBound(cn, 0)); 1011 } 1012 1013 @Test unbindOtherUserServices()1014 public void unbindOtherUserServices() throws PackageManager.NameNotFoundException { 1015 Context context = mock(Context.class); 1016 PackageManager pm = mock(PackageManager.class); 1017 ApplicationInfo ai = new ApplicationInfo(); 1018 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1019 1020 when(context.getPackageName()).thenReturn(mPkg); 1021 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1022 when(context.getPackageManager()).thenReturn(pm); 1023 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1024 1025 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1026 APPROVAL_BY_COMPONENT); 1027 ComponentName cn = ComponentName.unflattenFromString("a/a"); 1028 1029 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1030 Object[] args = invocation.getArguments(); 1031 ServiceConnection sc = (ServiceConnection) args[1]; 1032 sc.onServiceConnected(cn, mock(IBinder.class)); 1033 return true; 1034 }); 1035 1036 service.registerService(cn, 0); 1037 service.registerService(cn, 10); 1038 service.registerService(cn, 11); 1039 service.unbindOtherUserServices(11); 1040 1041 assertFalse(service.isBound(cn, 0)); 1042 assertFalse(service.isBound(cn, 10)); 1043 assertTrue(service.isBound(cn, 11)); 1044 } 1045 1046 @Test testPackageUninstall_packageNoLongerInApprovedList()1047 public void testPackageUninstall_packageNoLongerInApprovedList() throws Exception { 1048 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1049 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1050 mIpm, approvalLevel); 1051 writeExpectedValuesToSettings(approvalLevel); 1052 service.migrateToXml(); 1053 1054 mExpectedPrimaryPackages.put(0, "another.package"); 1055 mExpectedPrimaryComponentNames.put(0, "another.package/B1"); 1056 service.onPackagesChanged(true, new String[]{"this.is.a.package.name"}, new int[]{103}); 1057 1058 verifyExpectedApprovedEntries(service); 1059 } 1060 } 1061 1062 @Test testPackageUninstall_componentNoLongerInApprovedList()1063 public void testPackageUninstall_componentNoLongerInApprovedList() throws Exception { 1064 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1065 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1066 mIpm, approvalLevel); 1067 writeExpectedValuesToSettings(approvalLevel); 1068 service.migrateToXml(); 1069 1070 mExpectedSecondaryComponentNames.put(10, "component/2"); 1071 mExpectedSecondaryPackages.put(10, "component"); 1072 service.onPackagesChanged(true, new String[]{"this.is.another.package"}, new int[]{ 1073 UserHandle.PER_USER_RANGE + 1}); 1074 1075 verifyExpectedApprovedEntries(service); 1076 } 1077 } 1078 1079 @Test testIsPackageAllowed()1080 public void testIsPackageAllowed() { 1081 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1082 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1083 mIpm, approvalLevel); 1084 writeExpectedValuesToSettings(approvalLevel); 1085 service.migrateToXml(); 1086 1087 verifyExpectedApprovedPackages(service); 1088 } 1089 } 1090 1091 @Test testUpgradeAppBindsNewServices()1092 public void testUpgradeAppBindsNewServices() throws Exception { 1093 // If the primary and secondary lists contain component names, only those components within 1094 // the package should be matched 1095 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1096 mIpm, 1097 ManagedServices.APPROVAL_BY_PACKAGE); 1098 1099 List<String> packages = new ArrayList<>(); 1100 packages.add("package"); 1101 addExpectedServices(service, packages, 0); 1102 1103 // only 2 components are approved per package 1104 mExpectedPrimaryComponentNames.clear(); 1105 mExpectedPrimaryPackages.clear(); 1106 mExpectedPrimaryComponentNames.put(0, "package/C1:package/C2"); 1107 mExpectedSecondaryComponentNames.clear(); 1108 mExpectedSecondaryPackages.clear(); 1109 1110 loadXml(service); 1111 1112 // new component expected 1113 mExpectedPrimaryComponentNames.put(0, "package/C1:package/C2:package/C3"); 1114 1115 service.onPackagesChanged(false, new String[]{"package"}, new int[]{0}); 1116 1117 // verify the 3 components per package are enabled (bound) 1118 verifyExpectedBoundEntries(service, true); 1119 1120 // verify the last component per package is not enabled/we don't try to bind to it 1121 for (String pkg : packages) { 1122 ComponentName unapprovedAdditionalComponent = 1123 ComponentName.unflattenFromString(pkg + "/C3"); 1124 assertFalse( 1125 service.isComponentEnabledForCurrentProfiles( 1126 unapprovedAdditionalComponent)); 1127 verify(mIpm, never()).getServiceInfo( 1128 eq(unapprovedAdditionalComponent), anyLong(), anyInt()); 1129 } 1130 } 1131 1132 @Test testSetPackageOrComponentEnabled()1133 public void testSetPackageOrComponentEnabled() throws Exception { 1134 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1135 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1136 mIpm, approvalLevel); 1137 ArrayMap<Integer, ArrayList<String>> expectedEnabled = new ArrayMap<>(); 1138 expectedEnabled.put(0, 1139 Lists.newArrayList(new String[]{"package/Comp", "package/C2", "again/M4"})); 1140 expectedEnabled.put(10, 1141 Lists.newArrayList(new String[]{"user10package/B", "user10/Component", 1142 "user10package1/K", "user10.3/Component", "user10package2/L", 1143 "user10.4/Component"})); 1144 1145 for (int userId : expectedEnabled.keySet()) { 1146 ArrayList<String> expectedForUser = expectedEnabled.get(userId); 1147 for (int i = 0; i < expectedForUser.size(); i++) { 1148 boolean primary = i % 2 == 0; 1149 service.setPackageOrComponentEnabled(expectedForUser.get(i), userId, primary, 1150 true); 1151 } 1152 } 1153 1154 // verify everything added is approved 1155 for (int userId : expectedEnabled.keySet()) { 1156 ArrayList<String> expectedForUser = expectedEnabled.get(userId); 1157 for (int i = 0; i < expectedForUser.size(); i++) { 1158 String verifyValue = (approvalLevel == APPROVAL_BY_COMPONENT) 1159 ? expectedForUser.get(i) 1160 : service.getPackageName(expectedForUser.get(i)); 1161 assertTrue("Not allowed: user: " + userId + " entry: " + verifyValue 1162 + " for approval level " + approvalLevel, 1163 service.isPackageOrComponentAllowed(verifyValue, userId)); 1164 } 1165 } 1166 1167 ArrayMap<Integer, ArrayList<String>> expectedNoAccess = new ArrayMap<>(); 1168 for (int userId : expectedEnabled.keySet()) { 1169 ArrayList<String> expectedForUser = expectedEnabled.get(userId); 1170 for (int i = expectedForUser.size() - 1; i >= 0; i--) { 1171 ArrayList<String> removed = new ArrayList<>(); 1172 if (i % 3 == 0) { 1173 String revokeAccessFor = expectedForUser.remove(i); 1174 removed.add(revokeAccessFor); 1175 service.setPackageOrComponentEnabled( 1176 revokeAccessFor, userId, i % 2 == 0, false); 1177 } 1178 expectedNoAccess.put(userId, removed); 1179 } 1180 } 1181 1182 // verify everything still there is approved 1183 for (int userId : expectedEnabled.keySet()) { 1184 ArrayList<String> expectedForUser = expectedEnabled.get(userId); 1185 for (int i = 0; i < expectedForUser.size(); i++) { 1186 String verifyValue = (approvalLevel == APPROVAL_BY_COMPONENT) 1187 ? expectedForUser.get(i) 1188 : service.getPackageName(expectedForUser.get(i)); 1189 assertTrue("Not allowed: user: " + userId + " entry: " + verifyValue, 1190 service.isPackageOrComponentAllowed(verifyValue, userId)); 1191 } 1192 } 1193 // verify everything removed isn't 1194 for (int userId : expectedNoAccess.keySet()) { 1195 ArrayList<String> notExpectedForUser = expectedNoAccess.get(userId); 1196 for (int i = 0; i < notExpectedForUser.size(); i++) { 1197 assertFalse( 1198 "Is allowed: user: " + userId + " entry: " + notExpectedForUser.get(i), 1199 service.isPackageOrComponentAllowed(notExpectedForUser.get(i), userId)); 1200 } 1201 } 1202 } 1203 } 1204 1205 @Test testGetAllowedPackages_byUser()1206 public void testGetAllowedPackages_byUser() throws Exception { 1207 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1208 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1209 mIpm, approvalLevel); 1210 loadXml(service); 1211 1212 assertThat(service.getAllowedPackages(0)).containsExactly("this.is.a.package.name", 1213 "another.package", "secondary"); 1214 assertThat(service.getAllowedPackages(10)).containsExactly("this.is.another.package", 1215 "package", "this.is.another.package", "component"); 1216 assertThat(service.getAllowedPackages(999)).isEmpty(); 1217 } 1218 } 1219 1220 @Test testGetAllowedComponentsByUser()1221 public void testGetAllowedComponentsByUser() throws Exception { 1222 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 1223 APPROVAL_BY_COMPONENT); 1224 loadXml(service); 1225 1226 List<ComponentName> expected = new ArrayList<>(); 1227 expected.add(ComponentName.unflattenFromString("this.is.another.package/M1")); 1228 expected.add(ComponentName.unflattenFromString("this.is.another.package/with.Component")); 1229 expected.add(ComponentName.unflattenFromString("component/2")); 1230 expected.add(ComponentName.unflattenFromString("package/component2")); 1231 1232 List<ComponentName> actual = service.getAllowedComponents(10); 1233 1234 assertContentsInAnyOrder(expected, actual); 1235 1236 assertEquals(expected.size(), actual.size()); 1237 1238 for (ComponentName cn : expected) { 1239 assertTrue("Actual missing " + cn, actual.contains(cn)); 1240 } 1241 1242 for (ComponentName cn : actual) { 1243 assertTrue("Actual contains extra " + cn, expected.contains(cn)); 1244 } 1245 } 1246 1247 @Test testGetAllowedComponents_approvalByPackage()1248 public void testGetAllowedComponents_approvalByPackage() throws Exception { 1249 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 1250 APPROVAL_BY_PACKAGE); 1251 loadXml(service); 1252 1253 assertEquals(0, service.getAllowedComponents(10).size()); 1254 } 1255 1256 @Test testOnUserRemoved()1257 public void testOnUserRemoved() throws Exception { 1258 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1259 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1260 mIpm, approvalLevel); 1261 loadXml(service); 1262 1263 ArrayMap<Integer, String> verifyMap = mExpectedPrimary.get(service.mApprovalLevel); 1264 String user0 = verifyMap.remove(0); 1265 verifyMap = mExpectedSecondary.get(service.mApprovalLevel); 1266 user0 = user0 + ":" + verifyMap.remove(0); 1267 1268 service.onUserRemoved(0); 1269 1270 for (String verifyValue : user0.split(":")) { 1271 if (!TextUtils.isEmpty(verifyValue)) { 1272 assertFalse("service type " + service.mApprovalLevel + ":" + verifyValue 1273 + " is still allowed", 1274 service.isPackageOrComponentAllowed(verifyValue, 0)); 1275 } 1276 } 1277 1278 verifyExpectedApprovedEntries(service); 1279 } 1280 } 1281 1282 @Test testIsSameUser()1283 public void testIsSameUser() { 1284 IInterface service = mock(IInterface.class); 1285 when(service.asBinder()).thenReturn(mock(IBinder.class)); 1286 ManagedServices services = new TestManagedServices(getContext(), mLock, mUserProfiles, 1287 mIpm, APPROVAL_BY_PACKAGE); 1288 services.registerSystemService(service, null, 10, 1000); 1289 ManagedServices.ManagedServiceInfo info = services.checkServiceTokenLocked(service); 1290 info.isSystem = true; 1291 1292 assertFalse(services.isSameUser(service, 0)); 1293 assertTrue(services.isSameUser(service, 10)); 1294 assertTrue(services.isSameUser(service, UserHandle.USER_ALL)); 1295 } 1296 1297 @Test testGetAllowedComponents()1298 public void testGetAllowedComponents() throws Exception { 1299 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 1300 APPROVAL_BY_COMPONENT); 1301 loadXml(service); 1302 1303 SparseArray<ArraySet<ComponentName>> expected = new SparseArray<>(); 1304 1305 ArraySet<ComponentName> expected10 = new ArraySet<>(); 1306 expected10.add(ComponentName.unflattenFromString("this.is.another.package/M1")); 1307 expected10.add(ComponentName.unflattenFromString("this.is.another.package/with.Component")); 1308 expected10.add(ComponentName.unflattenFromString("component/2")); 1309 expected10.add(ComponentName.unflattenFromString("package/component2")); 1310 expected.put(10, expected10); 1311 ArraySet<ComponentName> expected0 = new ArraySet<>(); 1312 expected0.add(ComponentName.unflattenFromString("secondary/component.Name")); 1313 expected0.add(ComponentName.unflattenFromString("this.is.a.package.name/Ba")); 1314 expected0.add(ComponentName.unflattenFromString("another.package/B1")); 1315 expected.put(0, expected0); 1316 ArraySet<ComponentName> expected12 = new ArraySet<>(); 1317 expected12.add(ComponentName.unflattenFromString("bananas!/Bananas!")); 1318 expected.put(12, expected12); 1319 expected.put(11, new ArraySet<>()); 1320 ArraySet<ComponentName> expected13 = new ArraySet<>(); 1321 expected13.add(ComponentName.unflattenFromString("non.user.set.package/M1")); 1322 expected.put(13, expected13); 1323 1324 SparseArray<ArraySet<ComponentName>> actual = 1325 service.getAllowedComponents(mUserProfiles.getCurrentProfileIds()); 1326 1327 assertContentsInAnyOrder(expected, actual); 1328 } 1329 1330 @Test testPopulateComponentsToUnbind_forceRebind()1331 public void testPopulateComponentsToUnbind_forceRebind() { 1332 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 1333 APPROVAL_BY_COMPONENT); 1334 1335 IInterface iInterface = mock(IInterface.class); 1336 when(iInterface.asBinder()).thenReturn(mock(IBinder.class)); 1337 1338 ManagedServices.ManagedServiceInfo service0 = service.new ManagedServiceInfo( 1339 iInterface, ComponentName.unflattenFromString("a/a"), 0, false, 1340 mock(ServiceConnection.class), 26, 34); 1341 ManagedServices.ManagedServiceInfo service10 = service.new ManagedServiceInfo( 1342 iInterface, ComponentName.unflattenFromString("b/b"), 10, false, 1343 mock(ServiceConnection.class), 26, 345); 1344 Set<ManagedServices.ManagedServiceInfo> removableBoundServices = new ArraySet<>(); 1345 removableBoundServices.add(service0); 1346 removableBoundServices.add(service10); 1347 1348 SparseArray<Set<ComponentName>> allowedComponentsToBind = new SparseArray<>(); 1349 Set<ComponentName> allowed0 = new ArraySet<>(); 1350 allowed0.add(ComponentName.unflattenFromString("a/a")); 1351 allowedComponentsToBind.put(0, allowed0); 1352 Set<ComponentName> allowed10 = new ArraySet<>(); 1353 allowed10.add(ComponentName.unflattenFromString("b/b")); 1354 allowedComponentsToBind.put(10, allowed10); 1355 1356 SparseArray<Set<ComponentName>> componentsToUnbind = new SparseArray<>(); 1357 1358 service.populateComponentsToUnbind(true, removableBoundServices, allowedComponentsToBind, 1359 componentsToUnbind); 1360 1361 assertEquals(2, componentsToUnbind.size()); 1362 assertTrue(componentsToUnbind.get(0).contains(ComponentName.unflattenFromString("a/a"))); 1363 assertTrue(componentsToUnbind.get(10).contains(ComponentName.unflattenFromString("b/b"))); 1364 } 1365 1366 @Test testPopulateComponentsToUnbind()1367 public void testPopulateComponentsToUnbind() { 1368 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 1369 APPROVAL_BY_COMPONENT); 1370 1371 IInterface iInterface = mock(IInterface.class); 1372 when(iInterface.asBinder()).thenReturn(mock(IBinder.class)); 1373 1374 ManagedServices.ManagedServiceInfo service0 = service.new ManagedServiceInfo( 1375 iInterface, ComponentName.unflattenFromString("a/a"), 0, false, 1376 mock(ServiceConnection.class), 26, 345); 1377 ManagedServices.ManagedServiceInfo service0a = service.new ManagedServiceInfo( 1378 iInterface, ComponentName.unflattenFromString("c/c"), 0, false, 1379 mock(ServiceConnection.class), 26, 3456); 1380 ManagedServices.ManagedServiceInfo service10 = service.new ManagedServiceInfo( 1381 iInterface, ComponentName.unflattenFromString("b/b"), 10, false, 1382 mock(ServiceConnection.class), 26, 34567); 1383 Set<ManagedServices.ManagedServiceInfo> removableBoundServices = new ArraySet<>(); 1384 removableBoundServices.add(service0); 1385 removableBoundServices.add(service0a); 1386 removableBoundServices.add(service10); 1387 1388 SparseArray<Set<ComponentName>> allowedComponentsToBind = new SparseArray<>(); 1389 Set<ComponentName> allowed0 = new ArraySet<>(); 1390 allowed0.add(ComponentName.unflattenFromString("a/a")); 1391 allowedComponentsToBind.put(0, allowed0); 1392 Set<ComponentName> allowed10 = new ArraySet<>(); 1393 allowed10.add(ComponentName.unflattenFromString("b/b")); 1394 allowedComponentsToBind.put(10, allowed10); 1395 1396 SparseArray<Set<ComponentName>> componentsToUnbind = new SparseArray<>(); 1397 1398 service.populateComponentsToUnbind(false, removableBoundServices, allowedComponentsToBind, 1399 componentsToUnbind); 1400 1401 assertEquals(1, componentsToUnbind.size()); 1402 assertEquals(1, componentsToUnbind.get(0).size()); 1403 assertTrue(componentsToUnbind.get(0).contains(ComponentName.unflattenFromString("c/c"))); 1404 } 1405 1406 @Test populateComponentsToBind()1407 public void populateComponentsToBind() { 1408 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, mIpm, 1409 APPROVAL_BY_COMPONENT); 1410 1411 SparseArray<ArraySet<ComponentName>> approvedComponentsByUser = new SparseArray<>(); 1412 ArraySet<ComponentName> allowed0 = new ArraySet<>(); 1413 allowed0.add(ComponentName.unflattenFromString("a/a")); 1414 approvedComponentsByUser.put(0, allowed0); 1415 ArraySet<ComponentName> allowed10 = new ArraySet<>(); 1416 allowed10.add(ComponentName.unflattenFromString("b/b")); 1417 allowed10.add(ComponentName.unflattenFromString("c/c")); 1418 approvedComponentsByUser.put(10, allowed10); 1419 ArraySet<ComponentName> allowed15 = new ArraySet<>(); 1420 allowed15.add(ComponentName.unflattenFromString("d/d")); 1421 approvedComponentsByUser.put(15, allowed15); 1422 1423 IntArray users = new IntArray(); 1424 users.add(10); 1425 users.add(0); 1426 1427 SparseArray<Set<ComponentName>> componentsToBind = new SparseArray<>(); 1428 1429 service.populateComponentsToBind(componentsToBind, users, approvedComponentsByUser); 1430 1431 assertEquals(2, componentsToBind.size()); 1432 assertEquals(1, componentsToBind.get(0).size()); 1433 assertTrue(componentsToBind.get(0).contains(ComponentName.unflattenFromString("a/a"))); 1434 assertEquals(2, componentsToBind.get(10).size()); 1435 assertTrue(componentsToBind.get(10).contains(ComponentName.unflattenFromString("b/b"))); 1436 assertTrue(componentsToBind.get(10).contains(ComponentName.unflattenFromString("c/c"))); 1437 } 1438 1439 @Test testOnNullBinding()1440 public void testOnNullBinding() throws Exception { 1441 Context context = mock(Context.class); 1442 PackageManager pm = mock(PackageManager.class); 1443 ApplicationInfo ai = new ApplicationInfo(); 1444 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1445 1446 when(context.getPackageName()).thenReturn(mPkg); 1447 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1448 when(context.getPackageManager()).thenReturn(pm); 1449 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1450 1451 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1452 APPROVAL_BY_COMPONENT); 1453 ComponentName cn = ComponentName.unflattenFromString("a/a"); 1454 1455 ArgumentCaptor<ServiceConnection> captor = ArgumentCaptor.forClass(ServiceConnection.class); 1456 when(context.bindServiceAsUser(any(), captor.capture(), anyInt(), any())) 1457 .thenAnswer(invocation -> { 1458 captor.getValue().onNullBinding(cn); 1459 return true; 1460 }); 1461 1462 service.registerSystemService(cn, 0); 1463 verify(context).unbindService(captor.getValue()); 1464 } 1465 1466 @Test testOnServiceConnected()1467 public void testOnServiceConnected() throws Exception { 1468 Context context = mock(Context.class); 1469 PackageManager pm = mock(PackageManager.class); 1470 ApplicationInfo ai = new ApplicationInfo(); 1471 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1472 1473 when(context.getPackageName()).thenReturn(mPkg); 1474 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1475 when(context.getPackageManager()).thenReturn(pm); 1476 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1477 1478 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1479 APPROVAL_BY_COMPONENT); 1480 ComponentName cn = ComponentName.unflattenFromString("a/a"); 1481 1482 service.registerSystemService(cn, 0); 1483 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1484 Object[] args = invocation.getArguments(); 1485 ServiceConnection sc = (ServiceConnection) args[1]; 1486 sc.onServiceConnected(cn, mock(IBinder.class)); 1487 return true; 1488 }); 1489 1490 service.registerSystemService(cn, 0); 1491 assertTrue(service.isBound(cn, 0)); 1492 } 1493 1494 @Test testSetComponentState()1495 public void testSetComponentState() throws Exception { 1496 Context context = mock(Context.class); 1497 PackageManager pm = mock(PackageManager.class); 1498 ApplicationInfo ai = new ApplicationInfo(); 1499 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1500 1501 when(context.getPackageName()).thenReturn(mPkg); 1502 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1503 when(context.getPackageManager()).thenReturn(pm); 1504 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1505 1506 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1507 APPROVAL_BY_COMPONENT); 1508 ComponentName cn = ComponentName.unflattenFromString("a/a"); 1509 1510 service.registerSystemService(cn, 0); 1511 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1512 Object[] args = invocation.getArguments(); 1513 ServiceConnection sc = (ServiceConnection) args[1]; 1514 sc.onServiceConnected(cn, mock(IBinder.class)); 1515 return true; 1516 }); 1517 1518 service.registerSystemService(cn, mZero.id); 1519 1520 service.setComponentState(cn, mZero.id, false); 1521 verify(context).unbindService(any()); 1522 } 1523 1524 @Test testSetComponentState_workProfile()1525 public void testSetComponentState_workProfile() throws Exception { 1526 Context context = mock(Context.class); 1527 PackageManager pm = mock(PackageManager.class); 1528 ApplicationInfo ai = new ApplicationInfo(); 1529 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1530 1531 when(context.getPackageName()).thenReturn(mPkg); 1532 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1533 when(context.getPackageManager()).thenReturn(pm); 1534 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1535 1536 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1537 APPROVAL_BY_COMPONENT); 1538 ComponentName cn = ComponentName.unflattenFromString("a/a"); 1539 1540 service.registerSystemService(cn, 0); 1541 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1542 Object[] args = invocation.getArguments(); 1543 ServiceConnection sc = (ServiceConnection) args[1]; 1544 sc.onServiceConnected(cn, mock(IBinder.class)); 1545 return true; 1546 }); 1547 1548 service.registerSystemService(cn, mZero.id); 1549 1550 service.setComponentState(cn, mTen.id, false); 1551 verify(context, never()).unbindService(any()); 1552 } 1553 1554 @Test testSetComponentState_differentUsers()1555 public void testSetComponentState_differentUsers() throws Exception { 1556 Context context = mock(Context.class); 1557 PackageManager pm = mock(PackageManager.class); 1558 ApplicationInfo ai = new ApplicationInfo(); 1559 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1560 1561 when(context.getPackageName()).thenReturn(mPkg); 1562 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1563 when(context.getPackageManager()).thenReturn(pm); 1564 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1565 1566 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1567 APPROVAL_BY_COMPONENT); 1568 ComponentName cn = ComponentName.unflattenFromString("a/a"); 1569 1570 addExpectedServices(service, Arrays.asList("a"), mZero.id); 1571 addExpectedServices(service, Arrays.asList("a"), mTen.id); 1572 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1573 Object[] args = invocation.getArguments(); 1574 ServiceConnection sc = (ServiceConnection) args[1]; 1575 sc.onServiceConnected(cn, mock(IBinder.class)); 1576 return true; 1577 }); 1578 service.addApprovedList("a/a", 0, true); 1579 service.addApprovedList("a/a", 10, false); 1580 1581 service.registerService(cn, mZero.id); 1582 assertTrue(service.isBound(cn, mZero.id)); 1583 1584 service.onUserSwitched(mTen.id); 1585 assertFalse(service.isBound(cn, mZero.id)); 1586 service.registerService(cn, mTen.id); 1587 assertTrue(service.isBound(cn, mTen.id)); 1588 1589 service.setComponentState(cn, mTen.id, false); 1590 assertFalse(service.isBound(cn, mZero.id)); 1591 assertFalse(service.isBound(cn, mTen.id)); 1592 1593 // Service should be rebound on user 0, since it was only disabled for user 10. 1594 service.onUserSwitched(mZero.id); 1595 assertTrue(service.isBound(cn, mZero.id)); 1596 assertFalse(service.isBound(cn, mTen.id)); 1597 1598 // Service should stay unbound on going back to user 10. 1599 service.onUserSwitched(mTen.id); 1600 assertFalse(service.isBound(cn, mZero.id)); 1601 assertFalse(service.isBound(cn, mTen.id)); 1602 } 1603 @Test testOnPackagesChanged_nullValuesPassed_noNullPointers()1604 public void testOnPackagesChanged_nullValuesPassed_noNullPointers() { 1605 for (int approvalLevel : new int[] {APPROVAL_BY_COMPONENT, APPROVAL_BY_PACKAGE}) { 1606 ManagedServices service = new TestManagedServices(getContext(), mLock, mUserProfiles, 1607 mIpm, approvalLevel); 1608 // null uid list 1609 service.onPackagesChanged(true, new String[]{"this.is.a.package.name"}, null); 1610 1611 // null package list 1612 service.onPackagesChanged(true, null, new int[]{103}); 1613 } 1614 } 1615 1616 @Test loadDefaults_noVersionNoDefaults()1617 public void loadDefaults_noVersionNoDefaults() throws Exception { 1618 resetComponentsAndPackages(); 1619 loadXml(mService); 1620 assertEquals(mService.getDefaultComponents().size(), 0); 1621 } 1622 1623 @Test loadDefaults_noVersionNoDefaultsOneActive()1624 public void loadDefaults_noVersionNoDefaultsOneActive() throws Exception { 1625 resetComponentsAndPackages(); 1626 mService.addDefaultComponentOrPackage("package/class"); 1627 loadXml(mService); 1628 assertEquals(1, mService.getDefaultComponents().size()); 1629 assertTrue(mService.getDefaultComponents() 1630 .contains(ComponentName.unflattenFromString("package/class"))); 1631 } 1632 1633 @Test loadDefaults_noVersionWithDefaults()1634 public void loadDefaults_noVersionWithDefaults() throws Exception { 1635 resetComponentsAndPackages(); 1636 mDefaults.add(new ComponentName("default", "class")); 1637 mVersionString = null; 1638 loadXml(mService); 1639 assertEquals(mService.getDefaultComponents(), mDefaults); 1640 } 1641 1642 @Test loadDefaults_versionOneWithDefaultsWithActive()1643 public void loadDefaults_versionOneWithDefaultsWithActive() throws Exception { 1644 resetComponentsAndPackages(); 1645 mDefaults.add(new ComponentName("default", "class")); 1646 mExpectedPrimaryComponentNames.put(0, "package/class"); 1647 mVersionString = "1"; 1648 loadXml(mService); 1649 assertEquals(mService.getDefaultComponents(), 1650 new ArraySet(Arrays.asList(new ComponentName("package", "class")))); 1651 } 1652 1653 @Test loadDefaults_versionTwoWithDefaultsWithActive()1654 public void loadDefaults_versionTwoWithDefaultsWithActive() throws Exception { 1655 resetComponentsAndPackages(); 1656 mDefaults.add(new ComponentName("default", "class")); 1657 mDefaultsString = "default/class"; 1658 mExpectedPrimaryComponentNames.put(0, "package/class"); 1659 mVersionString = "2"; 1660 loadXml(mService); 1661 assertEquals(1, mService.getDefaultComponents().size()); 1662 mDefaults.forEach(pkg -> { 1663 assertTrue(mService.getDefaultComponents().contains(pkg)); 1664 }); 1665 } 1666 1667 @Test loadDefaults_versionOneWithXMLDefaultsWithActive()1668 public void loadDefaults_versionOneWithXMLDefaultsWithActive() throws Exception { 1669 resetComponentsAndPackages(); 1670 mDefaults.add(new ComponentName("default", "class")); 1671 mDefaultsString = "xml/class"; 1672 mExpectedPrimaryComponentNames.put(0, "package/class"); 1673 mVersionString = "1"; 1674 loadXml(mService); 1675 assertEquals(mService.getDefaultComponents(), 1676 new ArraySet(Arrays.asList(new ComponentName("xml", "class")))); 1677 } 1678 1679 @Test loadDefaults_versionTwoWithXMLDefaultsWithActive()1680 public void loadDefaults_versionTwoWithXMLDefaultsWithActive() throws Exception { 1681 resetComponentsAndPackages(); 1682 mDefaults.add(new ComponentName("default", "class")); 1683 mDefaultsString = "xml/class"; 1684 mExpectedPrimaryComponentNames.put(0, "package/class"); 1685 mVersionString = "2"; 1686 loadXml(mService); 1687 assertEquals(mService.getDefaultComponents(), 1688 new ArraySet(Arrays.asList(new ComponentName("xml", "class")))); 1689 } 1690 1691 @Test loadDefaults_versionLatest_NoLoadDefaults()1692 public void loadDefaults_versionLatest_NoLoadDefaults() throws Exception { 1693 resetComponentsAndPackages(); 1694 mDefaults.add(new ComponentName("default", "class")); 1695 mDefaultsString = "xml/class"; 1696 loadXml(mService); 1697 assertEquals(mService.getDefaultComponents(), 1698 new ArraySet(Arrays.asList(new ComponentName("xml", "class")))); 1699 } 1700 1701 @Test upgradeUserSet_versionThree()1702 public void upgradeUserSet_versionThree() throws Exception { 1703 resetComponentsAndPackages(); 1704 1705 List<UserInfo> users = new ArrayList<>(); 1706 users.add(new UserInfo(98, "98", 0)); 1707 users.add(new UserInfo(99, "99", 0)); 1708 for (UserInfo user : users) { 1709 when(mUm.getUserInfo(eq(user.id))).thenReturn(user); 1710 } 1711 1712 mDefaultsString = "xml/class"; 1713 mVersionString = "3"; 1714 mUserSetString = "xml/class"; 1715 loadXml(mService); 1716 1717 //Test services without overriding upgradeUserSet() remain unchanged 1718 assertEquals(new ArraySet(Arrays.asList(mUserSetString)), 1719 mService.mUserSetServices.get(98)); 1720 assertEquals(new ArraySet(Arrays.asList(mUserSetString)), 1721 mService.mUserSetServices.get(99)); 1722 assertEquals(new ArrayMap(), mService.mIsUserChanged); 1723 } 1724 1725 @Test testInfoIsPermittedForProfile_notProfile()1726 public void testInfoIsPermittedForProfile_notProfile() { 1727 when(mUserProfiles.isProfileUser(anyInt())).thenReturn(false); 1728 1729 IInterface service = mock(IInterface.class); 1730 when(service.asBinder()).thenReturn(mock(IBinder.class)); 1731 ManagedServices services = new TestManagedServices(getContext(), mLock, mUserProfiles, 1732 mIpm, APPROVAL_BY_PACKAGE); 1733 services.registerSystemService(service, null, 10, 1000); 1734 ManagedServices.ManagedServiceInfo info = services.checkServiceTokenLocked(service); 1735 1736 assertTrue(info.isPermittedForProfile(0)); 1737 } 1738 1739 @Test testInfoIsPermittedForProfile_profileAndDpmAllows()1740 public void testInfoIsPermittedForProfile_profileAndDpmAllows() { 1741 when(mUserProfiles.isProfileUser(anyInt())).thenReturn(true); 1742 when(mDpm.isNotificationListenerServicePermitted(anyString(), anyInt())).thenReturn(true); 1743 1744 IInterface service = mock(IInterface.class); 1745 when(service.asBinder()).thenReturn(mock(IBinder.class)); 1746 ManagedServices services = new TestManagedServices(getContext(), mLock, mUserProfiles, 1747 mIpm, APPROVAL_BY_PACKAGE); 1748 services.registerSystemService(service, null, 10, 1000); 1749 ManagedServices.ManagedServiceInfo info = services.checkServiceTokenLocked(service); 1750 info.component = new ComponentName("a","b"); 1751 1752 assertTrue(info.isPermittedForProfile(0)); 1753 } 1754 1755 @Test testInfoIsPermittedForProfile_profileAndDpmDenies()1756 public void testInfoIsPermittedForProfile_profileAndDpmDenies() { 1757 when(mUserProfiles.isProfileUser(anyInt())).thenReturn(true); 1758 when(mDpm.isNotificationListenerServicePermitted(anyString(), anyInt())).thenReturn(false); 1759 1760 IInterface service = mock(IInterface.class); 1761 when(service.asBinder()).thenReturn(mock(IBinder.class)); 1762 ManagedServices services = new TestManagedServices(getContext(), mLock, mUserProfiles, 1763 mIpm, APPROVAL_BY_PACKAGE); 1764 services.registerSystemService(service, null, 10, 1000); 1765 ManagedServices.ManagedServiceInfo info = services.checkServiceTokenLocked(service); 1766 info.component = new ComponentName("a","b"); 1767 1768 assertFalse(info.isPermittedForProfile(0)); 1769 } 1770 1771 @Test testUserProfiles_canProfileUseBoundServices_managedProfile()1772 public void testUserProfiles_canProfileUseBoundServices_managedProfile() { 1773 List<UserInfo> users = new ArrayList<>(); 1774 UserInfo profile = new UserInfo(ActivityManager.getCurrentUser(), "current", 0); 1775 profile.userType = USER_TYPE_FULL_SECONDARY; 1776 users.add(profile); 1777 UserInfo managed = new UserInfo(12, "12", 0); 1778 managed.userType = USER_TYPE_PROFILE_MANAGED; 1779 users.add(managed); 1780 UserInfo clone = new UserInfo(13, "13", 0); 1781 clone.userType = USER_TYPE_PROFILE_CLONE; 1782 users.add(clone); 1783 when(mUm.getProfiles(ActivityManager.getCurrentUser())).thenReturn(users); 1784 1785 ManagedServices.UserProfiles profiles = new ManagedServices.UserProfiles(); 1786 profiles.updateCache(mContext); 1787 1788 assertFalse(profiles.isProfileUser(ActivityManager.getCurrentUser())); 1789 assertTrue(profiles.isProfileUser(12)); 1790 assertTrue(profiles.isProfileUser(13)); 1791 } 1792 1793 @Test rebindServices_onlyBindsIfAutobindMetaDataTrue()1794 public void rebindServices_onlyBindsIfAutobindMetaDataTrue() throws Exception { 1795 Context context = mock(Context.class); 1796 PackageManager pm = mock(PackageManager.class); 1797 ApplicationInfo ai = new ApplicationInfo(); 1798 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1799 1800 when(context.getPackageName()).thenReturn(mPkg); 1801 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1802 when(context.getPackageManager()).thenReturn(pm); 1803 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1804 1805 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1806 APPROVAL_BY_COMPONENT); 1807 final ComponentName cn_allowed = ComponentName.unflattenFromString("anotherPackage/C1"); 1808 final ComponentName cn_disallowed = ComponentName.unflattenFromString("package/C1"); 1809 1810 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1811 Object[] args = invocation.getArguments(); 1812 ServiceConnection sc = (ServiceConnection) args[1]; 1813 sc.onServiceConnected(cn_allowed, mock(IBinder.class)); 1814 return true; 1815 }); 1816 1817 List<ComponentName> componentNames = new ArrayList<>(); 1818 componentNames.add(cn_allowed); 1819 componentNames.add(cn_disallowed); 1820 ArrayMap<ComponentName, Bundle> metaDatas = new ArrayMap<>(); 1821 Bundle metaDataAutobindDisallow = new Bundle(); 1822 metaDataAutobindDisallow.putBoolean(META_DATA_DEFAULT_AUTOBIND, false); 1823 metaDatas.put(cn_disallowed, metaDataAutobindDisallow); 1824 Bundle metaDataAutobindAllow = new Bundle(); 1825 metaDataAutobindAllow.putBoolean(META_DATA_DEFAULT_AUTOBIND, true); 1826 metaDatas.put(cn_allowed, metaDataAutobindAllow); 1827 1828 mockServiceInfoWithMetaData(componentNames, service, metaDatas); 1829 1830 service.addApprovedList(cn_allowed.flattenToString(), 0, true); 1831 service.addApprovedList(cn_disallowed.flattenToString(), 0, true); 1832 1833 service.rebindServices(true, 0); 1834 1835 assertTrue(service.isBound(cn_allowed, 0)); 1836 assertFalse(service.isBound(cn_disallowed, 0)); 1837 } 1838 1839 @Test rebindServices_bindsIfAutobindMetaDataFalseWhenServiceBound()1840 public void rebindServices_bindsIfAutobindMetaDataFalseWhenServiceBound() throws Exception { 1841 Context context = mock(Context.class); 1842 PackageManager pm = mock(PackageManager.class); 1843 ApplicationInfo ai = new ApplicationInfo(); 1844 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1845 1846 when(context.getPackageName()).thenReturn(mPkg); 1847 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1848 when(context.getPackageManager()).thenReturn(pm); 1849 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1850 1851 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1852 APPROVAL_BY_COMPONENT); 1853 final ComponentName cn_disallowed = ComponentName.unflattenFromString("package/C1"); 1854 1855 // mock isBoundOrRebinding => consider listener service bound 1856 service = spy(service); 1857 when(service.isBoundOrRebinding(cn_disallowed, 0)).thenReturn(true); 1858 1859 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1860 Object[] args = invocation.getArguments(); 1861 ServiceConnection sc = (ServiceConnection) args[1]; 1862 sc.onServiceConnected(cn_disallowed, mock(IBinder.class)); 1863 return true; 1864 }); 1865 1866 List<ComponentName> componentNames = new ArrayList<>(); 1867 componentNames.add(cn_disallowed); 1868 ArrayMap<ComponentName, Bundle> metaDatas = new ArrayMap<>(); 1869 Bundle metaDataAutobindDisallow = new Bundle(); 1870 metaDataAutobindDisallow.putBoolean(META_DATA_DEFAULT_AUTOBIND, false); 1871 metaDatas.put(cn_disallowed, metaDataAutobindDisallow); 1872 1873 mockServiceInfoWithMetaData(componentNames, service, metaDatas); 1874 1875 service.addApprovedList(cn_disallowed.flattenToString(), 0, true); 1876 1877 // Listener service should be bound by rebindService when forceRebind is false 1878 service.rebindServices(false, 0); 1879 assertTrue(service.isBound(cn_disallowed, 0)); 1880 } 1881 1882 @Test setComponentState_ignoresAutobindMetaData()1883 public void setComponentState_ignoresAutobindMetaData() throws Exception { 1884 Context context = mock(Context.class); 1885 PackageManager pm = mock(PackageManager.class); 1886 ApplicationInfo ai = new ApplicationInfo(); 1887 ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT; 1888 1889 when(context.getPackageName()).thenReturn(mPkg); 1890 when(context.getUserId()).thenReturn(mUser.getIdentifier()); 1891 when(context.getPackageManager()).thenReturn(pm); 1892 when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai); 1893 1894 ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm, 1895 APPROVAL_BY_COMPONENT); 1896 final ComponentName cn_disallowed = ComponentName.unflattenFromString("package/C1"); 1897 1898 when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> { 1899 Object[] args = invocation.getArguments(); 1900 ServiceConnection sc = (ServiceConnection) args[1]; 1901 sc.onServiceConnected(cn_disallowed, mock(IBinder.class)); 1902 return true; 1903 }); 1904 1905 List<ComponentName> componentNames = new ArrayList<>(); 1906 componentNames.add(cn_disallowed); 1907 ArrayMap<ComponentName, Bundle> metaDatas = new ArrayMap<>(); 1908 Bundle metaDataAutobindDisallow = new Bundle(); 1909 metaDataAutobindDisallow.putBoolean(META_DATA_DEFAULT_AUTOBIND, false); 1910 metaDatas.put(cn_disallowed, metaDataAutobindDisallow); 1911 1912 mockServiceInfoWithMetaData(componentNames, service, metaDatas); 1913 1914 service.addApprovedList(cn_disallowed.flattenToString(), 0, true); 1915 1916 // add component to snoozing list 1917 service.setComponentState(cn_disallowed, 0, false); 1918 1919 // Test that setComponentState overrides the meta-data and service is bound 1920 service.setComponentState(cn_disallowed, 0, true); 1921 assertTrue(service.isBound(cn_disallowed, 0)); 1922 } 1923 1924 @Test isComponentEnabledForCurrentProfiles_isThreadSafe()1925 public void isComponentEnabledForCurrentProfiles_isThreadSafe() throws InterruptedException { 1926 for (UserInfo userInfo : mUm.getUsers()) { 1927 mService.addApprovedList("pkg1/cmp1:pkg2/cmp2:pkg3/cmp3", userInfo.id, true); 1928 } 1929 testThreadSafety(() -> { 1930 mService.rebindServices(false, 0); 1931 assertThat(mService.isComponentEnabledForCurrentProfiles( 1932 new ComponentName("pkg1", "cmp1"))).isTrue(); 1933 }, 20, 30); 1934 } 1935 1936 @Test isComponentEnabledForCurrentProfiles_profileUserId()1937 public void isComponentEnabledForCurrentProfiles_profileUserId() { 1938 final int profileUserId = 10; 1939 when(mUserProfiles.isProfileUser(profileUserId)).thenReturn(true); 1940 // Only approve for parent user (0) 1941 mService.addApprovedList("pkg1/cmp1:pkg2/cmp2:pkg3/cmp3", 0, true); 1942 1943 // Test that the component is enabled after calling rebindServices with profile userId (10) 1944 mService.rebindServices(false, profileUserId); 1945 assertThat(mService.isComponentEnabledForCurrentProfiles( 1946 new ComponentName("pkg1", "cmp1"))).isTrue(); 1947 } 1948 1949 @Test isComponentEnabledForCurrentProfiles_profileUserId_NAS()1950 public void isComponentEnabledForCurrentProfiles_profileUserId_NAS() { 1951 final int profileUserId = 10; 1952 when(mUserProfiles.isProfileUser(profileUserId)).thenReturn(true); 1953 // Do not rebind for parent users (NAS use-case) 1954 ManagedServices service = spy(mService); 1955 when(service.allowRebindForParentUser()).thenReturn(false); 1956 1957 // Only approve for parent user (0) 1958 service.addApprovedList("pkg1/cmp1:pkg2/cmp2:pkg3/cmp3", 0, true); 1959 1960 // Test that the component is disabled after calling rebindServices with profile userId (10) 1961 service.rebindServices(false, profileUserId); 1962 assertThat(service.isComponentEnabledForCurrentProfiles( 1963 new ComponentName("pkg1", "cmp1"))).isFalse(); 1964 } 1965 mockServiceInfoWithMetaData(List<ComponentName> componentNames, ManagedServices service, ArrayMap<ComponentName, Bundle> metaDatas)1966 private void mockServiceInfoWithMetaData(List<ComponentName> componentNames, 1967 ManagedServices service, ArrayMap<ComponentName, Bundle> metaDatas) 1968 throws RemoteException { 1969 when(mIpm.getServiceInfo(any(), anyLong(), anyInt())).thenAnswer( 1970 (Answer<ServiceInfo>) invocation -> { 1971 ComponentName invocationCn = invocation.getArgument(0); 1972 if (invocationCn != null && componentNames.contains(invocationCn)) { 1973 ServiceInfo serviceInfo = new ServiceInfo(); 1974 serviceInfo.packageName = invocationCn.getPackageName(); 1975 serviceInfo.name = invocationCn.getClassName(); 1976 serviceInfo.permission = service.getConfig().bindPermission; 1977 serviceInfo.metaData = metaDatas.get(invocationCn); 1978 return serviceInfo; 1979 } 1980 return null; 1981 } 1982 ); 1983 } 1984 resetComponentsAndPackages()1985 private void resetComponentsAndPackages() { 1986 ArrayMap<Integer, ArrayMap<Integer, String>> empty = new ArrayMap(1); 1987 ArrayMap<Integer, String> emptyPkgs = new ArrayMap(0); 1988 empty.append(mService.mApprovalLevel, emptyPkgs); 1989 mExpectedPrimary = empty; 1990 mExpectedPrimaryComponentNames = emptyPkgs; 1991 mExpectedPrimaryPackages = emptyPkgs; 1992 mExpectedSecondary = empty; 1993 mExpectedSecondaryComponentNames = emptyPkgs; 1994 mExpectedSecondaryPackages = emptyPkgs; 1995 } 1996 loadXml(ManagedServices service)1997 private void loadXml(ManagedServices service) throws Exception { 1998 String xmlString = createXml(service); 1999 TypedXmlPullParser parser = Xml.newFastPullParser(); 2000 parser.setInput(new BufferedInputStream( 2001 new ByteArrayInputStream(xmlString.getBytes())), null); 2002 parser.nextTag(); 2003 service.readXml(parser, null, false, UserHandle.USER_ALL); 2004 } 2005 createXml(ManagedServices service)2006 private String createXml(ManagedServices service) { 2007 final StringBuffer xml = new StringBuffer(); 2008 String xmlTag = service.getConfig().xmlTag; 2009 xml.append("<" + xmlTag 2010 + (mDefaultsString != null ? " defaults=\"" + mDefaultsString + "\" " : "") 2011 + (mVersionString != null ? " version=\"" + mVersionString + "\" " : "") 2012 + ">\n"); 2013 for (int userId : mExpectedPrimary.get(service.mApprovalLevel).keySet()) { 2014 String pkgOrCmp = mExpectedPrimary.get(service.mApprovalLevel).get(userId); 2015 xml.append(getXmlEntry( 2016 pkgOrCmp, userId, true, 2017 !(pkgOrCmp.startsWith("non.user.set.package")))); 2018 } 2019 for (int userId : mExpectedSecondary.get(service.mApprovalLevel).keySet()) { 2020 xml.append(getXmlEntry( 2021 mExpectedSecondary.get(service.mApprovalLevel).get(userId), userId, false)); 2022 } 2023 xml.append("<" + ManagedServices.TAG_MANAGED_SERVICES + " " 2024 + ManagedServices.ATT_USER_ID + "=\"99\" " 2025 + ManagedServices.ATT_IS_PRIMARY + "=\"true\" " 2026 + ManagedServices.ATT_APPROVED_LIST + "=\"990\" " 2027 + (mUserSetString != null ? ManagedServices.ATT_USER_SET + "=\"" 2028 + mUserSetString + "\" " : "") 2029 + "/>\n"); 2030 xml.append("<" + ManagedServices.TAG_MANAGED_SERVICES + " " 2031 + ManagedServices.ATT_USER_ID + "=\"98\" " 2032 + ManagedServices.ATT_IS_PRIMARY + "=\"false\" " 2033 + ManagedServices.ATT_APPROVED_LIST + "=\"981\" " 2034 + (mUserSetString != null ? ManagedServices.ATT_USER_SET + "=\"" 2035 + mUserSetString + "\" " : "") 2036 + " />\n"); 2037 xml.append("</" + xmlTag + ">"); 2038 2039 return xml.toString(); 2040 } 2041 getParserWithEntries(ManagedServices service, String... xmlEntries)2042 private TypedXmlPullParser getParserWithEntries(ManagedServices service, String... xmlEntries) 2043 throws Exception { 2044 final StringBuffer xml = new StringBuffer(); 2045 xml.append("<" + service.getConfig().xmlTag 2046 + (mVersionString != null ? " version=\"" + mVersionString + "\" " : "") 2047 + ">\n"); 2048 for (String xmlEntry : xmlEntries) { 2049 xml.append(xmlEntry); 2050 } 2051 xml.append("</" + service.getConfig().xmlTag + ">"); 2052 2053 TypedXmlPullParser parser = Xml.newFastPullParser(); 2054 parser.setInput(new BufferedInputStream( 2055 new ByteArrayInputStream(xml.toString().getBytes())), null); 2056 parser.nextTag(); 2057 return parser; 2058 } 2059 addExpectedServices(final ManagedServices service, final List<String> packages, int userId)2060 private void addExpectedServices(final ManagedServices service, final List<String> packages, 2061 int userId) throws Exception { 2062 ManagedServices.Config config = service.getConfig(); 2063 when(mPm.queryIntentServicesAsUser(any(), anyInt(), eq(userId))). 2064 thenAnswer(new Answer<List<ResolveInfo>>() { 2065 @Override 2066 public List<ResolveInfo> answer(InvocationOnMock invocationOnMock) 2067 throws Throwable { 2068 Object[] args = invocationOnMock.getArguments(); 2069 Intent invocationIntent = (Intent) args[0]; 2070 if (invocationIntent != null) { 2071 if (invocationIntent.getAction().equals( 2072 config.serviceInterface) 2073 && packages.contains(invocationIntent.getPackage())) { 2074 List<ResolveInfo> dummyServices = new ArrayList<>(); 2075 for (int i = 1; i <= 3; i ++) { 2076 ResolveInfo resolveInfo = new ResolveInfo(); 2077 ServiceInfo serviceInfo = new ServiceInfo(); 2078 serviceInfo.packageName = invocationIntent.getPackage(); 2079 serviceInfo.name = "C"+i; 2080 serviceInfo.permission = service.getConfig().bindPermission; 2081 resolveInfo.serviceInfo = serviceInfo; 2082 dummyServices.add(resolveInfo); 2083 } 2084 return dummyServices; 2085 } 2086 } 2087 return new ArrayList<>(); 2088 } 2089 }); 2090 2091 when(mIpm.getServiceInfo(any(), anyLong(), anyInt())).thenAnswer( 2092 (Answer<ServiceInfo>) invocation -> { 2093 ComponentName invocationCn = invocation.getArgument(0); 2094 if (invocationCn != null && packages.contains(invocationCn.getPackageName())) { 2095 ServiceInfo serviceInfo = new ServiceInfo(); 2096 serviceInfo.packageName = invocationCn.getPackageName(); 2097 serviceInfo.name = invocationCn.getClassName(); 2098 serviceInfo.permission = service.getConfig().bindPermission; 2099 return serviceInfo; 2100 } 2101 return null; 2102 } 2103 ); 2104 } 2105 stringToList(String list)2106 private List<String> stringToList(String list) { 2107 if (list == null) { 2108 list = ""; 2109 } 2110 return new ArrayList<>(Lists.newArrayList(list.split( 2111 ManagedServices.ENABLED_SERVICES_SEPARATOR))); 2112 } 2113 assertContentsInAnyOrder(Collection<?> expected, Collection<?> actual)2114 private void assertContentsInAnyOrder(Collection<?> expected, Collection<?> actual) { 2115 assertNotNull(actual); 2116 assertEquals(expected + " : " + actual, expected.size(), actual.size()); 2117 2118 for (Object o : expected) { 2119 assertTrue("Actual missing " + o, actual.contains(o)); 2120 } 2121 2122 for (Object o : actual) { 2123 assertTrue("Actual contains extra " + o, expected.contains(o)); 2124 } 2125 } 2126 assertContentsInAnyOrder(SparseArray<ArraySet<ComponentName>> expected, SparseArray<ArraySet<ComponentName>> actual)2127 private void assertContentsInAnyOrder(SparseArray<ArraySet<ComponentName>> expected, 2128 SparseArray<ArraySet<ComponentName>> actual) throws Exception { 2129 assertEquals(expected.size(), actual.size()); 2130 2131 for (int i = 0; i < expected.size(); i++) { 2132 int key = expected.keyAt(i); 2133 assertTrue(actual.indexOfKey(key) >= 0); 2134 try { 2135 assertContentsInAnyOrder(expected.valueAt(i), actual.get(key)); 2136 } catch (Throwable t) { 2137 throw new Exception("Error validating " + key, t); 2138 } 2139 } 2140 } 2141 verifyExpectedBoundEntries(ManagedServices service, boolean primary)2142 private void verifyExpectedBoundEntries(ManagedServices service, boolean primary) 2143 throws Exception { 2144 ArrayMap<Integer, String> verifyMap = primary ? mExpectedPrimary.get(service.mApprovalLevel) 2145 : mExpectedSecondary.get(service.mApprovalLevel); 2146 for (int userId : verifyMap.keySet()) { 2147 for (String packageOrComponent : verifyMap.get(userId).split(":")) { 2148 if (!TextUtils.isEmpty(packageOrComponent)) { 2149 if (service.mApprovalLevel == APPROVAL_BY_PACKAGE) { 2150 assertTrue(packageOrComponent, 2151 service.isComponentEnabledForPackage(packageOrComponent)); 2152 for (int i = 1; i <= 3; i++) { 2153 ComponentName componentName = ComponentName.unflattenFromString( 2154 packageOrComponent +"/C" + i); 2155 assertTrue(service.isComponentEnabledForCurrentProfiles( 2156 componentName)); 2157 verify(mIpm, times(1)).getServiceInfo( 2158 eq(componentName), anyLong(), anyInt()); 2159 } 2160 } else { 2161 ComponentName componentName = 2162 ComponentName.unflattenFromString(packageOrComponent); 2163 assertTrue(service.isComponentEnabledForCurrentProfiles(componentName)); 2164 verify(mIpm, times(1)).getServiceInfo( 2165 eq(componentName), anyLong(), anyInt()); 2166 } 2167 } 2168 } 2169 } 2170 } 2171 verifyExpectedApprovedEntries(ManagedServices service)2172 private void verifyExpectedApprovedEntries(ManagedServices service) { 2173 verifyExpectedApprovedEntries(service, true); 2174 verifyExpectedApprovedEntries(service, false); 2175 } 2176 verifyExpectedApprovedEntries(ManagedServices service, boolean primary)2177 private void verifyExpectedApprovedEntries(ManagedServices service, boolean primary) { 2178 ArrayMap<Integer, String> verifyMap = primary 2179 ? mExpectedPrimary.get(service.mApprovalLevel) 2180 : mExpectedSecondary.get(service.mApprovalLevel); 2181 verifyExpectedApprovedEntries(service, verifyMap); 2182 } 2183 verifyExpectedApprovedEntries(ManagedServices service, ArrayMap<Integer, String> verifyMap)2184 private void verifyExpectedApprovedEntries(ManagedServices service, 2185 ArrayMap<Integer, String> verifyMap) { 2186 for (int userId : verifyMap.keySet()) { 2187 for (String verifyValue : verifyMap.get(userId).split(":")) { 2188 if (!TextUtils.isEmpty(verifyValue)) { 2189 assertTrue("service type " + service.mApprovalLevel + ":" 2190 + verifyValue + " is not allowed for user " + userId, 2191 service.isPackageOrComponentAllowed(verifyValue, userId)); 2192 } 2193 } 2194 } 2195 } 2196 2197 verifyExpectedApprovedPackages(ManagedServices service)2198 private void verifyExpectedApprovedPackages(ManagedServices service) { 2199 verifyExpectedApprovedPackages(service, true); 2200 verifyExpectedApprovedPackages(service, false); 2201 } 2202 verifyExpectedApprovedPackages(ManagedServices service, boolean primary)2203 private void verifyExpectedApprovedPackages(ManagedServices service, boolean primary) { 2204 ArrayMap<Integer, String> verifyMap = primary 2205 ? mExpectedPrimary.get(service.mApprovalLevel) 2206 : mExpectedSecondary.get(service.mApprovalLevel); 2207 verifyExpectedApprovedPackages(service, verifyMap); 2208 } 2209 verifyExpectedApprovedPackages(ManagedServices service, ArrayMap<Integer, String> verifyMap)2210 private void verifyExpectedApprovedPackages(ManagedServices service, 2211 ArrayMap<Integer, String> verifyMap) { 2212 for (int userId : verifyMap.keySet()) { 2213 for (String verifyValue : verifyMap.get(userId).split(":")) { 2214 if (!TextUtils.isEmpty(verifyValue)) { 2215 ComponentName component = ComponentName.unflattenFromString(verifyValue); 2216 if (component != null ) { 2217 assertTrue("service type " + service.mApprovalLevel + ":" 2218 + verifyValue + " is not allowed for user " + userId, 2219 service.isPackageAllowed(component.getPackageName(), userId)); 2220 } else { 2221 assertTrue("service type " + service.mApprovalLevel + ":" 2222 + verifyValue + " is not allowed for user " + userId, 2223 service.isPackageAllowed(verifyValue, userId)); 2224 } 2225 } 2226 } 2227 } 2228 } 2229 writeExpectedValuesToSettings(int approvalLevel)2230 private void writeExpectedValuesToSettings(int approvalLevel) { 2231 for (int userId : mExpectedPrimary.get(approvalLevel).keySet()) { 2232 Settings.Secure.putStringForUser(getContext().getContentResolver(), SETTING, 2233 mExpectedPrimary.get(approvalLevel).get(userId), userId); 2234 } 2235 for (int userId : mExpectedSecondary.get(approvalLevel).keySet()) { 2236 Settings.Secure.putStringForUser(getContext().getContentResolver(), SECONDARY_SETTING, 2237 mExpectedSecondary.get(approvalLevel).get(userId), userId); 2238 } 2239 } 2240 getXmlEntry(String approved, int userId, boolean isPrimary)2241 private String getXmlEntry(String approved, int userId, boolean isPrimary) { 2242 return getXmlEntry(approved, userId, isPrimary, true); 2243 } 2244 getXmlEntry(String approved, int userId, boolean isPrimary, boolean userSet)2245 private String getXmlEntry(String approved, int userId, boolean isPrimary, boolean userSet) { 2246 String userSetString = ""; 2247 if (mVersionString.equals("4")) { 2248 userSetString = 2249 ManagedServices.ATT_USER_CHANGED + "=\"" + String.valueOf(userSet) + "\" "; 2250 } else if (mVersionString.equals("3")) { 2251 userSetString = 2252 ManagedServices.ATT_USER_SET + "=\"" + (userSet ? approved : "") + "\" "; 2253 } 2254 return "<" + ManagedServices.TAG_MANAGED_SERVICES + " " 2255 + ManagedServices.ATT_USER_ID + "=\"" + userId +"\" " 2256 + ManagedServices.ATT_IS_PRIMARY + "=\"" + isPrimary +"\" " 2257 + ManagedServices.ATT_APPROVED_LIST + "=\"" + approved +"\" " 2258 + userSetString + "/>\n"; 2259 } 2260 2261 class TestManagedServices extends ManagedServices { 2262 TestManagedServices(Context context, Object mutex, UserProfiles userProfiles, IPackageManager pm, int approvedServiceType)2263 public TestManagedServices(Context context, Object mutex, UserProfiles userProfiles, 2264 IPackageManager pm, int approvedServiceType) { 2265 super(context, mutex, userProfiles, pm); 2266 mApprovalLevel = approvedServiceType; 2267 } 2268 2269 @Override getConfig()2270 protected Config getConfig() { 2271 final Config c = new Config(); 2272 c.xmlTag = "test"; 2273 c.secureSettingName = SETTING; 2274 c.secondarySettingName = SECONDARY_SETTING; 2275 c.bindPermission = "permission"; 2276 c.serviceInterface = "serviceInterface"; 2277 return c; 2278 } 2279 2280 @Override asInterface(IBinder binder)2281 protected IInterface asInterface(IBinder binder) { 2282 return null; 2283 } 2284 2285 @Override checkType(IInterface service)2286 protected boolean checkType(IInterface service) { 2287 return true; 2288 } 2289 2290 @Override onServiceAdded(ManagedServiceInfo info)2291 protected void onServiceAdded(ManagedServiceInfo info) { 2292 2293 } 2294 2295 @Override ensureFilters(ServiceInfo si, int userId)2296 protected void ensureFilters(ServiceInfo si, int userId) { 2297 2298 } 2299 2300 @Override loadDefaultsFromConfig()2301 protected void loadDefaultsFromConfig() { 2302 mDefaultComponents.addAll(mDefaults); 2303 } 2304 2305 @Override getRequiredPermission()2306 protected String getRequiredPermission() { 2307 return null; 2308 } 2309 2310 @Override allowRebindForParentUser()2311 protected boolean allowRebindForParentUser() { 2312 return true; 2313 } 2314 } 2315 2316 class TestManagedServicesSettings extends TestManagedServices { 2317 TestManagedServicesSettings(Context context, Object mutex, UserProfiles userProfiles, IPackageManager pm, int approvedServiceType)2318 public TestManagedServicesSettings(Context context, Object mutex, UserProfiles userProfiles, 2319 IPackageManager pm, int approvedServiceType) { 2320 super(context, mutex, userProfiles, pm, approvedServiceType); 2321 } 2322 2323 @Override shouldReflectToSettings()2324 public boolean shouldReflectToSettings() { 2325 return true; 2326 } 2327 } 2328 2329 class TestManagedServicesNoSettings extends TestManagedServices { 2330 TestManagedServicesNoSettings(Context context, Object mutex, UserProfiles userProfiles, IPackageManager pm, int approvedServiceType)2331 public TestManagedServicesNoSettings(Context context, Object mutex, UserProfiles userProfiles, 2332 IPackageManager pm, int approvedServiceType) { 2333 super(context, mutex, userProfiles, pm, approvedServiceType); 2334 } 2335 2336 @Override getConfig()2337 protected Config getConfig() { 2338 Config c = super.getConfig(); 2339 c.secureSettingName = null; 2340 c.secondarySettingName = null; 2341 return c; 2342 } 2343 2344 @Override shouldReflectToSettings()2345 public boolean shouldReflectToSettings() { 2346 return false; 2347 } 2348 } 2349 2350 /** 2351 * Helper method to test the thread safety of some operations. 2352 * 2353 * <p>Runs the supplied {@code operationToTest}, {@code nRunsPerThread} times, 2354 * concurrently using {@code nThreads} threads, and waits for all of them to finish. 2355 */ testThreadSafety(Runnable operationToTest, int nThreads, int nRunsPerThread)2356 private static void testThreadSafety(Runnable operationToTest, int nThreads, 2357 int nRunsPerThread) throws InterruptedException { 2358 final CountDownLatch startLatch = new CountDownLatch(1); 2359 final CountDownLatch doneLatch = new CountDownLatch(nThreads); 2360 2361 for (int i = 0; i < nThreads; i++) { 2362 Runnable threadRunnable = () -> { 2363 try { 2364 startLatch.await(); 2365 for (int j = 0; j < nRunsPerThread; j++) { 2366 operationToTest.run(); 2367 } 2368 } catch (InterruptedException e) { 2369 e.printStackTrace(); 2370 } finally { 2371 doneLatch.countDown(); 2372 } 2373 }; 2374 new Thread(threadRunnable, "Test Thread #" + i).start(); 2375 } 2376 2377 // Ready set go 2378 startLatch.countDown(); 2379 2380 // Wait for all test threads to be done. 2381 doneLatch.await(); 2382 } 2383 } 2384