1 /** 2 * Copyright (c) 2014, 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 17 package com.android.server.notification; 18 19 import static android.app.Flags.FLAG_LIFETIME_EXTENSION_REFACTOR; 20 import static android.content.Context.BIND_ALLOW_WHITELIST_MANAGEMENT; 21 import static android.content.Context.BIND_AUTO_CREATE; 22 import static android.content.Context.BIND_FOREGROUND_SERVICE; 23 import static android.content.Context.DEVICE_POLICY_SERVICE; 24 import static android.os.UserHandle.USER_ALL; 25 import static android.os.UserHandle.USER_SYSTEM; 26 import static android.service.notification.NotificationListenerService.META_DATA_DEFAULT_AUTOBIND; 27 28 import static com.android.server.notification.NotificationManagerService.privateSpaceFlagsEnabled; 29 30 import android.annotation.FlaggedApi; 31 import android.annotation.NonNull; 32 import android.app.ActivityManager; 33 import android.app.ActivityOptions; 34 import android.app.PendingIntent; 35 import android.app.admin.DevicePolicyManager; 36 import android.content.ComponentName; 37 import android.content.ContentResolver; 38 import android.content.Context; 39 import android.content.Intent; 40 import android.content.ServiceConnection; 41 import android.content.pm.ApplicationInfo; 42 import android.content.pm.IPackageManager; 43 import android.content.pm.PackageManager; 44 import android.content.pm.PackageManager.NameNotFoundException; 45 import android.content.pm.ResolveInfo; 46 import android.content.pm.ServiceInfo; 47 import android.content.pm.UserInfo; 48 import android.os.Binder; 49 import android.os.Build; 50 import android.os.Handler; 51 import android.os.IBinder; 52 import android.os.IInterface; 53 import android.os.Looper; 54 import android.os.RemoteException; 55 import android.os.UserHandle; 56 import android.os.UserManager; 57 import android.provider.Settings; 58 import android.service.notification.ManagedServiceInfoProto; 59 import android.service.notification.ManagedServicesProto; 60 import android.service.notification.ManagedServicesProto.ServiceProto; 61 import android.text.TextUtils; 62 import android.util.ArrayMap; 63 import android.util.ArraySet; 64 import android.util.IntArray; 65 import android.util.Log; 66 import android.util.Pair; 67 import android.util.Slog; 68 import android.util.SparseArray; 69 import android.util.SparseSetArray; 70 import android.util.proto.ProtoOutputStream; 71 72 import com.android.internal.annotations.GuardedBy; 73 import com.android.internal.annotations.VisibleForTesting; 74 import com.android.internal.util.XmlUtils; 75 import com.android.internal.util.function.TriPredicate; 76 import com.android.modules.utils.TypedXmlPullParser; 77 import com.android.modules.utils.TypedXmlSerializer; 78 import com.android.server.notification.NotificationManagerService.DumpFilter; 79 import com.android.server.utils.TimingsTraceAndSlog; 80 81 import org.xmlpull.v1.XmlPullParser; 82 import org.xmlpull.v1.XmlPullParserException; 83 84 import java.io.IOException; 85 import java.io.PrintWriter; 86 import java.util.ArrayList; 87 import java.util.Arrays; 88 import java.util.HashSet; 89 import java.util.List; 90 import java.util.Objects; 91 import java.util.Set; 92 93 /** 94 * Manages the lifecycle of application-provided services bound by system server. 95 * 96 * Services managed by this helper must have: 97 * - An associated system settings value with a list of enabled component names. 98 * - A well-known action for services to use in their intent-filter. 99 * - A system permission for services to require in order to ensure system has exclusive binding. 100 * - A settings page for user configuration of enabled services, and associated intent action. 101 * - A remote interface definition (aidl) provided by the service used for communication. 102 */ 103 abstract public class ManagedServices { 104 protected final String TAG = getClass().getSimpleName(); 105 protected final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG); 106 107 private static final int ON_BINDING_DIED_REBIND_DELAY_MS = 10000; 108 protected static final String ENABLED_SERVICES_SEPARATOR = ":"; 109 private static final String DB_VERSION_1 = "1"; 110 private static final String DB_VERSION_2 = "2"; 111 private static final String DB_VERSION_3 = "3"; 112 113 114 /** 115 * List of components and apps that can have running {@link ManagedServices}. 116 */ 117 static final String TAG_MANAGED_SERVICES = "service_listing"; 118 static final String ATT_APPROVED_LIST = "approved"; 119 static final String ATT_USER_ID = "user"; 120 static final String ATT_IS_PRIMARY = "primary"; 121 static final String ATT_VERSION = "version"; 122 static final String ATT_DEFAULTS = "defaults"; 123 static final String ATT_USER_SET = "user_set_services"; 124 static final String ATT_USER_SET_OLD = "user_set"; 125 static final String ATT_USER_CHANGED = "user_changed"; 126 127 static final String DB_VERSION = "4"; 128 129 static final int APPROVAL_BY_PACKAGE = 0; 130 static final int APPROVAL_BY_COMPONENT = 1; 131 132 protected final Context mContext; 133 protected final Object mMutex; 134 private final UserProfiles mUserProfiles; 135 protected final IPackageManager mPm; 136 protected final UserManager mUm; 137 private final Config mConfig; 138 private final Handler mHandler = new Handler(Looper.getMainLooper()); 139 140 // contains connections to all connected services, including app services 141 // and system services 142 @GuardedBy("mMutex") 143 private final ArrayList<ManagedServiceInfo> mServices = new ArrayList<>(); 144 /** 145 * The services that have been bound by us. If the service is also connected, it will also 146 * be in {@link #mServices}. 147 */ 148 @GuardedBy("mMutex") 149 private final ArrayList<Pair<ComponentName, Integer>> mServicesBound = new ArrayList<>(); 150 @GuardedBy("mMutex") 151 private final ArraySet<Pair<ComponentName, Integer>> mServicesRebinding = new ArraySet<>(); 152 // we need these packages to be protected because classes that inherit from it need to see it 153 protected final Object mDefaultsLock = new Object(); 154 @GuardedBy("mDefaultsLock") 155 protected final ArraySet<ComponentName> mDefaultComponents = new ArraySet<>(); 156 @GuardedBy("mDefaultsLock") 157 protected final ArraySet<String> mDefaultPackages = new ArraySet<>(); 158 159 // lists the component names of all enabled (and therefore potentially connected) 160 // app services for current profiles. 161 @GuardedBy("mMutex") 162 private final ArraySet<ComponentName> mEnabledServicesForCurrentProfiles = new ArraySet<>(); 163 // Just the packages from mEnabledServicesForCurrentProfiles 164 @GuardedBy("mMutex") 165 private final ArraySet<String> mEnabledServicesPackageNames = new ArraySet<>(); 166 // Per user id, list of enabled packages that have nevertheless asked not to be run 167 @GuardedBy("mSnoozing") 168 private final SparseSetArray<ComponentName> mSnoozing = new SparseSetArray<>(); 169 170 // List of approved packages or components (by user, then by primary/secondary) that are 171 // allowed to be bound as managed services. A package or component appearing in this list does 172 // not mean that we are currently bound to said package/component. 173 @GuardedBy("mApproved") 174 protected final ArrayMap<Integer, ArrayMap<Boolean, ArraySet<String>>> mApproved = 175 new ArrayMap<>(); 176 // List of packages or components (by user) that are configured to be enabled/disabled 177 // explicitly by the user 178 @GuardedBy("mApproved") 179 protected ArrayMap<Integer, ArraySet<String>> mUserSetServices = new ArrayMap<>(); 180 @GuardedBy("mApproved") 181 protected ArrayMap<Integer, Boolean> mIsUserChanged = new ArrayMap<>(); 182 183 // True if approved services are stored in xml, not settings. 184 private boolean mUseXml; 185 186 // Whether managed services are approved individually or package wide 187 protected int mApprovalLevel; 188 ManagedServices(Context context, Object mutex, UserProfiles userProfiles, IPackageManager pm)189 public ManagedServices(Context context, Object mutex, UserProfiles userProfiles, 190 IPackageManager pm) { 191 mContext = context; 192 mMutex = mutex; 193 mUserProfiles = userProfiles; 194 mPm = pm; 195 mConfig = getConfig(); 196 mApprovalLevel = APPROVAL_BY_COMPONENT; 197 mUm = (UserManager) mContext.getSystemService(Context.USER_SERVICE); 198 } 199 getConfig()200 abstract protected Config getConfig(); 201 getCaption()202 private String getCaption() { 203 return mConfig.caption; 204 } 205 asInterface(IBinder binder)206 abstract protected IInterface asInterface(IBinder binder); 207 checkType(IInterface service)208 abstract protected boolean checkType(IInterface service); 209 onServiceAdded(ManagedServiceInfo info)210 abstract protected void onServiceAdded(ManagedServiceInfo info); 211 ensureFilters(ServiceInfo si, int userId)212 abstract protected void ensureFilters(ServiceInfo si, int userId); 213 getServices()214 protected List<ManagedServiceInfo> getServices() { 215 synchronized (mMutex) { 216 List<ManagedServiceInfo> services = new ArrayList<>(mServices); 217 return services; 218 } 219 } 220 addDefaultComponentOrPackage(String packageOrComponent)221 protected void addDefaultComponentOrPackage(String packageOrComponent) { 222 if (!TextUtils.isEmpty(packageOrComponent)) { 223 synchronized (mDefaultsLock) { 224 if (mApprovalLevel == APPROVAL_BY_PACKAGE) { 225 mDefaultPackages.add(packageOrComponent); 226 return; 227 } 228 ComponentName cn = ComponentName.unflattenFromString(packageOrComponent); 229 if (cn != null && mApprovalLevel == APPROVAL_BY_COMPONENT) { 230 mDefaultPackages.add(cn.getPackageName()); 231 mDefaultComponents.add(cn); 232 return; 233 } 234 } 235 } 236 } 237 loadDefaultsFromConfig()238 protected abstract void loadDefaultsFromConfig(); 239 isDefaultComponentOrPackage(String packageOrComponent)240 boolean isDefaultComponentOrPackage(String packageOrComponent) { 241 synchronized (mDefaultsLock) { 242 ComponentName cn = ComponentName.unflattenFromString(packageOrComponent); 243 if (cn == null) { 244 return mDefaultPackages.contains(packageOrComponent); 245 } else { 246 return mDefaultComponents.contains(cn); 247 } 248 } 249 } 250 getDefaultComponents()251 ArraySet<ComponentName> getDefaultComponents() { 252 synchronized (mDefaultsLock) { 253 return new ArraySet<>(mDefaultComponents); 254 } 255 } 256 getDefaultPackages()257 ArraySet<String> getDefaultPackages() { 258 synchronized (mDefaultsLock) { 259 return new ArraySet<>(mDefaultPackages); 260 } 261 } 262 263 /** 264 * When resetting a package, we need to enable default components that belong to that packages 265 * we also need to disable components that are not default to return the managed service state 266 * to when a new android device is first turned on for that package. 267 * 268 * @param packageName package to reset. 269 * @param userId the android user id 270 * @return a list of components that were permitted 271 */ 272 @NonNull resetComponents(String packageName, int userId)273 ArrayMap<Boolean, ArrayList<ComponentName>> resetComponents(String packageName, int userId) { 274 // components that we want to enable 275 ArrayList<ComponentName> componentsToEnable; 276 // components that were removed 277 ArrayList<ComponentName> disabledComponents; 278 // all components that are enabled now 279 ArraySet<ComponentName> enabledComponents = new ArraySet<>(getAllowedComponents(userId)); 280 281 boolean changed = false; 282 283 synchronized (mDefaultsLock) { 284 componentsToEnable = new ArrayList<>(mDefaultComponents.size()); 285 disabledComponents = new ArrayList<>(mDefaultComponents.size()); 286 287 // record all components that are enabled but should not be by default 288 for (int i = 0; i < mDefaultComponents.size() && enabledComponents.size() > 0; i++) { 289 ComponentName currentDefault = mDefaultComponents.valueAt(i); 290 if (packageName.equals(currentDefault.getPackageName()) 291 && !enabledComponents.contains(currentDefault)) { 292 componentsToEnable.add(currentDefault); 293 } 294 } 295 synchronized (mApproved) { 296 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.get( 297 userId); 298 if (approvedByType != null) { 299 final int M = approvedByType.size(); 300 for (int j = 0; j < M; j++) { 301 final ArraySet<String> approved = approvedByType.valueAt(j); 302 for (int i = 0; i < enabledComponents.size(); i++) { 303 ComponentName currentComponent = enabledComponents.valueAt(i); 304 if (packageName.equals(currentComponent.getPackageName()) 305 && !mDefaultComponents.contains(currentComponent)) { 306 if (approved.remove(currentComponent.flattenToString())) { 307 disabledComponents.add(currentComponent); 308 clearUserSetFlagLocked(currentComponent, userId); 309 changed = true; 310 } 311 } 312 } 313 for (int i = 0; i < componentsToEnable.size(); i++) { 314 ComponentName candidate = componentsToEnable.get(i); 315 changed |= approved.add(candidate.flattenToString()); 316 } 317 } 318 319 } 320 } 321 } 322 if (changed) rebindServices(false, USER_ALL); 323 324 ArrayMap<Boolean, ArrayList<ComponentName>> changes = new ArrayMap<>(); 325 changes.put(true, componentsToEnable); 326 changes.put(false, disabledComponents); 327 328 return changes; 329 } 330 331 @GuardedBy("mApproved") clearUserSetFlagLocked(ComponentName component, int userId)332 private boolean clearUserSetFlagLocked(ComponentName component, int userId) { 333 String approvedValue = getApprovedValue(component.flattenToString()); 334 ArraySet<String> userSet = mUserSetServices.get(userId); 335 return userSet != null && userSet.remove(approvedValue); 336 } 337 getBindFlags()338 protected int getBindFlags() { 339 return BIND_AUTO_CREATE | BIND_FOREGROUND_SERVICE | BIND_ALLOW_WHITELIST_MANAGEMENT; 340 } 341 onServiceRemovedLocked(ManagedServiceInfo removed)342 protected void onServiceRemovedLocked(ManagedServiceInfo removed) { } 343 newServiceInfo(IInterface service, ComponentName component, int userId, boolean isSystem, ServiceConnection connection, int targetSdkVersion, int uid)344 private ManagedServiceInfo newServiceInfo(IInterface service, 345 ComponentName component, int userId, boolean isSystem, ServiceConnection connection, 346 int targetSdkVersion, int uid) { 347 return new ManagedServiceInfo(service, component, userId, isSystem, connection, 348 targetSdkVersion, uid); 349 } 350 onBootPhaseAppsCanStart()351 public void onBootPhaseAppsCanStart() {} 352 dump(PrintWriter pw, DumpFilter filter)353 public void dump(PrintWriter pw, DumpFilter filter) { 354 pw.println(" Allowed " + getCaption() + "s:"); 355 synchronized (mApproved) { 356 final int N = mApproved.size(); 357 for (int i = 0; i < N; i++) { 358 final int userId = mApproved.keyAt(i); 359 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.valueAt(i); 360 final Boolean userChanged = mIsUserChanged.get(userId); 361 if (approvedByType != null) { 362 final int M = approvedByType.size(); 363 for (int j = 0; j < M; j++) { 364 final boolean isPrimary = approvedByType.keyAt(j); 365 final ArraySet<String> approved = approvedByType.valueAt(j); 366 if (approvedByType != null && approvedByType.size() > 0) { 367 pw.println(" " + String.join(ENABLED_SERVICES_SEPARATOR, approved) 368 + " (user: " + userId + " isPrimary: " + isPrimary 369 + (userChanged == null ? "" : " isUserChanged: " 370 + userChanged) + ")"); 371 } 372 } 373 } 374 } 375 pw.println(" Has user set:"); 376 Set<Integer> userIds = mUserSetServices.keySet(); 377 for (int userId : userIds) { 378 if (mIsUserChanged.get(userId) == null) { 379 pw.println(" userId=" + userId + " value=" 380 + (mUserSetServices.get(userId))); 381 } 382 } 383 } 384 385 synchronized (mMutex) { 386 pw.println(" All " + getCaption() + "s (" + mEnabledServicesForCurrentProfiles.size() 387 + ") enabled for current profiles:"); 388 for (ComponentName cmpt : mEnabledServicesForCurrentProfiles) { 389 if (filter != null && !filter.matches(cmpt)) continue; 390 pw.println(" " + cmpt); 391 } 392 393 pw.println(" Live " + getCaption() + "s (" + mServices.size() + "):"); 394 for (ManagedServiceInfo info : mServices) { 395 if (filter != null && !filter.matches(info.component)) continue; 396 pw.println(" " + info.component 397 + " (user " + info.userid + "): " + info.service 398 + (info.isSystem ? " SYSTEM" : "") 399 + (info.isGuest(this) ? " GUEST" : "")); 400 } 401 } 402 403 final SparseSetArray<ComponentName> snoozingComponents; 404 synchronized (mSnoozing) { 405 snoozingComponents = new SparseSetArray<>(mSnoozing); 406 } 407 pw.println(" Snoozed " + getCaption() + "s (" 408 + snoozingComponents.size() + "):"); 409 for (int i = 0; i < snoozingComponents.size(); i++) { 410 pw.println(" User: " + snoozingComponents.keyAt(i)); 411 for (ComponentName name : snoozingComponents.valuesAt(i)) { 412 final ServiceInfo info = getServiceInfo(name, snoozingComponents.keyAt(i)); 413 pw.println(" " + name.flattenToShortString() + (isAutobindAllowed(info) ? "" 414 : " (META_DATA_DEFAULT_AUTOBIND=false)")); 415 } 416 } 417 } 418 dump(ProtoOutputStream proto, DumpFilter filter)419 public void dump(ProtoOutputStream proto, DumpFilter filter) { 420 proto.write(ManagedServicesProto.CAPTION, getCaption()); 421 synchronized (mApproved) { 422 final int N = mApproved.size(); 423 for (int i = 0; i < N; i++) { 424 final int userId = mApproved.keyAt(i); 425 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.valueAt(i); 426 if (approvedByType != null) { 427 final int M = approvedByType.size(); 428 for (int j = 0; j < M; j++) { 429 final boolean isPrimary = approvedByType.keyAt(j); 430 final ArraySet<String> approved = approvedByType.valueAt(j); 431 if (approvedByType != null && approvedByType.size() > 0) { 432 final long sToken = proto.start(ManagedServicesProto.APPROVED); 433 for (String s : approved) { 434 proto.write(ServiceProto.NAME, s); 435 } 436 proto.write(ServiceProto.USER_ID, userId); 437 proto.write(ServiceProto.IS_PRIMARY, isPrimary); 438 proto.end(sToken); 439 } 440 } 441 } 442 } 443 } 444 445 446 synchronized (mMutex) { 447 for (ComponentName cmpt : mEnabledServicesForCurrentProfiles) { 448 if (filter != null && !filter.matches(cmpt)) continue; 449 cmpt.dumpDebug(proto, ManagedServicesProto.ENABLED); 450 } 451 for (ManagedServiceInfo info : mServices) { 452 if (filter != null && !filter.matches(info.component)) continue; 453 info.dumpDebug(proto, ManagedServicesProto.LIVE_SERVICES, this); 454 } 455 } 456 457 synchronized (mSnoozing) { 458 for (int i = 0; i < mSnoozing.size(); i++) { 459 long token = proto.start(ManagedServicesProto.SNOOZED); 460 proto.write(ManagedServicesProto.SnoozedServices.USER_ID, 461 mSnoozing.keyAt(i)); 462 for (ComponentName name : mSnoozing.valuesAt(i)) { 463 name.dumpDebug(proto, ManagedServicesProto.SnoozedServices.SNOOZED); 464 } 465 proto.end(token); 466 } 467 } 468 } 469 onSettingRestored(String element, String value, int backupSdkInt, int userId)470 protected void onSettingRestored(String element, String value, int backupSdkInt, int userId) { 471 if (!mUseXml) { 472 Slog.d(TAG, "Restored managed service setting: " + element); 473 if (mConfig.secureSettingName.equals(element) || 474 (mConfig.secondarySettingName != null 475 && mConfig.secondarySettingName.equals(element))) { 476 if (backupSdkInt < Build.VERSION_CODES.O) { 477 // automatic system grants were added in O, so append the approved apps 478 // rather than wiping out the setting 479 String currentSetting = 480 getApproved(userId, mConfig.secureSettingName.equals(element)); 481 if (!TextUtils.isEmpty(currentSetting)) { 482 if (!TextUtils.isEmpty(value)) { 483 value = value + ENABLED_SERVICES_SEPARATOR + currentSetting; 484 } else { 485 value = currentSetting; 486 } 487 } 488 } 489 if (shouldReflectToSettings()) { 490 Settings.Secure.putStringForUser( 491 mContext.getContentResolver(), element, value, userId); 492 } 493 494 for (UserInfo user : mUm.getUsers()) { 495 addApprovedList(value, user.id, mConfig.secureSettingName.equals(element)); 496 } 497 Slog.d(TAG, "Done loading approved values from settings"); 498 rebindServices(false, userId); 499 } 500 } 501 } 502 writeDefaults(TypedXmlSerializer out)503 void writeDefaults(TypedXmlSerializer out) throws IOException { 504 synchronized (mDefaultsLock) { 505 List<String> componentStrings = new ArrayList<>(mDefaultComponents.size()); 506 for (int i = 0; i < mDefaultComponents.size(); i++) { 507 componentStrings.add(mDefaultComponents.valueAt(i).flattenToString()); 508 } 509 String defaults = String.join(ENABLED_SERVICES_SEPARATOR, componentStrings); 510 out.attribute(null, ATT_DEFAULTS, defaults); 511 } 512 } 513 writeXml(TypedXmlSerializer out, boolean forBackup, int userId)514 public void writeXml(TypedXmlSerializer out, boolean forBackup, int userId) throws IOException { 515 out.startTag(null, getConfig().xmlTag); 516 517 out.attributeInt(null, ATT_VERSION, Integer.parseInt(DB_VERSION)); 518 519 writeDefaults(out); 520 521 if (forBackup) { 522 trimApprovedListsAccordingToInstalledServices(userId); 523 } 524 525 synchronized (mApproved) { 526 final int N = mApproved.size(); 527 for (int i = 0; i < N; i++) { 528 final int approvedUserId = mApproved.keyAt(i); 529 if (forBackup && approvedUserId != userId) { 530 continue; 531 } 532 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.valueAt(i); 533 final Boolean isUserChanged = mIsUserChanged.get(approvedUserId); 534 if (approvedByType != null) { 535 final int M = approvedByType.size(); 536 for (int j = 0; j < M; j++) { 537 final boolean isPrimary = approvedByType.keyAt(j); 538 final Set<String> approved = approvedByType.valueAt(j); 539 final Set<String> userSet = mUserSetServices.get(approvedUserId); 540 if (approved != null || userSet != null || isUserChanged != null) { 541 String allowedItems = approved == null 542 ? "" 543 : String.join(ENABLED_SERVICES_SEPARATOR, approved); 544 out.startTag(null, TAG_MANAGED_SERVICES); 545 out.attribute(null, ATT_APPROVED_LIST, allowedItems); 546 out.attributeInt(null, ATT_USER_ID, approvedUserId); 547 out.attributeBoolean(null, ATT_IS_PRIMARY, isPrimary); 548 if (isUserChanged != null) { 549 out.attributeBoolean(null, ATT_USER_CHANGED, isUserChanged); 550 } else if (userSet != null) { 551 String userSetItems = 552 String.join(ENABLED_SERVICES_SEPARATOR, userSet); 553 out.attribute(null, ATT_USER_SET, userSetItems); 554 } 555 writeExtraAttributes(out, approvedUserId); 556 out.endTag(null, TAG_MANAGED_SERVICES); 557 558 if (!forBackup && isPrimary) { 559 if (shouldReflectToSettings()) { 560 // Also write values to settings, for observers who haven't 561 // migrated yet 562 Settings.Secure.putStringForUser(mContext.getContentResolver(), 563 getConfig().secureSettingName, allowedItems, 564 approvedUserId); 565 } 566 } 567 568 } 569 } 570 } 571 } 572 } 573 574 writeExtraXmlTags(out); 575 576 out.endTag(null, getConfig().xmlTag); 577 } 578 579 /** 580 * Returns whether the approved list of services should also be written to the Settings db 581 */ shouldReflectToSettings()582 protected boolean shouldReflectToSettings() { 583 return false; 584 } 585 586 /** 587 * Writes extra xml attributes to {@link #TAG_MANAGED_SERVICES} tag. 588 */ writeExtraAttributes(TypedXmlSerializer out, int userId)589 protected void writeExtraAttributes(TypedXmlSerializer out, int userId) throws IOException {} 590 591 /** 592 * Writes extra xml tags within the parent tag specified in {@link Config#xmlTag}. 593 */ writeExtraXmlTags(TypedXmlSerializer out)594 protected void writeExtraXmlTags(TypedXmlSerializer out) throws IOException {} 595 596 /** 597 * This is called to process tags other than {@link #TAG_MANAGED_SERVICES}. 598 */ readExtraTag(String tag, TypedXmlPullParser parser)599 protected void readExtraTag(String tag, TypedXmlPullParser parser) 600 throws IOException, XmlPullParserException {} 601 migrateToXml()602 protected final void migrateToXml() { 603 for (UserInfo user : mUm.getUsers()) { 604 final ContentResolver cr = mContext.getContentResolver(); 605 if (!TextUtils.isEmpty(getConfig().secureSettingName)) { 606 addApprovedList(Settings.Secure.getStringForUser( 607 cr, 608 getConfig().secureSettingName, 609 user.id), user.id, true); 610 } 611 if (!TextUtils.isEmpty(getConfig().secondarySettingName)) { 612 addApprovedList(Settings.Secure.getStringForUser( 613 cr, 614 getConfig().secondarySettingName, 615 user.id), user.id, false); 616 } 617 } 618 } 619 readDefaults(TypedXmlPullParser parser)620 void readDefaults(TypedXmlPullParser parser) { 621 String defaultComponents = XmlUtils.readStringAttribute(parser, ATT_DEFAULTS); 622 623 if (!TextUtils.isEmpty(defaultComponents)) { 624 String[] components = defaultComponents.split(ENABLED_SERVICES_SEPARATOR); 625 synchronized (mDefaultsLock) { 626 for (int i = 0; i < components.length; i++) { 627 if (!TextUtils.isEmpty(components[i])) { 628 ComponentName cn = ComponentName.unflattenFromString(components[i]); 629 if (cn != null) { 630 mDefaultPackages.add(cn.getPackageName()); 631 mDefaultComponents.add(cn); 632 } else { 633 mDefaultPackages.add(components[i]); 634 } 635 } 636 } 637 } 638 } 639 } 640 readXml( TypedXmlPullParser parser, TriPredicate<String, Integer, String> allowedManagedServicePackages, boolean forRestore, int userId)641 public void readXml( 642 TypedXmlPullParser parser, 643 TriPredicate<String, Integer, String> allowedManagedServicePackages, 644 boolean forRestore, 645 int userId) 646 throws XmlPullParserException, IOException { 647 // read grants 648 int type; 649 String version = XmlUtils.readStringAttribute(parser, ATT_VERSION); 650 boolean needUpgradeUserset = false; 651 readDefaults(parser); 652 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT) { 653 String tag = parser.getName(); 654 if (type == XmlPullParser.END_TAG 655 && getConfig().xmlTag.equals(tag)) { 656 break; 657 } 658 if (type == XmlPullParser.START_TAG) { 659 if (TAG_MANAGED_SERVICES.equals(tag)) { 660 Slog.i(TAG, "Read " + mConfig.caption + " permissions from xml"); 661 662 final String approved = XmlUtils.readStringAttribute(parser, ATT_APPROVED_LIST); 663 // Ignore parser's user id for restore. 664 final int resolvedUserId = forRestore 665 ? userId : parser.getAttributeInt(null, ATT_USER_ID, 0); 666 final boolean isPrimary = 667 parser.getAttributeBoolean(null, ATT_IS_PRIMARY, true); 668 669 // Load three different userSet attributes from xml 670 // user_changed, not null if version == 4 and is NAS setting 671 final String isUserChanged = XmlUtils.readStringAttribute(parser, 672 ATT_USER_CHANGED); 673 // user_set, not null if version <= 3 674 final String isUserChanged_Old = XmlUtils.readStringAttribute(parser, 675 ATT_USER_SET_OLD); 676 // user_set_services, not null if version >= 3 and is non-NAS setting 677 String userSetComponent = XmlUtils.readStringAttribute(parser, ATT_USER_SET); 678 679 // since the same xml version may have different userSet attributes, 680 // we need to check both xml version and userSet values to know how to set 681 // the userSetComponent/mIsUserChanged to the correct value 682 if (DB_VERSION.equals(version)) { 683 // version 4, NAS contains user_changed and 684 // NLS/others contain user_set_services 685 if (isUserChanged == null) { //NLS 686 userSetComponent = TextUtils.emptyIfNull(userSetComponent); 687 } else { //NAS 688 synchronized (mApproved) { 689 mIsUserChanged.put(resolvedUserId, Boolean.valueOf(isUserChanged)); 690 } 691 userSetComponent = Boolean.valueOf(isUserChanged) ? approved : ""; 692 } 693 } else { 694 // version 3 may contain user_set (R) or user_set_services (S) 695 // version 2 or older contain user_set or nothing 696 needUpgradeUserset = true; 697 if (userSetComponent == null) { //contains user_set 698 if (isUserChanged_Old != null && Boolean.valueOf(isUserChanged_Old)) { 699 //user_set = true 700 userSetComponent = approved; 701 synchronized (mApproved) { 702 mIsUserChanged.put(resolvedUserId, true); 703 } 704 needUpgradeUserset = false; 705 } else { 706 userSetComponent = ""; 707 } 708 } 709 } 710 readExtraAttributes(tag, parser, resolvedUserId); 711 if (allowedManagedServicePackages == null || allowedManagedServicePackages.test( 712 getPackageName(approved), resolvedUserId, getRequiredPermission()) 713 || approved.isEmpty()) { 714 if (mUm.getUserInfo(resolvedUserId) != null) { 715 addApprovedList(approved, resolvedUserId, isPrimary, userSetComponent); 716 } 717 mUseXml = true; 718 } 719 } else { 720 readExtraTag(tag, parser); 721 } 722 } 723 } 724 boolean isOldVersion = TextUtils.isEmpty(version) 725 || DB_VERSION_1.equals(version) 726 || DB_VERSION_2.equals(version) 727 || DB_VERSION_3.equals(version); 728 if (isOldVersion) { 729 upgradeDefaultsXmlVersion(); 730 } 731 if (needUpgradeUserset) { 732 upgradeUserSet(); 733 } 734 735 rebindServices(false, USER_ALL); 736 } 737 upgradeDefaultsXmlVersion()738 void upgradeDefaultsXmlVersion() { 739 int defaultsSize; 740 synchronized (mDefaultsLock) { 741 // check if any defaults are loaded 742 defaultsSize = mDefaultComponents.size() + mDefaultPackages.size(); 743 } 744 if (defaultsSize == 0) { 745 // load defaults from current allowed 746 if (this.mApprovalLevel == APPROVAL_BY_COMPONENT) { 747 List<ComponentName> approvedComponents = getAllowedComponents(USER_SYSTEM); 748 for (int i = 0; i < approvedComponents.size(); i++) { 749 addDefaultComponentOrPackage(approvedComponents.get(i).flattenToString()); 750 } 751 } 752 if (this.mApprovalLevel == APPROVAL_BY_PACKAGE) { 753 List<String> approvedPkgs = getAllowedPackages(USER_SYSTEM); 754 for (int i = 0; i < approvedPkgs.size(); i++) { 755 addDefaultComponentOrPackage(approvedPkgs.get(i)); 756 } 757 } 758 } 759 synchronized (mDefaultsLock) { 760 defaultsSize = mDefaultComponents.size() + mDefaultPackages.size(); 761 } 762 // if no defaults are loaded, then load from config 763 if (defaultsSize == 0) { 764 loadDefaultsFromConfig(); 765 } 766 } 767 upgradeUserSet()768 protected void upgradeUserSet() {}; 769 770 /** 771 * Read extra attributes in the {@link #TAG_MANAGED_SERVICES} tag. 772 */ readExtraAttributes(String tag, TypedXmlPullParser parser, int userId)773 protected void readExtraAttributes(String tag, TypedXmlPullParser parser, int userId) 774 throws IOException {} 775 getRequiredPermission()776 protected abstract String getRequiredPermission(); 777 addApprovedList(String approved, int userId, boolean isPrimary)778 protected void addApprovedList(String approved, int userId, boolean isPrimary) { 779 addApprovedList(approved, userId, isPrimary, approved); 780 } 781 addApprovedList(String approved, int userId, boolean isPrimary, String userSet)782 protected void addApprovedList(String approved, int userId, boolean isPrimary, String userSet) { 783 if (TextUtils.isEmpty(approved)) { 784 approved = ""; 785 } 786 if (userSet == null) { 787 userSet = approved; 788 } 789 synchronized (mApproved) { 790 ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.get(userId); 791 if (approvedByType == null) { 792 approvedByType = new ArrayMap<>(); 793 mApproved.put(userId, approvedByType); 794 } 795 796 ArraySet<String> approvedList = approvedByType.get(isPrimary); 797 if (approvedList == null) { 798 approvedList = new ArraySet<>(); 799 approvedByType.put(isPrimary, approvedList); 800 } 801 802 String[] approvedArray = approved.split(ENABLED_SERVICES_SEPARATOR); 803 for (String pkgOrComponent : approvedArray) { 804 String approvedItem = getApprovedValue(pkgOrComponent); 805 if (approvedItem != null) { 806 approvedList.add(approvedItem); 807 } 808 } 809 810 ArraySet<String> userSetList = mUserSetServices.get(userId); 811 if (userSetList == null) { 812 userSetList = new ArraySet<>(); 813 mUserSetServices.put(userId, userSetList); 814 } 815 String[] userSetArray = userSet.split(ENABLED_SERVICES_SEPARATOR); 816 for (String pkgOrComponent : userSetArray) { 817 String approvedItem = getApprovedValue(pkgOrComponent); 818 if (approvedItem != null) { 819 userSetList.add(approvedItem); 820 } 821 } 822 } 823 } 824 isComponentEnabledForPackage(String pkg)825 protected boolean isComponentEnabledForPackage(String pkg) { 826 synchronized (mMutex) { 827 return mEnabledServicesPackageNames.contains(pkg); 828 } 829 } 830 setPackageOrComponentEnabled(String pkgOrComponent, int userId, boolean isPrimary, boolean enabled)831 protected void setPackageOrComponentEnabled(String pkgOrComponent, int userId, 832 boolean isPrimary, boolean enabled) { 833 setPackageOrComponentEnabled(pkgOrComponent, userId, isPrimary, enabled, true); 834 } 835 setPackageOrComponentEnabled(String pkgOrComponent, int userId, boolean isPrimary, boolean enabled, boolean userSet)836 protected void setPackageOrComponentEnabled(String pkgOrComponent, int userId, 837 boolean isPrimary, boolean enabled, boolean userSet) { 838 Slog.i(TAG, 839 (enabled ? " Allowing " : "Disallowing ") + mConfig.caption + " " 840 + pkgOrComponent + " (userSet: " + userSet + ")"); 841 synchronized (mApproved) { 842 ArrayMap<Boolean, ArraySet<String>> allowedByType = mApproved.get(userId); 843 if (allowedByType == null) { 844 allowedByType = new ArrayMap<>(); 845 mApproved.put(userId, allowedByType); 846 } 847 ArraySet<String> approved = allowedByType.get(isPrimary); 848 if (approved == null) { 849 approved = new ArraySet<>(); 850 allowedByType.put(isPrimary, approved); 851 } 852 String approvedItem = getApprovedValue(pkgOrComponent); 853 854 if (approvedItem != null) { 855 if (enabled) { 856 approved.add(approvedItem); 857 } else { 858 approved.remove(approvedItem); 859 } 860 } 861 ArraySet<String> userSetServices = mUserSetServices.get(userId); 862 if (userSetServices == null) { 863 userSetServices = new ArraySet<>(); 864 mUserSetServices.put(userId, userSetServices); 865 } 866 if (userSet) { 867 userSetServices.add(pkgOrComponent); 868 } else { 869 userSetServices.remove(pkgOrComponent); 870 } 871 } 872 873 rebindServices(false, userId); 874 } 875 getApprovedValue(String pkgOrComponent)876 private String getApprovedValue(String pkgOrComponent) { 877 if (mApprovalLevel == APPROVAL_BY_COMPONENT) { 878 if(ComponentName.unflattenFromString(pkgOrComponent) != null) { 879 return pkgOrComponent; 880 } 881 return null; 882 } else { 883 return getPackageName(pkgOrComponent); 884 } 885 } 886 getApproved(int userId, boolean primary)887 protected String getApproved(int userId, boolean primary) { 888 synchronized (mApproved) { 889 final ArrayMap<Boolean, ArraySet<String>> allowedByType = 890 mApproved.getOrDefault(userId, new ArrayMap<>()); 891 ArraySet<String> approved = allowedByType.getOrDefault(primary, new ArraySet<>()); 892 return String.join(ENABLED_SERVICES_SEPARATOR, approved); 893 } 894 } 895 getAllowedComponents(int userId)896 protected List<ComponentName> getAllowedComponents(int userId) { 897 final List<ComponentName> allowedComponents = new ArrayList<>(); 898 synchronized (mApproved) { 899 final ArrayMap<Boolean, ArraySet<String>> allowedByType = 900 mApproved.getOrDefault(userId, new ArrayMap<>()); 901 for (int i = 0; i < allowedByType.size(); i++) { 902 final ArraySet<String> allowed = allowedByType.valueAt(i); 903 for (int j = 0; j < allowed.size(); j++) { 904 ComponentName cn = ComponentName.unflattenFromString(allowed.valueAt(j)); 905 if (cn != null) { 906 allowedComponents.add(cn); 907 } 908 } 909 } 910 } 911 return allowedComponents; 912 } 913 914 @NonNull getAllowedPackages(int userId)915 protected List<String> getAllowedPackages(int userId) { 916 final List<String> allowedPackages = new ArrayList<>(); 917 synchronized (mApproved) { 918 final ArrayMap<Boolean, ArraySet<String>> allowedByType = 919 mApproved.getOrDefault(userId, new ArrayMap<>()); 920 for (int i = 0; i < allowedByType.size(); i++) { 921 final ArraySet<String> allowed = allowedByType.valueAt(i); 922 for (int j = 0; j < allowed.size(); j++) { 923 String pkgName = getPackageName(allowed.valueAt(j)); 924 if (!TextUtils.isEmpty(pkgName)) { 925 allowedPackages.add(pkgName); 926 } 927 } 928 } 929 } 930 return allowedPackages; 931 } 932 isPackageOrComponentAllowed(String pkgOrComponent, int userId)933 protected boolean isPackageOrComponentAllowed(String pkgOrComponent, int userId) { 934 synchronized (mApproved) { 935 ArrayMap<Boolean, ArraySet<String>> allowedByType = 936 mApproved.getOrDefault(userId, new ArrayMap<>()); 937 for (int i = 0; i < allowedByType.size(); i++) { 938 ArraySet<String> allowed = allowedByType.valueAt(i); 939 if (allowed.contains(pkgOrComponent)) { 940 return true; 941 } 942 } 943 } 944 return false; 945 } 946 isPackageOrComponentAllowedWithPermission(ComponentName component, int userId)947 protected boolean isPackageOrComponentAllowedWithPermission(ComponentName component, 948 int userId) { 949 if (!(isPackageOrComponentAllowed(component.flattenToString(), userId) 950 || isPackageOrComponentAllowed(component.getPackageName(), userId))) { 951 return false; 952 } 953 return componentHasBindPermission(component, userId); 954 } 955 componentHasBindPermission(ComponentName component, int userId)956 private boolean componentHasBindPermission(ComponentName component, int userId) { 957 ServiceInfo info = getServiceInfo(component, userId); 958 if (info == null) { 959 return false; 960 } 961 return mConfig.bindPermission.equals(info.permission); 962 } 963 isPackageOrComponentUserSet(String pkgOrComponent, int userId)964 boolean isPackageOrComponentUserSet(String pkgOrComponent, int userId) { 965 synchronized (mApproved) { 966 ArraySet<String> services = mUserSetServices.get(userId); 967 return services != null && services.contains(pkgOrComponent); 968 } 969 } 970 isPackageAllowed(String pkg, int userId)971 protected boolean isPackageAllowed(String pkg, int userId) { 972 if (pkg == null) { 973 return false; 974 } 975 synchronized (mApproved) { 976 ArrayMap<Boolean, ArraySet<String>> allowedByType = 977 mApproved.getOrDefault(userId, new ArrayMap<>()); 978 for (int i = 0; i < allowedByType.size(); i++) { 979 ArraySet<String> allowed = allowedByType.valueAt(i); 980 for (String allowedEntry : allowed) { 981 ComponentName component = ComponentName.unflattenFromString(allowedEntry); 982 if (component != null) { 983 if (pkg.equals(component.getPackageName())) { 984 return true; 985 } 986 } else { 987 if (pkg.equals(allowedEntry)) { 988 return true; 989 } 990 } 991 } 992 } 993 } 994 return false; 995 } 996 onPackagesChanged(boolean removingPackage, String[] pkgList, int[] uidList)997 public void onPackagesChanged(boolean removingPackage, String[] pkgList, int[] uidList) { 998 if (DEBUG) { 999 synchronized (mMutex) { 1000 Slog.d(TAG, "onPackagesChanged removingPackage=" + removingPackage 1001 + " pkgList=" + (pkgList == null ? null : Arrays.asList(pkgList)) 1002 + " mEnabledServicesPackageNames=" + mEnabledServicesPackageNames); 1003 } 1004 } 1005 1006 if (pkgList != null && (pkgList.length > 0)) { 1007 boolean anyServicesInvolved = false; 1008 // Remove notification settings for uninstalled package 1009 if (removingPackage && uidList != null) { 1010 int size = Math.min(pkgList.length, uidList.length); 1011 for (int i = 0; i < size; i++) { 1012 final String pkg = pkgList[i]; 1013 final int userId = UserHandle.getUserId(uidList[i]); 1014 anyServicesInvolved = removeUninstalledItemsFromApprovedLists(userId, pkg); 1015 } 1016 } 1017 for (String pkgName : pkgList) { 1018 if (isComponentEnabledForPackage(pkgName)) { 1019 anyServicesInvolved = true; 1020 } 1021 if (uidList != null && uidList.length > 0) { 1022 for (int uid : uidList) { 1023 if (isPackageAllowed(pkgName, UserHandle.getUserId(uid))) { 1024 anyServicesInvolved = true; 1025 trimApprovedListsForInvalidServices(pkgName, UserHandle.getUserId(uid)); 1026 } 1027 } 1028 } 1029 } 1030 1031 if (anyServicesInvolved) { 1032 // make sure we're still bound to any of our services who may have just upgraded 1033 rebindServices(false, USER_ALL); 1034 } 1035 } 1036 } 1037 onUserRemoved(int user)1038 public void onUserRemoved(int user) { 1039 Slog.i(TAG, "Removing approved services for removed user " + user); 1040 synchronized (mApproved) { 1041 mApproved.remove(user); 1042 } 1043 synchronized (mSnoozing) { 1044 mSnoozing.remove(user); 1045 } 1046 unbindUserServices(user); 1047 } 1048 onUserSwitched(int user)1049 public void onUserSwitched(int user) { 1050 if (DEBUG) Slog.d(TAG, "onUserSwitched u=" + user); 1051 unbindOtherUserServices(user); 1052 rebindServices(true, user); 1053 } 1054 onUserUnlocked(int user)1055 public void onUserUnlocked(int user) { 1056 if (DEBUG) Slog.d(TAG, "onUserUnlocked u=" + user); 1057 rebindServices(false, user); 1058 } 1059 getServiceFromTokenLocked(IInterface service)1060 private ManagedServiceInfo getServiceFromTokenLocked(IInterface service) { 1061 if (service == null) { 1062 return null; 1063 } 1064 final IBinder token = service.asBinder(); 1065 synchronized (mMutex) { 1066 final int nServices = mServices.size(); 1067 for (int i = 0; i < nServices; i++) { 1068 final ManagedServiceInfo info = mServices.get(i); 1069 if (info.service.asBinder() == token) return info; 1070 } 1071 } 1072 return null; 1073 } 1074 isServiceTokenValidLocked(IInterface service)1075 protected boolean isServiceTokenValidLocked(IInterface service) { 1076 if (service == null) { 1077 return false; 1078 } 1079 ManagedServiceInfo info = getServiceFromTokenLocked(service); 1080 if (info != null) { 1081 return true; 1082 } 1083 return false; 1084 } 1085 checkServiceTokenLocked(IInterface service)1086 protected ManagedServiceInfo checkServiceTokenLocked(IInterface service) { 1087 checkNotNull(service); 1088 ManagedServiceInfo info = getServiceFromTokenLocked(service); 1089 if (info != null) { 1090 return info; 1091 } 1092 throw new SecurityException("Disallowed call from unknown " + getCaption() + ": " 1093 + service + " " + service.getClass()); 1094 } 1095 isSameUser(IInterface service, int userId)1096 public boolean isSameUser(IInterface service, int userId) { 1097 checkNotNull(service); 1098 synchronized (mMutex) { 1099 ManagedServiceInfo info = getServiceFromTokenLocked(service); 1100 if (info != null) { 1101 return info.isSameUser(userId); 1102 } 1103 return false; 1104 } 1105 } 1106 unregisterService(IInterface service, int userid)1107 public void unregisterService(IInterface service, int userid) { 1108 checkNotNull(service); 1109 // no need to check permissions; if your service binder is in the list, 1110 // that's proof that you had permission to add it in the first place 1111 unregisterServiceImpl(service, userid); 1112 } 1113 registerSystemService(IInterface service, ComponentName component, int userid, int uid)1114 public void registerSystemService(IInterface service, ComponentName component, int userid, 1115 int uid) { 1116 checkNotNull(service); 1117 ManagedServiceInfo info = registerServiceImpl( 1118 service, component, userid, Build.VERSION_CODES.CUR_DEVELOPMENT, uid); 1119 if (info != null) { 1120 onServiceAdded(info); 1121 } 1122 } 1123 1124 /** 1125 * Add a service to our callbacks. The lifecycle of this service is managed externally, 1126 * but unlike a system service, it should not be considered privileged. 1127 * */ registerGuestService(ManagedServiceInfo guest)1128 protected void registerGuestService(ManagedServiceInfo guest) { 1129 checkNotNull(guest.service); 1130 if (!checkType(guest.service)) { 1131 throw new IllegalArgumentException(); 1132 } 1133 if (registerServiceImpl(guest) != null) { 1134 onServiceAdded(guest); 1135 } 1136 } 1137 setComponentState(ComponentName component, int userId, boolean enabled)1138 protected void setComponentState(ComponentName component, int userId, boolean enabled) { 1139 synchronized (mSnoozing) { 1140 boolean previous = !mSnoozing.contains(userId, component); 1141 if (previous == enabled) { 1142 return; 1143 } 1144 1145 if (enabled) { 1146 mSnoozing.remove(userId, component); 1147 } else { 1148 mSnoozing.add(userId, component); 1149 } 1150 } 1151 1152 // State changed 1153 Slog.d(TAG, ((enabled) ? "Enabling " : "Disabling ") + "component " + 1154 component.flattenToShortString()); 1155 1156 synchronized (mMutex) { 1157 if (enabled) { 1158 if (isPackageOrComponentAllowedWithPermission(component, userId)) { 1159 registerServiceLocked(component, userId); 1160 } else { 1161 Slog.d(TAG, component + " no longer has permission to be bound"); 1162 } 1163 } else { 1164 unregisterServiceLocked(component, userId); 1165 } 1166 } 1167 } 1168 loadComponentNamesFromValues( ArraySet<String> approved, int userId)1169 private @NonNull ArraySet<ComponentName> loadComponentNamesFromValues( 1170 ArraySet<String> approved, int userId) { 1171 if (approved == null || approved.size() == 0) 1172 return new ArraySet<>(); 1173 ArraySet<ComponentName> result = new ArraySet<>(approved.size()); 1174 for (int i = 0; i < approved.size(); i++) { 1175 final String packageOrComponent = approved.valueAt(i); 1176 if (!TextUtils.isEmpty(packageOrComponent)) { 1177 ComponentName component = ComponentName.unflattenFromString(packageOrComponent); 1178 if (component != null) { 1179 result.add(component); 1180 } else { 1181 result.addAll(queryPackageForServices(packageOrComponent, userId)); 1182 } 1183 } 1184 } 1185 return result; 1186 } 1187 queryPackageForServices(String packageName, int userId)1188 protected Set<ComponentName> queryPackageForServices(String packageName, int userId) { 1189 return queryPackageForServices(packageName, 0, userId); 1190 } 1191 queryPackageForServices(String packageName, int extraFlags, int userId)1192 protected ArraySet<ComponentName> queryPackageForServices(String packageName, int extraFlags, 1193 int userId) { 1194 ArraySet<ComponentName> installed = new ArraySet<>(); 1195 final PackageManager pm = mContext.getPackageManager(); 1196 Intent queryIntent = new Intent(mConfig.serviceInterface); 1197 if (!TextUtils.isEmpty(packageName)) { 1198 queryIntent.setPackage(packageName); 1199 } 1200 List<ResolveInfo> installedServices = pm.queryIntentServicesAsUser( 1201 queryIntent, 1202 PackageManager.GET_SERVICES | PackageManager.GET_META_DATA | extraFlags, 1203 userId); 1204 if (DEBUG) 1205 Slog.v(TAG, mConfig.serviceInterface + " services: " + installedServices); 1206 if (installedServices != null) { 1207 for (int i = 0, count = installedServices.size(); i < count; i++) { 1208 ResolveInfo resolveInfo = installedServices.get(i); 1209 ServiceInfo info = resolveInfo.serviceInfo; 1210 1211 ComponentName component = new ComponentName(info.packageName, info.name); 1212 if (!mConfig.bindPermission.equals(info.permission)) { 1213 Slog.w(TAG, "Skipping " + getCaption() + " service " 1214 + info.packageName + "/" + info.name 1215 + ": it does not require the permission " 1216 + mConfig.bindPermission); 1217 continue; 1218 } 1219 installed.add(component); 1220 } 1221 } 1222 return installed; 1223 } 1224 trimApprovedListsAccordingToInstalledServices(int userId)1225 private void trimApprovedListsAccordingToInstalledServices(int userId) { 1226 synchronized (mApproved) { 1227 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.get(userId); 1228 if (approvedByType == null) { 1229 return; 1230 } 1231 for (int i = 0; i < approvedByType.size(); i++) { 1232 final ArraySet<String> approved = approvedByType.valueAt(i); 1233 for (int j = approved.size() - 1; j >= 0; j--) { 1234 final String approvedPackageOrComponent = approved.valueAt(j); 1235 if (!isValidEntry(approvedPackageOrComponent, userId)) { 1236 approved.removeAt(j); 1237 Slog.v(TAG, "Removing " + approvedPackageOrComponent 1238 + " from approved list; no matching services found"); 1239 } else { 1240 if (DEBUG) { 1241 Slog.v(TAG, "Keeping " + approvedPackageOrComponent 1242 + " on approved list; matching services found"); 1243 } 1244 } 1245 } 1246 } 1247 } 1248 } 1249 removeUninstalledItemsFromApprovedLists(int uninstalledUserId, String pkg)1250 private boolean removeUninstalledItemsFromApprovedLists(int uninstalledUserId, String pkg) { 1251 boolean removed = false; 1252 synchronized (mApproved) { 1253 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.get( 1254 uninstalledUserId); 1255 if (approvedByType != null) { 1256 int M = approvedByType.size(); 1257 for (int j = 0; j < M; j++) { 1258 final ArraySet<String> approved = approvedByType.valueAt(j); 1259 int O = approved.size(); 1260 for (int k = O - 1; k >= 0; k--) { 1261 final String packageOrComponent = approved.valueAt(k); 1262 final String packageName = getPackageName(packageOrComponent); 1263 if (TextUtils.equals(pkg, packageName)) { 1264 approved.removeAt(k); 1265 if (DEBUG) { 1266 Slog.v(TAG, "Removing " + packageOrComponent 1267 + " from approved list; uninstalled"); 1268 } 1269 } 1270 } 1271 } 1272 } 1273 // Remove uninstalled components from user-set list 1274 final ArraySet<String> userSet = mUserSetServices.get(uninstalledUserId); 1275 if (userSet != null) { 1276 int numServices = userSet.size(); 1277 for (int i = numServices - 1; i >= 0; i--) { 1278 String pkgOrComponent = userSet.valueAt(i); 1279 if (TextUtils.equals(pkg, getPackageName(pkgOrComponent))) { 1280 userSet.removeAt(i); 1281 if (DEBUG) { 1282 Slog.v(TAG, "Removing " + pkgOrComponent 1283 + " from user-set list; uninstalled"); 1284 } 1285 } 1286 } 1287 } 1288 } 1289 return removed; 1290 } 1291 trimApprovedListsForInvalidServices(String packageName, int userId)1292 private void trimApprovedListsForInvalidServices(String packageName, int userId) { 1293 synchronized (mApproved) { 1294 final ArrayMap<Boolean, ArraySet<String>> approvedByType = mApproved.get(userId); 1295 if (approvedByType == null) { 1296 return; 1297 } 1298 for (int i = 0; i < approvedByType.size(); i++) { 1299 final ArraySet<String> approved = approvedByType.valueAt(i); 1300 for (int j = approved.size() - 1; j >= 0; j--) { 1301 final String approvedPackageOrComponent = approved.valueAt(j); 1302 if (TextUtils.equals(getPackageName(approvedPackageOrComponent), packageName)) { 1303 final ComponentName component = ComponentName.unflattenFromString( 1304 approvedPackageOrComponent); 1305 if (component != null && !componentHasBindPermission(component, userId)) { 1306 approved.removeAt(j); 1307 if (DEBUG) { 1308 Slog.v(TAG, "Removing " + approvedPackageOrComponent 1309 + " from approved list; no bind permission found " 1310 + mConfig.bindPermission); 1311 } 1312 } 1313 } 1314 } 1315 } 1316 } 1317 } 1318 getPackageName(String packageOrComponent)1319 protected String getPackageName(String packageOrComponent) { 1320 final ComponentName component = ComponentName.unflattenFromString(packageOrComponent); 1321 if (component != null) { 1322 return component.getPackageName(); 1323 } else { 1324 return packageOrComponent; 1325 } 1326 } 1327 isValidEntry(String packageOrComponent, int userId)1328 protected boolean isValidEntry(String packageOrComponent, int userId) { 1329 return hasMatchingServices(packageOrComponent, userId); 1330 } 1331 hasMatchingServices(String packageOrComponent, int userId)1332 private boolean hasMatchingServices(String packageOrComponent, int userId) { 1333 if (!TextUtils.isEmpty(packageOrComponent)) { 1334 final String packageName = getPackageName(packageOrComponent); 1335 return queryPackageForServices(packageName, userId).size() > 0; 1336 } 1337 return false; 1338 } 1339 1340 @VisibleForTesting getAllowedComponents(IntArray userIds)1341 protected SparseArray<ArraySet<ComponentName>> getAllowedComponents(IntArray userIds) { 1342 final int nUserIds = userIds.size(); 1343 final SparseArray<ArraySet<ComponentName>> componentsByUser = new SparseArray<>(); 1344 1345 for (int i = 0; i < nUserIds; ++i) { 1346 final int userId = userIds.get(i); 1347 synchronized (mApproved) { 1348 final ArrayMap<Boolean, ArraySet<String>> approvedLists = mApproved.get(userId); 1349 if (approvedLists != null) { 1350 final int N = approvedLists.size(); 1351 for (int j = 0; j < N; j++) { 1352 ArraySet<ComponentName> approvedByUser = componentsByUser.get(userId); 1353 if (approvedByUser == null) { 1354 approvedByUser = new ArraySet<>(); 1355 componentsByUser.put(userId, approvedByUser); 1356 } 1357 approvedByUser.addAll( 1358 loadComponentNamesFromValues(approvedLists.valueAt(j), userId)); 1359 } 1360 } 1361 } 1362 } 1363 return componentsByUser; 1364 } 1365 1366 @GuardedBy("mMutex") populateComponentsToBind(SparseArray<Set<ComponentName>> componentsToBind, final IntArray activeUsers, SparseArray<ArraySet<ComponentName>> approvedComponentsByUser)1367 protected void populateComponentsToBind(SparseArray<Set<ComponentName>> componentsToBind, 1368 final IntArray activeUsers, 1369 SparseArray<ArraySet<ComponentName>> approvedComponentsByUser) { 1370 mEnabledServicesForCurrentProfiles.clear(); 1371 mEnabledServicesPackageNames.clear(); 1372 final int nUserIds = activeUsers.size(); 1373 1374 for (int i = 0; i < nUserIds; ++i) { 1375 // decode the list of components 1376 final int userId = activeUsers.get(i); 1377 final ArraySet<ComponentName> userComponents = approvedComponentsByUser.get(userId); 1378 if (null == userComponents) { 1379 componentsToBind.put(userId, new ArraySet<>()); 1380 continue; 1381 } 1382 1383 final Set<ComponentName> add = new HashSet<>(userComponents); 1384 synchronized (mSnoozing) { 1385 ArraySet<ComponentName> snoozed = mSnoozing.get(userId); 1386 if (snoozed != null) { 1387 add.removeAll(snoozed); 1388 } 1389 } 1390 1391 componentsToBind.put(userId, add); 1392 1393 mEnabledServicesForCurrentProfiles.addAll(userComponents); 1394 1395 for (int j = 0; j < userComponents.size(); j++) { 1396 final ComponentName component = userComponents.valueAt(j); 1397 mEnabledServicesPackageNames.add(component.getPackageName()); 1398 } 1399 } 1400 } 1401 1402 @GuardedBy("mMutex") getRemovableConnectedServices()1403 protected Set<ManagedServiceInfo> getRemovableConnectedServices() { 1404 final Set<ManagedServiceInfo> removableBoundServices = new ArraySet<>(); 1405 for (ManagedServiceInfo service : mServices) { 1406 if (!service.isSystem && !service.isGuest(this)) { 1407 removableBoundServices.add(service); 1408 } 1409 } 1410 return removableBoundServices; 1411 } 1412 populateComponentsToUnbind( boolean forceRebind, Set<ManagedServiceInfo> removableBoundServices, SparseArray<Set<ComponentName>> allowedComponentsToBind, SparseArray<Set<ComponentName>> componentsToUnbind)1413 protected void populateComponentsToUnbind( 1414 boolean forceRebind, 1415 Set<ManagedServiceInfo> removableBoundServices, 1416 SparseArray<Set<ComponentName>> allowedComponentsToBind, 1417 SparseArray<Set<ComponentName>> componentsToUnbind) { 1418 for (ManagedServiceInfo info : removableBoundServices) { 1419 final Set<ComponentName> allowedComponents = allowedComponentsToBind.get(info.userid); 1420 if (allowedComponents != null) { 1421 if (forceRebind || !allowedComponents.contains(info.component)) { 1422 Set<ComponentName> toUnbind = 1423 componentsToUnbind.get(info.userid, new ArraySet<>()); 1424 toUnbind.add(info.component); 1425 componentsToUnbind.put(info.userid, toUnbind); 1426 } 1427 } 1428 } 1429 } 1430 1431 /** 1432 * Called whenever packages change, the user switches, or the secure setting 1433 * is altered. (For example in response to USER_SWITCHED in our broadcast receiver) 1434 */ rebindServices(boolean forceRebind, int userToRebind)1435 protected void rebindServices(boolean forceRebind, int userToRebind) { 1436 if (DEBUG) Slog.d(TAG, "rebindServices " + forceRebind + " " + userToRebind); 1437 IntArray userIds = mUserProfiles.getCurrentProfileIds(); 1438 boolean rebindAllCurrentUsers = mUserProfiles.isProfileUser(userToRebind, mContext) 1439 && allowRebindForParentUser(); 1440 if (userToRebind != USER_ALL && !rebindAllCurrentUsers) { 1441 userIds = new IntArray(1); 1442 userIds.add(userToRebind); 1443 } 1444 1445 final SparseArray<Set<ComponentName>> componentsToBind = new SparseArray<>(); 1446 final SparseArray<Set<ComponentName>> componentsToUnbind = new SparseArray<>(); 1447 1448 synchronized (mMutex) { 1449 final SparseArray<ArraySet<ComponentName>> approvedComponentsByUser = 1450 getAllowedComponents(userIds); 1451 final Set<ManagedServiceInfo> removableBoundServices = getRemovableConnectedServices(); 1452 1453 // Filter approvedComponentsByUser to collect all of the components that are allowed 1454 // for the currently active user(s). 1455 populateComponentsToBind(componentsToBind, userIds, approvedComponentsByUser); 1456 1457 // For every current non-system connection, disconnect services that are no longer 1458 // approved, or ALL services if we are force rebinding 1459 populateComponentsToUnbind( 1460 forceRebind, removableBoundServices, componentsToBind, componentsToUnbind); 1461 } 1462 1463 unbindFromServices(componentsToUnbind); 1464 bindToServices(componentsToBind); 1465 } 1466 1467 /** 1468 * Called when user switched to unbind all services from other users. 1469 */ 1470 @VisibleForTesting unbindOtherUserServices(int currentUser)1471 void unbindOtherUserServices(int currentUser) { 1472 TimingsTraceAndSlog t = new TimingsTraceAndSlog(); 1473 t.traceBegin("ManagedServices.unbindOtherUserServices_current" + currentUser); 1474 unbindServicesImpl(currentUser, true /* allExceptUser */); 1475 t.traceEnd(); 1476 } 1477 unbindUserServices(int user)1478 void unbindUserServices(int user) { 1479 TimingsTraceAndSlog t = new TimingsTraceAndSlog(); 1480 t.traceBegin("ManagedServices.unbindUserServices" + user); 1481 unbindServicesImpl(user, false /* allExceptUser */); 1482 t.traceEnd(); 1483 } 1484 unbindServicesImpl(int user, boolean allExceptUser)1485 void unbindServicesImpl(int user, boolean allExceptUser) { 1486 final SparseArray<Set<ComponentName>> componentsToUnbind = new SparseArray<>(); 1487 synchronized (mMutex) { 1488 final Set<ManagedServiceInfo> removableBoundServices = getRemovableConnectedServices(); 1489 for (ManagedServiceInfo info : removableBoundServices) { 1490 if ((allExceptUser && (info.userid != user)) 1491 || (!allExceptUser && (info.userid == user))) { 1492 Set<ComponentName> toUnbind = 1493 componentsToUnbind.get(info.userid, new ArraySet<>()); 1494 toUnbind.add(info.component); 1495 componentsToUnbind.put(info.userid, toUnbind); 1496 } 1497 } 1498 } 1499 unbindFromServices(componentsToUnbind); 1500 } 1501 unbindFromServices(SparseArray<Set<ComponentName>> componentsToUnbind)1502 protected void unbindFromServices(SparseArray<Set<ComponentName>> componentsToUnbind) { 1503 for (int i = 0; i < componentsToUnbind.size(); i++) { 1504 final int userId = componentsToUnbind.keyAt(i); 1505 final Set<ComponentName> removableComponents = componentsToUnbind.get(userId); 1506 for (ComponentName cn : removableComponents) { 1507 // No longer allowed to be bound, or must rebind. 1508 Slog.v(TAG, "disabling " + getCaption() + " for user " + userId + ": " + cn); 1509 unregisterService(cn, userId); 1510 } 1511 } 1512 } 1513 1514 // Attempt to bind to services, skipping those that cannot be found or lack the permission. bindToServices(SparseArray<Set<ComponentName>> componentsToBind)1515 private void bindToServices(SparseArray<Set<ComponentName>> componentsToBind) { 1516 for (int i = 0; i < componentsToBind.size(); i++) { 1517 final int userId = componentsToBind.keyAt(i); 1518 final Set<ComponentName> add = componentsToBind.get(userId); 1519 for (ComponentName component : add) { 1520 ServiceInfo info = getServiceInfo(component, userId); 1521 if (info == null) { 1522 Slog.w(TAG, "Not binding " + getCaption() + " service " + component 1523 + ": service not found"); 1524 continue; 1525 } 1526 if (!mConfig.bindPermission.equals(info.permission)) { 1527 Slog.w(TAG, "Not binding " + getCaption() + " service " + component 1528 + ": it does not require the permission " + mConfig.bindPermission); 1529 continue; 1530 } 1531 // Do not (auto)bind if service has meta-data to explicitly disallow it 1532 if (!isAutobindAllowed(info) && !isBoundOrRebinding(component, userId)) { 1533 synchronized (mSnoozing) { 1534 Slog.d(TAG, "Not binding " + getCaption() + " service " + component 1535 + ": has META_DATA_DEFAULT_AUTOBIND = false"); 1536 mSnoozing.add(userId, component); 1537 } 1538 continue; 1539 } 1540 1541 Slog.v(TAG, 1542 "enabling " + getCaption() + " for " + userId + ": " + component); 1543 registerService(info, userId); 1544 } 1545 } 1546 } 1547 1548 /** 1549 * Version of registerService that takes the name of a service component to bind to. 1550 */ 1551 @VisibleForTesting registerService(final ServiceInfo si, final int userId)1552 void registerService(final ServiceInfo si, final int userId) { 1553 ensureFilters(si, userId); 1554 registerService(si.getComponentName(), userId); 1555 } 1556 1557 @VisibleForTesting registerService(final ComponentName cn, final int userId)1558 void registerService(final ComponentName cn, final int userId) { 1559 synchronized (mMutex) { 1560 registerServiceLocked(cn, userId); 1561 } 1562 } 1563 1564 @VisibleForTesting reregisterService(final ComponentName cn, final int userId)1565 void reregisterService(final ComponentName cn, final int userId) { 1566 // If rebinding a package that died, ensure it still has permission 1567 // after the rebind delay 1568 if (isPackageOrComponentAllowedWithPermission(cn, userId)) { 1569 registerService(cn, userId); 1570 } 1571 } 1572 1573 /** 1574 * Inject a system service into the management list. 1575 */ registerSystemService(final ComponentName name, final int userid)1576 public void registerSystemService(final ComponentName name, final int userid) { 1577 synchronized (mMutex) { 1578 registerServiceLocked(name, userid, true /* isSystem */); 1579 } 1580 } 1581 1582 @GuardedBy("mMutex") registerServiceLocked(final ComponentName name, final int userid)1583 private void registerServiceLocked(final ComponentName name, final int userid) { 1584 registerServiceLocked(name, userid, false /* isSystem */); 1585 } 1586 1587 @GuardedBy("mMutex") registerServiceLocked(final ComponentName name, final int userid, final boolean isSystem)1588 private void registerServiceLocked(final ComponentName name, final int userid, 1589 final boolean isSystem) { 1590 if (DEBUG) Slog.v(TAG, "registerService: " + name + " u=" + userid); 1591 1592 final Pair<ComponentName, Integer> servicesBindingTag = Pair.create(name, userid); 1593 if (mServicesBound.contains(servicesBindingTag)) { 1594 Slog.v(TAG, "Not registering " + name + " is already bound"); 1595 // stop registering this thing already! we're working on it 1596 return; 1597 } 1598 mServicesBound.add(servicesBindingTag); 1599 1600 final int N = mServices.size(); 1601 for (int i = N - 1; i >= 0; i--) { 1602 final ManagedServiceInfo info = mServices.get(i); 1603 if (name.equals(info.component) 1604 && info.userid == userid) { 1605 // cut old connections 1606 Slog.v(TAG, " disconnecting old " + getCaption() + ": " + info.service); 1607 removeServiceLocked(i); 1608 if (info.connection != null) { 1609 unbindService(info.connection, info.component, info.userid); 1610 } 1611 } 1612 } 1613 1614 Intent intent = new Intent(mConfig.serviceInterface); 1615 intent.setComponent(name); 1616 1617 intent.putExtra(Intent.EXTRA_CLIENT_LABEL, mConfig.clientLabel); 1618 1619 final ActivityOptions activityOptions = ActivityOptions.makeBasic(); 1620 activityOptions.setPendingIntentCreatorBackgroundActivityStartMode( 1621 ActivityOptions.MODE_BACKGROUND_ACTIVITY_START_DENIED); 1622 final PendingIntent pendingIntent = PendingIntent.getActivity( 1623 mContext, 0, new Intent(mConfig.settingsAction), PendingIntent.FLAG_IMMUTABLE, 1624 activityOptions.toBundle()); 1625 intent.putExtra(Intent.EXTRA_CLIENT_INTENT, pendingIntent); 1626 1627 ApplicationInfo appInfo = null; 1628 try { 1629 appInfo = mContext.getPackageManager().getApplicationInfoAsUser( 1630 name.getPackageName(), 0, userid); 1631 } catch (NameNotFoundException e) { 1632 // Ignore if the package doesn't exist we won't be able to bind to the service. 1633 } 1634 final int targetSdkVersion = 1635 appInfo != null ? appInfo.targetSdkVersion : Build.VERSION_CODES.BASE; 1636 final int uid = appInfo != null ? appInfo.uid : -1; 1637 1638 try { 1639 Slog.v(TAG, "binding: " + intent); 1640 ServiceConnection serviceConnection = new ServiceConnection() { 1641 IInterface mService; 1642 1643 @Override 1644 public void onServiceConnected(ComponentName name, IBinder binder) { 1645 Slog.v(TAG, userid + " " + getCaption() + " service connected: " + name); 1646 boolean added = false; 1647 ManagedServiceInfo info = null; 1648 synchronized (mMutex) { 1649 mServicesRebinding.remove(servicesBindingTag); 1650 try { 1651 mService = asInterface(binder); 1652 info = newServiceInfo(mService, name, 1653 userid, isSystem, this, targetSdkVersion, uid); 1654 binder.linkToDeath(info, 0); 1655 added = mServices.add(info); 1656 } catch (RemoteException e) { 1657 Slog.e(TAG, "Failed to linkToDeath, already dead", e); 1658 } 1659 } 1660 if (added) { 1661 onServiceAdded(info); 1662 } 1663 } 1664 1665 @Override 1666 public void onServiceDisconnected(ComponentName name) { 1667 Slog.v(TAG, userid + " " + getCaption() + " connection lost: " + name); 1668 } 1669 1670 @Override 1671 public void onBindingDied(ComponentName name) { 1672 Slog.w(TAG, userid + " " + getCaption() + " binding died: " + name); 1673 synchronized (mMutex) { 1674 unbindService(this, name, userid); 1675 if (!mServicesRebinding.contains(servicesBindingTag)) { 1676 mServicesRebinding.add(servicesBindingTag); 1677 mHandler.postDelayed(() -> 1678 reregisterService(name, userid), 1679 ON_BINDING_DIED_REBIND_DELAY_MS); 1680 } else { 1681 Slog.v(TAG, getCaption() + " not rebinding in user " + userid 1682 + " as a previous rebind attempt was made: " + name); 1683 } 1684 } 1685 } 1686 1687 @Override 1688 public void onNullBinding(ComponentName name) { 1689 Slog.v(TAG, "onNullBinding() called with: name = [" + name + "]"); 1690 mContext.unbindService(this); 1691 } 1692 }; 1693 if (!mContext.bindServiceAsUser(intent, 1694 serviceConnection, 1695 getBindFlags(), 1696 new UserHandle(userid))) { 1697 mServicesBound.remove(servicesBindingTag); 1698 Slog.w(TAG, "Unable to bind " + getCaption() + " service: " + intent 1699 + " in user " + userid); 1700 return; 1701 } 1702 } catch (SecurityException ex) { 1703 mServicesBound.remove(servicesBindingTag); 1704 Slog.e(TAG, "Unable to bind " + getCaption() + " service: " + intent, ex); 1705 } 1706 } 1707 1708 @VisibleForTesting isBound(ComponentName cn, int userId)1709 boolean isBound(ComponentName cn, int userId) { 1710 final Pair<ComponentName, Integer> servicesBindingTag = Pair.create(cn, userId); 1711 synchronized (mMutex) { 1712 return mServicesBound.contains(servicesBindingTag); 1713 } 1714 } 1715 isBoundOrRebinding(final ComponentName cn, final int userId)1716 protected boolean isBoundOrRebinding(final ComponentName cn, final int userId) { 1717 synchronized (mMutex) { 1718 return isBound(cn, userId) || mServicesRebinding.contains(Pair.create(cn, userId)); 1719 } 1720 } 1721 1722 /** 1723 * Remove a service for the given user by ComponentName 1724 */ unregisterService(ComponentName name, int userid)1725 private void unregisterService(ComponentName name, int userid) { 1726 synchronized (mMutex) { 1727 unregisterServiceLocked(name, userid); 1728 } 1729 } 1730 1731 @GuardedBy("mMutex") unregisterServiceLocked(ComponentName name, int userid)1732 private void unregisterServiceLocked(ComponentName name, int userid) { 1733 final int N = mServices.size(); 1734 for (int i = N - 1; i >= 0; i--) { 1735 final ManagedServiceInfo info = mServices.get(i); 1736 if (name.equals(info.component) && info.userid == userid) { 1737 removeServiceLocked(i); 1738 if (info.connection != null) { 1739 unbindService(info.connection, info.component, info.userid); 1740 } 1741 } 1742 } 1743 } 1744 1745 /** 1746 * Removes a service from the list but does not unbind 1747 * 1748 * @return the removed service. 1749 */ removeServiceImpl(IInterface service, final int userid)1750 private ManagedServiceInfo removeServiceImpl(IInterface service, final int userid) { 1751 if (DEBUG) Slog.d(TAG, "removeServiceImpl service=" + service + " u=" + userid); 1752 ManagedServiceInfo serviceInfo = null; 1753 synchronized (mMutex) { 1754 final int N = mServices.size(); 1755 for (int i = N - 1; i >= 0; i--) { 1756 final ManagedServiceInfo info = mServices.get(i); 1757 if (info.service.asBinder() == service.asBinder() && info.userid == userid) { 1758 Slog.d(TAG, "Removing active service " + info.component); 1759 serviceInfo = removeServiceLocked(i); 1760 } 1761 } 1762 } 1763 return serviceInfo; 1764 } 1765 1766 @GuardedBy("mMutex") removeServiceLocked(int i)1767 private ManagedServiceInfo removeServiceLocked(int i) { 1768 final ManagedServiceInfo info = mServices.remove(i); 1769 onServiceRemovedLocked(info); 1770 return info; 1771 } 1772 checkNotNull(IInterface service)1773 private void checkNotNull(IInterface service) { 1774 if (service == null) { 1775 throw new IllegalArgumentException(getCaption() + " must not be null"); 1776 } 1777 } 1778 registerServiceImpl(final IInterface service, final ComponentName component, final int userid, int targetSdk, int uid)1779 private ManagedServiceInfo registerServiceImpl(final IInterface service, 1780 final ComponentName component, final int userid, int targetSdk, int uid) { 1781 ManagedServiceInfo info = newServiceInfo(service, component, userid, 1782 true /*isSystem*/, null /*connection*/, targetSdk, uid); 1783 return registerServiceImpl(info); 1784 } 1785 registerServiceImpl(ManagedServiceInfo info)1786 private ManagedServiceInfo registerServiceImpl(ManagedServiceInfo info) { 1787 synchronized (mMutex) { 1788 try { 1789 info.service.asBinder().linkToDeath(info, 0); 1790 mServices.add(info); 1791 return info; 1792 } catch (RemoteException e) { 1793 // already dead 1794 } 1795 } 1796 return null; 1797 } 1798 1799 /** 1800 * Removes a service from the list and unbinds. 1801 */ unregisterServiceImpl(IInterface service, int userid)1802 private void unregisterServiceImpl(IInterface service, int userid) { 1803 ManagedServiceInfo info = removeServiceImpl(service, userid); 1804 if (info != null && info.connection != null && !info.isGuest(this)) { 1805 unbindService(info.connection, info.component, info.userid); 1806 } 1807 } 1808 unbindService(ServiceConnection connection, ComponentName component, int userId)1809 private void unbindService(ServiceConnection connection, ComponentName component, int userId) { 1810 try { 1811 mContext.unbindService(connection); 1812 } catch (IllegalArgumentException e) { 1813 Slog.e(TAG, getCaption() + " " + component + " could not be unbound", e); 1814 } 1815 synchronized (mMutex) { 1816 mServicesBound.remove(Pair.create(component, userId)); 1817 } 1818 } 1819 getServiceInfo(ComponentName component, int userId)1820 private ServiceInfo getServiceInfo(ComponentName component, int userId) { 1821 try { 1822 return mPm.getServiceInfo(component, 1823 PackageManager.GET_META_DATA 1824 | PackageManager.MATCH_DIRECT_BOOT_AWARE 1825 | PackageManager.MATCH_DIRECT_BOOT_UNAWARE, 1826 userId); 1827 } catch (RemoteException e) { 1828 e.rethrowFromSystemServer(); 1829 } 1830 return null; 1831 } 1832 isAutobindAllowed(ServiceInfo serviceInfo)1833 private boolean isAutobindAllowed(ServiceInfo serviceInfo) { 1834 if (serviceInfo != null && serviceInfo.metaData != null && serviceInfo.metaData.containsKey( 1835 META_DATA_DEFAULT_AUTOBIND)) { 1836 return serviceInfo.metaData.getBoolean(META_DATA_DEFAULT_AUTOBIND, true); 1837 } 1838 return true; 1839 } 1840 1841 /** 1842 * Returns true if services in the parent user should be rebound 1843 * when rebindServices is called with a profile userId. 1844 * Must be false for NotificationAssistants. 1845 */ allowRebindForParentUser()1846 protected abstract boolean allowRebindForParentUser(); 1847 1848 public class ManagedServiceInfo implements IBinder.DeathRecipient { 1849 public IInterface service; 1850 public ComponentName component; 1851 public int userid; 1852 public boolean isSystem; 1853 @FlaggedApi(FLAG_LIFETIME_EXTENSION_REFACTOR) 1854 public boolean isSystemUi; 1855 public ServiceConnection connection; 1856 public int targetSdkVersion; 1857 public Pair<ComponentName, Integer> mKey; 1858 public int uid; 1859 ManagedServiceInfo(IInterface service, ComponentName component, int userid, boolean isSystem, ServiceConnection connection, int targetSdkVersion, int uid)1860 public ManagedServiceInfo(IInterface service, ComponentName component, 1861 int userid, boolean isSystem, ServiceConnection connection, int targetSdkVersion, 1862 int uid) { 1863 this.service = service; 1864 this.component = component; 1865 this.userid = userid; 1866 this.isSystem = isSystem; 1867 this.connection = connection; 1868 this.targetSdkVersion = targetSdkVersion; 1869 this.uid = uid; 1870 mKey = Pair.create(component, userid); 1871 } 1872 isGuest(ManagedServices host)1873 public boolean isGuest(ManagedServices host) { 1874 return ManagedServices.this != host; 1875 } 1876 getOwner()1877 public ManagedServices getOwner() { 1878 return ManagedServices.this; 1879 } 1880 getService()1881 public IInterface getService() { 1882 return service; 1883 } 1884 isSystem()1885 public boolean isSystem() { 1886 return isSystem; 1887 } 1888 1889 @FlaggedApi(FLAG_LIFETIME_EXTENSION_REFACTOR) isSystemUi()1890 public boolean isSystemUi() { 1891 return isSystemUi; 1892 } 1893 1894 @Override toString()1895 public String toString() { 1896 return new StringBuilder("ManagedServiceInfo[") 1897 .append("component=").append(component) 1898 .append(",userid=").append(userid) 1899 .append(",isSystem=").append(isSystem) 1900 .append(",targetSdkVersion=").append(targetSdkVersion) 1901 .append(",connection=").append(connection == null ? null : "<connection>") 1902 .append(",service=").append(service) 1903 .append(']').toString(); 1904 } 1905 dumpDebug(ProtoOutputStream proto, long fieldId, ManagedServices host)1906 public void dumpDebug(ProtoOutputStream proto, long fieldId, ManagedServices host) { 1907 final long token = proto.start(fieldId); 1908 component.dumpDebug(proto, ManagedServiceInfoProto.COMPONENT); 1909 proto.write(ManagedServiceInfoProto.USER_ID, userid); 1910 proto.write(ManagedServiceInfoProto.SERVICE, service.getClass().getName()); 1911 proto.write(ManagedServiceInfoProto.IS_SYSTEM, isSystem); 1912 proto.write(ManagedServiceInfoProto.IS_GUEST, isGuest(host)); 1913 proto.end(token); 1914 } 1915 isSameUser(int userId)1916 public boolean isSameUser(int userId) { 1917 if (!isEnabledForCurrentProfiles()) { 1918 return false; 1919 } 1920 return userId == USER_ALL || userId == this.userid; 1921 } 1922 enabledAndUserMatches(int nid)1923 public boolean enabledAndUserMatches(int nid) { 1924 if (!isEnabledForCurrentProfiles()) { 1925 return false; 1926 } 1927 if (this.userid == USER_ALL) return true; 1928 if (this.isSystem) return true; 1929 if (nid == USER_ALL || nid == this.userid) return true; 1930 return supportsProfiles() 1931 && mUserProfiles.isCurrentProfile(nid) 1932 && isPermittedForProfile(nid); 1933 } 1934 supportsProfiles()1935 public boolean supportsProfiles() { 1936 return targetSdkVersion >= Build.VERSION_CODES.LOLLIPOP; 1937 } 1938 1939 @Override binderDied()1940 public void binderDied() { 1941 if (DEBUG) Slog.d(TAG, "binderDied"); 1942 // Remove the service, but don't unbind from the service. The system will bring the 1943 // service back up, and the onServiceConnected handler will read the service with the 1944 // new binding. If this isn't a bound service, and is just a registered 1945 // service, just removing it from the list is all we need to do anyway. 1946 removeServiceImpl(this.service, this.userid); 1947 } 1948 1949 /** convenience method for looking in mEnabledServicesForCurrentProfiles */ isEnabledForCurrentProfiles()1950 public boolean isEnabledForCurrentProfiles() { 1951 if (this.isSystem) return true; 1952 if (this.connection == null) return false; 1953 synchronized (mMutex) { 1954 return mEnabledServicesForCurrentProfiles.contains(this.component); 1955 } 1956 } 1957 1958 /** 1959 * Returns true if this service is allowed to receive events for the given userId. A 1960 * managed profile owner can disallow non-system services running outside of the profile 1961 * from receiving events from the profile. 1962 */ isPermittedForProfile(int userId)1963 public boolean isPermittedForProfile(int userId) { 1964 if (!mUserProfiles.isProfileUser(userId, mContext)) { 1965 return true; 1966 } 1967 DevicePolicyManager dpm = 1968 (DevicePolicyManager) mContext.getSystemService(DEVICE_POLICY_SERVICE); 1969 final long identity = Binder.clearCallingIdentity(); 1970 try { 1971 return dpm.isNotificationListenerServicePermitted( 1972 component.getPackageName(), userId); 1973 } finally { 1974 Binder.restoreCallingIdentity(identity); 1975 } 1976 } 1977 1978 @Override equals(Object o)1979 public boolean equals(Object o) { 1980 if (this == o) return true; 1981 if (o == null || getClass() != o.getClass()) return false; 1982 ManagedServiceInfo that = (ManagedServiceInfo) o; 1983 return userid == that.userid 1984 && isSystem == that.isSystem 1985 && targetSdkVersion == that.targetSdkVersion 1986 && Objects.equals(service, that.service) 1987 && Objects.equals(component, that.component) 1988 && Objects.equals(connection, that.connection); 1989 } 1990 1991 @Override hashCode()1992 public int hashCode() { 1993 return Objects.hash(service, component, userid, isSystem, connection, targetSdkVersion); 1994 } 1995 } 1996 1997 /** convenience method for looking in mEnabledServicesForCurrentProfiles */ isComponentEnabledForCurrentProfiles(ComponentName component)1998 public boolean isComponentEnabledForCurrentProfiles(ComponentName component) { 1999 synchronized (mMutex) { 2000 return mEnabledServicesForCurrentProfiles.contains(component); 2001 } 2002 } 2003 2004 public static class UserProfiles { 2005 // Profiles of the current user. 2006 private final SparseArray<UserInfo> mCurrentProfiles = new SparseArray<>(); 2007 updateCache(@onNull Context context)2008 public void updateCache(@NonNull Context context) { 2009 UserManager userManager = (UserManager) context.getSystemService(Context.USER_SERVICE); 2010 if (userManager != null) { 2011 int currentUserId = ActivityManager.getCurrentUser(); 2012 List<UserInfo> profiles = userManager.getProfiles(currentUserId); 2013 synchronized (mCurrentProfiles) { 2014 mCurrentProfiles.clear(); 2015 for (UserInfo user : profiles) { 2016 mCurrentProfiles.put(user.id, user); 2017 } 2018 } 2019 } 2020 } 2021 2022 /** 2023 * Returns the currently active users (generally one user and its work profile). 2024 */ getCurrentProfileIds()2025 public IntArray getCurrentProfileIds() { 2026 synchronized (mCurrentProfiles) { 2027 IntArray users = new IntArray(mCurrentProfiles.size()); 2028 final int N = mCurrentProfiles.size(); 2029 for (int i = 0; i < N; ++i) { 2030 users.add(mCurrentProfiles.keyAt(i)); 2031 } 2032 return users; 2033 } 2034 } 2035 isCurrentProfile(int userId)2036 public boolean isCurrentProfile(int userId) { 2037 synchronized (mCurrentProfiles) { 2038 return mCurrentProfiles.get(userId) != null; 2039 } 2040 } 2041 isProfileUser(int userId, Context context)2042 public boolean isProfileUser(int userId, Context context) { 2043 synchronized (mCurrentProfiles) { 2044 UserInfo user = mCurrentProfiles.get(userId); 2045 if (user == null) { 2046 return false; 2047 } 2048 if (privateSpaceFlagsEnabled()) { 2049 return user.isProfile() && hasParent(user, context); 2050 } 2051 return user.isManagedProfile() || user.isCloneProfile(); 2052 } 2053 } 2054 hasParent(UserInfo profile, Context context)2055 boolean hasParent(UserInfo profile, Context context) { 2056 final long identity = Binder.clearCallingIdentity(); 2057 try { 2058 UserManager um = context.getSystemService(UserManager.class); 2059 return um.getProfileParent(profile.id) != null; 2060 } finally { 2061 Binder.restoreCallingIdentity(identity); 2062 } 2063 } 2064 } 2065 2066 public static class Config { 2067 public String caption; 2068 public String serviceInterface; 2069 public String secureSettingName; 2070 public String secondarySettingName; 2071 public String xmlTag; 2072 public String bindPermission; 2073 public String settingsAction; 2074 public int clientLabel; 2075 } 2076 } 2077