diff --git a/core/java/android/os/storage/IStorageManager.aidl b/core/java/android/os/storage/IStorageManager.aidl index fbac954b0a35c..bff5c62ed3f12 100644 --- a/core/java/android/os/storage/IStorageManager.aidl +++ b/core/java/android/os/storage/IStorageManager.aidl @@ -90,9 +90,9 @@ interface IStorageManager { */ int changeEncryptionPassword(int type, in String password) = 28; /** - * Returns list of all mountable volumes. + * Returns list of all mountable volumes for the specified userId */ - StorageVolume[] getVolumeList(int uid, in String packageName, int flags) = 29; + StorageVolume[] getVolumeList(int userId, in String callingPackage, int flags) = 29; /** * Determines the encryption state of the volume. * @return a numerical value. See {@code ENCRYPTION_STATE_*} for possible diff --git a/core/java/android/os/storage/StorageManager.java b/core/java/android/os/storage/StorageManager.java index 77c794cd17a89..627e09eadd26c 100644 --- a/core/java/android/os/storage/StorageManager.java +++ b/core/java/android/os/storage/StorageManager.java @@ -1391,13 +1391,7 @@ public class StorageManager { } packageName = packageNames[0]; } - final int uid = ActivityThread.getPackageManager().getPackageUid(packageName, - PackageManager.MATCH_DEBUG_TRIAGED_MISSING, userId); - if (uid <= 0) { - Log.w(TAG, "Missing UID; no storage volumes available"); - return new StorageVolume[0]; - } - return storageManager.getVolumeList(uid, packageName, flags); + return storageManager.getVolumeList(userId, packageName, flags); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } diff --git a/services/core/java/com/android/server/StorageManagerService.java b/services/core/java/com/android/server/StorageManagerService.java index 311555e326ddd..6f009b6c2f40d 100644 --- a/services/core/java/com/android/server/StorageManagerService.java +++ b/services/core/java/com/android/server/StorageManagerService.java @@ -3713,8 +3713,19 @@ class StorageManagerService extends IStorageManager.Stub } @Override - public StorageVolume[] getVolumeList(int uid, String packageName, int flags) { - final int userId = UserHandle.getUserId(uid); + public StorageVolume[] getVolumeList(int userId, String callingPackage, int flags) { + final int callingUid = Binder.getCallingUid(); + final int callingUserId = UserHandle.getUserId(callingUid); + + if (!isUidOwnerOfPackageOrSystem(callingPackage, callingUid)) { + throw new SecurityException("callingPackage does not match UID"); + } + if (callingUserId != userId) { + // Callers can ask for volumes of different users, but only with the correct permissions + mContext.enforceCallingOrSelfPermission( + android.Manifest.permission.INTERACT_ACROSS_USERS, + "Need INTERACT_ACROSS_USERS to get volumes for another user"); + } final boolean forWrite = (flags & StorageManager.FLAG_FOR_WRITE) != 0; final boolean realState = (flags & StorageManager.FLAG_REAL_STATE) != 0; @@ -3730,7 +3741,7 @@ class StorageManagerService extends IStorageManager.Stub // should never attempt to augment the actual storage volume state, // otherwise we risk confusing it with race conditions as users go // through various unlocked states - final boolean callerIsMediaStore = UserHandle.isSameApp(Binder.getCallingUid(), + final boolean callerIsMediaStore = UserHandle.isSameApp(callingUid, mMediaStoreAuthorityAppId); final boolean userIsDemo; @@ -3740,8 +3751,9 @@ class StorageManagerService extends IStorageManager.Stub try { userIsDemo = LocalServices.getService(UserManagerInternal.class) .getUserInfo(userId).isDemo(); + storagePermission = mStorageManagerInternal.hasExternalStorage(callingUid, + callingPackage); userKeyUnlocked = isUserKeyUnlocked(userId); - storagePermission = mStorageManagerInternal.hasExternalStorage(uid, packageName); } finally { Binder.restoreCallingIdentity(token); }