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

Commit 3ba22246 authored by Hai Zhang's avatar Hai Zhang
Browse files

Skip updating flags for a permission that's not requested.

If a permission isn't requested, there shouldn't be a PermissionState
for it, however updatePermissionFlags() may create such a state and
confuse restorePermissionState() for what is a new implicit
permission. So don't allow adding a new PermissionState for a
permission that's not requested, and make it a no-op because the
caller might just have seen an older package and we shouldn't crash
them. Updating flags for a permission with an existing PermissionState
is still allowed so that a permission state can be erased by revoking
and clearing all its flags.

See also b/159585979#comment7.

Bug: 159585979
Bug: 152580253
Test: atest --rerun-until-failure 100 SplitPermissionTest
Test: The test above fails within 2 or 3 attempts without this fix,
      but passes successfully for 100 times with this fix. Logcat
      shows that the logic in the fix is hit multiple times during the
      test.
Change-Id: I17d252bdc2cfa65485b7950da099dff73c4979a9
parent 9e7c4619
Loading
Loading
Loading
Loading
+25 −0
Original line number Diff line number Diff line
@@ -789,6 +789,31 @@ public class PermissionManagerService extends IPermissionManager.Stub {
        final PermissionsState permissionsState = ps.getPermissionsState();
        final boolean hadState =
                permissionsState.getRuntimePermissionState(permName, userId) != null;
        if (!hadState) {
            boolean isRequested = false;
            // Fast path, the current package has requested the permission.
            if (pkg.getRequestedPermissions().contains(permName)) {
                isRequested = true;
            }
            if (!isRequested) {
                // Slow path, go through all shared user packages.
                String[] sharedUserPackageNames =
                        mPackageManagerInt.getSharedUserPackagesForPackage(packageName, userId);
                for (String sharedUserPackageName : sharedUserPackageNames) {
                    AndroidPackage sharedUserPkg = mPackageManagerInt.getPackage(
                            sharedUserPackageName);
                    if (sharedUserPkg != null
                            && sharedUserPkg.getRequestedPermissions().contains(permName)) {
                        isRequested = true;
                        break;
                    }
                }
            }
            if (!isRequested) {
                Log.e(TAG, "Permission " + permName + " isn't requested by package " + packageName);
                return;
            }
        }
        final boolean permissionUpdated =
                permissionsState.updatePermissionFlags(bp, userId, flagMask, flagValues);
        if (permissionUpdated && bp.isRuntime()) {