UserManagerService.java revision 1d13eaea8380a43a31b12804f26d888f829feedf
1/* 2 * Copyright (C) 2011 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 17package com.android.server.pm; 18 19import static android.content.Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS; 20import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK; 21 22import android.Manifest; 23import android.annotation.NonNull; 24import android.annotation.Nullable; 25import android.annotation.UserIdInt; 26import android.app.Activity; 27import android.app.ActivityManager; 28import android.app.ActivityManagerInternal; 29import android.app.ActivityManagerNative; 30import android.app.IActivityManager; 31import android.app.IStopUserCallback; 32import android.app.KeyguardManager; 33import android.app.PendingIntent; 34import android.app.admin.DevicePolicyManager; 35import android.content.BroadcastReceiver; 36import android.content.Context; 37import android.content.Intent; 38import android.content.IntentFilter; 39import android.content.IntentSender; 40import android.content.pm.PackageManager; 41import android.content.pm.PackageManager.NameNotFoundException; 42import android.content.pm.ShortcutServiceInternal; 43import android.content.pm.UserInfo; 44import android.content.res.Resources; 45import android.graphics.Bitmap; 46import android.os.Binder; 47import android.os.Build; 48import android.os.Bundle; 49import android.os.Debug; 50import android.os.Environment; 51import android.os.FileUtils; 52import android.os.Handler; 53import android.os.IBinder; 54import android.os.IProgressListener; 55import android.os.IUserManager; 56import android.os.Message; 57import android.os.ParcelFileDescriptor; 58import android.os.Parcelable; 59import android.os.PersistableBundle; 60import android.os.Process; 61import android.os.RemoteException; 62import android.os.ResultReceiver; 63import android.os.SELinux; 64import android.os.ServiceManager; 65import android.os.ShellCallback; 66import android.os.ShellCommand; 67import android.os.SystemClock; 68import android.os.SystemProperties; 69import android.os.UserHandle; 70import android.os.UserManager; 71import android.os.UserManager.EnforcingUser; 72import android.os.UserManagerInternal; 73import android.os.UserManagerInternal.UserRestrictionsListener; 74import android.os.storage.StorageManager; 75import android.provider.Settings; 76import android.security.GateKeeper; 77import android.service.gatekeeper.IGateKeeperService; 78import android.util.AtomicFile; 79import android.util.IntArray; 80import android.util.Log; 81import android.util.Slog; 82import android.util.SparseArray; 83import android.util.SparseBooleanArray; 84import android.util.SparseIntArray; 85import android.util.SparseLongArray; 86import android.util.TimeUtils; 87import android.util.Xml; 88 89import com.android.internal.annotations.GuardedBy; 90import com.android.internal.annotations.VisibleForTesting; 91import com.android.internal.app.IAppOpsService; 92import com.android.internal.logging.MetricsLogger; 93import com.android.internal.os.BackgroundThread; 94import com.android.internal.util.DumpUtils; 95import com.android.internal.util.FastXmlSerializer; 96import com.android.internal.util.Preconditions; 97import com.android.internal.util.XmlUtils; 98import com.android.internal.widget.LockPatternUtils; 99import com.android.server.LocalServices; 100import com.android.server.LockGuard; 101import com.android.server.SystemService; 102import com.android.server.am.UserState; 103import com.android.server.storage.DeviceStorageMonitorInternal; 104 105import libcore.io.IoUtils; 106 107import org.xmlpull.v1.XmlPullParser; 108import org.xmlpull.v1.XmlPullParserException; 109import org.xmlpull.v1.XmlSerializer; 110 111import java.io.BufferedOutputStream; 112import java.io.File; 113import java.io.FileDescriptor; 114import java.io.FileInputStream; 115import java.io.FileNotFoundException; 116import java.io.FileOutputStream; 117import java.io.IOException; 118import java.io.InputStream; 119import java.io.OutputStream; 120import java.io.PrintWriter; 121import java.nio.charset.StandardCharsets; 122import java.util.ArrayList; 123import java.util.Collections; 124import java.util.LinkedList; 125import java.util.List; 126import java.util.Objects; 127 128/** 129 * Service for {@link UserManager}. 130 * 131 * Method naming convention: 132 * <ul> 133 * <li> Methods suffixed with "LAr" should be called within the {@link #mAppRestrictionsLock} lock. 134 * <li> Methods suffixed with "LP" should be called within the {@link #mPackagesLock} lock. 135 * <li> Methods suffixed with "LR" should be called within the {@link #mRestrictionsLock} lock. 136 * <li> Methods suffixed with "LU" should be called within the {@link #mUsersLock} lock. 137 * </ul> 138 */ 139public class UserManagerService extends IUserManager.Stub { 140 141 private static final String LOG_TAG = "UserManagerService"; 142 static final boolean DBG = false; // DO NOT SUBMIT WITH TRUE 143 private static final boolean DBG_WITH_STACKTRACE = false; // DO NOT SUBMIT WITH TRUE 144 // Can be used for manual testing of id recycling 145 private static final boolean RELEASE_DELETED_USER_ID = false; // DO NOT SUBMIT WITH TRUE 146 147 private static final String TAG_NAME = "name"; 148 private static final String TAG_ACCOUNT = "account"; 149 private static final String ATTR_FLAGS = "flags"; 150 private static final String ATTR_ICON_PATH = "icon"; 151 private static final String ATTR_ID = "id"; 152 private static final String ATTR_CREATION_TIME = "created"; 153 private static final String ATTR_LAST_LOGGED_IN_TIME = "lastLoggedIn"; 154 private static final String ATTR_LAST_LOGGED_IN_FINGERPRINT = "lastLoggedInFingerprint"; 155 private static final String ATTR_SERIAL_NO = "serialNumber"; 156 private static final String ATTR_NEXT_SERIAL_NO = "nextSerialNumber"; 157 private static final String ATTR_PARTIAL = "partial"; 158 private static final String ATTR_GUEST_TO_REMOVE = "guestToRemove"; 159 private static final String ATTR_USER_VERSION = "version"; 160 private static final String ATTR_PROFILE_GROUP_ID = "profileGroupId"; 161 private static final String ATTR_PROFILE_BADGE = "profileBadge"; 162 private static final String ATTR_RESTRICTED_PROFILE_PARENT_ID = "restrictedProfileParentId"; 163 private static final String ATTR_SEED_ACCOUNT_NAME = "seedAccountName"; 164 private static final String ATTR_SEED_ACCOUNT_TYPE = "seedAccountType"; 165 private static final String TAG_GUEST_RESTRICTIONS = "guestRestrictions"; 166 private static final String TAG_USERS = "users"; 167 private static final String TAG_USER = "user"; 168 private static final String TAG_RESTRICTIONS = "restrictions"; 169 private static final String TAG_DEVICE_POLICY_RESTRICTIONS = "device_policy_restrictions"; 170 private static final String TAG_DEVICE_POLICY_GLOBAL_RESTRICTIONS = 171 "device_policy_global_restrictions"; 172 /** Legacy name for device owner id tag. */ 173 private static final String TAG_GLOBAL_RESTRICTION_OWNER_ID = "globalRestrictionOwnerUserId"; 174 private static final String TAG_DEVICE_OWNER_USER_ID = "deviceOwnerUserId"; 175 private static final String TAG_ENTRY = "entry"; 176 private static final String TAG_VALUE = "value"; 177 private static final String TAG_SEED_ACCOUNT_OPTIONS = "seedAccountOptions"; 178 private static final String ATTR_KEY = "key"; 179 private static final String ATTR_VALUE_TYPE = "type"; 180 private static final String ATTR_MULTIPLE = "m"; 181 182 private static final String ATTR_TYPE_STRING_ARRAY = "sa"; 183 private static final String ATTR_TYPE_STRING = "s"; 184 private static final String ATTR_TYPE_BOOLEAN = "b"; 185 private static final String ATTR_TYPE_INTEGER = "i"; 186 private static final String ATTR_TYPE_BUNDLE = "B"; 187 private static final String ATTR_TYPE_BUNDLE_ARRAY = "BA"; 188 189 private static final String USER_INFO_DIR = "system" + File.separator + "users"; 190 private static final String USER_LIST_FILENAME = "userlist.xml"; 191 private static final String USER_PHOTO_FILENAME = "photo.png"; 192 private static final String USER_PHOTO_FILENAME_TMP = USER_PHOTO_FILENAME + ".tmp"; 193 194 private static final String RESTRICTIONS_FILE_PREFIX = "res_"; 195 private static final String XML_SUFFIX = ".xml"; 196 197 private static final int ALLOWED_FLAGS_FOR_CREATE_USERS_PERMISSION = 198 UserInfo.FLAG_MANAGED_PROFILE 199 | UserInfo.FLAG_EPHEMERAL 200 | UserInfo.FLAG_RESTRICTED 201 | UserInfo.FLAG_GUEST 202 | UserInfo.FLAG_DEMO; 203 204 @VisibleForTesting 205 static final int MIN_USER_ID = 10; 206 // We need to keep process uid within Integer.MAX_VALUE. 207 @VisibleForTesting 208 static final int MAX_USER_ID = Integer.MAX_VALUE / UserHandle.PER_USER_RANGE; 209 210 // Max size of the queue of recently removed users 211 @VisibleForTesting 212 static final int MAX_RECENTLY_REMOVED_IDS_SIZE = 100; 213 214 private static final int USER_VERSION = 7; 215 216 private static final long EPOCH_PLUS_30_YEARS = 30L * 365 * 24 * 60 * 60 * 1000L; // ms 217 218 // Maximum number of managed profiles permitted per user is 1. This cannot be increased 219 // without first making sure that the rest of the framework is prepared for it. 220 @VisibleForTesting 221 static final int MAX_MANAGED_PROFILES = 1; 222 223 static final int WRITE_USER_MSG = 1; 224 static final int WRITE_USER_DELAY = 2*1000; // 2 seconds 225 226 // Tron counters 227 private static final String TRON_GUEST_CREATED = "users_guest_created"; 228 private static final String TRON_USER_CREATED = "users_user_created"; 229 private static final String TRON_DEMO_CREATED = "users_demo_created"; 230 231 private final Context mContext; 232 private final PackageManagerService mPm; 233 private final Object mPackagesLock; 234 private final UserDataPreparer mUserDataPreparer; 235 // Short-term lock for internal state, when interaction/sync with PM is not required 236 private final Object mUsersLock = LockGuard.installNewLock(LockGuard.INDEX_USER); 237 private final Object mRestrictionsLock = new Object(); 238 // Used for serializing access to app restriction files 239 private final Object mAppRestrictionsLock = new Object(); 240 241 private final Handler mHandler; 242 243 private final File mUsersDir; 244 private final File mUserListFile; 245 246 private static final IBinder mUserRestriconToken = new Binder(); 247 248 /** 249 * Internal non-parcelable wrapper for UserInfo that is not exposed to other system apps. 250 */ 251 @VisibleForTesting 252 static class UserData { 253 // Basic user information and properties 254 UserInfo info; 255 // Account name used when there is a strong association between a user and an account 256 String account; 257 // Account information for seeding into a newly created user. This could also be 258 // used for login validation for an existing user, for updating their credentials. 259 // In the latter case, data may not need to be persisted as it is only valid for the 260 // current login session. 261 String seedAccountName; 262 String seedAccountType; 263 PersistableBundle seedAccountOptions; 264 // Whether to perist the seed account information to be available after a boot 265 boolean persistSeedData; 266 267 /** Elapsed realtime since boot when the user started. */ 268 long startRealtime; 269 270 /** Elapsed realtime since boot when the user was unlocked. */ 271 long unlockRealtime; 272 273 void clearSeedAccountData() { 274 seedAccountName = null; 275 seedAccountType = null; 276 seedAccountOptions = null; 277 persistSeedData = false; 278 } 279 } 280 281 @GuardedBy("mUsersLock") 282 private final SparseArray<UserData> mUsers = new SparseArray<>(); 283 284 /** 285 * User restrictions set via UserManager. This doesn't include restrictions set by 286 * device owner / profile owners. Only non-empty restriction bundles are stored. 287 * 288 * DO NOT Change existing {@link Bundle} in it. When changing a restriction for a user, 289 * a new {@link Bundle} should always be created and set. This is because a {@link Bundle} 290 * maybe shared between {@link #mBaseUserRestrictions} and 291 * {@link #mCachedEffectiveUserRestrictions}, but they should always updated separately. 292 * (Otherwise we won't be able to detect what restrictions have changed in 293 * {@link #updateUserRestrictionsInternalLR}. 294 */ 295 @GuardedBy("mRestrictionsLock") 296 private final SparseArray<Bundle> mBaseUserRestrictions = new SparseArray<>(); 297 298 /** 299 * Cached user restrictions that are in effect -- i.e. {@link #mBaseUserRestrictions} combined 300 * with device / profile owner restrictions. We'll initialize it lazily; use 301 * {@link #getEffectiveUserRestrictions} to access it. 302 * 303 * DO NOT Change existing {@link Bundle} in it. When changing a restriction for a user, 304 * a new {@link Bundle} should always be created and set. This is because a {@link Bundle} 305 * maybe shared between {@link #mBaseUserRestrictions} and 306 * {@link #mCachedEffectiveUserRestrictions}, but they should always updated separately. 307 * (Otherwise we won't be able to detect what restrictions have changed in 308 * {@link #updateUserRestrictionsInternalLR}. 309 */ 310 @GuardedBy("mRestrictionsLock") 311 private final SparseArray<Bundle> mCachedEffectiveUserRestrictions = new SparseArray<>(); 312 313 /** 314 * User restrictions that have already been applied in 315 * {@link #updateUserRestrictionsInternalLR(Bundle, int)}. We use it to detect restrictions 316 * that have changed since the last 317 * {@link #updateUserRestrictionsInternalLR(Bundle, int)} call. 318 */ 319 @GuardedBy("mRestrictionsLock") 320 private final SparseArray<Bundle> mAppliedUserRestrictions = new SparseArray<>(); 321 322 /** 323 * User restrictions set by {@link com.android.server.devicepolicy.DevicePolicyManagerService} 324 * that should be applied to all users, including guests. Only non-empty restriction bundles are 325 * stored. 326 */ 327 @GuardedBy("mRestrictionsLock") 328 private final SparseArray<Bundle> mDevicePolicyGlobalUserRestrictions = new SparseArray<>(); 329 330 /** 331 * Id of the user that set global restrictions. 332 */ 333 @GuardedBy("mRestrictionsLock") 334 private int mDeviceOwnerUserId = UserHandle.USER_NULL; 335 336 /** 337 * User restrictions set by {@link com.android.server.devicepolicy.DevicePolicyManagerService} 338 * for each user. Only non-empty restriction bundles are stored. 339 */ 340 @GuardedBy("mRestrictionsLock") 341 private final SparseArray<Bundle> mDevicePolicyLocalUserRestrictions = new SparseArray<>(); 342 343 @GuardedBy("mGuestRestrictions") 344 private final Bundle mGuestRestrictions = new Bundle(); 345 346 /** 347 * Set of user IDs being actively removed. Removed IDs linger in this set 348 * for several seconds to work around a VFS caching issue. 349 * Use {@link #addRemovingUserIdLocked(int)} to add elements to this array 350 */ 351 @GuardedBy("mUsersLock") 352 private final SparseBooleanArray mRemovingUserIds = new SparseBooleanArray(); 353 354 /** 355 * Queue of recently removed userIds. Used for recycling of userIds 356 */ 357 @GuardedBy("mUsersLock") 358 private final LinkedList<Integer> mRecentlyRemovedIds = new LinkedList<>(); 359 360 @GuardedBy("mUsersLock") 361 private int[] mUserIds; 362 @GuardedBy("mPackagesLock") 363 private int mNextSerialNumber; 364 private int mUserVersion = 0; 365 366 private IAppOpsService mAppOpsService; 367 368 private final LocalService mLocalService; 369 370 @GuardedBy("mUsersLock") 371 private boolean mIsDeviceManaged; 372 373 @GuardedBy("mUsersLock") 374 private final SparseBooleanArray mIsUserManaged = new SparseBooleanArray(); 375 376 @GuardedBy("mUserRestrictionsListeners") 377 private final ArrayList<UserRestrictionsListener> mUserRestrictionsListeners = 378 new ArrayList<>(); 379 380 private final LockPatternUtils mLockPatternUtils; 381 382 private final String ACTION_DISABLE_QUIET_MODE_AFTER_UNLOCK = 383 "com.android.server.pm.DISABLE_QUIET_MODE_AFTER_UNLOCK"; 384 385 private final BroadcastReceiver mDisableQuietModeCallback = new BroadcastReceiver() { 386 @Override 387 public void onReceive(Context context, Intent intent) { 388 if (!ACTION_DISABLE_QUIET_MODE_AFTER_UNLOCK.equals(intent.getAction())) { 389 return; 390 } 391 final IntentSender target = intent.getParcelableExtra(Intent.EXTRA_INTENT); 392 final int userHandle = intent.getIntExtra(Intent.EXTRA_USER_ID, UserHandle.USER_NULL); 393 // Call setQuietModeEnabled on bg thread to avoid ANR 394 BackgroundThread.getHandler() 395 .post(() -> setQuietModeEnabled(userHandle, false, target)); 396 } 397 }; 398 399 /** 400 * Start an {@link IntentSender} when user is unlocked after disabling quiet mode. 401 * 402 * @see {@link #requestQuietModeEnabled(String, boolean, int, IntentSender)} 403 */ 404 private class DisableQuietModeUserUnlockedCallback extends IProgressListener.Stub { 405 private final IntentSender mTarget; 406 407 public DisableQuietModeUserUnlockedCallback(IntentSender target) { 408 Preconditions.checkNotNull(target); 409 mTarget = target; 410 } 411 412 @Override 413 public void onStarted(int id, Bundle extras) {} 414 415 @Override 416 public void onProgress(int id, int progress, Bundle extras) {} 417 418 @Override 419 public void onFinished(int id, Bundle extras) { 420 try { 421 mContext.startIntentSender(mTarget, null, 0, 0, 0); 422 } catch (IntentSender.SendIntentException e) { 423 Slog.e(LOG_TAG, "Failed to start the target in the callback", e); 424 } 425 } 426 } 427 428 /** 429 * Whether all users should be created ephemeral. 430 */ 431 @GuardedBy("mUsersLock") 432 private boolean mForceEphemeralUsers; 433 434 @GuardedBy("mUserStates") 435 private final SparseIntArray mUserStates = new SparseIntArray(); 436 437 private static UserManagerService sInstance; 438 439 public static UserManagerService getInstance() { 440 synchronized (UserManagerService.class) { 441 return sInstance; 442 } 443 } 444 445 public static class LifeCycle extends SystemService { 446 447 private UserManagerService mUms; 448 449 /** 450 * @param context 451 */ 452 public LifeCycle(Context context) { 453 super(context); 454 } 455 456 @Override 457 public void onStart() { 458 mUms = UserManagerService.getInstance(); 459 publishBinderService(Context.USER_SERVICE, mUms); 460 } 461 462 @Override 463 public void onBootPhase(int phase) { 464 if (phase == SystemService.PHASE_ACTIVITY_MANAGER_READY) { 465 mUms.cleanupPartialUsers(); 466 } 467 } 468 469 @Override 470 public void onStartUser(int userHandle) { 471 synchronized (mUms.mUsersLock) { 472 final UserData user = mUms.getUserDataLU(userHandle); 473 if (user != null) { 474 user.startRealtime = SystemClock.elapsedRealtime(); 475 } 476 } 477 } 478 479 @Override 480 public void onUnlockUser(int userHandle) { 481 synchronized (mUms.mUsersLock) { 482 final UserData user = mUms.getUserDataLU(userHandle); 483 if (user != null) { 484 user.unlockRealtime = SystemClock.elapsedRealtime(); 485 } 486 } 487 } 488 489 @Override 490 public void onStopUser(int userHandle) { 491 synchronized (mUms.mUsersLock) { 492 final UserData user = mUms.getUserDataLU(userHandle); 493 if (user != null) { 494 user.startRealtime = 0; 495 user.unlockRealtime = 0; 496 } 497 } 498 } 499 } 500 501 // TODO b/28848102 Add support for test dependencies injection 502 @VisibleForTesting 503 UserManagerService(Context context) { 504 this(context, null, null, new Object(), context.getCacheDir()); 505 } 506 507 /** 508 * Called by package manager to create the service. This is closely 509 * associated with the package manager, and the given lock is the 510 * package manager's own lock. 511 */ 512 UserManagerService(Context context, PackageManagerService pm, UserDataPreparer userDataPreparer, 513 Object packagesLock) { 514 this(context, pm, userDataPreparer, packagesLock, Environment.getDataDirectory()); 515 } 516 517 private UserManagerService(Context context, PackageManagerService pm, 518 UserDataPreparer userDataPreparer, Object packagesLock, File dataDir) { 519 mContext = context; 520 mPm = pm; 521 mPackagesLock = packagesLock; 522 mHandler = new MainHandler(); 523 mUserDataPreparer = userDataPreparer; 524 synchronized (mPackagesLock) { 525 mUsersDir = new File(dataDir, USER_INFO_DIR); 526 mUsersDir.mkdirs(); 527 // Make zeroth user directory, for services to migrate their files to that location 528 File userZeroDir = new File(mUsersDir, String.valueOf(UserHandle.USER_SYSTEM)); 529 userZeroDir.mkdirs(); 530 FileUtils.setPermissions(mUsersDir.toString(), 531 FileUtils.S_IRWXU | FileUtils.S_IRWXG | FileUtils.S_IROTH | FileUtils.S_IXOTH, 532 -1, -1); 533 mUserListFile = new File(mUsersDir, USER_LIST_FILENAME); 534 initDefaultGuestRestrictions(); 535 readUserListLP(); 536 sInstance = this; 537 } 538 mLocalService = new LocalService(); 539 LocalServices.addService(UserManagerInternal.class, mLocalService); 540 mLockPatternUtils = new LockPatternUtils(mContext); 541 mUserStates.put(UserHandle.USER_SYSTEM, UserState.STATE_BOOTING); 542 } 543 544 void systemReady() { 545 mAppOpsService = IAppOpsService.Stub.asInterface( 546 ServiceManager.getService(Context.APP_OPS_SERVICE)); 547 548 synchronized (mRestrictionsLock) { 549 applyUserRestrictionsLR(UserHandle.USER_SYSTEM); 550 } 551 552 UserInfo currentGuestUser = findCurrentGuestUser(); 553 if (currentGuestUser != null && !hasUserRestriction( 554 UserManager.DISALLOW_CONFIG_WIFI, currentGuestUser.id)) { 555 // If a guest user currently exists, apply the DISALLOW_CONFIG_WIFI option 556 // to it, in case this guest was created in a previous version where this 557 // user restriction was not a default guest restriction. 558 setUserRestriction(UserManager.DISALLOW_CONFIG_WIFI, true, currentGuestUser.id); 559 } 560 561 mContext.registerReceiver(mDisableQuietModeCallback, 562 new IntentFilter(ACTION_DISABLE_QUIET_MODE_AFTER_UNLOCK), 563 null, mHandler); 564 } 565 566 void cleanupPartialUsers() { 567 // Prune out any partially created, partially removed and ephemeral users. 568 ArrayList<UserInfo> partials = new ArrayList<>(); 569 synchronized (mUsersLock) { 570 final int userSize = mUsers.size(); 571 for (int i = 0; i < userSize; i++) { 572 UserInfo ui = mUsers.valueAt(i).info; 573 if ((ui.partial || ui.guestToRemove || ui.isEphemeral()) && i != 0) { 574 partials.add(ui); 575 addRemovingUserIdLocked(ui.id); 576 ui.partial = true; 577 } 578 } 579 } 580 final int partialsSize = partials.size(); 581 for (int i = 0; i < partialsSize; i++) { 582 UserInfo ui = partials.get(i); 583 Slog.w(LOG_TAG, "Removing partially created user " + ui.id 584 + " (name=" + ui.name + ")"); 585 removeUserState(ui.id); 586 } 587 } 588 589 @Override 590 public String getUserAccount(int userId) { 591 checkManageUserAndAcrossUsersFullPermission("get user account"); 592 synchronized (mUsersLock) { 593 return mUsers.get(userId).account; 594 } 595 } 596 597 @Override 598 public void setUserAccount(int userId, String accountName) { 599 checkManageUserAndAcrossUsersFullPermission("set user account"); 600 UserData userToUpdate = null; 601 synchronized (mPackagesLock) { 602 synchronized (mUsersLock) { 603 final UserData userData = mUsers.get(userId); 604 if (userData == null) { 605 Slog.e(LOG_TAG, "User not found for setting user account: u" + userId); 606 return; 607 } 608 String currentAccount = userData.account; 609 if (!Objects.equals(currentAccount, accountName)) { 610 userData.account = accountName; 611 userToUpdate = userData; 612 } 613 } 614 615 if (userToUpdate != null) { 616 writeUserLP(userToUpdate); 617 } 618 } 619 } 620 621 @Override 622 public UserInfo getPrimaryUser() { 623 checkManageUsersPermission("query users"); 624 synchronized (mUsersLock) { 625 final int userSize = mUsers.size(); 626 for (int i = 0; i < userSize; i++) { 627 UserInfo ui = mUsers.valueAt(i).info; 628 if (ui.isPrimary() && !mRemovingUserIds.get(ui.id)) { 629 return ui; 630 } 631 } 632 } 633 return null; 634 } 635 636 @Override 637 public @NonNull List<UserInfo> getUsers(boolean excludeDying) { 638 checkManageOrCreateUsersPermission("query users"); 639 synchronized (mUsersLock) { 640 ArrayList<UserInfo> users = new ArrayList<UserInfo>(mUsers.size()); 641 final int userSize = mUsers.size(); 642 for (int i = 0; i < userSize; i++) { 643 UserInfo ui = mUsers.valueAt(i).info; 644 if (ui.partial) { 645 continue; 646 } 647 if (!excludeDying || !mRemovingUserIds.get(ui.id)) { 648 users.add(userWithName(ui)); 649 } 650 } 651 return users; 652 } 653 } 654 655 @Override 656 public List<UserInfo> getProfiles(int userId, boolean enabledOnly) { 657 boolean returnFullInfo = true; 658 if (userId != UserHandle.getCallingUserId()) { 659 checkManageOrCreateUsersPermission("getting profiles related to user " + userId); 660 } else { 661 returnFullInfo = hasManageUsersPermission(); 662 } 663 final long ident = Binder.clearCallingIdentity(); 664 try { 665 synchronized (mUsersLock) { 666 return getProfilesLU(userId, enabledOnly, returnFullInfo); 667 } 668 } finally { 669 Binder.restoreCallingIdentity(ident); 670 } 671 } 672 673 @Override 674 public int[] getProfileIds(int userId, boolean enabledOnly) { 675 if (userId != UserHandle.getCallingUserId()) { 676 checkManageOrCreateUsersPermission("getting profiles related to user " + userId); 677 } 678 final long ident = Binder.clearCallingIdentity(); 679 try { 680 synchronized (mUsersLock) { 681 return getProfileIdsLU(userId, enabledOnly).toArray(); 682 } 683 } finally { 684 Binder.restoreCallingIdentity(ident); 685 } 686 } 687 688 /** Assume permissions already checked and caller's identity cleared */ 689 private List<UserInfo> getProfilesLU(int userId, boolean enabledOnly, boolean fullInfo) { 690 IntArray profileIds = getProfileIdsLU(userId, enabledOnly); 691 ArrayList<UserInfo> users = new ArrayList<>(profileIds.size()); 692 for (int i = 0; i < profileIds.size(); i++) { 693 int profileId = profileIds.get(i); 694 UserInfo userInfo = mUsers.get(profileId).info; 695 // If full info is not required - clear PII data to prevent 3P apps from reading it 696 if (!fullInfo) { 697 userInfo = new UserInfo(userInfo); 698 userInfo.name = null; 699 userInfo.iconPath = null; 700 } else { 701 userInfo = userWithName(userInfo); 702 } 703 users.add(userInfo); 704 } 705 return users; 706 } 707 708 /** 709 * Assume permissions already checked and caller's identity cleared 710 */ 711 private IntArray getProfileIdsLU(int userId, boolean enabledOnly) { 712 UserInfo user = getUserInfoLU(userId); 713 IntArray result = new IntArray(mUsers.size()); 714 if (user == null) { 715 // Probably a dying user 716 return result; 717 } 718 final int userSize = mUsers.size(); 719 for (int i = 0; i < userSize; i++) { 720 UserInfo profile = mUsers.valueAt(i).info; 721 if (!isProfileOf(user, profile)) { 722 continue; 723 } 724 if (enabledOnly && !profile.isEnabled()) { 725 continue; 726 } 727 if (mRemovingUserIds.get(profile.id)) { 728 continue; 729 } 730 if (profile.partial) { 731 continue; 732 } 733 result.add(profile.id); 734 } 735 return result; 736 } 737 738 @Override 739 public int getCredentialOwnerProfile(int userHandle) { 740 checkManageUsersPermission("get the credential owner"); 741 if (!mLockPatternUtils.isSeparateProfileChallengeEnabled(userHandle)) { 742 synchronized (mUsersLock) { 743 UserInfo profileParent = getProfileParentLU(userHandle); 744 if (profileParent != null) { 745 return profileParent.id; 746 } 747 } 748 } 749 750 return userHandle; 751 } 752 753 @Override 754 public boolean isSameProfileGroup(int userId, int otherUserId) { 755 if (userId == otherUserId) return true; 756 checkManageUsersPermission("check if in the same profile group"); 757 return isSameProfileGroupNoChecks(userId, otherUserId); 758 } 759 760 private boolean isSameProfileGroupNoChecks(int userId, int otherUserId) { 761 synchronized (mUsersLock) { 762 UserInfo userInfo = getUserInfoLU(userId); 763 if (userInfo == null || userInfo.profileGroupId == UserInfo.NO_PROFILE_GROUP_ID) { 764 return false; 765 } 766 UserInfo otherUserInfo = getUserInfoLU(otherUserId); 767 if (otherUserInfo == null 768 || otherUserInfo.profileGroupId == UserInfo.NO_PROFILE_GROUP_ID) { 769 return false; 770 } 771 return userInfo.profileGroupId == otherUserInfo.profileGroupId; 772 } 773 } 774 775 @Override 776 public UserInfo getProfileParent(int userHandle) { 777 checkManageUsersPermission("get the profile parent"); 778 synchronized (mUsersLock) { 779 return getProfileParentLU(userHandle); 780 } 781 } 782 783 @Override 784 public int getProfileParentId(int userHandle) { 785 checkManageUsersPermission("get the profile parent"); 786 return mLocalService.getProfileParentId(userHandle); 787 } 788 789 private UserInfo getProfileParentLU(int userHandle) { 790 UserInfo profile = getUserInfoLU(userHandle); 791 if (profile == null) { 792 return null; 793 } 794 int parentUserId = profile.profileGroupId; 795 if (parentUserId == userHandle || parentUserId == UserInfo.NO_PROFILE_GROUP_ID) { 796 return null; 797 } else { 798 return getUserInfoLU(parentUserId); 799 } 800 } 801 802 private static boolean isProfileOf(UserInfo user, UserInfo profile) { 803 return user.id == profile.id || 804 (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID 805 && user.profileGroupId == profile.profileGroupId); 806 } 807 808 private void broadcastProfileAvailabilityChanges(UserHandle profileHandle, 809 UserHandle parentHandle, boolean inQuietMode) { 810 Intent intent = new Intent(); 811 if (inQuietMode) { 812 intent.setAction(Intent.ACTION_MANAGED_PROFILE_UNAVAILABLE); 813 } else { 814 intent.setAction(Intent.ACTION_MANAGED_PROFILE_AVAILABLE); 815 } 816 intent.putExtra(Intent.EXTRA_QUIET_MODE, inQuietMode); 817 intent.putExtra(Intent.EXTRA_USER, profileHandle); 818 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileHandle.getIdentifier()); 819 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 820 mContext.sendBroadcastAsUser(intent, parentHandle); 821 } 822 823 @Override 824 public boolean requestQuietModeEnabled(@NonNull String callingPackage, boolean enableQuietMode, 825 int userHandle, @Nullable IntentSender target) { 826 Preconditions.checkNotNull(callingPackage); 827 828 if (enableQuietMode && target != null) { 829 throw new IllegalArgumentException( 830 "target should only be specified when we are disabling quiet mode."); 831 } 832 833 ensureCanModifyQuietMode(callingPackage, Binder.getCallingUid(), target != null); 834 final long identity = Binder.clearCallingIdentity(); 835 try { 836 if (enableQuietMode) { 837 setQuietModeEnabled(userHandle, true /* enableQuietMode */, target); 838 return true; 839 } else { 840 boolean needToShowConfirmCredential = 841 mLockPatternUtils.isSecure(userHandle) 842 && !StorageManager.isUserKeyUnlocked(userHandle); 843 if (needToShowConfirmCredential) { 844 showConfirmCredentialToDisableQuietMode(userHandle, target); 845 return false; 846 } else { 847 setQuietModeEnabled(userHandle, false /* enableQuietMode */, target); 848 return true; 849 } 850 } 851 } finally { 852 Binder.restoreCallingIdentity(identity); 853 } 854 } 855 856 /** 857 * The caller can modify quiet mode if it meets one of these conditions: 858 * <ul> 859 * <li>Has system UID or root UID</li> 860 * <li>Has {@link Manifest.permission#MODIFY_QUIET_MODE}</li> 861 * <li>Has {@link Manifest.permission#MANAGE_USERS}</li> 862 * </ul> 863 * <p> 864 * If caller wants to start an intent after disabling the quiet mode, it must has 865 * {@link Manifest.permission#MANAGE_USERS}. 866 */ 867 private void ensureCanModifyQuietMode(String callingPackage, int callingUid, 868 boolean startIntent) { 869 if (hasManageUsersPermission()) { 870 return; 871 } 872 if (startIntent) { 873 throw new SecurityException("MANAGE_USERS permission is required to start intent " 874 + "after disabling quiet mode."); 875 } 876 final boolean hasModifyQuietModePermission = ActivityManager.checkComponentPermission( 877 Manifest.permission.MODIFY_QUIET_MODE, 878 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED; 879 if (hasModifyQuietModePermission) { 880 return; 881 } 882 883 verifyCallingPackage(callingPackage, callingUid); 884 final ShortcutServiceInternal shortcutInternal = 885 LocalServices.getService(ShortcutServiceInternal.class); 886 if (shortcutInternal != null) { 887 boolean isForegroundLauncher = 888 shortcutInternal.isForegroundDefaultLauncher(callingPackage, callingUid); 889 if (isForegroundLauncher) { 890 return; 891 } 892 } 893 throw new SecurityException("Can't modify quiet mode, caller is neither foreground " 894 + "default launcher nor has MANAGE_USERS/MODIFY_QUIET_MODE permission"); 895 } 896 897 private void setQuietModeEnabled( 898 int userHandle, boolean enableQuietMode, IntentSender target) { 899 final UserInfo profile, parent; 900 final UserData profileUserData; 901 synchronized (mUsersLock) { 902 profile = getUserInfoLU(userHandle); 903 parent = getProfileParentLU(userHandle); 904 905 if (profile == null || !profile.isManagedProfile()) { 906 throw new IllegalArgumentException("User " + userHandle + " is not a profile"); 907 } 908 if (profile.isQuietModeEnabled() == enableQuietMode) { 909 Slog.i(LOG_TAG, "Quiet mode is already " + enableQuietMode); 910 return; 911 } 912 profile.flags ^= UserInfo.FLAG_QUIET_MODE; 913 profileUserData = getUserDataLU(profile.id); 914 } 915 synchronized (mPackagesLock) { 916 writeUserLP(profileUserData); 917 } 918 try { 919 if (enableQuietMode) { 920 ActivityManager.getService().stopUser(userHandle, /* force */true, null); 921 LocalServices.getService(ActivityManagerInternal.class) 922 .killForegroundAppsForUser(userHandle); 923 } else { 924 IProgressListener callback = target != null 925 ? new DisableQuietModeUserUnlockedCallback(target) 926 : null; 927 ActivityManager.getService().startUserInBackgroundWithListener( 928 userHandle, callback); 929 } 930 } catch (RemoteException e) { 931 // Should not happen, same process. 932 e.rethrowAsRuntimeException(); 933 } 934 broadcastProfileAvailabilityChanges(profile.getUserHandle(), parent.getUserHandle(), 935 enableQuietMode); 936 } 937 938 @Override 939 public boolean isQuietModeEnabled(int userHandle) { 940 synchronized (mPackagesLock) { 941 UserInfo info; 942 synchronized (mUsersLock) { 943 info = getUserInfoLU(userHandle); 944 } 945 if (info == null || !info.isManagedProfile()) { 946 return false; 947 } 948 return info.isQuietModeEnabled(); 949 } 950 } 951 952 /** 953 * Show confirm credential screen to unlock user in order to turn off quiet mode. 954 */ 955 private void showConfirmCredentialToDisableQuietMode( 956 @UserIdInt int userHandle, @Nullable IntentSender target) { 957 // otherwise, we show a profile challenge to trigger decryption of the user 958 final KeyguardManager km = (KeyguardManager) mContext.getSystemService( 959 Context.KEYGUARD_SERVICE); 960 // We should use userHandle not credentialOwnerUserId here, as even if it is unified 961 // lock, confirm screenlock page will know and show personal challenge, and unlock 962 // work profile when personal challenge is correct 963 final Intent unlockIntent = km.createConfirmDeviceCredentialIntent(null, null, 964 userHandle); 965 if (unlockIntent == null) { 966 return; 967 } 968 final Intent callBackIntent = new Intent( 969 ACTION_DISABLE_QUIET_MODE_AFTER_UNLOCK); 970 if (target != null) { 971 callBackIntent.putExtra(Intent.EXTRA_INTENT, target); 972 } 973 callBackIntent.putExtra(Intent.EXTRA_USER_ID, userHandle); 974 callBackIntent.setPackage(mContext.getPackageName()); 975 callBackIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 976 final PendingIntent pendingIntent = PendingIntent.getBroadcast( 977 mContext, 978 0, 979 callBackIntent, 980 PendingIntent.FLAG_CANCEL_CURRENT | 981 PendingIntent.FLAG_ONE_SHOT | 982 PendingIntent.FLAG_IMMUTABLE); 983 // After unlocking the challenge, it will disable quiet mode and run the original 984 // intentSender 985 unlockIntent.putExtra(Intent.EXTRA_INTENT, pendingIntent.getIntentSender()); 986 unlockIntent.setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 987 mContext.startActivity(unlockIntent); 988 } 989 990 @Override 991 public void setUserEnabled(int userId) { 992 checkManageUsersPermission("enable user"); 993 synchronized (mPackagesLock) { 994 UserInfo info; 995 synchronized (mUsersLock) { 996 info = getUserInfoLU(userId); 997 } 998 if (info != null && !info.isEnabled()) { 999 info.flags ^= UserInfo.FLAG_DISABLED; 1000 writeUserLP(getUserDataLU(info.id)); 1001 } 1002 } 1003 } 1004 1005 /** 1006 * Evicts a user's CE key by stopping and restarting the user. 1007 * 1008 * The key is evicted automatically by the user controller when the user has stopped. 1009 */ 1010 @Override 1011 public void evictCredentialEncryptionKey(@UserIdInt int userId) { 1012 checkManageUsersPermission("evict CE key"); 1013 final IActivityManager am = ActivityManagerNative.getDefault(); 1014 final long identity = Binder.clearCallingIdentity(); 1015 try { 1016 am.restartUserInBackground(userId); 1017 } catch (RemoteException re) { 1018 throw re.rethrowAsRuntimeException(); 1019 } finally { 1020 Binder.restoreCallingIdentity(identity); 1021 } 1022 } 1023 1024 @Override 1025 public UserInfo getUserInfo(int userId) { 1026 checkManageOrCreateUsersPermission("query user"); 1027 synchronized (mUsersLock) { 1028 return userWithName(getUserInfoLU(userId)); 1029 } 1030 } 1031 1032 /** 1033 * Returns a UserInfo object with the name filled in, for Owner, or the original 1034 * if the name is already set. 1035 */ 1036 private UserInfo userWithName(UserInfo orig) { 1037 if (orig != null && orig.name == null && orig.id == UserHandle.USER_SYSTEM) { 1038 UserInfo withName = new UserInfo(orig); 1039 withName.name = getOwnerName(); 1040 return withName; 1041 } else { 1042 return orig; 1043 } 1044 } 1045 1046 @Override 1047 public int getManagedProfileBadge(@UserIdInt int userId) { 1048 int callingUserId = UserHandle.getCallingUserId(); 1049 if (callingUserId != userId && !hasManageUsersPermission()) { 1050 if (!isSameProfileGroupNoChecks(callingUserId, userId)) { 1051 throw new SecurityException( 1052 "You need MANAGE_USERS permission to: check if specified user a " + 1053 "managed profile outside your profile group"); 1054 } 1055 } 1056 synchronized (mUsersLock) { 1057 UserInfo userInfo = getUserInfoLU(userId); 1058 return userInfo != null ? userInfo.profileBadge : 0; 1059 } 1060 } 1061 1062 @Override 1063 public boolean isManagedProfile(int userId) { 1064 int callingUserId = UserHandle.getCallingUserId(); 1065 if (callingUserId != userId && !hasManageUsersPermission()) { 1066 if (!isSameProfileGroupNoChecks(callingUserId, userId)) { 1067 throw new SecurityException( 1068 "You need MANAGE_USERS permission to: check if specified user a " + 1069 "managed profile outside your profile group"); 1070 } 1071 } 1072 synchronized (mUsersLock) { 1073 UserInfo userInfo = getUserInfoLU(userId); 1074 return userInfo != null && userInfo.isManagedProfile(); 1075 } 1076 } 1077 1078 @Override 1079 public boolean isUserUnlockingOrUnlocked(int userId) { 1080 checkManageOrInteractPermIfCallerInOtherProfileGroup(userId, "isUserUnlockingOrUnlocked"); 1081 return mLocalService.isUserUnlockingOrUnlocked(userId); 1082 } 1083 1084 @Override 1085 public boolean isUserUnlocked(int userId) { 1086 checkManageOrInteractPermIfCallerInOtherProfileGroup(userId, "isUserUnlocked"); 1087 return mLocalService.isUserUnlocked(userId); 1088 } 1089 1090 @Override 1091 public boolean isUserRunning(int userId) { 1092 checkManageOrInteractPermIfCallerInOtherProfileGroup(userId, "isUserRunning"); 1093 return mLocalService.isUserRunning(userId); 1094 } 1095 1096 @Override 1097 public long getUserStartRealtime() { 1098 final int userId = UserHandle.getUserId(Binder.getCallingUid()); 1099 synchronized (mUsersLock) { 1100 final UserData user = getUserDataLU(userId); 1101 if (user != null) { 1102 return user.startRealtime; 1103 } 1104 return 0; 1105 } 1106 } 1107 1108 @Override 1109 public long getUserUnlockRealtime() { 1110 synchronized (mUsersLock) { 1111 final UserData user = getUserDataLU(UserHandle.getUserId(Binder.getCallingUid())); 1112 if (user != null) { 1113 return user.unlockRealtime; 1114 } 1115 return 0; 1116 } 1117 } 1118 1119 private void checkManageOrInteractPermIfCallerInOtherProfileGroup(int userId, String name) { 1120 int callingUserId = UserHandle.getCallingUserId(); 1121 if (callingUserId == userId || isSameProfileGroupNoChecks(callingUserId, userId) || 1122 hasManageUsersPermission()) { 1123 return; 1124 } 1125 if (ActivityManager.checkComponentPermission(Manifest.permission.INTERACT_ACROSS_USERS, 1126 Binder.getCallingUid(), -1, true) != PackageManager.PERMISSION_GRANTED) { 1127 throw new SecurityException("You need INTERACT_ACROSS_USERS or MANAGE_USERS permission " 1128 + "to: check " + name); 1129 } 1130 } 1131 1132 @Override 1133 public boolean isDemoUser(int userId) { 1134 int callingUserId = UserHandle.getCallingUserId(); 1135 if (callingUserId != userId && !hasManageUsersPermission()) { 1136 throw new SecurityException("You need MANAGE_USERS permission to query if u=" + userId 1137 + " is a demo user"); 1138 } 1139 synchronized (mUsersLock) { 1140 UserInfo userInfo = getUserInfoLU(userId); 1141 return userInfo != null && userInfo.isDemo(); 1142 } 1143 } 1144 1145 @Override 1146 public boolean isRestricted() { 1147 synchronized (mUsersLock) { 1148 return getUserInfoLU(UserHandle.getCallingUserId()).isRestricted(); 1149 } 1150 } 1151 1152 @Override 1153 public boolean canHaveRestrictedProfile(int userId) { 1154 checkManageUsersPermission("canHaveRestrictedProfile"); 1155 synchronized (mUsersLock) { 1156 final UserInfo userInfo = getUserInfoLU(userId); 1157 if (userInfo == null || !userInfo.canHaveProfile()) { 1158 return false; 1159 } 1160 if (!userInfo.isAdmin()) { 1161 return false; 1162 } 1163 // restricted profile can be created if there is no DO set and the admin user has no PO; 1164 return !mIsDeviceManaged && !mIsUserManaged.get(userId); 1165 } 1166 } 1167 1168 @Override 1169 public boolean hasRestrictedProfiles() { 1170 checkManageUsersPermission("hasRestrictedProfiles"); 1171 final int callingUserId = UserHandle.getCallingUserId(); 1172 synchronized (mUsersLock) { 1173 final int userSize = mUsers.size(); 1174 for (int i = 0; i < userSize; i++) { 1175 UserInfo profile = mUsers.valueAt(i).info; 1176 if (callingUserId != profile.id 1177 && profile.restrictedProfileParentId == callingUserId) { 1178 return true; 1179 } 1180 } 1181 return false; 1182 } 1183 } 1184 1185 /* 1186 * Should be locked on mUsers before calling this. 1187 */ 1188 private UserInfo getUserInfoLU(int userId) { 1189 final UserData userData = mUsers.get(userId); 1190 // If it is partial and not in the process of being removed, return as unknown user. 1191 if (userData != null && userData.info.partial && !mRemovingUserIds.get(userId)) { 1192 Slog.w(LOG_TAG, "getUserInfo: unknown user #" + userId); 1193 return null; 1194 } 1195 return userData != null ? userData.info : null; 1196 } 1197 1198 private UserData getUserDataLU(int userId) { 1199 final UserData userData = mUsers.get(userId); 1200 // If it is partial and not in the process of being removed, return as unknown user. 1201 if (userData != null && userData.info.partial && !mRemovingUserIds.get(userId)) { 1202 return null; 1203 } 1204 return userData; 1205 } 1206 1207 /** 1208 * Obtains {@link #mUsersLock} and return UserInfo from mUsers. 1209 * <p>No permissions checking or any addition checks are made</p> 1210 */ 1211 private UserInfo getUserInfoNoChecks(int userId) { 1212 synchronized (mUsersLock) { 1213 final UserData userData = mUsers.get(userId); 1214 return userData != null ? userData.info : null; 1215 } 1216 } 1217 1218 /** 1219 * Obtains {@link #mUsersLock} and return UserData from mUsers. 1220 * <p>No permissions checking or any addition checks are made</p> 1221 */ 1222 private UserData getUserDataNoChecks(int userId) { 1223 synchronized (mUsersLock) { 1224 return mUsers.get(userId); 1225 } 1226 } 1227 1228 /** Called by PackageManagerService */ 1229 public boolean exists(int userId) { 1230 return mLocalService.exists(userId); 1231 } 1232 1233 @Override 1234 public void setUserName(int userId, String name) { 1235 checkManageUsersPermission("rename users"); 1236 boolean changed = false; 1237 synchronized (mPackagesLock) { 1238 UserData userData = getUserDataNoChecks(userId); 1239 if (userData == null || userData.info.partial) { 1240 Slog.w(LOG_TAG, "setUserName: unknown user #" + userId); 1241 return; 1242 } 1243 if (name != null && !name.equals(userData.info.name)) { 1244 userData.info.name = name; 1245 writeUserLP(userData); 1246 changed = true; 1247 } 1248 } 1249 if (changed) { 1250 sendUserInfoChangedBroadcast(userId); 1251 } 1252 } 1253 1254 @Override 1255 public void setUserIcon(int userId, Bitmap bitmap) { 1256 checkManageUsersPermission("update users"); 1257 if (hasUserRestriction(UserManager.DISALLOW_SET_USER_ICON, userId)) { 1258 Log.w(LOG_TAG, "Cannot set user icon. DISALLOW_SET_USER_ICON is enabled."); 1259 return; 1260 } 1261 mLocalService.setUserIcon(userId, bitmap); 1262 } 1263 1264 1265 1266 private void sendUserInfoChangedBroadcast(int userId) { 1267 Intent changedIntent = new Intent(Intent.ACTION_USER_INFO_CHANGED); 1268 changedIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 1269 changedIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 1270 mContext.sendBroadcastAsUser(changedIntent, UserHandle.ALL); 1271 } 1272 1273 @Override 1274 public ParcelFileDescriptor getUserIcon(int targetUserId) { 1275 String iconPath; 1276 synchronized (mPackagesLock) { 1277 UserInfo targetUserInfo = getUserInfoNoChecks(targetUserId); 1278 if (targetUserInfo == null || targetUserInfo.partial) { 1279 Slog.w(LOG_TAG, "getUserIcon: unknown user #" + targetUserId); 1280 return null; 1281 } 1282 1283 final int callingUserId = UserHandle.getCallingUserId(); 1284 final int callingGroupId = getUserInfoNoChecks(callingUserId).profileGroupId; 1285 final int targetGroupId = targetUserInfo.profileGroupId; 1286 final boolean sameGroup = (callingGroupId != UserInfo.NO_PROFILE_GROUP_ID 1287 && callingGroupId == targetGroupId); 1288 if ((callingUserId != targetUserId) && !sameGroup) { 1289 checkManageUsersPermission("get the icon of a user who is not related"); 1290 } 1291 1292 if (targetUserInfo.iconPath == null) { 1293 return null; 1294 } 1295 iconPath = targetUserInfo.iconPath; 1296 } 1297 1298 try { 1299 return ParcelFileDescriptor.open( 1300 new File(iconPath), ParcelFileDescriptor.MODE_READ_ONLY); 1301 } catch (FileNotFoundException e) { 1302 Log.e(LOG_TAG, "Couldn't find icon file", e); 1303 } 1304 return null; 1305 } 1306 1307 public void makeInitialized(int userId) { 1308 checkManageUsersPermission("makeInitialized"); 1309 boolean scheduleWriteUser = false; 1310 UserData userData; 1311 synchronized (mUsersLock) { 1312 userData = mUsers.get(userId); 1313 if (userData == null || userData.info.partial) { 1314 Slog.w(LOG_TAG, "makeInitialized: unknown user #" + userId); 1315 return; 1316 } 1317 if ((userData.info.flags & UserInfo.FLAG_INITIALIZED) == 0) { 1318 userData.info.flags |= UserInfo.FLAG_INITIALIZED; 1319 scheduleWriteUser = true; 1320 } 1321 } 1322 if (scheduleWriteUser) { 1323 scheduleWriteUser(userData); 1324 } 1325 } 1326 1327 /** 1328 * If default guest restrictions haven't been initialized yet, add the basic 1329 * restrictions. 1330 */ 1331 private void initDefaultGuestRestrictions() { 1332 synchronized (mGuestRestrictions) { 1333 if (mGuestRestrictions.isEmpty()) { 1334 mGuestRestrictions.putBoolean(UserManager.DISALLOW_CONFIG_WIFI, true); 1335 mGuestRestrictions.putBoolean(UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES, true); 1336 mGuestRestrictions.putBoolean(UserManager.DISALLOW_OUTGOING_CALLS, true); 1337 mGuestRestrictions.putBoolean(UserManager.DISALLOW_SMS, true); 1338 } 1339 } 1340 } 1341 1342 @Override 1343 public Bundle getDefaultGuestRestrictions() { 1344 checkManageUsersPermission("getDefaultGuestRestrictions"); 1345 synchronized (mGuestRestrictions) { 1346 return new Bundle(mGuestRestrictions); 1347 } 1348 } 1349 1350 @Override 1351 public void setDefaultGuestRestrictions(Bundle restrictions) { 1352 checkManageUsersPermission("setDefaultGuestRestrictions"); 1353 synchronized (mGuestRestrictions) { 1354 mGuestRestrictions.clear(); 1355 mGuestRestrictions.putAll(restrictions); 1356 } 1357 synchronized (mPackagesLock) { 1358 writeUserListLP(); 1359 } 1360 } 1361 1362 /** 1363 * See {@link UserManagerInternal#setDevicePolicyUserRestrictions} 1364 */ 1365 private void setDevicePolicyUserRestrictionsInner(int userId, @Nullable Bundle restrictions, 1366 boolean isDeviceOwner, int cameraRestrictionScope) { 1367 final Bundle global = new Bundle(); 1368 final Bundle local = new Bundle(); 1369 1370 // Sort restrictions into local and global ensuring they don't overlap. 1371 UserRestrictionsUtils.sortToGlobalAndLocal(restrictions, isDeviceOwner, 1372 cameraRestrictionScope, global, local); 1373 1374 boolean globalChanged, localChanged; 1375 synchronized (mRestrictionsLock) { 1376 // Update global and local restrictions if they were changed. 1377 globalChanged = updateRestrictionsIfNeededLR( 1378 userId, global, mDevicePolicyGlobalUserRestrictions); 1379 localChanged = updateRestrictionsIfNeededLR( 1380 userId, local, mDevicePolicyLocalUserRestrictions); 1381 1382 if (isDeviceOwner) { 1383 // Remember the global restriction owner userId to be able to make a distinction 1384 // in getUserRestrictionSource on who set local policies. 1385 mDeviceOwnerUserId = userId; 1386 } else { 1387 if (mDeviceOwnerUserId == userId) { 1388 // When profile owner sets restrictions it passes null global bundle and we 1389 // reset global restriction owner userId. 1390 // This means this user used to have DO, but now the DO is gone and the user 1391 // instead has PO. 1392 mDeviceOwnerUserId = UserHandle.USER_NULL; 1393 } 1394 } 1395 } 1396 if (DBG) { 1397 Log.d(LOG_TAG, "setDevicePolicyUserRestrictions: userId=" + userId 1398 + " global=" + global + (globalChanged ? " (changed)" : "") 1399 + " local=" + local + (localChanged ? " (changed)" : "") 1400 ); 1401 } 1402 // Don't call them within the mRestrictionsLock. 1403 synchronized (mPackagesLock) { 1404 if (localChanged || globalChanged) { 1405 writeUserLP(getUserDataNoChecks(userId)); 1406 } 1407 } 1408 1409 synchronized (mRestrictionsLock) { 1410 if (globalChanged) { 1411 applyUserRestrictionsForAllUsersLR(); 1412 } else if (localChanged) { 1413 applyUserRestrictionsLR(userId); 1414 } 1415 } 1416 } 1417 1418 /** 1419 * Updates restriction bundle for a given user in a given restriction array. If new bundle is 1420 * empty, record is removed from the array. 1421 * @return whether restrictions bundle is different from the old one. 1422 */ 1423 private boolean updateRestrictionsIfNeededLR(int userId, @Nullable Bundle restrictions, 1424 SparseArray<Bundle> restrictionsArray) { 1425 final boolean changed = 1426 !UserRestrictionsUtils.areEqual(restrictionsArray.get(userId), restrictions); 1427 if (changed) { 1428 if (!UserRestrictionsUtils.isEmpty(restrictions)) { 1429 restrictionsArray.put(userId, restrictions); 1430 } else { 1431 restrictionsArray.delete(userId); 1432 } 1433 } 1434 return changed; 1435 } 1436 1437 @GuardedBy("mRestrictionsLock") 1438 private Bundle computeEffectiveUserRestrictionsLR(int userId) { 1439 final Bundle baseRestrictions = 1440 UserRestrictionsUtils.nonNull(mBaseUserRestrictions.get(userId)); 1441 final Bundle global = UserRestrictionsUtils.mergeAll(mDevicePolicyGlobalUserRestrictions); 1442 final Bundle local = mDevicePolicyLocalUserRestrictions.get(userId); 1443 1444 if (UserRestrictionsUtils.isEmpty(global) && UserRestrictionsUtils.isEmpty(local)) { 1445 // Common case first. 1446 return baseRestrictions; 1447 } 1448 final Bundle effective = UserRestrictionsUtils.clone(baseRestrictions); 1449 UserRestrictionsUtils.merge(effective, global); 1450 UserRestrictionsUtils.merge(effective, local); 1451 1452 return effective; 1453 } 1454 1455 @GuardedBy("mRestrictionsLock") 1456 private void invalidateEffectiveUserRestrictionsLR(int userId) { 1457 if (DBG) { 1458 Log.d(LOG_TAG, "invalidateEffectiveUserRestrictions userId=" + userId); 1459 } 1460 mCachedEffectiveUserRestrictions.remove(userId); 1461 } 1462 1463 private Bundle getEffectiveUserRestrictions(int userId) { 1464 synchronized (mRestrictionsLock) { 1465 Bundle restrictions = mCachedEffectiveUserRestrictions.get(userId); 1466 if (restrictions == null) { 1467 restrictions = computeEffectiveUserRestrictionsLR(userId); 1468 mCachedEffectiveUserRestrictions.put(userId, restrictions); 1469 } 1470 return restrictions; 1471 } 1472 } 1473 1474 /** @return a specific user restriction that's in effect currently. */ 1475 @Override 1476 public boolean hasUserRestriction(String restrictionKey, int userId) { 1477 if (!UserRestrictionsUtils.isValidRestriction(restrictionKey)) { 1478 return false; 1479 } 1480 Bundle restrictions = getEffectiveUserRestrictions(userId); 1481 return restrictions != null && restrictions.getBoolean(restrictionKey); 1482 } 1483 1484 /** @return if any user has the given restriction. */ 1485 @Override 1486 public boolean hasUserRestrictionOnAnyUser(String restrictionKey) { 1487 if (!UserRestrictionsUtils.isValidRestriction(restrictionKey)) { 1488 return false; 1489 } 1490 final List<UserInfo> users = getUsers(/* excludeDying= */ true); 1491 for (int i = 0; i < users.size(); i++) { 1492 final int userId = users.get(i).id; 1493 Bundle restrictions = getEffectiveUserRestrictions(userId); 1494 if (restrictions != null && restrictions.getBoolean(restrictionKey)) { 1495 return true; 1496 } 1497 } 1498 return false; 1499 } 1500 1501 /** 1502 * @hide 1503 * 1504 * Returns who set a user restriction on a user. 1505 * Requires {@link android.Manifest.permission#MANAGE_USERS} permission. 1506 * @param restrictionKey the string key representing the restriction 1507 * @param userId the id of the user for whom to retrieve the restrictions. 1508 * @return The source of user restriction. Any combination of 1509 * {@link UserManager#RESTRICTION_NOT_SET}, 1510 * {@link UserManager#RESTRICTION_SOURCE_SYSTEM}, 1511 * {@link UserManager#RESTRICTION_SOURCE_DEVICE_OWNER} 1512 * and {@link UserManager#RESTRICTION_SOURCE_PROFILE_OWNER} 1513 */ 1514 @Override 1515 public int getUserRestrictionSource(String restrictionKey, int userId) { 1516 List<EnforcingUser> enforcingUsers = getUserRestrictionSources(restrictionKey, userId); 1517 // Get "bitwise or" of restriction sources for all enforcing users. 1518 int result = UserManager.RESTRICTION_NOT_SET; 1519 for (int i = enforcingUsers.size() - 1; i >= 0; i--) { 1520 result |= enforcingUsers.get(i).getUserRestrictionSource(); 1521 } 1522 return result; 1523 } 1524 1525 @Override 1526 public List<EnforcingUser> getUserRestrictionSources( 1527 String restrictionKey, @UserIdInt int userId) { 1528 checkManageUsersPermission("getUserRestrictionSource"); 1529 1530 // Shortcut for the most common case 1531 if (!hasUserRestriction(restrictionKey, userId)) { 1532 return Collections.emptyList(); 1533 } 1534 1535 final List<EnforcingUser> result = new ArrayList<>(); 1536 1537 // Check if it is base restriction. 1538 if (hasBaseUserRestriction(restrictionKey, userId)) { 1539 result.add(new EnforcingUser( 1540 UserHandle.USER_NULL, UserManager.RESTRICTION_SOURCE_SYSTEM)); 1541 } 1542 1543 synchronized (mRestrictionsLock) { 1544 // Check if it is set by profile owner. 1545 Bundle profileOwnerRestrictions = mDevicePolicyLocalUserRestrictions.get(userId); 1546 if (UserRestrictionsUtils.contains(profileOwnerRestrictions, restrictionKey)) { 1547 result.add(getEnforcingUserLocked(userId)); 1548 } 1549 1550 // Iterate over all users who enforce global restrictions. 1551 for (int i = mDevicePolicyGlobalUserRestrictions.size() - 1; i >= 0; i--) { 1552 Bundle globalRestrictions = mDevicePolicyGlobalUserRestrictions.valueAt(i); 1553 int profileUserId = mDevicePolicyGlobalUserRestrictions.keyAt(i); 1554 if (UserRestrictionsUtils.contains(globalRestrictions, restrictionKey)) { 1555 result.add(getEnforcingUserLocked(profileUserId)); 1556 } 1557 } 1558 } 1559 return result; 1560 } 1561 1562 @GuardedBy("mRestrictionsLock") 1563 private EnforcingUser getEnforcingUserLocked(@UserIdInt int userId) { 1564 int source = mDeviceOwnerUserId == userId ? UserManager.RESTRICTION_SOURCE_DEVICE_OWNER 1565 : UserManager.RESTRICTION_SOURCE_PROFILE_OWNER; 1566 return new EnforcingUser(userId, source); 1567 } 1568 1569 /** 1570 * @return UserRestrictions that are in effect currently. This always returns a new 1571 * {@link Bundle}. 1572 */ 1573 @Override 1574 public Bundle getUserRestrictions(int userId) { 1575 return UserRestrictionsUtils.clone(getEffectiveUserRestrictions(userId)); 1576 } 1577 1578 @Override 1579 public boolean hasBaseUserRestriction(String restrictionKey, int userId) { 1580 checkManageUsersPermission("hasBaseUserRestriction"); 1581 if (!UserRestrictionsUtils.isValidRestriction(restrictionKey)) { 1582 return false; 1583 } 1584 synchronized (mRestrictionsLock) { 1585 Bundle bundle = mBaseUserRestrictions.get(userId); 1586 return (bundle != null && bundle.getBoolean(restrictionKey, false)); 1587 } 1588 } 1589 1590 @Override 1591 public void setUserRestriction(String key, boolean value, int userId) { 1592 checkManageUsersPermission("setUserRestriction"); 1593 if (!UserRestrictionsUtils.isValidRestriction(key)) { 1594 return; 1595 } 1596 synchronized (mRestrictionsLock) { 1597 // Note we can't modify Bundles stored in mBaseUserRestrictions directly, so create 1598 // a copy. 1599 final Bundle newRestrictions = UserRestrictionsUtils.clone( 1600 mBaseUserRestrictions.get(userId)); 1601 newRestrictions.putBoolean(key, value); 1602 1603 updateUserRestrictionsInternalLR(newRestrictions, userId); 1604 } 1605 } 1606 1607 /** 1608 * Optionally updating user restrictions, calculate the effective user restrictions and also 1609 * propagate to other services and system settings. 1610 * 1611 * @param newBaseRestrictions User restrictions to set. 1612 * If null, will not update user restrictions and only does the propagation. 1613 * @param userId target user ID. 1614 */ 1615 @GuardedBy("mRestrictionsLock") 1616 private void updateUserRestrictionsInternalLR( 1617 @Nullable Bundle newBaseRestrictions, int userId) { 1618 final Bundle prevAppliedRestrictions = UserRestrictionsUtils.nonNull( 1619 mAppliedUserRestrictions.get(userId)); 1620 1621 // Update base restrictions. 1622 if (newBaseRestrictions != null) { 1623 // If newBaseRestrictions == the current one, it's probably a bug. 1624 final Bundle prevBaseRestrictions = mBaseUserRestrictions.get(userId); 1625 1626 Preconditions.checkState(prevBaseRestrictions != newBaseRestrictions); 1627 Preconditions.checkState(mCachedEffectiveUserRestrictions.get(userId) 1628 != newBaseRestrictions); 1629 1630 if (updateRestrictionsIfNeededLR(userId, newBaseRestrictions, mBaseUserRestrictions)) { 1631 scheduleWriteUser(getUserDataNoChecks(userId)); 1632 } 1633 } 1634 1635 final Bundle effective = computeEffectiveUserRestrictionsLR(userId); 1636 1637 mCachedEffectiveUserRestrictions.put(userId, effective); 1638 1639 // Apply the new restrictions. 1640 if (DBG) { 1641 debug("Applying user restrictions: userId=" + userId 1642 + " new=" + effective + " prev=" + prevAppliedRestrictions); 1643 } 1644 1645 if (mAppOpsService != null) { // We skip it until system-ready. 1646 mHandler.post(new Runnable() { 1647 @Override 1648 public void run() { 1649 try { 1650 mAppOpsService.setUserRestrictions(effective, mUserRestriconToken, userId); 1651 } catch (RemoteException e) { 1652 Log.w(LOG_TAG, "Unable to notify AppOpsService of UserRestrictions"); 1653 } 1654 } 1655 }); 1656 } 1657 1658 propagateUserRestrictionsLR(userId, effective, prevAppliedRestrictions); 1659 1660 mAppliedUserRestrictions.put(userId, new Bundle(effective)); 1661 } 1662 1663 private void propagateUserRestrictionsLR(final int userId, 1664 Bundle newRestrictions, Bundle prevRestrictions) { 1665 // Note this method doesn't touch any state, meaning it doesn't require mRestrictionsLock 1666 // actually, but we still need some kind of synchronization otherwise we might end up 1667 // calling listeners out-of-order, thus "LR". 1668 1669 if (UserRestrictionsUtils.areEqual(newRestrictions, prevRestrictions)) { 1670 return; 1671 } 1672 1673 final Bundle newRestrictionsFinal = new Bundle(newRestrictions); 1674 final Bundle prevRestrictionsFinal = new Bundle(prevRestrictions); 1675 1676 mHandler.post(new Runnable() { 1677 @Override 1678 public void run() { 1679 UserRestrictionsUtils.applyUserRestrictions( 1680 mContext, userId, newRestrictionsFinal, prevRestrictionsFinal); 1681 1682 final UserRestrictionsListener[] listeners; 1683 synchronized (mUserRestrictionsListeners) { 1684 listeners = new UserRestrictionsListener[mUserRestrictionsListeners.size()]; 1685 mUserRestrictionsListeners.toArray(listeners); 1686 } 1687 for (int i = 0; i < listeners.length; i++) { 1688 listeners[i].onUserRestrictionsChanged(userId, 1689 newRestrictionsFinal, prevRestrictionsFinal); 1690 } 1691 1692 final Intent broadcast = new Intent(UserManager.ACTION_USER_RESTRICTIONS_CHANGED) 1693 .setFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 1694 mContext.sendBroadcastAsUser(broadcast, UserHandle.of(userId)); 1695 } 1696 }); 1697 } 1698 1699 // Package private for the inner class. 1700 void applyUserRestrictionsLR(int userId) { 1701 updateUserRestrictionsInternalLR(null, userId); 1702 } 1703 1704 @GuardedBy("mRestrictionsLock") 1705 // Package private for the inner class. 1706 void applyUserRestrictionsForAllUsersLR() { 1707 if (DBG) { 1708 debug("applyUserRestrictionsForAllUsersLR"); 1709 } 1710 // First, invalidate all cached values. 1711 mCachedEffectiveUserRestrictions.clear(); 1712 1713 // We don't want to call into ActivityManagerService while taking a lock, so we'll call 1714 // it on a handler. 1715 final Runnable r = new Runnable() { 1716 @Override 1717 public void run() { 1718 // Then get the list of running users. 1719 final int[] runningUsers; 1720 try { 1721 runningUsers = ActivityManager.getService().getRunningUserIds(); 1722 } catch (RemoteException e) { 1723 Log.w(LOG_TAG, "Unable to access ActivityManagerService"); 1724 return; 1725 } 1726 // Then re-calculate the effective restrictions and apply, only for running users. 1727 // It's okay if a new user has started after the getRunningUserIds() call, 1728 // because we'll do the same thing (re-calculate the restrictions and apply) 1729 // when we start a user. 1730 synchronized (mRestrictionsLock) { 1731 for (int i = 0; i < runningUsers.length; i++) { 1732 applyUserRestrictionsLR(runningUsers[i]); 1733 } 1734 } 1735 } 1736 }; 1737 mHandler.post(r); 1738 } 1739 1740 /** 1741 * Check if we've hit the limit of how many users can be created. 1742 */ 1743 private boolean isUserLimitReached() { 1744 int count; 1745 synchronized (mUsersLock) { 1746 count = getAliveUsersExcludingGuestsCountLU(); 1747 } 1748 return count >= UserManager.getMaxSupportedUsers(); 1749 } 1750 1751 @Override 1752 public boolean canAddMoreManagedProfiles(int userId, boolean allowedToRemoveOne) { 1753 checkManageUsersPermission("check if more managed profiles can be added."); 1754 if (ActivityManager.isLowRamDeviceStatic()) { 1755 return false; 1756 } 1757 if (!mContext.getPackageManager().hasSystemFeature( 1758 PackageManager.FEATURE_MANAGED_USERS)) { 1759 return false; 1760 } 1761 // Limit number of managed profiles that can be created 1762 final int managedProfilesCount = getProfiles(userId, false).size() - 1; 1763 final int profilesRemovedCount = managedProfilesCount > 0 && allowedToRemoveOne ? 1 : 0; 1764 if (managedProfilesCount - profilesRemovedCount >= getMaxManagedProfiles()) { 1765 return false; 1766 } 1767 synchronized(mUsersLock) { 1768 UserInfo userInfo = getUserInfoLU(userId); 1769 if (userInfo == null || !userInfo.canHaveProfile()) { 1770 return false; 1771 } 1772 int usersCountAfterRemoving = getAliveUsersExcludingGuestsCountLU() 1773 - profilesRemovedCount; 1774 // We allow creating a managed profile in the special case where there is only one user. 1775 return usersCountAfterRemoving == 1 1776 || usersCountAfterRemoving < UserManager.getMaxSupportedUsers(); 1777 } 1778 } 1779 1780 private int getAliveUsersExcludingGuestsCountLU() { 1781 int aliveUserCount = 0; 1782 final int totalUserCount = mUsers.size(); 1783 // Skip over users being removed 1784 for (int i = 0; i < totalUserCount; i++) { 1785 UserInfo user = mUsers.valueAt(i).info; 1786 if (!mRemovingUserIds.get(user.id) && !user.isGuest()) { 1787 aliveUserCount++; 1788 } 1789 } 1790 return aliveUserCount; 1791 } 1792 1793 /** 1794 * Enforces that only the system UID or root's UID or apps that have the 1795 * {@link android.Manifest.permission#MANAGE_USERS MANAGE_USERS} and 1796 * {@link android.Manifest.permission#INTERACT_ACROSS_USERS_FULL INTERACT_ACROSS_USERS_FULL} 1797 * permissions can make certain calls to the UserManager. 1798 * 1799 * @param message used as message if SecurityException is thrown 1800 * @throws SecurityException if the caller does not have enough privilege. 1801 */ 1802 private static final void checkManageUserAndAcrossUsersFullPermission(String message) { 1803 final int uid = Binder.getCallingUid(); 1804 if (uid != Process.SYSTEM_UID && uid != 0 1805 && ActivityManager.checkComponentPermission( 1806 Manifest.permission.MANAGE_USERS, 1807 uid, -1, true) != PackageManager.PERMISSION_GRANTED 1808 && ActivityManager.checkComponentPermission( 1809 Manifest.permission.INTERACT_ACROSS_USERS_FULL, 1810 uid, -1, true) != PackageManager.PERMISSION_GRANTED) { 1811 throw new SecurityException( 1812 "You need MANAGE_USERS and INTERACT_ACROSS_USERS_FULL permission to: " 1813 + message); 1814 } 1815 } 1816 1817 /** 1818 * Enforces that only the system UID or root's UID or apps that have the 1819 * {@link android.Manifest.permission#MANAGE_USERS MANAGE_USERS} 1820 * permission can make certain calls to the UserManager. 1821 * 1822 * @param message used as message if SecurityException is thrown 1823 * @throws SecurityException if the caller is not system or root 1824 * @see #hasManageUsersPermission() 1825 */ 1826 private static final void checkManageUsersPermission(String message) { 1827 if (!hasManageUsersPermission()) { 1828 throw new SecurityException("You need MANAGE_USERS permission to: " + message); 1829 } 1830 } 1831 1832 /** 1833 * Enforces that only the system UID or root's UID or apps that have the 1834 * {@link android.Manifest.permission#MANAGE_USERS MANAGE_USERS} or 1835 * {@link android.Manifest.permission#CREATE_USERS CREATE_USERS} 1836 * can make certain calls to the UserManager. 1837 * 1838 * @param message used as message if SecurityException is thrown 1839 * @throws SecurityException if the caller is not system or root 1840 * @see #hasManageOrCreateUsersPermission() 1841 */ 1842 private static final void checkManageOrCreateUsersPermission(String message) { 1843 if (!hasManageOrCreateUsersPermission()) { 1844 throw new SecurityException( 1845 "You either need MANAGE_USERS or CREATE_USERS permission to: " + message); 1846 } 1847 } 1848 1849 /** 1850 * Similar to {@link #checkManageOrCreateUsersPermission(String)} but when the caller is tries 1851 * to create user/profiles other than what is allowed for 1852 * {@link android.Manifest.permission#CREATE_USERS CREATE_USERS} permission, then it will only 1853 * allow callers with {@link android.Manifest.permission#MANAGE_USERS MANAGE_USERS} permission. 1854 */ 1855 private static final void checkManageOrCreateUsersPermission(int creationFlags) { 1856 if ((creationFlags & ~ALLOWED_FLAGS_FOR_CREATE_USERS_PERMISSION) == 0) { 1857 if (!hasManageOrCreateUsersPermission()) { 1858 throw new SecurityException("You either need MANAGE_USERS or CREATE_USERS " 1859 + "permission to create an user with flags: " + creationFlags); 1860 } 1861 } else if (!hasManageUsersPermission()) { 1862 throw new SecurityException("You need MANAGE_USERS permission to create an user " 1863 + " with flags: " + creationFlags); 1864 } 1865 } 1866 1867 /** 1868 * @return whether the calling UID is system UID or root's UID or the calling app has the 1869 * {@link android.Manifest.permission#MANAGE_USERS MANAGE_USERS}. 1870 */ 1871 private static final boolean hasManageUsersPermission() { 1872 final int callingUid = Binder.getCallingUid(); 1873 return UserHandle.isSameApp(callingUid, Process.SYSTEM_UID) 1874 || callingUid == Process.ROOT_UID 1875 || ActivityManager.checkComponentPermission( 1876 android.Manifest.permission.MANAGE_USERS, 1877 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED; 1878 } 1879 1880 /** 1881 * @return whether the calling UID is system UID or root's UID or the calling app has the 1882 * {@link android.Manifest.permission#MANAGE_USERS MANAGE_USERS} or 1883 * {@link android.Manifest.permission#CREATE_USERS CREATE_USERS}. 1884 */ 1885 private static final boolean hasManageOrCreateUsersPermission() { 1886 final int callingUid = Binder.getCallingUid(); 1887 return UserHandle.isSameApp(callingUid, Process.SYSTEM_UID) 1888 || callingUid == Process.ROOT_UID 1889 || ActivityManager.checkComponentPermission( 1890 android.Manifest.permission.MANAGE_USERS, 1891 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 1892 || ActivityManager.checkComponentPermission( 1893 android.Manifest.permission.CREATE_USERS, 1894 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED; 1895 } 1896 1897 /** 1898 * Enforces that only the system UID or root's UID (on any user) can make certain calls to the 1899 * UserManager. 1900 * 1901 * @param message used as message if SecurityException is thrown 1902 * @throws SecurityException if the caller is not system or root 1903 */ 1904 private static void checkSystemOrRoot(String message) { 1905 final int uid = Binder.getCallingUid(); 1906 if (!UserHandle.isSameApp(uid, Process.SYSTEM_UID) && uid != Process.ROOT_UID) { 1907 throw new SecurityException("Only system may: " + message); 1908 } 1909 } 1910 1911 private void writeBitmapLP(UserInfo info, Bitmap bitmap) { 1912 try { 1913 File dir = new File(mUsersDir, Integer.toString(info.id)); 1914 File file = new File(dir, USER_PHOTO_FILENAME); 1915 File tmp = new File(dir, USER_PHOTO_FILENAME_TMP); 1916 if (!dir.exists()) { 1917 dir.mkdir(); 1918 FileUtils.setPermissions( 1919 dir.getPath(), 1920 FileUtils.S_IRWXU|FileUtils.S_IRWXG|FileUtils.S_IXOTH, 1921 -1, -1); 1922 } 1923 FileOutputStream os; 1924 if (bitmap.compress(Bitmap.CompressFormat.PNG, 100, os = new FileOutputStream(tmp)) 1925 && tmp.renameTo(file) && SELinux.restorecon(file)) { 1926 info.iconPath = file.getAbsolutePath(); 1927 } 1928 try { 1929 os.close(); 1930 } catch (IOException ioe) { 1931 // What the ... ! 1932 } 1933 tmp.delete(); 1934 } catch (FileNotFoundException e) { 1935 Slog.w(LOG_TAG, "Error setting photo for user ", e); 1936 } 1937 } 1938 1939 /** 1940 * Returns an array of user ids. This array is cached here for quick access, so do not modify or 1941 * cache it elsewhere. 1942 * @return the array of user ids. 1943 */ 1944 public int[] getUserIds() { 1945 synchronized (mUsersLock) { 1946 return mUserIds; 1947 } 1948 } 1949 1950 private void readUserListLP() { 1951 if (!mUserListFile.exists()) { 1952 fallbackToSingleUserLP(); 1953 return; 1954 } 1955 FileInputStream fis = null; 1956 AtomicFile userListFile = new AtomicFile(mUserListFile); 1957 try { 1958 fis = userListFile.openRead(); 1959 XmlPullParser parser = Xml.newPullParser(); 1960 parser.setInput(fis, StandardCharsets.UTF_8.name()); 1961 int type; 1962 while ((type = parser.next()) != XmlPullParser.START_TAG 1963 && type != XmlPullParser.END_DOCUMENT) { 1964 // Skip 1965 } 1966 1967 if (type != XmlPullParser.START_TAG) { 1968 Slog.e(LOG_TAG, "Unable to read user list"); 1969 fallbackToSingleUserLP(); 1970 return; 1971 } 1972 1973 mNextSerialNumber = -1; 1974 if (parser.getName().equals(TAG_USERS)) { 1975 String lastSerialNumber = parser.getAttributeValue(null, ATTR_NEXT_SERIAL_NO); 1976 if (lastSerialNumber != null) { 1977 mNextSerialNumber = Integer.parseInt(lastSerialNumber); 1978 } 1979 String versionNumber = parser.getAttributeValue(null, ATTR_USER_VERSION); 1980 if (versionNumber != null) { 1981 mUserVersion = Integer.parseInt(versionNumber); 1982 } 1983 } 1984 1985 // Pre-O global user restriction were stored as a single bundle (as opposed to per-user 1986 // currently), take care of it in case of upgrade. 1987 Bundle oldDevicePolicyGlobalUserRestrictions = null; 1988 1989 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT) { 1990 if (type == XmlPullParser.START_TAG) { 1991 final String name = parser.getName(); 1992 if (name.equals(TAG_USER)) { 1993 String id = parser.getAttributeValue(null, ATTR_ID); 1994 1995 UserData userData = readUserLP(Integer.parseInt(id)); 1996 1997 if (userData != null) { 1998 synchronized (mUsersLock) { 1999 mUsers.put(userData.info.id, userData); 2000 if (mNextSerialNumber < 0 2001 || mNextSerialNumber <= userData.info.id) { 2002 mNextSerialNumber = userData.info.id + 1; 2003 } 2004 } 2005 } 2006 } else if (name.equals(TAG_GUEST_RESTRICTIONS)) { 2007 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT 2008 && type != XmlPullParser.END_TAG) { 2009 if (type == XmlPullParser.START_TAG) { 2010 if (parser.getName().equals(TAG_RESTRICTIONS)) { 2011 synchronized (mGuestRestrictions) { 2012 UserRestrictionsUtils 2013 .readRestrictions(parser, mGuestRestrictions); 2014 } 2015 } 2016 break; 2017 } 2018 } 2019 } else if (name.equals(TAG_DEVICE_OWNER_USER_ID) 2020 // Legacy name, should only be encountered when upgrading from pre-O. 2021 || name.equals(TAG_GLOBAL_RESTRICTION_OWNER_ID)) { 2022 String ownerUserId = parser.getAttributeValue(null, ATTR_ID); 2023 if (ownerUserId != null) { 2024 mDeviceOwnerUserId = Integer.parseInt(ownerUserId); 2025 } 2026 } else if (name.equals(TAG_DEVICE_POLICY_RESTRICTIONS)) { 2027 // Should only happen when upgrading from pre-O (version < 7). 2028 oldDevicePolicyGlobalUserRestrictions = 2029 UserRestrictionsUtils.readRestrictions(parser); 2030 } 2031 } 2032 } 2033 2034 updateUserIds(); 2035 upgradeIfNecessaryLP(oldDevicePolicyGlobalUserRestrictions); 2036 } catch (IOException | XmlPullParserException e) { 2037 fallbackToSingleUserLP(); 2038 } finally { 2039 IoUtils.closeQuietly(fis); 2040 } 2041 } 2042 2043 /** 2044 * Upgrade steps between versions, either for fixing bugs or changing the data format. 2045 * @param oldGlobalUserRestrictions Pre-O global device policy restrictions. 2046 */ 2047 private void upgradeIfNecessaryLP(Bundle oldGlobalUserRestrictions) { 2048 final int originalVersion = mUserVersion; 2049 int userVersion = mUserVersion; 2050 if (userVersion < 1) { 2051 // Assign a proper name for the owner, if not initialized correctly before 2052 UserData userData = getUserDataNoChecks(UserHandle.USER_SYSTEM); 2053 if ("Primary".equals(userData.info.name)) { 2054 userData.info.name = 2055 mContext.getResources().getString(com.android.internal.R.string.owner_name); 2056 scheduleWriteUser(userData); 2057 } 2058 userVersion = 1; 2059 } 2060 2061 if (userVersion < 2) { 2062 // Owner should be marked as initialized 2063 UserData userData = getUserDataNoChecks(UserHandle.USER_SYSTEM); 2064 if ((userData.info.flags & UserInfo.FLAG_INITIALIZED) == 0) { 2065 userData.info.flags |= UserInfo.FLAG_INITIALIZED; 2066 scheduleWriteUser(userData); 2067 } 2068 userVersion = 2; 2069 } 2070 2071 2072 if (userVersion < 4) { 2073 userVersion = 4; 2074 } 2075 2076 if (userVersion < 5) { 2077 initDefaultGuestRestrictions(); 2078 userVersion = 5; 2079 } 2080 2081 if (userVersion < 6) { 2082 final boolean splitSystemUser = UserManager.isSplitSystemUser(); 2083 synchronized (mUsersLock) { 2084 for (int i = 0; i < mUsers.size(); i++) { 2085 UserData userData = mUsers.valueAt(i); 2086 // In non-split mode, only user 0 can have restricted profiles 2087 if (!splitSystemUser && userData.info.isRestricted() 2088 && (userData.info.restrictedProfileParentId 2089 == UserInfo.NO_PROFILE_GROUP_ID)) { 2090 userData.info.restrictedProfileParentId = UserHandle.USER_SYSTEM; 2091 scheduleWriteUser(userData); 2092 } 2093 } 2094 } 2095 userVersion = 6; 2096 } 2097 2098 if (userVersion < 7) { 2099 // Previously only one user could enforce global restrictions, now it is per-user. 2100 synchronized (mRestrictionsLock) { 2101 if (!UserRestrictionsUtils.isEmpty(oldGlobalUserRestrictions) 2102 && mDeviceOwnerUserId != UserHandle.USER_NULL) { 2103 mDevicePolicyGlobalUserRestrictions.put( 2104 mDeviceOwnerUserId, oldGlobalUserRestrictions); 2105 } 2106 // ENSURE_VERIFY_APPS is now enforced globally even if put by profile owner, so move 2107 // it from local to global bundle for all users who set it. 2108 UserRestrictionsUtils.moveRestriction(UserManager.ENSURE_VERIFY_APPS, 2109 mDevicePolicyLocalUserRestrictions, mDevicePolicyGlobalUserRestrictions 2110 ); 2111 } 2112 userVersion = 7; 2113 } 2114 2115 if (userVersion < USER_VERSION) { 2116 Slog.w(LOG_TAG, "User version " + mUserVersion + " didn't upgrade as expected to " 2117 + USER_VERSION); 2118 } else { 2119 mUserVersion = userVersion; 2120 2121 if (originalVersion < mUserVersion) { 2122 writeUserListLP(); 2123 } 2124 } 2125 } 2126 2127 private void fallbackToSingleUserLP() { 2128 int flags = UserInfo.FLAG_INITIALIZED; 2129 // In split system user mode, the admin and primary flags are assigned to the first human 2130 // user. 2131 if (!UserManager.isSplitSystemUser()) { 2132 flags |= UserInfo.FLAG_ADMIN | UserInfo.FLAG_PRIMARY; 2133 } 2134 // Create the system user 2135 UserInfo system = new UserInfo(UserHandle.USER_SYSTEM, null, null, flags); 2136 UserData userData = putUserInfo(system); 2137 mNextSerialNumber = MIN_USER_ID; 2138 mUserVersion = USER_VERSION; 2139 2140 Bundle restrictions = new Bundle(); 2141 try { 2142 final String[] defaultFirstUserRestrictions = mContext.getResources().getStringArray( 2143 com.android.internal.R.array.config_defaultFirstUserRestrictions); 2144 for (String userRestriction : defaultFirstUserRestrictions) { 2145 if (UserRestrictionsUtils.isValidRestriction(userRestriction)) { 2146 restrictions.putBoolean(userRestriction, true); 2147 } 2148 } 2149 } catch (Resources.NotFoundException e) { 2150 Log.e(LOG_TAG, "Couldn't find resource: config_defaultFirstUserRestrictions", e); 2151 } 2152 2153 if (!restrictions.isEmpty()) { 2154 synchronized (mRestrictionsLock) { 2155 mBaseUserRestrictions.append(UserHandle.USER_SYSTEM, restrictions); 2156 } 2157 } 2158 2159 updateUserIds(); 2160 initDefaultGuestRestrictions(); 2161 2162 writeUserLP(userData); 2163 writeUserListLP(); 2164 } 2165 2166 private String getOwnerName() { 2167 return mContext.getResources().getString(com.android.internal.R.string.owner_name); 2168 } 2169 2170 private void scheduleWriteUser(UserData UserData) { 2171 if (DBG) { 2172 debug("scheduleWriteUser"); 2173 } 2174 // No need to wrap it within a lock -- worst case, we'll just post the same message 2175 // twice. 2176 if (!mHandler.hasMessages(WRITE_USER_MSG, UserData)) { 2177 Message msg = mHandler.obtainMessage(WRITE_USER_MSG, UserData); 2178 mHandler.sendMessageDelayed(msg, WRITE_USER_DELAY); 2179 } 2180 } 2181 2182 private void writeUserLP(UserData userData) { 2183 if (DBG) { 2184 debug("writeUserLP " + userData); 2185 } 2186 FileOutputStream fos = null; 2187 AtomicFile userFile = new AtomicFile(new File(mUsersDir, userData.info.id + XML_SUFFIX)); 2188 try { 2189 fos = userFile.startWrite(); 2190 final BufferedOutputStream bos = new BufferedOutputStream(fos); 2191 writeUserLP(userData, bos); 2192 userFile.finishWrite(fos); 2193 } catch (Exception ioe) { 2194 Slog.e(LOG_TAG, "Error writing user info " + userData.info.id, ioe); 2195 userFile.failWrite(fos); 2196 } 2197 } 2198 2199 /* 2200 * Writes the user file in this format: 2201 * 2202 * <user flags="20039023" id="0"> 2203 * <name>Primary</name> 2204 * </user> 2205 */ 2206 @VisibleForTesting 2207 void writeUserLP(UserData userData, OutputStream os) 2208 throws IOException, XmlPullParserException { 2209 // XmlSerializer serializer = XmlUtils.serializerInstance(); 2210 final XmlSerializer serializer = new FastXmlSerializer(); 2211 serializer.setOutput(os, StandardCharsets.UTF_8.name()); 2212 serializer.startDocument(null, true); 2213 serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true); 2214 2215 final UserInfo userInfo = userData.info; 2216 serializer.startTag(null, TAG_USER); 2217 serializer.attribute(null, ATTR_ID, Integer.toString(userInfo.id)); 2218 serializer.attribute(null, ATTR_SERIAL_NO, Integer.toString(userInfo.serialNumber)); 2219 serializer.attribute(null, ATTR_FLAGS, Integer.toString(userInfo.flags)); 2220 serializer.attribute(null, ATTR_CREATION_TIME, Long.toString(userInfo.creationTime)); 2221 serializer.attribute(null, ATTR_LAST_LOGGED_IN_TIME, 2222 Long.toString(userInfo.lastLoggedInTime)); 2223 if (userInfo.lastLoggedInFingerprint != null) { 2224 serializer.attribute(null, ATTR_LAST_LOGGED_IN_FINGERPRINT, 2225 userInfo.lastLoggedInFingerprint); 2226 } 2227 if (userInfo.iconPath != null) { 2228 serializer.attribute(null, ATTR_ICON_PATH, userInfo.iconPath); 2229 } 2230 if (userInfo.partial) { 2231 serializer.attribute(null, ATTR_PARTIAL, "true"); 2232 } 2233 if (userInfo.guestToRemove) { 2234 serializer.attribute(null, ATTR_GUEST_TO_REMOVE, "true"); 2235 } 2236 if (userInfo.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 2237 serializer.attribute(null, ATTR_PROFILE_GROUP_ID, 2238 Integer.toString(userInfo.profileGroupId)); 2239 } 2240 serializer.attribute(null, ATTR_PROFILE_BADGE, 2241 Integer.toString(userInfo.profileBadge)); 2242 if (userInfo.restrictedProfileParentId != UserInfo.NO_PROFILE_GROUP_ID) { 2243 serializer.attribute(null, ATTR_RESTRICTED_PROFILE_PARENT_ID, 2244 Integer.toString(userInfo.restrictedProfileParentId)); 2245 } 2246 // Write seed data 2247 if (userData.persistSeedData) { 2248 if (userData.seedAccountName != null) { 2249 serializer.attribute(null, ATTR_SEED_ACCOUNT_NAME, userData.seedAccountName); 2250 } 2251 if (userData.seedAccountType != null) { 2252 serializer.attribute(null, ATTR_SEED_ACCOUNT_TYPE, userData.seedAccountType); 2253 } 2254 } 2255 if (userInfo.name != null) { 2256 serializer.startTag(null, TAG_NAME); 2257 serializer.text(userInfo.name); 2258 serializer.endTag(null, TAG_NAME); 2259 } 2260 synchronized (mRestrictionsLock) { 2261 UserRestrictionsUtils.writeRestrictions(serializer, 2262 mBaseUserRestrictions.get(userInfo.id), TAG_RESTRICTIONS); 2263 UserRestrictionsUtils.writeRestrictions(serializer, 2264 mDevicePolicyLocalUserRestrictions.get(userInfo.id), 2265 TAG_DEVICE_POLICY_RESTRICTIONS); 2266 UserRestrictionsUtils.writeRestrictions(serializer, 2267 mDevicePolicyGlobalUserRestrictions.get(userInfo.id), 2268 TAG_DEVICE_POLICY_GLOBAL_RESTRICTIONS); 2269 } 2270 2271 if (userData.account != null) { 2272 serializer.startTag(null, TAG_ACCOUNT); 2273 serializer.text(userData.account); 2274 serializer.endTag(null, TAG_ACCOUNT); 2275 } 2276 2277 if (userData.persistSeedData && userData.seedAccountOptions != null) { 2278 serializer.startTag(null, TAG_SEED_ACCOUNT_OPTIONS); 2279 userData.seedAccountOptions.saveToXml(serializer); 2280 serializer.endTag(null, TAG_SEED_ACCOUNT_OPTIONS); 2281 } 2282 2283 serializer.endTag(null, TAG_USER); 2284 2285 serializer.endDocument(); 2286 } 2287 2288 /* 2289 * Writes the user list file in this format: 2290 * 2291 * <users nextSerialNumber="3"> 2292 * <user id="0"></user> 2293 * <user id="2"></user> 2294 * </users> 2295 */ 2296 private void writeUserListLP() { 2297 if (DBG) { 2298 debug("writeUserList"); 2299 } 2300 FileOutputStream fos = null; 2301 AtomicFile userListFile = new AtomicFile(mUserListFile); 2302 try { 2303 fos = userListFile.startWrite(); 2304 final BufferedOutputStream bos = new BufferedOutputStream(fos); 2305 2306 // XmlSerializer serializer = XmlUtils.serializerInstance(); 2307 final XmlSerializer serializer = new FastXmlSerializer(); 2308 serializer.setOutput(bos, StandardCharsets.UTF_8.name()); 2309 serializer.startDocument(null, true); 2310 serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true); 2311 2312 serializer.startTag(null, TAG_USERS); 2313 serializer.attribute(null, ATTR_NEXT_SERIAL_NO, Integer.toString(mNextSerialNumber)); 2314 serializer.attribute(null, ATTR_USER_VERSION, Integer.toString(mUserVersion)); 2315 2316 serializer.startTag(null, TAG_GUEST_RESTRICTIONS); 2317 synchronized (mGuestRestrictions) { 2318 UserRestrictionsUtils 2319 .writeRestrictions(serializer, mGuestRestrictions, TAG_RESTRICTIONS); 2320 } 2321 serializer.endTag(null, TAG_GUEST_RESTRICTIONS); 2322 serializer.startTag(null, TAG_DEVICE_OWNER_USER_ID); 2323 serializer.attribute(null, ATTR_ID, Integer.toString(mDeviceOwnerUserId)); 2324 serializer.endTag(null, TAG_DEVICE_OWNER_USER_ID); 2325 int[] userIdsToWrite; 2326 synchronized (mUsersLock) { 2327 userIdsToWrite = new int[mUsers.size()]; 2328 for (int i = 0; i < userIdsToWrite.length; i++) { 2329 UserInfo user = mUsers.valueAt(i).info; 2330 userIdsToWrite[i] = user.id; 2331 } 2332 } 2333 for (int id : userIdsToWrite) { 2334 serializer.startTag(null, TAG_USER); 2335 serializer.attribute(null, ATTR_ID, Integer.toString(id)); 2336 serializer.endTag(null, TAG_USER); 2337 } 2338 2339 serializer.endTag(null, TAG_USERS); 2340 2341 serializer.endDocument(); 2342 userListFile.finishWrite(fos); 2343 } catch (Exception e) { 2344 userListFile.failWrite(fos); 2345 Slog.e(LOG_TAG, "Error writing user list"); 2346 } 2347 } 2348 2349 private UserData readUserLP(int id) { 2350 FileInputStream fis = null; 2351 try { 2352 AtomicFile userFile = 2353 new AtomicFile(new File(mUsersDir, Integer.toString(id) + XML_SUFFIX)); 2354 fis = userFile.openRead(); 2355 return readUserLP(id, fis); 2356 } catch (IOException ioe) { 2357 Slog.e(LOG_TAG, "Error reading user list"); 2358 } catch (XmlPullParserException pe) { 2359 Slog.e(LOG_TAG, "Error reading user list"); 2360 } finally { 2361 IoUtils.closeQuietly(fis); 2362 } 2363 return null; 2364 } 2365 2366 @VisibleForTesting 2367 UserData readUserLP(int id, InputStream is) throws IOException, 2368 XmlPullParserException { 2369 int flags = 0; 2370 int serialNumber = id; 2371 String name = null; 2372 String account = null; 2373 String iconPath = null; 2374 long creationTime = 0L; 2375 long lastLoggedInTime = 0L; 2376 String lastLoggedInFingerprint = null; 2377 int profileGroupId = UserInfo.NO_PROFILE_GROUP_ID; 2378 int profileBadge = 0; 2379 int restrictedProfileParentId = UserInfo.NO_PROFILE_GROUP_ID; 2380 boolean partial = false; 2381 boolean guestToRemove = false; 2382 boolean persistSeedData = false; 2383 String seedAccountName = null; 2384 String seedAccountType = null; 2385 PersistableBundle seedAccountOptions = null; 2386 Bundle baseRestrictions = null; 2387 Bundle localRestrictions = null; 2388 Bundle globalRestrictions = null; 2389 2390 XmlPullParser parser = Xml.newPullParser(); 2391 parser.setInput(is, StandardCharsets.UTF_8.name()); 2392 int type; 2393 while ((type = parser.next()) != XmlPullParser.START_TAG 2394 && type != XmlPullParser.END_DOCUMENT) { 2395 // Skip 2396 } 2397 2398 if (type != XmlPullParser.START_TAG) { 2399 Slog.e(LOG_TAG, "Unable to read user " + id); 2400 return null; 2401 } 2402 2403 if (type == XmlPullParser.START_TAG && parser.getName().equals(TAG_USER)) { 2404 int storedId = readIntAttribute(parser, ATTR_ID, -1); 2405 if (storedId != id) { 2406 Slog.e(LOG_TAG, "User id does not match the file name"); 2407 return null; 2408 } 2409 serialNumber = readIntAttribute(parser, ATTR_SERIAL_NO, id); 2410 flags = readIntAttribute(parser, ATTR_FLAGS, 0); 2411 iconPath = parser.getAttributeValue(null, ATTR_ICON_PATH); 2412 creationTime = readLongAttribute(parser, ATTR_CREATION_TIME, 0); 2413 lastLoggedInTime = readLongAttribute(parser, ATTR_LAST_LOGGED_IN_TIME, 0); 2414 lastLoggedInFingerprint = parser.getAttributeValue(null, 2415 ATTR_LAST_LOGGED_IN_FINGERPRINT); 2416 profileGroupId = readIntAttribute(parser, ATTR_PROFILE_GROUP_ID, 2417 UserInfo.NO_PROFILE_GROUP_ID); 2418 profileBadge = readIntAttribute(parser, ATTR_PROFILE_BADGE, 0); 2419 restrictedProfileParentId = readIntAttribute(parser, 2420 ATTR_RESTRICTED_PROFILE_PARENT_ID, UserInfo.NO_PROFILE_GROUP_ID); 2421 String valueString = parser.getAttributeValue(null, ATTR_PARTIAL); 2422 if ("true".equals(valueString)) { 2423 partial = true; 2424 } 2425 valueString = parser.getAttributeValue(null, ATTR_GUEST_TO_REMOVE); 2426 if ("true".equals(valueString)) { 2427 guestToRemove = true; 2428 } 2429 2430 seedAccountName = parser.getAttributeValue(null, ATTR_SEED_ACCOUNT_NAME); 2431 seedAccountType = parser.getAttributeValue(null, ATTR_SEED_ACCOUNT_TYPE); 2432 if (seedAccountName != null || seedAccountType != null) { 2433 persistSeedData = true; 2434 } 2435 2436 int outerDepth = parser.getDepth(); 2437 while ((type = parser.next()) != XmlPullParser.END_DOCUMENT 2438 && (type != XmlPullParser.END_TAG || parser.getDepth() > outerDepth)) { 2439 if (type == XmlPullParser.END_TAG || type == XmlPullParser.TEXT) { 2440 continue; 2441 } 2442 String tag = parser.getName(); 2443 if (TAG_NAME.equals(tag)) { 2444 type = parser.next(); 2445 if (type == XmlPullParser.TEXT) { 2446 name = parser.getText(); 2447 } 2448 } else if (TAG_RESTRICTIONS.equals(tag)) { 2449 baseRestrictions = UserRestrictionsUtils.readRestrictions(parser); 2450 } else if (TAG_DEVICE_POLICY_RESTRICTIONS.equals(tag)) { 2451 localRestrictions = UserRestrictionsUtils.readRestrictions(parser); 2452 } else if (TAG_DEVICE_POLICY_GLOBAL_RESTRICTIONS.equals(tag)) { 2453 globalRestrictions = UserRestrictionsUtils.readRestrictions(parser); 2454 } else if (TAG_ACCOUNT.equals(tag)) { 2455 type = parser.next(); 2456 if (type == XmlPullParser.TEXT) { 2457 account = parser.getText(); 2458 } 2459 } else if (TAG_SEED_ACCOUNT_OPTIONS.equals(tag)) { 2460 seedAccountOptions = PersistableBundle.restoreFromXml(parser); 2461 persistSeedData = true; 2462 } 2463 } 2464 } 2465 2466 // Create the UserInfo object that gets passed around 2467 UserInfo userInfo = new UserInfo(id, name, iconPath, flags); 2468 userInfo.serialNumber = serialNumber; 2469 userInfo.creationTime = creationTime; 2470 userInfo.lastLoggedInTime = lastLoggedInTime; 2471 userInfo.lastLoggedInFingerprint = lastLoggedInFingerprint; 2472 userInfo.partial = partial; 2473 userInfo.guestToRemove = guestToRemove; 2474 userInfo.profileGroupId = profileGroupId; 2475 userInfo.profileBadge = profileBadge; 2476 userInfo.restrictedProfileParentId = restrictedProfileParentId; 2477 2478 // Create the UserData object that's internal to this class 2479 UserData userData = new UserData(); 2480 userData.info = userInfo; 2481 userData.account = account; 2482 userData.seedAccountName = seedAccountName; 2483 userData.seedAccountType = seedAccountType; 2484 userData.persistSeedData = persistSeedData; 2485 userData.seedAccountOptions = seedAccountOptions; 2486 2487 synchronized (mRestrictionsLock) { 2488 if (baseRestrictions != null) { 2489 mBaseUserRestrictions.put(id, baseRestrictions); 2490 } 2491 if (localRestrictions != null) { 2492 mDevicePolicyLocalUserRestrictions.put(id, localRestrictions); 2493 } 2494 if (globalRestrictions != null) { 2495 mDevicePolicyGlobalUserRestrictions.put(id, globalRestrictions); 2496 } 2497 } 2498 return userData; 2499 } 2500 2501 private int readIntAttribute(XmlPullParser parser, String attr, int defaultValue) { 2502 String valueString = parser.getAttributeValue(null, attr); 2503 if (valueString == null) return defaultValue; 2504 try { 2505 return Integer.parseInt(valueString); 2506 } catch (NumberFormatException nfe) { 2507 return defaultValue; 2508 } 2509 } 2510 2511 private long readLongAttribute(XmlPullParser parser, String attr, long defaultValue) { 2512 String valueString = parser.getAttributeValue(null, attr); 2513 if (valueString == null) return defaultValue; 2514 try { 2515 return Long.parseLong(valueString); 2516 } catch (NumberFormatException nfe) { 2517 return defaultValue; 2518 } 2519 } 2520 2521 /** 2522 * Removes the app restrictions file for a specific package and user id, if it exists. 2523 */ 2524 private static void cleanAppRestrictionsForPackageLAr(String pkg, int userId) { 2525 File dir = Environment.getUserSystemDirectory(userId); 2526 File resFile = new File(dir, packageToRestrictionsFileName(pkg)); 2527 if (resFile.exists()) { 2528 resFile.delete(); 2529 } 2530 } 2531 2532 @Override 2533 public UserInfo createProfileForUser(String name, int flags, int userId, 2534 String[] disallowedPackages) { 2535 checkManageOrCreateUsersPermission(flags); 2536 return createUserInternal(name, flags, userId, disallowedPackages); 2537 } 2538 2539 @Override 2540 public UserInfo createProfileForUserEvenWhenDisallowed(String name, int flags, int userId, 2541 String[] disallowedPackages) { 2542 checkManageOrCreateUsersPermission(flags); 2543 return createUserInternalUnchecked(name, flags, userId, disallowedPackages); 2544 } 2545 2546 @Override 2547 public boolean removeUserEvenWhenDisallowed(@UserIdInt int userHandle) { 2548 checkManageOrCreateUsersPermission("Only the system can remove users"); 2549 return removeUserUnchecked(userHandle); 2550 } 2551 2552 @Override 2553 public UserInfo createUser(String name, int flags) { 2554 checkManageOrCreateUsersPermission(flags); 2555 return createUserInternal(name, flags, UserHandle.USER_NULL); 2556 } 2557 2558 private UserInfo createUserInternal(String name, int flags, int parentId) { 2559 return createUserInternal(name, flags, parentId, null); 2560 } 2561 2562 private UserInfo createUserInternal(String name, int flags, int parentId, 2563 String[] disallowedPackages) { 2564 String restriction = ((flags & UserInfo.FLAG_MANAGED_PROFILE) != 0) 2565 ? UserManager.DISALLOW_ADD_MANAGED_PROFILE 2566 : UserManager.DISALLOW_ADD_USER; 2567 if (hasUserRestriction(restriction, UserHandle.getCallingUserId())) { 2568 Log.w(LOG_TAG, "Cannot add user. " + restriction + " is enabled."); 2569 return null; 2570 } 2571 return createUserInternalUnchecked(name, flags, parentId, disallowedPackages); 2572 } 2573 2574 private UserInfo createUserInternalUnchecked(String name, int flags, int parentId, 2575 String[] disallowedPackages) { 2576 DeviceStorageMonitorInternal dsm = LocalServices 2577 .getService(DeviceStorageMonitorInternal.class); 2578 if (dsm.isMemoryLow()) { 2579 Log.w(LOG_TAG, "Cannot add user. Not enough space on disk."); 2580 return null; 2581 } 2582 final boolean isGuest = (flags & UserInfo.FLAG_GUEST) != 0; 2583 final boolean isManagedProfile = (flags & UserInfo.FLAG_MANAGED_PROFILE) != 0; 2584 final boolean isRestricted = (flags & UserInfo.FLAG_RESTRICTED) != 0; 2585 final boolean isDemo = (flags & UserInfo.FLAG_DEMO) != 0; 2586 final long ident = Binder.clearCallingIdentity(); 2587 UserInfo userInfo; 2588 UserData userData; 2589 final int userId; 2590 try { 2591 synchronized (mPackagesLock) { 2592 UserData parent = null; 2593 if (parentId != UserHandle.USER_NULL) { 2594 synchronized (mUsersLock) { 2595 parent = getUserDataLU(parentId); 2596 } 2597 if (parent == null) return null; 2598 } 2599 if (isManagedProfile && !canAddMoreManagedProfiles(parentId, false)) { 2600 Log.e(LOG_TAG, "Cannot add more managed profiles for user " + parentId); 2601 return null; 2602 } 2603 if (!isGuest && !isManagedProfile && !isDemo && isUserLimitReached()) { 2604 // If we're not adding a guest/demo user or a managed profile and the limit has 2605 // been reached, cannot add a user. 2606 return null; 2607 } 2608 // If we're adding a guest and there already exists one, bail. 2609 if (isGuest && findCurrentGuestUser() != null) { 2610 return null; 2611 } 2612 // In legacy mode, restricted profile's parent can only be the owner user 2613 if (isRestricted && !UserManager.isSplitSystemUser() 2614 && (parentId != UserHandle.USER_SYSTEM)) { 2615 Log.w(LOG_TAG, "Cannot add restricted profile - parent user must be owner"); 2616 return null; 2617 } 2618 if (isRestricted && UserManager.isSplitSystemUser()) { 2619 if (parent == null) { 2620 Log.w(LOG_TAG, "Cannot add restricted profile - parent user must be " 2621 + "specified"); 2622 return null; 2623 } 2624 if (!parent.info.canHaveProfile()) { 2625 Log.w(LOG_TAG, "Cannot add restricted profile - profiles cannot be " 2626 + "created for the specified parent user id " + parentId); 2627 return null; 2628 } 2629 } 2630 // In split system user mode, we assign the first human user the primary flag. 2631 // And if there is no device owner, we also assign the admin flag to primary user. 2632 if (UserManager.isSplitSystemUser() 2633 && !isGuest && !isManagedProfile && getPrimaryUser() == null) { 2634 flags |= UserInfo.FLAG_PRIMARY; 2635 synchronized (mUsersLock) { 2636 if (!mIsDeviceManaged) { 2637 flags |= UserInfo.FLAG_ADMIN; 2638 } 2639 } 2640 } 2641 2642 userId = getNextAvailableId(); 2643 Environment.getUserSystemDirectory(userId).mkdirs(); 2644 boolean ephemeralGuests = Resources.getSystem() 2645 .getBoolean(com.android.internal.R.bool.config_guestUserEphemeral); 2646 2647 synchronized (mUsersLock) { 2648 // Add ephemeral flag to guests/users if required. Also inherit it from parent. 2649 if ((isGuest && ephemeralGuests) || mForceEphemeralUsers 2650 || (parent != null && parent.info.isEphemeral())) { 2651 flags |= UserInfo.FLAG_EPHEMERAL; 2652 } 2653 2654 userInfo = new UserInfo(userId, name, null, flags); 2655 userInfo.serialNumber = mNextSerialNumber++; 2656 long now = System.currentTimeMillis(); 2657 userInfo.creationTime = (now > EPOCH_PLUS_30_YEARS) ? now : 0; 2658 userInfo.partial = true; 2659 userInfo.lastLoggedInFingerprint = Build.FINGERPRINT; 2660 if (isManagedProfile && parentId != UserHandle.USER_NULL) { 2661 userInfo.profileBadge = getFreeProfileBadgeLU(parentId); 2662 } 2663 userData = new UserData(); 2664 userData.info = userInfo; 2665 mUsers.put(userId, userData); 2666 } 2667 writeUserLP(userData); 2668 writeUserListLP(); 2669 if (parent != null) { 2670 if (isManagedProfile) { 2671 if (parent.info.profileGroupId == UserInfo.NO_PROFILE_GROUP_ID) { 2672 parent.info.profileGroupId = parent.info.id; 2673 writeUserLP(parent); 2674 } 2675 userInfo.profileGroupId = parent.info.profileGroupId; 2676 } else if (isRestricted) { 2677 if (parent.info.restrictedProfileParentId == UserInfo.NO_PROFILE_GROUP_ID) { 2678 parent.info.restrictedProfileParentId = parent.info.id; 2679 writeUserLP(parent); 2680 } 2681 userInfo.restrictedProfileParentId = parent.info.restrictedProfileParentId; 2682 } 2683 } 2684 } 2685 final StorageManager storage = mContext.getSystemService(StorageManager.class); 2686 storage.createUserKey(userId, userInfo.serialNumber, userInfo.isEphemeral()); 2687 mUserDataPreparer.prepareUserData(userId, userInfo.serialNumber, 2688 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 2689 mPm.createNewUser(userId, disallowedPackages); 2690 userInfo.partial = false; 2691 synchronized (mPackagesLock) { 2692 writeUserLP(userData); 2693 } 2694 updateUserIds(); 2695 Bundle restrictions = new Bundle(); 2696 if (isGuest) { 2697 synchronized (mGuestRestrictions) { 2698 restrictions.putAll(mGuestRestrictions); 2699 } 2700 } 2701 synchronized (mRestrictionsLock) { 2702 mBaseUserRestrictions.append(userId, restrictions); 2703 } 2704 mPm.onNewUserCreated(userId); 2705 Intent addedIntent = new Intent(Intent.ACTION_USER_ADDED); 2706 addedIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 2707 mContext.sendBroadcastAsUser(addedIntent, UserHandle.ALL, 2708 android.Manifest.permission.MANAGE_USERS); 2709 MetricsLogger.count(mContext, isGuest ? TRON_GUEST_CREATED 2710 : (isDemo ? TRON_DEMO_CREATED : TRON_USER_CREATED), 1); 2711 } finally { 2712 Binder.restoreCallingIdentity(ident); 2713 } 2714 return userInfo; 2715 } 2716 2717 @VisibleForTesting 2718 UserData putUserInfo(UserInfo userInfo) { 2719 final UserData userData = new UserData(); 2720 userData.info = userInfo; 2721 synchronized (mUsers) { 2722 mUsers.put(userInfo.id, userData); 2723 } 2724 return userData; 2725 } 2726 2727 @VisibleForTesting 2728 void removeUserInfo(int userId) { 2729 synchronized (mUsers) { 2730 mUsers.remove(userId); 2731 } 2732 } 2733 2734 /** 2735 * @hide 2736 */ 2737 @Override 2738 public UserInfo createRestrictedProfile(String name, int parentUserId) { 2739 checkManageOrCreateUsersPermission("setupRestrictedProfile"); 2740 final UserInfo user = createProfileForUser( 2741 name, UserInfo.FLAG_RESTRICTED, parentUserId, null); 2742 if (user == null) { 2743 return null; 2744 } 2745 long identity = Binder.clearCallingIdentity(); 2746 try { 2747 setUserRestriction(UserManager.DISALLOW_MODIFY_ACCOUNTS, true, user.id); 2748 // Change the setting before applying the DISALLOW_SHARE_LOCATION restriction, otherwise 2749 // the putIntForUser() will fail. 2750 android.provider.Settings.Secure.putIntForUser(mContext.getContentResolver(), 2751 android.provider.Settings.Secure.LOCATION_MODE, 2752 android.provider.Settings.Secure.LOCATION_MODE_OFF, user.id); 2753 setUserRestriction(UserManager.DISALLOW_SHARE_LOCATION, true, user.id); 2754 } finally { 2755 Binder.restoreCallingIdentity(identity); 2756 } 2757 return user; 2758 } 2759 2760 /** 2761 * Find the current guest user. If the Guest user is partial, 2762 * then do not include it in the results as it is about to die. 2763 */ 2764 private UserInfo findCurrentGuestUser() { 2765 synchronized (mUsersLock) { 2766 final int size = mUsers.size(); 2767 for (int i = 0; i < size; i++) { 2768 final UserInfo user = mUsers.valueAt(i).info; 2769 if (user.isGuest() && !user.guestToRemove && !mRemovingUserIds.get(user.id)) { 2770 return user; 2771 } 2772 } 2773 } 2774 return null; 2775 } 2776 2777 /** 2778 * Mark this guest user for deletion to allow us to create another guest 2779 * and switch to that user before actually removing this guest. 2780 * @param userHandle the userid of the current guest 2781 * @return whether the user could be marked for deletion 2782 */ 2783 @Override 2784 public boolean markGuestForDeletion(int userHandle) { 2785 checkManageUsersPermission("Only the system can remove users"); 2786 if (getUserRestrictions(UserHandle.getCallingUserId()).getBoolean( 2787 UserManager.DISALLOW_REMOVE_USER, false)) { 2788 Log.w(LOG_TAG, "Cannot remove user. DISALLOW_REMOVE_USER is enabled."); 2789 return false; 2790 } 2791 2792 long ident = Binder.clearCallingIdentity(); 2793 try { 2794 final UserData userData; 2795 synchronized (mPackagesLock) { 2796 synchronized (mUsersLock) { 2797 userData = mUsers.get(userHandle); 2798 if (userHandle == 0 || userData == null || mRemovingUserIds.get(userHandle)) { 2799 return false; 2800 } 2801 } 2802 if (!userData.info.isGuest()) { 2803 return false; 2804 } 2805 // We set this to a guest user that is to be removed. This is a temporary state 2806 // where we are allowed to add new Guest users, even if this one is still not 2807 // removed. This user will still show up in getUserInfo() calls. 2808 // If we don't get around to removing this Guest user, it will be purged on next 2809 // startup. 2810 userData.info.guestToRemove = true; 2811 // Mark it as disabled, so that it isn't returned any more when 2812 // profiles are queried. 2813 userData.info.flags |= UserInfo.FLAG_DISABLED; 2814 writeUserLP(userData); 2815 } 2816 } finally { 2817 Binder.restoreCallingIdentity(ident); 2818 } 2819 return true; 2820 } 2821 2822 /** 2823 * Removes a user and all data directories created for that user. This method should be called 2824 * after the user's processes have been terminated. 2825 * @param userHandle the user's id 2826 */ 2827 @Override 2828 public boolean removeUser(int userHandle) { 2829 Slog.i(LOG_TAG, "removeUser u" + userHandle); 2830 checkManageOrCreateUsersPermission("Only the system can remove users"); 2831 2832 final boolean isManagedProfile; 2833 synchronized (mUsersLock) { 2834 UserInfo userInfo = getUserInfoLU(userHandle); 2835 isManagedProfile = userInfo != null && userInfo.isManagedProfile(); 2836 } 2837 String restriction = isManagedProfile 2838 ? UserManager.DISALLOW_REMOVE_MANAGED_PROFILE : UserManager.DISALLOW_REMOVE_USER; 2839 if (getUserRestrictions(UserHandle.getCallingUserId()).getBoolean(restriction, false)) { 2840 Log.w(LOG_TAG, "Cannot remove user. " + restriction + " is enabled."); 2841 return false; 2842 } 2843 return removeUserUnchecked(userHandle); 2844 } 2845 2846 private boolean removeUserUnchecked(int userHandle) { 2847 long ident = Binder.clearCallingIdentity(); 2848 try { 2849 final UserData userData; 2850 int currentUser = ActivityManager.getCurrentUser(); 2851 if (currentUser == userHandle) { 2852 Log.w(LOG_TAG, "Current user cannot be removed"); 2853 return false; 2854 } 2855 synchronized (mPackagesLock) { 2856 synchronized (mUsersLock) { 2857 userData = mUsers.get(userHandle); 2858 if (userHandle == 0 || userData == null || mRemovingUserIds.get(userHandle)) { 2859 return false; 2860 } 2861 2862 addRemovingUserIdLocked(userHandle); 2863 } 2864 2865 // Set this to a partially created user, so that the user will be purged 2866 // on next startup, in case the runtime stops now before stopping and 2867 // removing the user completely. 2868 userData.info.partial = true; 2869 // Mark it as disabled, so that it isn't returned any more when 2870 // profiles are queried. 2871 userData.info.flags |= UserInfo.FLAG_DISABLED; 2872 writeUserLP(userData); 2873 } 2874 try { 2875 mAppOpsService.removeUser(userHandle); 2876 } catch (RemoteException e) { 2877 Log.w(LOG_TAG, "Unable to notify AppOpsService of removing user", e); 2878 } 2879 2880 if (userData.info.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID 2881 && userData.info.isManagedProfile()) { 2882 // Send broadcast to notify system that the user removed was a 2883 // managed user. 2884 sendProfileRemovedBroadcast(userData.info.profileGroupId, userData.info.id); 2885 } 2886 2887 if (DBG) Slog.i(LOG_TAG, "Stopping user " + userHandle); 2888 int res; 2889 try { 2890 res = ActivityManager.getService().stopUser(userHandle, /* force= */ true, 2891 new IStopUserCallback.Stub() { 2892 @Override 2893 public void userStopped(int userId) { 2894 finishRemoveUser(userId); 2895 } 2896 @Override 2897 public void userStopAborted(int userId) { 2898 } 2899 }); 2900 } catch (RemoteException e) { 2901 return false; 2902 } 2903 return res == ActivityManager.USER_OP_SUCCESS; 2904 } finally { 2905 Binder.restoreCallingIdentity(ident); 2906 } 2907 } 2908 2909 @GuardedBy("mUsersLock") 2910 @VisibleForTesting 2911 void addRemovingUserIdLocked(int userId) { 2912 // We remember deleted user IDs to prevent them from being 2913 // reused during the current boot; they can still be reused 2914 // after a reboot or recycling of userIds. 2915 mRemovingUserIds.put(userId, true); 2916 mRecentlyRemovedIds.add(userId); 2917 // Keep LRU queue of recently removed IDs for recycling 2918 if (mRecentlyRemovedIds.size() > MAX_RECENTLY_REMOVED_IDS_SIZE) { 2919 mRecentlyRemovedIds.removeFirst(); 2920 } 2921 } 2922 2923 void finishRemoveUser(final int userHandle) { 2924 if (DBG) Slog.i(LOG_TAG, "finishRemoveUser " + userHandle); 2925 // Let other services shutdown any activity and clean up their state before completely 2926 // wiping the user's system directory and removing from the user list 2927 long ident = Binder.clearCallingIdentity(); 2928 try { 2929 Intent addedIntent = new Intent(Intent.ACTION_USER_REMOVED); 2930 addedIntent.putExtra(Intent.EXTRA_USER_HANDLE, userHandle); 2931 mContext.sendOrderedBroadcastAsUser(addedIntent, UserHandle.ALL, 2932 android.Manifest.permission.MANAGE_USERS, 2933 2934 new BroadcastReceiver() { 2935 @Override 2936 public void onReceive(Context context, Intent intent) { 2937 if (DBG) { 2938 Slog.i(LOG_TAG, 2939 "USER_REMOVED broadcast sent, cleaning up user data " 2940 + userHandle); 2941 } 2942 new Thread() { 2943 @Override 2944 public void run() { 2945 // Clean up any ActivityManager state 2946 LocalServices.getService(ActivityManagerInternal.class) 2947 .onUserRemoved(userHandle); 2948 removeUserState(userHandle); 2949 } 2950 }.start(); 2951 } 2952 }, 2953 2954 null, Activity.RESULT_OK, null, null); 2955 } finally { 2956 Binder.restoreCallingIdentity(ident); 2957 } 2958 } 2959 2960 private void removeUserState(final int userHandle) { 2961 try { 2962 mContext.getSystemService(StorageManager.class).destroyUserKey(userHandle); 2963 } catch (IllegalStateException e) { 2964 // This may be simply because the user was partially created. 2965 Slog.i(LOG_TAG, 2966 "Destroying key for user " + userHandle + " failed, continuing anyway", e); 2967 } 2968 2969 // Cleanup gatekeeper secure user id 2970 try { 2971 final IGateKeeperService gk = GateKeeper.getService(); 2972 if (gk != null) { 2973 gk.clearSecureUserId(userHandle); 2974 } 2975 } catch (Exception ex) { 2976 Slog.w(LOG_TAG, "unable to clear GK secure user id"); 2977 } 2978 2979 // Cleanup package manager settings 2980 mPm.cleanUpUser(this, userHandle); 2981 2982 // Clean up all data before removing metadata 2983 mUserDataPreparer.destroyUserData(userHandle, 2984 StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE); 2985 2986 // Remove this user from the list 2987 synchronized (mUsersLock) { 2988 mUsers.remove(userHandle); 2989 mIsUserManaged.delete(userHandle); 2990 } 2991 synchronized (mUserStates) { 2992 mUserStates.delete(userHandle); 2993 } 2994 synchronized (mRestrictionsLock) { 2995 mBaseUserRestrictions.remove(userHandle); 2996 mAppliedUserRestrictions.remove(userHandle); 2997 mCachedEffectiveUserRestrictions.remove(userHandle); 2998 mDevicePolicyLocalUserRestrictions.remove(userHandle); 2999 if (mDevicePolicyGlobalUserRestrictions.get(userHandle) != null) { 3000 mDevicePolicyGlobalUserRestrictions.remove(userHandle); 3001 applyUserRestrictionsForAllUsersLR(); 3002 } 3003 } 3004 // Update the user list 3005 synchronized (mPackagesLock) { 3006 writeUserListLP(); 3007 } 3008 // Remove user file 3009 AtomicFile userFile = new AtomicFile(new File(mUsersDir, userHandle + XML_SUFFIX)); 3010 userFile.delete(); 3011 updateUserIds(); 3012 if (RELEASE_DELETED_USER_ID) { 3013 synchronized (mUsers) { 3014 mRemovingUserIds.delete(userHandle); 3015 } 3016 } 3017 } 3018 3019 private void sendProfileRemovedBroadcast(int parentUserId, int removedUserId) { 3020 Intent managedProfileIntent = new Intent(Intent.ACTION_MANAGED_PROFILE_REMOVED); 3021 managedProfileIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY | 3022 Intent.FLAG_RECEIVER_FOREGROUND); 3023 managedProfileIntent.putExtra(Intent.EXTRA_USER, new UserHandle(removedUserId)); 3024 managedProfileIntent.putExtra(Intent.EXTRA_USER_HANDLE, removedUserId); 3025 mContext.sendBroadcastAsUser(managedProfileIntent, new UserHandle(parentUserId), null); 3026 } 3027 3028 @Override 3029 public Bundle getApplicationRestrictions(String packageName) { 3030 return getApplicationRestrictionsForUser(packageName, UserHandle.getCallingUserId()); 3031 } 3032 3033 @Override 3034 public Bundle getApplicationRestrictionsForUser(String packageName, int userId) { 3035 if (UserHandle.getCallingUserId() != userId 3036 || !UserHandle.isSameApp(Binder.getCallingUid(), getUidForPackage(packageName))) { 3037 checkSystemOrRoot("get application restrictions for other user/app " + packageName); 3038 } 3039 synchronized (mAppRestrictionsLock) { 3040 // Read the restrictions from XML 3041 return readApplicationRestrictionsLAr(packageName, userId); 3042 } 3043 } 3044 3045 @Override 3046 public void setApplicationRestrictions(String packageName, Bundle restrictions, 3047 int userId) { 3048 checkSystemOrRoot("set application restrictions"); 3049 if (restrictions != null) { 3050 restrictions.setDefusable(true); 3051 } 3052 synchronized (mAppRestrictionsLock) { 3053 if (restrictions == null || restrictions.isEmpty()) { 3054 cleanAppRestrictionsForPackageLAr(packageName, userId); 3055 } else { 3056 // Write the restrictions to XML 3057 writeApplicationRestrictionsLAr(packageName, restrictions, userId); 3058 } 3059 } 3060 3061 // Notify package of changes via an intent - only sent to explicitly registered receivers. 3062 Intent changeIntent = new Intent(Intent.ACTION_APPLICATION_RESTRICTIONS_CHANGED); 3063 changeIntent.setPackage(packageName); 3064 changeIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 3065 mContext.sendBroadcastAsUser(changeIntent, UserHandle.of(userId)); 3066 } 3067 3068 private int getUidForPackage(String packageName) { 3069 long ident = Binder.clearCallingIdentity(); 3070 try { 3071 return mContext.getPackageManager().getApplicationInfo(packageName, 3072 PackageManager.MATCH_ANY_USER).uid; 3073 } catch (NameNotFoundException nnfe) { 3074 return -1; 3075 } finally { 3076 Binder.restoreCallingIdentity(ident); 3077 } 3078 } 3079 3080 @GuardedBy("mAppRestrictionsLock") 3081 private static Bundle readApplicationRestrictionsLAr(String packageName, int userId) { 3082 AtomicFile restrictionsFile = 3083 new AtomicFile(new File(Environment.getUserSystemDirectory(userId), 3084 packageToRestrictionsFileName(packageName))); 3085 return readApplicationRestrictionsLAr(restrictionsFile); 3086 } 3087 3088 @VisibleForTesting 3089 @GuardedBy("mAppRestrictionsLock") 3090 static Bundle readApplicationRestrictionsLAr(AtomicFile restrictionsFile) { 3091 final Bundle restrictions = new Bundle(); 3092 final ArrayList<String> values = new ArrayList<>(); 3093 if (!restrictionsFile.getBaseFile().exists()) { 3094 return restrictions; 3095 } 3096 3097 FileInputStream fis = null; 3098 try { 3099 fis = restrictionsFile.openRead(); 3100 XmlPullParser parser = Xml.newPullParser(); 3101 parser.setInput(fis, StandardCharsets.UTF_8.name()); 3102 XmlUtils.nextElement(parser); 3103 if (parser.getEventType() != XmlPullParser.START_TAG) { 3104 Slog.e(LOG_TAG, "Unable to read restrictions file " 3105 + restrictionsFile.getBaseFile()); 3106 return restrictions; 3107 } 3108 while (parser.next() != XmlPullParser.END_DOCUMENT) { 3109 readEntry(restrictions, values, parser); 3110 } 3111 } catch (IOException|XmlPullParserException e) { 3112 Log.w(LOG_TAG, "Error parsing " + restrictionsFile.getBaseFile(), e); 3113 } finally { 3114 IoUtils.closeQuietly(fis); 3115 } 3116 return restrictions; 3117 } 3118 3119 private static void readEntry(Bundle restrictions, ArrayList<String> values, 3120 XmlPullParser parser) throws XmlPullParserException, IOException { 3121 int type = parser.getEventType(); 3122 if (type == XmlPullParser.START_TAG && parser.getName().equals(TAG_ENTRY)) { 3123 String key = parser.getAttributeValue(null, ATTR_KEY); 3124 String valType = parser.getAttributeValue(null, ATTR_VALUE_TYPE); 3125 String multiple = parser.getAttributeValue(null, ATTR_MULTIPLE); 3126 if (multiple != null) { 3127 values.clear(); 3128 int count = Integer.parseInt(multiple); 3129 while (count > 0 && (type = parser.next()) != XmlPullParser.END_DOCUMENT) { 3130 if (type == XmlPullParser.START_TAG 3131 && parser.getName().equals(TAG_VALUE)) { 3132 values.add(parser.nextText().trim()); 3133 count--; 3134 } 3135 } 3136 String [] valueStrings = new String[values.size()]; 3137 values.toArray(valueStrings); 3138 restrictions.putStringArray(key, valueStrings); 3139 } else if (ATTR_TYPE_BUNDLE.equals(valType)) { 3140 restrictions.putBundle(key, readBundleEntry(parser, values)); 3141 } else if (ATTR_TYPE_BUNDLE_ARRAY.equals(valType)) { 3142 final int outerDepth = parser.getDepth(); 3143 ArrayList<Bundle> bundleList = new ArrayList<>(); 3144 while (XmlUtils.nextElementWithin(parser, outerDepth)) { 3145 Bundle childBundle = readBundleEntry(parser, values); 3146 bundleList.add(childBundle); 3147 } 3148 restrictions.putParcelableArray(key, 3149 bundleList.toArray(new Bundle[bundleList.size()])); 3150 } else { 3151 String value = parser.nextText().trim(); 3152 if (ATTR_TYPE_BOOLEAN.equals(valType)) { 3153 restrictions.putBoolean(key, Boolean.parseBoolean(value)); 3154 } else if (ATTR_TYPE_INTEGER.equals(valType)) { 3155 restrictions.putInt(key, Integer.parseInt(value)); 3156 } else { 3157 restrictions.putString(key, value); 3158 } 3159 } 3160 } 3161 } 3162 3163 private static Bundle readBundleEntry(XmlPullParser parser, ArrayList<String> values) 3164 throws IOException, XmlPullParserException { 3165 Bundle childBundle = new Bundle(); 3166 final int outerDepth = parser.getDepth(); 3167 while (XmlUtils.nextElementWithin(parser, outerDepth)) { 3168 readEntry(childBundle, values, parser); 3169 } 3170 return childBundle; 3171 } 3172 3173 @GuardedBy("mAppRestrictionsLock") 3174 private static void writeApplicationRestrictionsLAr(String packageName, 3175 Bundle restrictions, int userId) { 3176 AtomicFile restrictionsFile = new AtomicFile( 3177 new File(Environment.getUserSystemDirectory(userId), 3178 packageToRestrictionsFileName(packageName))); 3179 writeApplicationRestrictionsLAr(restrictions, restrictionsFile); 3180 } 3181 3182 @VisibleForTesting 3183 @GuardedBy("mAppRestrictionsLock") 3184 static void writeApplicationRestrictionsLAr(Bundle restrictions, AtomicFile restrictionsFile) { 3185 FileOutputStream fos = null; 3186 try { 3187 fos = restrictionsFile.startWrite(); 3188 final BufferedOutputStream bos = new BufferedOutputStream(fos); 3189 3190 final XmlSerializer serializer = new FastXmlSerializer(); 3191 serializer.setOutput(bos, StandardCharsets.UTF_8.name()); 3192 serializer.startDocument(null, true); 3193 serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true); 3194 3195 serializer.startTag(null, TAG_RESTRICTIONS); 3196 writeBundle(restrictions, serializer); 3197 serializer.endTag(null, TAG_RESTRICTIONS); 3198 3199 serializer.endDocument(); 3200 restrictionsFile.finishWrite(fos); 3201 } catch (Exception e) { 3202 restrictionsFile.failWrite(fos); 3203 Slog.e(LOG_TAG, "Error writing application restrictions list", e); 3204 } 3205 } 3206 3207 private static void writeBundle(Bundle restrictions, XmlSerializer serializer) 3208 throws IOException { 3209 for (String key : restrictions.keySet()) { 3210 Object value = restrictions.get(key); 3211 serializer.startTag(null, TAG_ENTRY); 3212 serializer.attribute(null, ATTR_KEY, key); 3213 3214 if (value instanceof Boolean) { 3215 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_BOOLEAN); 3216 serializer.text(value.toString()); 3217 } else if (value instanceof Integer) { 3218 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_INTEGER); 3219 serializer.text(value.toString()); 3220 } else if (value == null || value instanceof String) { 3221 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_STRING); 3222 serializer.text(value != null ? (String) value : ""); 3223 } else if (value instanceof Bundle) { 3224 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_BUNDLE); 3225 writeBundle((Bundle) value, serializer); 3226 } else if (value instanceof Parcelable[]) { 3227 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_BUNDLE_ARRAY); 3228 Parcelable[] array = (Parcelable[]) value; 3229 for (Parcelable parcelable : array) { 3230 if (!(parcelable instanceof Bundle)) { 3231 throw new IllegalArgumentException("bundle-array can only hold Bundles"); 3232 } 3233 serializer.startTag(null, TAG_ENTRY); 3234 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_BUNDLE); 3235 writeBundle((Bundle) parcelable, serializer); 3236 serializer.endTag(null, TAG_ENTRY); 3237 } 3238 } else { 3239 serializer.attribute(null, ATTR_VALUE_TYPE, ATTR_TYPE_STRING_ARRAY); 3240 String[] values = (String[]) value; 3241 serializer.attribute(null, ATTR_MULTIPLE, Integer.toString(values.length)); 3242 for (String choice : values) { 3243 serializer.startTag(null, TAG_VALUE); 3244 serializer.text(choice != null ? choice : ""); 3245 serializer.endTag(null, TAG_VALUE); 3246 } 3247 } 3248 serializer.endTag(null, TAG_ENTRY); 3249 } 3250 } 3251 3252 @Override 3253 public int getUserSerialNumber(int userHandle) { 3254 synchronized (mUsersLock) { 3255 if (!exists(userHandle)) return -1; 3256 return getUserInfoLU(userHandle).serialNumber; 3257 } 3258 } 3259 3260 @Override 3261 public boolean isUserNameSet(int userHandle) { 3262 synchronized (mUsersLock) { 3263 UserInfo userInfo = getUserInfoLU(userHandle); 3264 return userInfo != null && userInfo.name != null; 3265 } 3266 } 3267 3268 @Override 3269 public int getUserHandle(int userSerialNumber) { 3270 synchronized (mUsersLock) { 3271 for (int userId : mUserIds) { 3272 UserInfo info = getUserInfoLU(userId); 3273 if (info != null && info.serialNumber == userSerialNumber) return userId; 3274 } 3275 // Not found 3276 return -1; 3277 } 3278 } 3279 3280 @Override 3281 public long getUserCreationTime(int userHandle) { 3282 int callingUserId = UserHandle.getCallingUserId(); 3283 UserInfo userInfo = null; 3284 synchronized (mUsersLock) { 3285 if (callingUserId == userHandle) { 3286 userInfo = getUserInfoLU(userHandle); 3287 } else { 3288 UserInfo parent = getProfileParentLU(userHandle); 3289 if (parent != null && parent.id == callingUserId) { 3290 userInfo = getUserInfoLU(userHandle); 3291 } 3292 } 3293 } 3294 if (userInfo == null) { 3295 throw new SecurityException("userHandle can only be the calling user or a managed " 3296 + "profile associated with this user"); 3297 } 3298 return userInfo.creationTime; 3299 } 3300 3301 /** 3302 * Caches the list of user ids in an array, adjusting the array size when necessary. 3303 */ 3304 private void updateUserIds() { 3305 int num = 0; 3306 synchronized (mUsersLock) { 3307 final int userSize = mUsers.size(); 3308 for (int i = 0; i < userSize; i++) { 3309 if (!mUsers.valueAt(i).info.partial) { 3310 num++; 3311 } 3312 } 3313 final int[] newUsers = new int[num]; 3314 int n = 0; 3315 for (int i = 0; i < userSize; i++) { 3316 if (!mUsers.valueAt(i).info.partial) { 3317 newUsers[n++] = mUsers.keyAt(i); 3318 } 3319 } 3320 mUserIds = newUsers; 3321 } 3322 } 3323 3324 /** 3325 * Called right before a user is started. This gives us a chance to prepare 3326 * app storage and apply any user restrictions. 3327 */ 3328 public void onBeforeStartUser(int userId) { 3329 UserInfo userInfo = getUserInfo(userId); 3330 if (userInfo == null) { 3331 return; 3332 } 3333 final int userSerial = userInfo.serialNumber; 3334 // Migrate only if build fingerprints mismatch 3335 boolean migrateAppsData = !Build.FINGERPRINT.equals(userInfo.lastLoggedInFingerprint); 3336 mUserDataPreparer.prepareUserData(userId, userSerial, StorageManager.FLAG_STORAGE_DE); 3337 mPm.reconcileAppsData(userId, StorageManager.FLAG_STORAGE_DE, migrateAppsData); 3338 3339 if (userId != UserHandle.USER_SYSTEM) { 3340 synchronized (mRestrictionsLock) { 3341 applyUserRestrictionsLR(userId); 3342 } 3343 } 3344 } 3345 3346 /** 3347 * Called right before a user is unlocked. This gives us a chance to prepare 3348 * app storage. 3349 */ 3350 public void onBeforeUnlockUser(@UserIdInt int userId) { 3351 UserInfo userInfo = getUserInfo(userId); 3352 if (userInfo == null) { 3353 return; 3354 } 3355 final int userSerial = userInfo.serialNumber; 3356 // Migrate only if build fingerprints mismatch 3357 boolean migrateAppsData = !Build.FINGERPRINT.equals(userInfo.lastLoggedInFingerprint); 3358 mUserDataPreparer.prepareUserData(userId, userSerial, StorageManager.FLAG_STORAGE_CE); 3359 mPm.reconcileAppsData(userId, StorageManager.FLAG_STORAGE_CE, migrateAppsData); 3360 } 3361 3362 /** 3363 * Examine all users present on given mounted volume, and destroy data 3364 * belonging to users that are no longer valid, or whose user ID has been 3365 * recycled. 3366 */ 3367 void reconcileUsers(String volumeUuid) { 3368 mUserDataPreparer.reconcileUsers(volumeUuid, getUsers(true /* excludeDying */)); 3369 } 3370 3371 /** 3372 * Make a note of the last started time of a user and do some cleanup. 3373 * This is called with ActivityManagerService lock held. 3374 * @param userId the user that was just foregrounded 3375 */ 3376 public void onUserLoggedIn(@UserIdInt int userId) { 3377 UserData userData = getUserDataNoChecks(userId); 3378 if (userData == null || userData.info.partial) { 3379 Slog.w(LOG_TAG, "userForeground: unknown user #" + userId); 3380 return; 3381 } 3382 3383 final long now = System.currentTimeMillis(); 3384 if (now > EPOCH_PLUS_30_YEARS) { 3385 userData.info.lastLoggedInTime = now; 3386 } 3387 userData.info.lastLoggedInFingerprint = Build.FINGERPRINT; 3388 scheduleWriteUser(userData); 3389 } 3390 3391 /** 3392 * Returns the next available user id, filling in any holes in the ids. 3393 */ 3394 @VisibleForTesting 3395 int getNextAvailableId() { 3396 int nextId; 3397 synchronized (mUsersLock) { 3398 nextId = scanNextAvailableIdLocked(); 3399 if (nextId >= 0) { 3400 return nextId; 3401 } 3402 // All ids up to MAX_USER_ID were used. Remove all mRemovingUserIds, 3403 // except most recently removed 3404 if (mRemovingUserIds.size() > 0) { 3405 Slog.i(LOG_TAG, "All available IDs are used. Recycling LRU ids."); 3406 mRemovingUserIds.clear(); 3407 for (Integer recentlyRemovedId : mRecentlyRemovedIds) { 3408 mRemovingUserIds.put(recentlyRemovedId, true); 3409 } 3410 nextId = scanNextAvailableIdLocked(); 3411 } 3412 } 3413 if (nextId < 0) { 3414 throw new IllegalStateException("No user id available!"); 3415 } 3416 return nextId; 3417 } 3418 3419 @GuardedBy("mUsersLock") 3420 private int scanNextAvailableIdLocked() { 3421 for (int i = MIN_USER_ID; i < MAX_USER_ID; i++) { 3422 if (mUsers.indexOfKey(i) < 0 && !mRemovingUserIds.get(i)) { 3423 return i; 3424 } 3425 } 3426 return -1; 3427 } 3428 3429 private static String packageToRestrictionsFileName(String packageName) { 3430 return RESTRICTIONS_FILE_PREFIX + packageName + XML_SUFFIX; 3431 } 3432 3433 @Override 3434 public void setSeedAccountData(int userId, String accountName, String accountType, 3435 PersistableBundle accountOptions, boolean persist) { 3436 checkManageUsersPermission("Require MANAGE_USERS permission to set user seed data"); 3437 synchronized (mPackagesLock) { 3438 final UserData userData; 3439 synchronized (mUsersLock) { 3440 userData = getUserDataLU(userId); 3441 if (userData == null) { 3442 Slog.e(LOG_TAG, "No such user for settings seed data u=" + userId); 3443 return; 3444 } 3445 userData.seedAccountName = accountName; 3446 userData.seedAccountType = accountType; 3447 userData.seedAccountOptions = accountOptions; 3448 userData.persistSeedData = persist; 3449 } 3450 if (persist) { 3451 writeUserLP(userData); 3452 } 3453 } 3454 } 3455 3456 @Override 3457 public String getSeedAccountName() throws RemoteException { 3458 checkManageUsersPermission("Cannot get seed account information"); 3459 synchronized (mUsersLock) { 3460 UserData userData = getUserDataLU(UserHandle.getCallingUserId()); 3461 return userData.seedAccountName; 3462 } 3463 } 3464 3465 @Override 3466 public String getSeedAccountType() throws RemoteException { 3467 checkManageUsersPermission("Cannot get seed account information"); 3468 synchronized (mUsersLock) { 3469 UserData userData = getUserDataLU(UserHandle.getCallingUserId()); 3470 return userData.seedAccountType; 3471 } 3472 } 3473 3474 @Override 3475 public PersistableBundle getSeedAccountOptions() throws RemoteException { 3476 checkManageUsersPermission("Cannot get seed account information"); 3477 synchronized (mUsersLock) { 3478 UserData userData = getUserDataLU(UserHandle.getCallingUserId()); 3479 return userData.seedAccountOptions; 3480 } 3481 } 3482 3483 @Override 3484 public void clearSeedAccountData() throws RemoteException { 3485 checkManageUsersPermission("Cannot clear seed account information"); 3486 synchronized (mPackagesLock) { 3487 UserData userData; 3488 synchronized (mUsersLock) { 3489 userData = getUserDataLU(UserHandle.getCallingUserId()); 3490 if (userData == null) return; 3491 userData.clearSeedAccountData(); 3492 } 3493 writeUserLP(userData); 3494 } 3495 } 3496 3497 @Override 3498 public boolean someUserHasSeedAccount(String accountName, String accountType) 3499 throws RemoteException { 3500 checkManageUsersPermission("Cannot check seed account information"); 3501 synchronized (mUsersLock) { 3502 final int userSize = mUsers.size(); 3503 for (int i = 0; i < userSize; i++) { 3504 final UserData data = mUsers.valueAt(i); 3505 if (data.info.isInitialized()) continue; 3506 if (data.seedAccountName == null || !data.seedAccountName.equals(accountName)) { 3507 continue; 3508 } 3509 if (data.seedAccountType == null || !data.seedAccountType.equals(accountType)) { 3510 continue; 3511 } 3512 return true; 3513 } 3514 } 3515 return false; 3516 } 3517 3518 @Override 3519 public void onShellCommand(FileDescriptor in, FileDescriptor out, 3520 FileDescriptor err, String[] args, ShellCallback callback, 3521 ResultReceiver resultReceiver) { 3522 (new Shell()).exec(this, in, out, err, args, callback, resultReceiver); 3523 } 3524 3525 int onShellCommand(Shell shell, String cmd) { 3526 if (cmd == null) { 3527 return shell.handleDefaultCommands(cmd); 3528 } 3529 3530 final PrintWriter pw = shell.getOutPrintWriter(); 3531 try { 3532 switch(cmd) { 3533 case "list": 3534 return runList(pw); 3535 } 3536 } catch (RemoteException e) { 3537 pw.println("Remote exception: " + e); 3538 } 3539 return -1; 3540 } 3541 3542 private int runList(PrintWriter pw) throws RemoteException { 3543 final IActivityManager am = ActivityManager.getService(); 3544 final List<UserInfo> users = getUsers(false); 3545 if (users == null) { 3546 pw.println("Error: couldn't get users"); 3547 return 1; 3548 } else { 3549 pw.println("Users:"); 3550 for (int i = 0; i < users.size(); i++) { 3551 String running = am.isUserRunning(users.get(i).id, 0) ? " running" : ""; 3552 pw.println("\t" + users.get(i).toString() + running); 3553 } 3554 return 0; 3555 } 3556 } 3557 3558 @Override 3559 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 3560 if (!DumpUtils.checkDumpPermission(mContext, LOG_TAG, pw)) return; 3561 3562 long now = System.currentTimeMillis(); 3563 final long nowRealtime = SystemClock.elapsedRealtime(); 3564 StringBuilder sb = new StringBuilder(); 3565 synchronized (mPackagesLock) { 3566 synchronized (mUsersLock) { 3567 pw.println("Users:"); 3568 for (int i = 0; i < mUsers.size(); i++) { 3569 UserData userData = mUsers.valueAt(i); 3570 if (userData == null) { 3571 continue; 3572 } 3573 UserInfo userInfo = userData.info; 3574 final int userId = userInfo.id; 3575 pw.print(" "); pw.print(userInfo); 3576 pw.print(" serialNo="); pw.print(userInfo.serialNumber); 3577 if (mRemovingUserIds.get(userId)) { 3578 pw.print(" <removing> "); 3579 } 3580 if (userInfo.partial) { 3581 pw.print(" <partial>"); 3582 } 3583 pw.println(); 3584 pw.print(" State: "); 3585 final int state; 3586 synchronized (mUserStates) { 3587 state = mUserStates.get(userId, -1); 3588 } 3589 pw.println(UserState.stateToString(state)); 3590 pw.print(" Created: "); 3591 dumpTimeAgo(pw, sb, now, userInfo.creationTime); 3592 3593 pw.print(" Last logged in: "); 3594 dumpTimeAgo(pw, sb, now, userInfo.lastLoggedInTime); 3595 3596 pw.print(" Last logged in fingerprint: "); 3597 pw.println(userInfo.lastLoggedInFingerprint); 3598 3599 pw.print(" Start time: "); 3600 dumpTimeAgo(pw, sb, nowRealtime, userData.startRealtime); 3601 3602 pw.print(" Unlock time: "); 3603 dumpTimeAgo(pw, sb, nowRealtime, userData.unlockRealtime); 3604 3605 pw.print(" Has profile owner: "); 3606 pw.println(mIsUserManaged.get(userId)); 3607 pw.println(" Restrictions:"); 3608 synchronized (mRestrictionsLock) { 3609 UserRestrictionsUtils.dumpRestrictions( 3610 pw, " ", mBaseUserRestrictions.get(userInfo.id)); 3611 pw.println(" Device policy global restrictions:"); 3612 UserRestrictionsUtils.dumpRestrictions( 3613 pw, " ", mDevicePolicyGlobalUserRestrictions.get(userInfo.id)); 3614 pw.println(" Device policy local restrictions:"); 3615 UserRestrictionsUtils.dumpRestrictions( 3616 pw, " ", mDevicePolicyLocalUserRestrictions.get(userInfo.id)); 3617 pw.println(" Effective restrictions:"); 3618 UserRestrictionsUtils.dumpRestrictions( 3619 pw, " ", mCachedEffectiveUserRestrictions.get(userInfo.id)); 3620 } 3621 3622 if (userData.account != null) { 3623 pw.print(" Account name: " + userData.account); 3624 pw.println(); 3625 } 3626 3627 if (userData.seedAccountName != null) { 3628 pw.print(" Seed account name: " + userData.seedAccountName); 3629 pw.println(); 3630 if (userData.seedAccountType != null) { 3631 pw.print(" account type: " + userData.seedAccountType); 3632 pw.println(); 3633 } 3634 if (userData.seedAccountOptions != null) { 3635 pw.print(" account options exist"); 3636 pw.println(); 3637 } 3638 } 3639 } 3640 } 3641 pw.println(); 3642 pw.println(" Device owner id:" + mDeviceOwnerUserId); 3643 pw.println(); 3644 pw.println(" Guest restrictions:"); 3645 synchronized (mGuestRestrictions) { 3646 UserRestrictionsUtils.dumpRestrictions(pw, " ", mGuestRestrictions); 3647 } 3648 synchronized (mUsersLock) { 3649 pw.println(); 3650 pw.println(" Device managed: " + mIsDeviceManaged); 3651 if (mRemovingUserIds.size() > 0) { 3652 pw.println(); 3653 pw.println(" Recently removed userIds: " + mRecentlyRemovedIds); 3654 } 3655 } 3656 synchronized (mUserStates) { 3657 pw.println(" Started users state: " + mUserStates); 3658 } 3659 // Dump some capabilities 3660 pw.println(); 3661 pw.println(" Max users: " + UserManager.getMaxSupportedUsers()); 3662 pw.println(" Supports switchable users: " + UserManager.supportsMultipleUsers()); 3663 pw.println(" All guests ephemeral: " + Resources.getSystem().getBoolean( 3664 com.android.internal.R.bool.config_guestUserEphemeral)); 3665 } 3666 } 3667 3668 private static void dumpTimeAgo(PrintWriter pw, StringBuilder sb, long nowTime, long time) { 3669 if (time == 0) { 3670 pw.println("<unknown>"); 3671 } else { 3672 sb.setLength(0); 3673 TimeUtils.formatDuration(nowTime - time, sb); 3674 sb.append(" ago"); 3675 pw.println(sb); 3676 } 3677 } 3678 3679 final class MainHandler extends Handler { 3680 3681 @Override 3682 public void handleMessage(Message msg) { 3683 switch (msg.what) { 3684 case WRITE_USER_MSG: 3685 removeMessages(WRITE_USER_MSG, msg.obj); 3686 synchronized (mPackagesLock) { 3687 int userId = ((UserData) msg.obj).info.id; 3688 UserData userData = getUserDataNoChecks(userId); 3689 if (userData != null) { 3690 writeUserLP(userData); 3691 } 3692 } 3693 } 3694 } 3695 } 3696 3697 /** 3698 * @param userId 3699 * @return whether the user has been initialized yet 3700 */ 3701 boolean isUserInitialized(int userId) { 3702 return mLocalService.isUserInitialized(userId); 3703 } 3704 3705 private class LocalService extends UserManagerInternal { 3706 @Override 3707 public void setDevicePolicyUserRestrictions(int userId, @Nullable Bundle restrictions, 3708 boolean isDeviceOwner, int cameraRestrictionScope) { 3709 UserManagerService.this.setDevicePolicyUserRestrictionsInner(userId, restrictions, 3710 isDeviceOwner, cameraRestrictionScope); 3711 } 3712 3713 @Override 3714 public Bundle getBaseUserRestrictions(int userId) { 3715 synchronized (mRestrictionsLock) { 3716 return mBaseUserRestrictions.get(userId); 3717 } 3718 } 3719 3720 @Override 3721 public void setBaseUserRestrictionsByDpmsForMigration( 3722 int userId, Bundle baseRestrictions) { 3723 synchronized (mRestrictionsLock) { 3724 if (updateRestrictionsIfNeededLR( 3725 userId, new Bundle(baseRestrictions), mBaseUserRestrictions)) { 3726 invalidateEffectiveUserRestrictionsLR(userId); 3727 } 3728 } 3729 3730 final UserData userData = getUserDataNoChecks(userId); 3731 synchronized (mPackagesLock) { 3732 if (userData != null) { 3733 writeUserLP(userData); 3734 } else { 3735 Slog.w(LOG_TAG, "UserInfo not found for " + userId); 3736 } 3737 } 3738 } 3739 3740 @Override 3741 public boolean getUserRestriction(int userId, String key) { 3742 return getUserRestrictions(userId).getBoolean(key); 3743 } 3744 3745 @Override 3746 public void addUserRestrictionsListener(UserRestrictionsListener listener) { 3747 synchronized (mUserRestrictionsListeners) { 3748 mUserRestrictionsListeners.add(listener); 3749 } 3750 } 3751 3752 @Override 3753 public void removeUserRestrictionsListener(UserRestrictionsListener listener) { 3754 synchronized (mUserRestrictionsListeners) { 3755 mUserRestrictionsListeners.remove(listener); 3756 } 3757 } 3758 3759 @Override 3760 public void setDeviceManaged(boolean isManaged) { 3761 synchronized (mUsersLock) { 3762 mIsDeviceManaged = isManaged; 3763 } 3764 } 3765 3766 @Override 3767 public void setUserManaged(int userId, boolean isManaged) { 3768 synchronized (mUsersLock) { 3769 mIsUserManaged.put(userId, isManaged); 3770 } 3771 } 3772 3773 @Override 3774 public void setUserIcon(int userId, Bitmap bitmap) { 3775 long ident = Binder.clearCallingIdentity(); 3776 try { 3777 synchronized (mPackagesLock) { 3778 UserData userData = getUserDataNoChecks(userId); 3779 if (userData == null || userData.info.partial) { 3780 Slog.w(LOG_TAG, "setUserIcon: unknown user #" + userId); 3781 return; 3782 } 3783 writeBitmapLP(userData.info, bitmap); 3784 writeUserLP(userData); 3785 } 3786 sendUserInfoChangedBroadcast(userId); 3787 } finally { 3788 Binder.restoreCallingIdentity(ident); 3789 } 3790 } 3791 3792 @Override 3793 public void setForceEphemeralUsers(boolean forceEphemeralUsers) { 3794 synchronized (mUsersLock) { 3795 mForceEphemeralUsers = forceEphemeralUsers; 3796 } 3797 } 3798 3799 @Override 3800 public void removeAllUsers() { 3801 if (UserHandle.USER_SYSTEM == ActivityManager.getCurrentUser()) { 3802 // Remove the non-system users straight away. 3803 removeNonSystemUsers(); 3804 } else { 3805 // Switch to the system user first and then remove the other users. 3806 BroadcastReceiver userSwitchedReceiver = new BroadcastReceiver() { 3807 @Override 3808 public void onReceive(Context context, Intent intent) { 3809 int userId = 3810 intent.getIntExtra(Intent.EXTRA_USER_HANDLE, UserHandle.USER_NULL); 3811 if (userId != UserHandle.USER_SYSTEM) { 3812 return; 3813 } 3814 mContext.unregisterReceiver(this); 3815 removeNonSystemUsers(); 3816 } 3817 }; 3818 IntentFilter userSwitchedFilter = new IntentFilter(); 3819 userSwitchedFilter.addAction(Intent.ACTION_USER_SWITCHED); 3820 mContext.registerReceiver( 3821 userSwitchedReceiver, userSwitchedFilter, null, mHandler); 3822 3823 // Switch to the system user. 3824 ActivityManager am = 3825 (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE); 3826 am.switchUser(UserHandle.USER_SYSTEM); 3827 } 3828 } 3829 3830 @Override 3831 public void onEphemeralUserStop(int userId) { 3832 synchronized (mUsersLock) { 3833 UserInfo userInfo = getUserInfoLU(userId); 3834 if (userInfo != null && userInfo.isEphemeral()) { 3835 // Do not allow switching back to the ephemeral user again as the user is going 3836 // to be deleted. 3837 userInfo.flags |= UserInfo.FLAG_DISABLED; 3838 if (userInfo.isGuest()) { 3839 // Indicate that the guest will be deleted after it stops. 3840 userInfo.guestToRemove = true; 3841 } 3842 } 3843 } 3844 } 3845 3846 @Override 3847 public UserInfo createUserEvenWhenDisallowed(String name, int flags, 3848 String[] disallowedPackages) { 3849 UserInfo user = createUserInternalUnchecked(name, flags, UserHandle.USER_NULL, 3850 disallowedPackages); 3851 // Keep this in sync with UserManager.createUser 3852 if (user != null && !user.isAdmin() && !user.isDemo()) { 3853 setUserRestriction(UserManager.DISALLOW_SMS, true, user.id); 3854 setUserRestriction(UserManager.DISALLOW_OUTGOING_CALLS, true, user.id); 3855 } 3856 return user; 3857 } 3858 3859 @Override 3860 public boolean removeUserEvenWhenDisallowed(int userId) { 3861 return removeUserUnchecked(userId); 3862 } 3863 3864 @Override 3865 public boolean isUserRunning(int userId) { 3866 synchronized (mUserStates) { 3867 return mUserStates.get(userId, -1) >= 0; 3868 } 3869 } 3870 3871 @Override 3872 public void setUserState(int userId, int userState) { 3873 synchronized (mUserStates) { 3874 mUserStates.put(userId, userState); 3875 } 3876 } 3877 3878 @Override 3879 public void removeUserState(int userId) { 3880 synchronized (mUserStates) { 3881 mUserStates.delete(userId); 3882 } 3883 } 3884 3885 @Override 3886 public int[] getUserIds() { 3887 return UserManagerService.this.getUserIds(); 3888 } 3889 3890 @Override 3891 public boolean isUserUnlockingOrUnlocked(int userId) { 3892 int state; 3893 synchronized (mUserStates) { 3894 state = mUserStates.get(userId, -1); 3895 } 3896 // Special case, in the stopping/shutdown state user key can still be unlocked 3897 if (state == UserState.STATE_STOPPING || state == UserState.STATE_SHUTDOWN) { 3898 return StorageManager.isUserKeyUnlocked(userId); 3899 } 3900 return (state == UserState.STATE_RUNNING_UNLOCKING) 3901 || (state == UserState.STATE_RUNNING_UNLOCKED); 3902 } 3903 3904 @Override 3905 public boolean isUserUnlocked(int userId) { 3906 int state; 3907 synchronized (mUserStates) { 3908 state = mUserStates.get(userId, -1); 3909 } 3910 // Special case, in the stopping/shutdown state user key can still be unlocked 3911 if (state == UserState.STATE_STOPPING || state == UserState.STATE_SHUTDOWN) { 3912 return StorageManager.isUserKeyUnlocked(userId); 3913 } 3914 return state == UserState.STATE_RUNNING_UNLOCKED; 3915 } 3916 3917 @Override 3918 public boolean isUserInitialized(int userId) { 3919 return (getUserInfo(userId).flags & UserInfo.FLAG_INITIALIZED) != 0; 3920 } 3921 3922 @Override 3923 public boolean exists(int userId) { 3924 return getUserInfoNoChecks(userId) != null; 3925 } 3926 3927 @Override 3928 public boolean isProfileAccessible(int callingUserId, int targetUserId, String debugMsg, 3929 boolean throwSecurityException) { 3930 if (targetUserId == callingUserId) { 3931 return true; 3932 } 3933 synchronized (mUsersLock) { 3934 UserInfo callingUserInfo = getUserInfoLU(callingUserId); 3935 if (callingUserInfo == null || callingUserInfo.isManagedProfile()) { 3936 if (throwSecurityException) { 3937 throw new SecurityException( 3938 debugMsg + " for another profile " 3939 + targetUserId + " from " + callingUserId); 3940 } 3941 } 3942 3943 UserInfo targetUserInfo = getUserInfoLU(targetUserId); 3944 if (targetUserInfo == null || !targetUserInfo.isEnabled()) { 3945 // Do not throw any exception here as this could happen due to race conditions 3946 // between the system updating its state and the client getting notified. 3947 if (throwSecurityException) { 3948 Slog.w(LOG_TAG, debugMsg + " for disabled profile " 3949 + targetUserId + " from " + callingUserId); 3950 } 3951 return false; 3952 } 3953 3954 if (targetUserInfo.profileGroupId == UserInfo.NO_PROFILE_GROUP_ID || 3955 targetUserInfo.profileGroupId != callingUserInfo.profileGroupId) { 3956 if (throwSecurityException) { 3957 throw new SecurityException( 3958 debugMsg + " for unrelated profile " + targetUserId); 3959 } 3960 return false; 3961 } 3962 } 3963 return true; 3964 } 3965 3966 @Override 3967 public int getProfileParentId(int userId) { 3968 synchronized (mUsersLock) { 3969 UserInfo profileParent = getProfileParentLU(userId); 3970 if (profileParent == null) { 3971 return userId; 3972 } 3973 return profileParent.id; 3974 } 3975 } 3976 3977 @Override 3978 public boolean isSettingRestrictedForUser(String setting, @UserIdInt int userId, 3979 String value, int callingUid) { 3980 return UserRestrictionsUtils.isSettingRestrictedForUser(mContext, setting, userId, 3981 value, callingUid); 3982 } 3983 } 3984 3985 /* Remove all the users except of the system one. */ 3986 private void removeNonSystemUsers() { 3987 ArrayList<UserInfo> usersToRemove = new ArrayList<>(); 3988 synchronized (mUsersLock) { 3989 final int userSize = mUsers.size(); 3990 for (int i = 0; i < userSize; i++) { 3991 UserInfo ui = mUsers.valueAt(i).info; 3992 if (ui.id != UserHandle.USER_SYSTEM) { 3993 usersToRemove.add(ui); 3994 } 3995 } 3996 } 3997 for (UserInfo ui: usersToRemove) { 3998 removeUser(ui.id); 3999 } 4000 } 4001 4002 private class Shell extends ShellCommand { 4003 @Override 4004 public int onCommand(String cmd) { 4005 return onShellCommand(this, cmd); 4006 } 4007 4008 @Override 4009 public void onHelp() { 4010 final PrintWriter pw = getOutPrintWriter(); 4011 pw.println("User manager (user) commands:"); 4012 pw.println(" help"); 4013 pw.println(" Print this help text."); 4014 pw.println(""); 4015 pw.println(" list"); 4016 pw.println(" Prints all users on the system."); 4017 } 4018 } 4019 4020 private static void debug(String message) { 4021 Log.d(LOG_TAG, message + 4022 (DBG_WITH_STACKTRACE ? " called at\n" + Debug.getCallers(10, " ") : "")); 4023 } 4024 4025 @VisibleForTesting 4026 static int getMaxManagedProfiles() { 4027 // Allow overriding max managed profiles on debuggable builds for testing 4028 // of multiple profiles. 4029 if (!Build.IS_DEBUGGABLE) { 4030 return MAX_MANAGED_PROFILES; 4031 } else { 4032 return SystemProperties.getInt("persist.sys.max_profiles", 4033 MAX_MANAGED_PROFILES); 4034 } 4035 } 4036 4037 @VisibleForTesting 4038 int getFreeProfileBadgeLU(int parentUserId) { 4039 int maxManagedProfiles = getMaxManagedProfiles(); 4040 boolean[] usedBadges = new boolean[maxManagedProfiles]; 4041 final int userSize = mUsers.size(); 4042 for (int i = 0; i < userSize; i++) { 4043 UserInfo ui = mUsers.valueAt(i).info; 4044 // Check which badge indexes are already used by this profile group. 4045 if (ui.isManagedProfile() 4046 && ui.profileGroupId == parentUserId 4047 && !mRemovingUserIds.get(ui.id) 4048 && ui.profileBadge < maxManagedProfiles) { 4049 usedBadges[ui.profileBadge] = true; 4050 } 4051 } 4052 for (int i = 0; i < maxManagedProfiles; i++) { 4053 if (!usedBadges[i]) { 4054 return i; 4055 } 4056 } 4057 return 0; 4058 } 4059 4060 /** 4061 * Checks if the given user has a managed profile associated with it. 4062 * @param userId The parent user 4063 * @return 4064 */ 4065 boolean hasManagedProfile(int userId) { 4066 synchronized (mUsersLock) { 4067 UserInfo userInfo = getUserInfoLU(userId); 4068 final int userSize = mUsers.size(); 4069 for (int i = 0; i < userSize; i++) { 4070 UserInfo profile = mUsers.valueAt(i).info; 4071 if (userId != profile.id && isProfileOf(userInfo, profile)) { 4072 return true; 4073 } 4074 } 4075 return false; 4076 } 4077 } 4078 4079 /** 4080 * Check if the calling package name matches with the calling UID, throw 4081 * {@link SecurityException} if not. 4082 */ 4083 private void verifyCallingPackage(String callingPackage, int callingUid) { 4084 int packageUid = mPm.getPackageUid(callingPackage, 0, UserHandle.getUserId(callingUid)); 4085 if (packageUid != callingUid) { 4086 throw new SecurityException("Specified package " + callingPackage 4087 + " does not match the calling uid " + callingUid); 4088 } 4089 } 4090} 4091