Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 80573612 authored by Rhed Jao's avatar Rhed Jao
Browse files

Migrates to the new resolveContentProvider api

The original resolveContentProvider api gets the caller's uid using
the Binder#getCallingUid. That may cause the package information
disclosure issue if the caller has cleared the calling identify.
This cl migrates the callers of resolveContentProvider to use the
new one with a calling uid parameter. The caller could pass the
correct caller's uid to use the api.

Bug: 192354703
Test: atest UriGrantsManagerServiceTest
Test: atest UriPermissionTest
Test: atest ContextTest
Change-Id: I153df4e77642f0622c7f0f5804639795e90ded21
parent a549d465
Loading
Loading
Loading
Loading
+0 −5
Original line number Diff line number Diff line
@@ -561,11 +561,6 @@ public abstract class PackageManagerInternal implements PackageSettingsSnapshotP
    public abstract ResolveInfo resolveService(Intent intent, String resolvedType,
           int flags, int userId, int callingUid);

   /**
    * Resolves a content provider intent.
    */
    public abstract ProviderInfo resolveContentProvider(String name, int flags, int userId);

    /**
    * Resolves a content provider intent.
    */
+2 −2
Original line number Diff line number Diff line
@@ -1032,7 +1032,7 @@ class StorageManagerService extends IStorageManager.Stub
                final ProviderInfo provider = mPmInternal.resolveContentProvider(
                        MediaStore.AUTHORITY, PackageManager.MATCH_DIRECT_BOOT_AWARE
                                | PackageManager.MATCH_DIRECT_BOOT_UNAWARE,
                        user.id);
                        user.id, Process.SYSTEM_UID);
                if (provider != null) {
                    final IActivityManager am = ActivityManager.getService();
                    try {
@@ -2021,7 +2021,7 @@ class StorageManagerService extends IStorageManager.Stub
        return mPmInternal.resolveContentProvider(
                authority, PackageManager.MATCH_DIRECT_BOOT_AWARE
                        | PackageManager.MATCH_DIRECT_BOOT_UNAWARE,
                UserHandle.getUserId(UserHandle.USER_SYSTEM));
                UserHandle.getUserId(UserHandle.USER_SYSTEM), Process.SYSTEM_UID);
    }

    private void updateLegacyStorageApps(String packageName, int uid, boolean hasLegacy) {
+2 −16
Original line number Diff line number Diff line
@@ -11651,14 +11651,6 @@ public class PackageManagerService extends IPackageManager.Stub
    @Override
    public ProviderInfo resolveContentProvider(String name, int flags, int userId) {
        return resolveContentProviderInternal(name, flags, userId);
    }
    public ProviderInfo resolveContentProvider(String name, int flags, int userId, int callingUid) {
        return resolveContentProviderInternal(name, flags, userId, callingUid);
    }
    private ProviderInfo resolveContentProviderInternal(String name, int flags, int userId) {
        return resolveContentProviderInternal(name, flags, userId, Binder.getCallingUid());
    }
@@ -27829,12 +27821,6 @@ public class PackageManagerService extends IPackageManager.Stub
            return resolveServiceInternal(intent, resolvedType, flags, userId, callingUid);
        }
        @Override
        public ProviderInfo resolveContentProvider(String name, int flags, int userId) {
            return PackageManagerService.this.resolveContentProviderInternal(
                    name, flags, userId);
        }
        @Override
        public ProviderInfo resolveContentProvider(String name, int flags, int userId,
                int callingUid) {
@@ -28616,8 +28602,8 @@ public class PackageManagerService extends IPackageManager.Stub
    public void grantImplicitAccess(int recipientUid, String visibleAuthority) {
        // This API is exposed temporarily to only the contacts provider. (b/158688602)
        final int callingUid = Binder.getCallingUid();
        ProviderInfo contactsProvider = resolveContentProviderInternal(
                        ContactsContract.AUTHORITY, 0, UserHandle.getUserId(callingUid));
        ProviderInfo contactsProvider = resolveContentProviderInternal(ContactsContract.AUTHORITY,
                0, UserHandle.getUserId(callingUid), callingUid);
        if (contactsProvider == null || contactsProvider.applicationInfo == null
                || !UserHandle.isSameApp(contactsProvider.applicationInfo.uid, callingUid)) {
            throw new SecurityException(callingUid + " is not allow to call grantImplicitAccess");
+4 −8
Original line number Diff line number Diff line
@@ -695,7 +695,7 @@ public class UriGrantsManagerService extends IUriGrantsManager.Stub {
                        // Both direct boot aware and unaware packages are fine as we
                        // will do filtering at query time to avoid multiple parsing.
                        final ProviderInfo pi = getProviderInfo(uri.getAuthority(), sourceUserId,
                                MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE);
                                MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, SYSTEM_UID);
                        if (pi != null && sourcePkg.equals(pi.packageName)) {
                            int targetUid = mPmInternal.getPackageUid(
                                        targetPkg, MATCH_UNINSTALLED_PACKAGES, targetUserId);
@@ -759,9 +759,10 @@ public class UriGrantsManagerService extends IUriGrantsManager.Stub {
        if (DEBUG) Slog.v(TAG,
                "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri);

        // Unchecked call, passing the system's uid as the calling uid to the getProviderInfo
        final String authority = grantUri.uri.getAuthority();
        final ProviderInfo pi = getProviderInfo(authority, grantUri.sourceUserId,
                MATCH_DEBUG_TRIAGED_MISSING);
                MATCH_DEBUG_TRIAGED_MISSING, SYSTEM_UID);
        if (pi == null) {
            Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString());
            return;
@@ -812,7 +813,7 @@ public class UriGrantsManagerService extends IUriGrantsManager.Stub {

        final String authority = grantUri.uri.getAuthority();
        final ProviderInfo pi = getProviderInfo(authority, grantUri.sourceUserId,
                MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE);
                MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE, callingUid);
        if (pi == null) {
            Slog.w(TAG, "No content provider found for permission revoke: "
                    + grantUri.toSafeString());
@@ -1056,11 +1057,6 @@ public class UriGrantsManagerService extends IUriGrantsManager.Stub {
        }
    }

    private ProviderInfo getProviderInfo(String authority, int userHandle, int pmFlags) {
        return mPmInternal.resolveContentProvider(authority,
                PackageManager.GET_URI_PERMISSION_PATTERNS | pmFlags, userHandle);
    }

    private ProviderInfo getProviderInfo(String authority, int userHandle, int pmFlags,
            int callingUid) {
        return mPmInternal.resolveContentProvider(authority,
+2 −1
Original line number Diff line number Diff line
@@ -55,6 +55,7 @@ import android.content.ClipData;
import android.content.Intent;
import android.content.pm.ProviderInfo;
import android.net.Uri;
import android.os.Process;
import android.os.UserHandle;
import android.util.ArraySet;

@@ -356,7 +357,7 @@ public class UriGrantsManagerServiceTest {
        final UriPermissionOwner owner = new UriPermissionOwner(mService, "primary");

        final ProviderInfo cameraInfo = mContext.mPmInternal.resolveContentProvider(
                PKG_CAMERA, 0, USER_PRIMARY);
                PKG_CAMERA, 0, USER_PRIMARY, Process.SYSTEM_UID);

        // By default no social can see any camera
        assertFalse(mService.checkAuthorityGrants(UID_PRIMARY_SOCIAL,
Loading