public static final int FLAG_AND_LOCKED = 1 << 1;
/** {@hide} */
public static final int FLAG_AND_UNLOCKED = 1 << 2;
+ /** {@hide} */
+ public static final int FLAG_AND_UNLOCKING_OR_UNLOCKED = 1 << 3;
/**
* Return whether the given user is actively running. This means that
}
/** {@hide} */
- public boolean isUserRunningAndLocked(int userId) {
- try {
- return ActivityManagerNative.getDefault().isUserRunning(userId,
- ActivityManager.FLAG_AND_LOCKED);
- } catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
- }
- }
-
- /** {@hide} */
- public boolean isUserRunningAndUnlocked(int userId) {
- try {
- return ActivityManagerNative.getDefault().isUserRunning(userId,
- ActivityManager.FLAG_AND_UNLOCKED);
- } catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
- }
- }
-
- /** {@hide} */
public boolean isVrModePackageEnabled(ComponentName component) {
try {
return ActivityManagerNative.getDefault().isVrModePackageEnabled(component);
import android.graphics.BitmapFactory;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
-import android.os.storage.StorageManager;
import android.provider.Settings;
import android.telephony.TelephonyManager;
import android.view.WindowManager.LayoutParams;
/** {@hide} */
public boolean isUserUnlocked(@UserIdInt int userId) {
- // TODO: eventually pivot this back to look at ActivityManager state,
- // but there is race where we can start a non-encryption-aware launcher
- // before that lifecycle has entered the running unlocked state.
- return mContext.getSystemService(StorageManager.class).isUserKeyUnlocked(userId);
+ try {
+ return ActivityManagerNative.getDefault().isUserRunning(userId,
+ ActivityManager.FLAG_AND_UNLOCKED);
+ } catch (RemoteException re) {
+ throw re.rethrowFromSystemServer();
+ }
+ }
+
+ /** {@hide} */
+ public boolean isUserUnlockingOrUnlocked(UserHandle user) {
+ return isUserUnlockingOrUnlocked(user.getIdentifier());
+ }
+
+ /** {@hide} */
+ public boolean isUserUnlockingOrUnlocked(@UserIdInt int userId) {
+ try {
+ return ActivityManagerNative.getDefault().isUserRunning(userId,
+ ActivityManager.FLAG_AND_UNLOCKING_OR_UNLOCKED);
+ } catch (RemoteException re) {
+ throw re.rethrowFromSystemServer();
+ }
}
/**
import android.content.Context;
import android.content.pm.IPackageMoveObserver;
import android.content.pm.PackageManager;
+import android.os.Binder;
import android.os.Environment;
import android.os.FileUtils;
import android.os.Handler;
}
/** {@hide} */
- public boolean isUserKeyUnlocked(int userId) {
+ public static boolean isUserKeyUnlocked(int userId) {
+ final IMountService mount = IMountService.Stub
+ .asInterface(ServiceManager.getService("mount"));
+ if (mount == null) {
+ Slog.w(TAG, "Early during boot, assuming locked");
+ return false;
+ }
+ final long token = Binder.clearCallingIdentity();
try {
- return mMountService.isUserKeyUnlocked(userId);
+ return mount.isUserKeyUnlocked(userId);
} catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
+ throw e.rethrowAsRuntimeException();
+ } finally {
+ Binder.restoreCallingIdentity(token);
}
}
UserHandle user, ContentValues values) {
final ContentResolver resolver = context.getContentResolver();
+ // Since we're doing this operation on behalf of an app, we only
+ // want to use the actual "unlocked" state.
final Uri uri = ContentProvider.maybeAddUserId(
userManager.isUserUnlocked(user) ? CONTENT_URI : SHADOW_CONTENT_URI,
user.getIdentifier());
<java-symbol type="string" name="profile_encrypted_message" />
<java-symbol type="drawable" name="ic_user_secure" />
+ <java-symbol type="string" name="android_upgrading_notification_title" />
+ <java-symbol type="string" name="android_upgrading_notification_body" />
+
<java-symbol type="string" name="usb_mtp_launch_notification_title" />
<java-symbol type="string" name="usb_mtp_launch_notification_description" />
private void updateServicesLocked(UserState userState) {
Map<ComponentName, Service> componentNameToServiceMap =
userState.mComponentNameToServiceMap;
- boolean isUnlocked = mContext.getSystemService(UserManager.class)
- .isUserUnlocked(userState.mUserId);
+ boolean isUnlockingOrUnlocked = mContext.getSystemService(UserManager.class)
+ .isUserUnlockingOrUnlocked(userState.mUserId);
for (int i = 0, count = userState.mInstalledServices.size(); i < count; i++) {
AccessibilityServiceInfo installedService = userState.mInstalledServices.get(i);
Service service = componentNameToServiceMap.get(componentName);
// Ignore non-encryption-aware services until user is unlocked
- if (!isUnlocked && !installedService.isDirectBootAware()) {
+ if (!isUnlockingOrUnlocked && !installedService.isDirectBootAware()) {
Slog.d(LOG_TAG, "Ignoring non-encryption-aware service " + componentName);
continue;
}
Provider provider = installedProviders.get(i);
final int userId = provider.getUserId();
- if (!mUserManager.isUserUnlocked(userId) ||
+ if (!mUserManager.isUserUnlockingOrUnlocked(userId) ||
isProfileWithLockedParent(userId)) {
continue;
}
}
private void onPackageBroadcastReceived(Intent intent, int userId) {
- if (!mUserManager.isUserUnlocked(userId) ||
+ if (!mUserManager.isUserUnlockingOrUnlocked(userId) ||
isProfileWithLockedParent(userId)) {
return;
}
* userId must be the group parent.
*/
private void reloadWidgetsMaskedStateForGroup(int userId) {
- if (!mUserManager.isUserUnlocked(userId)) {
+ if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
return;
}
synchronized (mLock) {
try {
UserInfo user = mUserManager.getUserInfo(userId);
- boolean lockedProfile = !mUserManager.isUserUnlocked(userId);
+ boolean lockedProfile = !mUserManager.isUserUnlockingOrUnlocked(userId);
boolean quietProfile = user.isQuietModeEnabled();
final int N = mProviders.size();
for (int i = 0; i < N; i++) {
}
private void ensureGroupStateLoadedLocked(int userId) {
- if (!mUserManager.isUserUnlocked(userId)) {
+ if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
throw new IllegalStateException(
"User " + userId + " must be unlocked for widgets to be available");
}
if (userInfo != null && userInfo.isManagedProfile()) {
UserInfo parentInfo = mUserManager.getProfileParent(userId);
if (parentInfo != null
- && !mUserManager.isUserUnlocked(parentInfo.getUserHandle())) {
+ && !mUserManager.isUserUnlockingOrUnlocked(parentInfo.getUserHandle())) {
return true;
}
}
if (userInfo != null && userInfo.isManagedProfile()) {
UserInfo parentInfo = mUserManager.getProfileParent(userId);
if (parentInfo != null
- && mUserManager.isUserUnlocked(parentInfo.getUserHandle())) {
+ && mUserManager.isUserUnlockingOrUnlocked(parentInfo.getUserHandle())) {
return true;
}
}
// If the system is not ready or the device is not yed unlocked by the user, then we use
// copy-on-write settings.
final boolean useCopyOnWriteSettings =
- !mSystemReady || !mUserManager.isUserUnlocked(newUserId);
+ !mSystemReady || !mUserManager.isUserUnlockingOrUnlocked(newUserId);
mSettings.switchCurrentUser(newUserId, useCopyOnWriteSettings);
updateCurrentProfileIds();
// InputMethodFileManager should be reset when the user is changed
mSystemReady = true;
final int currentUserId = mSettings.getCurrentUserId();
mSettings.switchCurrentUser(currentUserId,
- !mUserManager.isUserUnlocked(currentUserId));
+ !mUserManager.isUserUnlockingOrUnlocked(currentUserId));
mKeyguardManager = mContext.getSystemService(KeyguardManager.class);
mNotificationManager = mContext.getSystemService(NotificationManager.class);
mStatusBar = statusBar;
for (int i = 0; i < users.size(); i++) {
UserInfo user = users.get(i);
UserHandle userHandle = user.getUserHandle();
- if (!mUserManager.isUserUnlocked(userHandle)) {
+ if (!mUserManager.isUserUnlockingOrUnlocked(userHandle)) {
if (!user.isManagedProfile()) {
showEncryptionNotification(userHandle);
} else {
UserInfo parent = mUserManager.getProfileParent(user.id);
if (parent != null &&
- mUserManager.isUserUnlocked(parent.getUserHandle()) &&
+ mUserManager.isUserUnlockingOrUnlocked(parent.getUserHandle()) &&
!mUserManager.isQuietModeEnabled(userHandle)) {
// Only show notifications for managed profiles once their parent
// user is unlocked.
UserInfo profile = profiles.get(i);
if (profile.isManagedProfile()) {
UserHandle userHandle = profile.getUserHandle();
- if (!mUserManager.isUserUnlocked(userHandle) &&
+ if (!mUserManager.isUserUnlockingOrUnlocked(userHandle) &&
!mUserManager.isQuietModeEnabled(userHandle)) {
showEncryptionNotificationForProfile(userHandle);
}
enforcePermission(android.Manifest.permission.STORAGE_INTERNAL);
waitForReady();
- // When a user has secure lock screen, require a challenge token to
- // actually unlock. This check is mostly in place for emulation mode.
- if (mLockPatternUtils.isSecure(userId) && ArrayUtils.isEmpty(token)) {
- throw new IllegalStateException("Token required to unlock secure user " + userId);
- }
+ if (StorageManager.isFileEncryptedNativeOrEmulated()) {
+ // When a user has secure lock screen, require a challenge token to
+ // actually unlock. This check is mostly in place for emulation mode.
+ if (mLockPatternUtils.isSecure(userId) && ArrayUtils.isEmpty(token)) {
+ throw new IllegalStateException("Token required to unlock secure user " + userId);
+ }
- try {
- mCryptConnector.execute("cryptfs", "unlock_user_key", userId, serialNumber,
- encodeBytes(token), encodeBytes(secret));
- } catch (NativeDaemonConnectorException e) {
- throw e.rethrowAsParcelableException();
+ try {
+ mCryptConnector.execute("cryptfs", "unlock_user_key", userId, serialNumber,
+ encodeBytes(token), encodeBytes(secret));
+ } catch (NativeDaemonConnectorException e) {
+ throw e.rethrowAsParcelableException();
+ }
}
synchronized (mLock) {
@Override
public boolean isUserKeyUnlocked(int userId) {
- if (StorageManager.isFileEncryptedNativeOrEmulated()) {
- synchronized (mLock) {
- return ArrayUtils.contains(mLocalUnlockedUsers, userId);
- }
- } else {
- return true;
+ synchronized (mLock) {
+ return ArrayUtils.contains(mLocalUnlockedUsers, userId);
}
}
mMonitor = new TextServicesMonitor();
mMonitor.register(context, null, true);
final boolean useCopyOnWriteSettings =
- !mSystemReady || !mUserManager.isUserUnlocked(userId);
+ !mSystemReady || !mUserManager.isUserUnlockingOrUnlocked(userId);
mSettings = new TextServicesSettings(context.getContentResolver(), userId,
useCopyOnWriteSettings);
private void resetInternalState(@UserIdInt int userId) {
final boolean useCopyOnWriteSettings =
- !mSystemReady || !mUserManager.isUserUnlocked(userId);
+ !mSystemReady || !mUserManager.isUserUnlockingOrUnlocked(userId);
mSettings.switchCurrentUser(userId, useCopyOnWriteSettings);
updateCurrentProfileIds();
unbindServiceLocked();
}
private final SparseArray<UserAccounts> mUsers = new SparseArray<>();
- private final SparseBooleanArray mUnlockedUsers = new SparseBooleanArray();
+ private final SparseBooleanArray mLocalUnlockedUsers = new SparseBooleanArray();
private static AtomicReference<AccountManagerService> sThis = new AtomicReference<>();
private static final Account[] EMPTY_ACCOUNT_ARRAY = new Account[]{};
if (Log.isLoggable(TAG, Log.DEBUG)) {
Log.d(TAG, "validateAccountsInternal " + accounts.userId
+ " isCeDatabaseAttached=" + accounts.openHelper.isCeDatabaseAttached()
- + " userLocked=" + mUnlockedUsers.get(accounts.userId));
+ + " userLocked=" + mLocalUnlockedUsers.get(accounts.userId));
}
if (invalidateAuthenticatorCache) {
mAuthenticatorCache.invalidateCache(accounts.userId);
validateAccounts = true;
}
// open CE database if necessary
- if (!accounts.openHelper.isCeDatabaseAttached() && mUnlockedUsers.get(userId)) {
+ if (!accounts.openHelper.isCeDatabaseAttached() && mLocalUnlockedUsers.get(userId)) {
Log.i(TAG, "User " + userId + " is unlocked - opening CE database");
synchronized (accounts.cacheLock) {
File preNDatabaseFile = new File(getPreNDatabaseName(userId));
synchronized (mUsers) {
accounts = mUsers.get(userId);
mUsers.remove(userId);
- userUnlocked = mUnlockedUsers.get(userId);
- mUnlockedUsers.delete(userId);
+ userUnlocked = mLocalUnlockedUsers.get(userId);
+ mLocalUnlockedUsers.delete(userId);
}
if (accounts != null) {
synchronized (accounts.cacheLock) {
Log.v(TAG, "onUserUnlocked " + userId);
}
synchronized (mUsers) {
- mUnlockedUsers.put(userId, true);
+ mLocalUnlockedUsers.put(userId, true);
}
if (userId < 1) return;
syncSharedAccounts(userId);
if (account == null) {
return null;
}
- if (!isUserUnlocked(accounts.userId)) {
+ if (!isLocalUnlockedUser(accounts.userId)) {
Log.w(TAG, "Password is not available - user " + accounts.userId + " data is locked");
return null;
}
account.type);
throw new SecurityException(msg);
}
- if (!isUserUnlocked(userId)) {
+ if (!isLocalUnlockedUser(userId)) {
Log.w(TAG, "User " + userId + " data is locked. callingUid " + callingUid);
return null;
}
if (account == null) {
return false;
}
- if (!isUserUnlocked(accounts.userId)) {
+ if (!isLocalUnlockedUser(accounts.userId)) {
Log.w(TAG, "Account " + account + " cannot be added - user " + accounts.userId
+ " is locked. callingUid=" + callingUid);
return false;
return true;
}
- private boolean isUserUnlocked(int userId) {
+ private boolean isLocalUnlockedUser(int userId) {
synchronized (mUsers) {
- return mUnlockedUsers.get(userId);
+ return mLocalUnlockedUsers.get(userId);
}
}
for (UserInfo user : users) {
if (user.isRestricted() && (parentUserId == user.restrictedProfileParentId)) {
addSharedAccountAsUser(account, user.id);
- if (getUserManager().isUserUnlocked(user.id)) {
+ if (isLocalUnlockedUser(user.id)) {
mMessageHandler.sendMessage(mMessageHandler.obtainMessage(
MESSAGE_COPY_SHARED_ACCOUNT, parentUserId, user.id, account));
}
private boolean removeAccountInternal(UserAccounts accounts, Account account, int callingUid) {
int deleted;
- boolean userUnlocked = isUserUnlocked(accounts.userId);
+ boolean userUnlocked = isLocalUnlockedUser(accounts.userId);
if (!userUnlocked) {
Slog.i(TAG, "Removing account " + account + " while user "+ accounts.userId
+ " is still locked. CE data will be removed later");
account.type);
throw new SecurityException(msg);
}
- if (!isUserUnlocked(userId)) {
+ if (!isLocalUnlockedUser(userId)) {
Log.w(TAG, "Authtoken not available - user " + userId + " data is locked. callingUid "
+ callingUid);
return null;
return false;
}
- final ActivityManager am = mContext.getSystemService(ActivityManager.class);
- if (am.isUserRunningAndLocked(mAccounts.userId)
+ if (!isLocalUnlockedUser(mAccounts.userId)
&& !authenticatorInfo.componentInfo.directBootAware) {
Slog.w(TAG, "Blocking binding to authenticator " + authenticatorInfo.componentName
+ " which isn't encryption aware");
startPersistentApps(PackageManager.MATCH_DIRECT_BOOT_UNAWARE);
}
installEncryptionUnawareProviders(userId);
- if (msg.obj instanceof ProgressReporter) {
- ((ProgressReporter) msg.obj).finish();
- }
+ mUserController.finishUserUnlocked((UserState) msg.obj);
break;
}
case SYSTEM_USER_CURRENT_MSG: {
app.debugging = false;
app.cached = false;
app.killedByAm = false;
- app.unlocked = mContext.getSystemService(UserManager.class).isUserUnlocked(app.userId);
+
+ // We carefully use the same state that PackageManager uses for
+ // filtering, since we use this flag to decide if we need to install
+ // providers when user is unlocked later
+ app.unlocked = StorageManager.isUserKeyUnlocked(app.userId);
mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
* belonging to any running apps.
*/
private void installEncryptionUnawareProviders(int userId) {
- if (!StorageManager.isFileEncryptedNativeOrEmulated()) {
- // TODO: eventually pivot this back to look at current user state,
- // similar to the comment in UserManager.isUserUnlocked(), but for
- // now, if we started apps when "unlocked" then unaware providers
- // have already been spun up.
- return;
- }
-
// We're only interested in providers that are encryption unaware, and
// we don't care about uninstalled apps, since there's no way they're
// running at this point.
Binder.restoreCallingIdentity(token);
}
if (parent != null
- && userManager.isUserUnlocked(parent.getUserHandle())
- && !userManager.isUserUnlocked(userInfo.getUserHandle())) {
+ && userManager.isUserUnlockingOrUnlocked(parent.getUserHandle())
+ && !userManager.isUserUnlockingOrUnlocked(userInfo.getUserHandle())) {
rInfo = mSupervisor.resolveIntent(intent, resolvedType, userId,
PackageManager.MATCH_DIRECT_BOOT_AWARE
| PackageManager.MATCH_DIRECT_BOOT_UNAWARE);
if (mStartedUsers.get(uss.mHandle.getIdentifier()) != uss) return;
// Only keep marching forward if user is actually unlocked
- if (!isUserKeyUnlocked(userId)) return;
+ if (!StorageManager.isUserKeyUnlocked(userId)) return;
if (uss.setState(STATE_RUNNING_LOCKED, STATE_RUNNING_UNLOCKING)) {
uss.mUnlockProgress.start();
mUserManager.onBeforeUnlockUser(userId);
uss.mUnlockProgress.setProgress(20);
- // Dispatch unlocked to system services
- mHandler.obtainMessage(SYSTEM_USER_UNLOCK_MSG, userId, 0, uss.mUnlockProgress)
+ // Dispatch unlocked to system services; when fully dispatched,
+ // that calls through to the next "unlocked" phase
+ mHandler.obtainMessage(SYSTEM_USER_UNLOCK_MSG, userId, 0, uss)
.sendToTarget();
+ }
+ }
+ }
+
+ /**
+ * Step from {@link UserState#STATE_RUNNING_UNLOCKING} to
+ * {@link UserState#STATE_RUNNING_UNLOCKED}.
+ */
+ void finishUserUnlocked(final UserState uss) {
+ final int userId = uss.mHandle.getIdentifier();
+ synchronized (mService) {
+ // Bail if we ended up with a stale user
+ if (mStartedUsers.get(uss.mHandle.getIdentifier()) != uss) return;
+
+ // Only keep marching forward if user is actually unlocked
+ if (!StorageManager.isUserKeyUnlocked(userId)) return;
+
+ if (uss.setState(STATE_RUNNING_UNLOCKING, STATE_RUNNING_UNLOCKED)) {
+ uss.mUnlockProgress.finish();
// Dispatch unlocked to external apps
final Intent unlockedIntent = new Intent(Intent.ACTION_USER_UNLOCKED);
}
}
- // Send PRE_BOOT broadcasts if fingerprint changed
+ // Send PRE_BOOT broadcasts if user fingerprint changed; we
+ // purposefully block sending BOOT_COMPLETED until after all
+ // PRE_BOOT receivers are finished to avoid ANR'ing apps
final UserInfo info = getUserInfo(userId);
if (!Objects.equals(info.lastLoggedInFingerprint, Build.FINGERPRINT)) {
new PreBootBroadcaster(mService, userId, null) {
@Override
public void onFinished() {
- finishUserUnlocked(uss);
+ finishUserUnlockedCompleted(uss);
}
}.sendNext();
} else {
- finishUserUnlocked(uss);
+ finishUserUnlockedCompleted(uss);
}
}
}
}
- /**
- * Step from {@link UserState#STATE_RUNNING_UNLOCKING} to
- * {@link UserState#STATE_RUNNING_UNLOCKED}.
- */
- private void finishUserUnlocked(UserState uss) {
+ private void finishUserUnlockedCompleted(UserState uss) {
final int userId = uss.mHandle.getIdentifier();
synchronized (mService) {
// Bail if we ended up with a stale user
}
// Only keep marching forward if user is actually unlocked
- if (!isUserKeyUnlocked(userId)) return;
-
- if (uss.setState(STATE_RUNNING_UNLOCKING, STATE_RUNNING_UNLOCKED)) {
- // Remember that we logged in
- mUserManager.onUserLoggedIn(userId);
-
- if (!userInfo.isInitialized()) {
- if (userId != UserHandle.USER_SYSTEM) {
- Slog.d(TAG, "Initializing user #" + userId);
- Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE);
- intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
- mService.broadcastIntentLocked(null, null, intent, null,
- new IIntentReceiver.Stub() {
- @Override
- public void performReceive(Intent intent, int resultCode,
- String data, Bundle extras, boolean ordered,
- boolean sticky, int sendingUser) {
- // Note: performReceive is called with mService lock held
- getUserManager().makeInitialized(userInfo.id);
- }
- }, 0, null, null, null, AppOpsManager.OP_NONE,
- null, true, false, MY_PID, SYSTEM_UID, userId);
- }
+ if (!StorageManager.isUserKeyUnlocked(userId)) return;
+
+ // Remember that we logged in
+ mUserManager.onUserLoggedIn(userId);
+
+ if (!userInfo.isInitialized()) {
+ if (userId != UserHandle.USER_SYSTEM) {
+ Slog.d(TAG, "Initializing user #" + userId);
+ Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE);
+ intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
+ mService.broadcastIntentLocked(null, null, intent, null,
+ new IIntentReceiver.Stub() {
+ @Override
+ public void performReceive(Intent intent, int resultCode,
+ String data, Bundle extras, boolean ordered,
+ boolean sticky, int sendingUser) {
+ // Note: performReceive is called with mService lock held
+ getUserManager().makeInitialized(userInfo.id);
+ }
+ }, 0, null, null, null, AppOpsManager.OP_NONE,
+ null, true, false, MY_PID, SYSTEM_UID, userId);
}
- Slog.d(TAG, "Sending BOOT_COMPLETE user #" + userId);
- final Intent bootIntent = new Intent(Intent.ACTION_BOOT_COMPLETED, null);
- bootIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
- bootIntent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT
- | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND);
- mService.broadcastIntentLocked(null, null, bootIntent, null, null, 0, null, null,
- new String[] { android.Manifest.permission.RECEIVE_BOOT_COMPLETED },
- AppOpsManager.OP_NONE, null, true, false, MY_PID, SYSTEM_UID, userId);
}
+
+ Slog.d(TAG, "Sending BOOT_COMPLETE user #" + userId);
+ final Intent bootIntent = new Intent(Intent.ACTION_BOOT_COMPLETED, null);
+ bootIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId);
+ bootIntent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT
+ | Intent.FLAG_RECEIVER_INCLUDE_BACKGROUND);
+ mService.broadcastIntentLocked(null, null, bootIntent, null, null, 0, null, null,
+ new String[] { android.Manifest.permission.RECEIVE_BOOT_COMPLETED },
+ AppOpsManager.OP_NONE, null, true, false, MY_PID, SYSTEM_UID, userId);
}
}
return IMountService.Stub.asInterface(ServiceManager.getService("mount"));
}
- private boolean isUserKeyUnlocked(int userId) {
- final IMountService mountService = getMountService();
- if (mountService != null) {
- try {
- return mountService.isUserKeyUnlocked(userId);
- } catch (RemoteException e) {
- throw e.rethrowAsRuntimeException();
- }
- } else {
- Slog.w(TAG, "Mount service not published; guessing locked state based on property");
- return !StorageManager.isFileEncryptedNativeOrEmulated();
- }
- }
-
/**
* Start user, if its not already running.
* <p>The user will be brought to the foreground, if {@code foreground} parameter is set.
}
}
- if (!isUserKeyUnlocked(userId)) {
+ if (!StorageManager.isUserKeyUnlocked(userId)) {
final UserInfo userInfo = getUserInfo(userId);
final IMountService mountService = getMountService();
try {
if ((flags & ActivityManager.FLAG_OR_STOPPED) != 0) {
return true;
}
-
- final boolean unlocked;
- switch (state.state) {
- case UserState.STATE_STOPPING:
- case UserState.STATE_SHUTDOWN:
- default:
- return false;
-
- case UserState.STATE_BOOTING:
- case UserState.STATE_RUNNING_LOCKED:
- unlocked = false;
- break;
-
- case UserState.STATE_RUNNING_UNLOCKING:
- case UserState.STATE_RUNNING_UNLOCKED:
- unlocked = true;
- break;
- }
-
if ((flags & ActivityManager.FLAG_AND_LOCKED) != 0) {
- return !unlocked;
+ switch (state.state) {
+ case UserState.STATE_BOOTING:
+ case UserState.STATE_RUNNING_LOCKED:
+ return true;
+ default:
+ return false;
+ }
+ }
+ if ((flags & ActivityManager.FLAG_AND_UNLOCKING_OR_UNLOCKED) != 0) {
+ switch (state.state) {
+ case UserState.STATE_RUNNING_UNLOCKING:
+ case UserState.STATE_RUNNING_UNLOCKED:
+ return true;
+ default:
+ return false;
+ }
}
if ((flags & ActivityManager.FLAG_AND_UNLOCKED) != 0) {
- return unlocked;
+ switch (state.state) {
+ case UserState.STATE_RUNNING_UNLOCKED:
+ return true;
+ default:
+ return false;
+ }
}
// One way or another, we're running!
// Prepare storage for system user really early during boot,
// since core system apps like SettingsProvider and SystemUI
// can't wait for user to start
- final int storageFlags;
- if (StorageManager.isFileEncryptedNativeOrEmulated()) {
- storageFlags = StorageManager.FLAG_STORAGE_DE;
- } else {
- storageFlags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
- }
reconcileAppsDataLI(StorageManager.UUID_PRIVATE_INTERNAL, UserHandle.USER_SYSTEM,
- storageFlags);
+ StorageManager.FLAG_STORAGE_DE);
// If this is first boot after an OTA, and a normal boot, then
// we need to clear code cache directories.
@Override
public void checkPackageStartable(String packageName, int userId) {
- final boolean userKeyUnlocked = isUserKeyUnlocked(userId);
+ final boolean userKeyUnlocked = StorageManager.isUserKeyUnlocked(userId);
synchronized (mPackages) {
final PackageSetting ps = mSettings.mPackages.get(packageName);
}
/**
- * Return if the user key is currently unlocked.
- */
- private boolean isUserKeyUnlocked(int userId) {
- if (StorageManager.isFileEncryptedNativeOrEmulated()) {
- final IMountService mount = IMountService.Stub
- .asInterface(ServiceManager.getService("mount"));
- if (mount == null) {
- Slog.w(TAG, "Early during boot, assuming locked");
- return false;
- }
- final long token = Binder.clearCallingIdentity();
- try {
- return mount.isUserKeyUnlocked(userId);
- } catch (RemoteException e) {
- throw e.rethrowAsRuntimeException();
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- } else {
- return true;
- }
- }
-
- /**
* Update given flags based on encryption status of current user.
*/
private int updateFlags(int flags, int userId) {
// give them what they want
} else {
// Caller expressed no opinion, so match based on user state
- if (isUserKeyUnlocked(userId)) {
+ if (StorageManager.isUserKeyUnlocked(userId)) {
flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE;
} else {
flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE;
final UserManager um = mContext.getSystemService(UserManager.class);
final int flags;
- if (um.isUserUnlocked(userId)) {
+ if (um.isUserUnlockingOrUnlocked(userId)) {
flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
} else if (um.isUserRunning(userId)) {
flags = StorageManager.FLAG_STORAGE_DE;
final UserManager um = mContext.getSystemService(UserManager.class);
for (UserInfo user : um.getUsers()) {
final int flags;
- if (um.isUserUnlocked(user.id)) {
+ if (um.isUserUnlockingOrUnlocked(user.id)) {
flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
} else if (um.isUserRunning(user.id)) {
flags = StorageManager.FLAG_STORAGE_DE;
// First look for stale data that doesn't belong, and check if things
// have changed since we did our last restorecon
if ((flags & StorageManager.FLAG_STORAGE_CE) != 0) {
- if (!isUserKeyUnlocked(userId)) {
+ if (!StorageManager.isUserKeyUnlocked(userId)) {
throw new RuntimeException(
"Yikes, someone asked us to reconcile CE storage while " + userId
+ " was still locked; this would have caused massive data loss!");
final UserManager um = mContext.getSystemService(UserManager.class);
for (UserInfo user : um.getUsers()) {
final int flags;
- if (um.isUserUnlocked(user.id)) {
+ if (um.isUserUnlockingOrUnlocked(user.id)) {
flags = StorageManager.FLAG_STORAGE_DE | StorageManager.FLAG_STORAGE_CE;
} else if (um.isUserRunning(user.id)) {
flags = StorageManager.FLAG_STORAGE_DE;
@Override
public boolean trySetQuietModeDisabled(int userHandle, IntentSender target) {
final int credentialOwnerUserId = getCredentialOwnerProfile(userHandle);
- if (mContext.getSystemService(StorageManager.class).isUserKeyUnlocked(userHandle)
+ if (StorageManager.isUserKeyUnlocked(userHandle)
|| !mLockPatternUtils.isSecure(credentialOwnerUserId)) {
// if the user is already unlocked, no need to show a profile challenge
setQuietModeEnabled(userHandle, false);
if (um.getUserInfo(userId) == null) {
throw new IllegalStateException("User " + userId + " doesn't exist");
}
- if (!um.isUserUnlocked(userId)) {
+ if (!um.isUserUnlockingOrUnlocked(userId)) {
throw new IllegalStateException("User " + userId + " isn't unlocked");
}
} finally {
}
private void enforceUserUnlocked(int userId) {
+ // Since we're doing this operation on behalf of an app, we only
+ // want to use the actual "unlocked" state.
Preconditions.checkState(mUserManager.isUserUnlocked(userId),
"User must be running and unlocked");
}
@Override
public void onPackageModified(String packageName) {
- if (!mUserManager.isUserUnlocked(getChangingUserId())) return;
+ if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return;
UserState userState = getOrCreateUserStateLocked(getChangingUserId(), false);
synchronized (mLock) {
@Override
public void onPackageRemoved(String packageName, int uid) {
- if (!mUserManager.isUserUnlocked(getChangingUserId())) return;
+ if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return;
UserState userState = getOrCreateUserStateLocked(getChangingUserId(), false);
synchronized (mLock) {
@Override
public boolean onHandleForceStop(Intent intent, String[] stoppedPackages,
int uid, boolean doit) {
- if (!mUserManager.isUserUnlocked(getChangingUserId())) return false;
+ if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return false;
synchronized (mLock) {
// A background user/profile's print jobs are running but there is
// no UI shown. Hence, if the packages of such a user change we need
@Override
public void onPackageAdded(String packageName, int uid) {
- if (!mUserManager.isUserUnlocked(getChangingUserId())) return;
+ if (!mUserManager.isUserUnlockingOrUnlocked(getChangingUserId())) return;
synchronized (mLock) {
if (hasPrintService(packageName)) {
UserState userState = getOrCreateUserStateLocked(getChangingUserId(),
}
private UserState getOrCreateUserStateLocked(int userId, boolean lowPriority) {
- if (!mUserManager.isUserUnlocked(userId)) {
+ if (!mUserManager.isUserUnlockingOrUnlocked(userId)) {
throw new IllegalStateException(
"User " + userId + " must be unlocked for printing to be available");
}