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