diff --git a/services/core/java/com/android/server/pm/InstallPackageHelper.java b/services/core/java/com/android/server/pm/InstallPackageHelper.java index 234a2309d76b4..11e731a28a790 100644 --- a/services/core/java/com/android/server/pm/InstallPackageHelper.java +++ b/services/core/java/com/android/server/pm/InstallPackageHelper.java @@ -36,7 +36,6 @@ import static android.content.pm.PackageManager.INSTALL_REASON_DEVICE_RESTORE; import static android.content.pm.PackageManager.INSTALL_REASON_DEVICE_SETUP; import static android.content.pm.PackageManager.INSTALL_SUCCEEDED; import static android.content.pm.PackageManager.UNINSTALL_REASON_UNKNOWN; -import static android.content.pm.PackageManagerInternal.PACKAGE_SETUP_WIZARD; import static android.content.pm.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V4; import static android.content.pm.parsing.ApkLiteParseUtils.isApkFile; import static android.os.PowerExemptionManager.REASON_PACKAGE_REPLACED; @@ -183,7 +182,6 @@ import java.util.Arrays; import java.util.Collections; import java.util.List; import java.util.Map; -import java.util.Objects; import java.util.Set; import java.util.concurrent.ExecutorService; @@ -1596,18 +1594,16 @@ final class InstallPackageHelper { parsedPackage.setRestrictUpdateHash(oldPackage.getRestrictUpdateHash()); } - // Check for shared user id changes - if (!Objects.equals(oldPackage.getSharedUserId(), - parsedPackage.getSharedUserId()) - // Don't mark as invalid if the app is trying to - // leave a sharedUserId - && parsedPackage.getSharedUserId() != null) { + // APK should not change its sharedUserId declarations + final var oldSharedUid = oldPackage.getSharedUserId() != null + ? oldPackage.getSharedUserId() : ""; + final var newSharedUid = parsedPackage.getSharedUserId() != null + ? parsedPackage.getSharedUserId() : ""; + if (!oldSharedUid.equals(newSharedUid)) { throw new PrepareFailure(INSTALL_FAILED_UID_CHANGED, "Package " + parsedPackage.getPackageName() + " shared user changed from " - + (oldPackage.getSharedUserId() != null - ? oldPackage.getSharedUserId() : "") - + " to " + parsedPackage.getSharedUserId()); + + oldSharedUid + " to " + newSharedUid); } // In case of rollback, remember per-user/profile install state @@ -3694,10 +3690,13 @@ final class InstallPackageHelper { } disabledPkgSetting = mPm.mSettings.getDisabledSystemPkgLPr( parsedPackage.getPackageName()); - sharedUserSetting = (parsedPackage.getSharedUserId() != null) - ? mPm.mSettings.getSharedUserLPw(parsedPackage.getSharedUserId(), - 0 /*pkgFlags*/, 0 /*pkgPrivateFlags*/, true) - : null; + if (parsedPackage.getSharedUserId() != null && !parsedPackage.isLeavingSharedUid()) { + sharedUserSetting = mPm.mSettings.getSharedUserLPw( + parsedPackage.getSharedUserId(), + 0 /*pkgFlags*/, 0 /*pkgPrivateFlags*/, true /*create*/); + } else { + sharedUserSetting = null; + } if (DEBUG_PACKAGE_SCANNING && (parseFlags & ParsingPackageUtils.PARSE_CHATTY) != 0 && sharedUserSetting != null) { diff --git a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackage.java b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackage.java index cdc2b1245b1ee..f6f9faf98c40a 100644 --- a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackage.java +++ b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackage.java @@ -290,6 +290,9 @@ public interface ParsingPackage extends ParsingPackageRead { /** @see R#styleable.AndroidManifest_inheritKeyStoreKeys */ ParsingPackage setInheritKeyStoreKeys(boolean inheritKeyStoreKeys); + /** @see R#styleable.AndroidManifest_sharedUserMaxSdkVersion */ + ParsingPackage setLeavingSharedUid(boolean leavingSharedUid); + ParsingPackage setLabelRes(int labelRes); ParsingPackage setLargestWidthLimitDp(int largestWidthLimitDp); diff --git a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageImpl.java b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageImpl.java index 177eaca8e06f5..67670272ef8b0 100644 --- a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageImpl.java +++ b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageImpl.java @@ -549,6 +549,7 @@ public class ParsingPackageImpl implements ParsingPackage, ParsingPackageHidden, private static final long SDK_LIBRARY = 1L << 49; private static final long INHERIT_KEYSTORE_KEYS = 1L << 50; private static final long ENABLE_ON_BACK_INVOKED_CALLBACK = 1L << 51; + private static final long LEAVING_SHARED_UID = 1L << 52; } private ParsingPackageImpl setBoolean(@Booleans.Values long flag, boolean value) { @@ -2402,6 +2403,11 @@ public class ParsingPackageImpl implements ParsingPackage, ParsingPackageHidden, return getBoolean(Booleans.ENABLE_ON_BACK_INVOKED_CALLBACK); } + @Override + public boolean isLeavingSharedUid() { + return getBoolean(Booleans.LEAVING_SHARED_UID); + } + @Override public ParsingPackageImpl setBaseRevisionCode(int value) { baseRevisionCode = value; @@ -2550,6 +2556,11 @@ public class ParsingPackageImpl implements ParsingPackage, ParsingPackageHidden, return setBoolean(Booleans.INHERIT_KEYSTORE_KEYS, value); } + @Override + public ParsingPackageImpl setLeavingSharedUid(boolean value) { + return setBoolean(Booleans.LEAVING_SHARED_UID, value); + } + @Override public ParsingPackageImpl setLabelRes(int value) { labelRes = value; diff --git a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageRead.java b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageRead.java index 428374fa21a89..50033f652bfd1 100644 --- a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageRead.java +++ b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageRead.java @@ -360,4 +360,11 @@ public interface ParsingPackageRead extends PkgWithoutStateAppInfo, PkgWithoutSt * @see R.styleable.AndroidManifestApplication_enableOnBackInvokedCallback */ boolean isOnBackInvokedCallbackEnabled(); + + /** + * Returns true if R.styleable#AndroidManifest_sharedUserMaxSdkVersion is set to a value + * smaller than the current SDK version. + * @see R.styleable#AndroidManifest_sharedUserMaxSdkVersion + */ + boolean isLeavingSharedUid(); } diff --git a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageUtils.java b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageUtils.java index f30daa930e6c5..ed1ab01e1d122 100644 --- a/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageUtils.java +++ b/services/core/java/com/android/server/pm/pkg/parsing/ParsingPackageUtils.java @@ -1032,11 +1032,6 @@ public class ParsingPackageUtils { private static ParseResult parseSharedUser(ParseInput input, ParsingPackage pkg, TypedArray sa) { - int maxSdkVersion = anInteger(0, R.styleable.AndroidManifest_sharedUserMaxSdkVersion, sa); - if ((maxSdkVersion != 0) && maxSdkVersion < Build.VERSION.RESOURCES_SDK_INT) { - return input.success(pkg); - } - String str = nonConfigString(0, R.styleable.AndroidManifest_sharedUserId, sa); if (TextUtils.isEmpty(str)) { return input.success(pkg); @@ -1052,7 +1047,11 @@ public class ParsingPackageUtils { } } + int maxSdkVersion = anInteger(0, R.styleable.AndroidManifest_sharedUserMaxSdkVersion, sa); + boolean leaving = (maxSdkVersion != 0) && (maxSdkVersion < Build.VERSION.RESOURCES_SDK_INT); + return input.success(pkg + .setLeavingSharedUid(leaving) .setSharedUserId(str.intern()) .setSharedUserLabel(resId(R.styleable.AndroidManifest_sharedUserLabel, sa))); } diff --git a/services/tests/PackageManagerServiceTests/unit/src/com/android/server/pm/test/parsing/parcelling/AndroidPackageTest.kt b/services/tests/PackageManagerServiceTests/unit/src/com/android/server/pm/test/parsing/parcelling/AndroidPackageTest.kt index cd2d0fce66917..83ccabf039359 100644 --- a/services/tests/PackageManagerServiceTests/unit/src/com/android/server/pm/test/parsing/parcelling/AndroidPackageTest.kt +++ b/services/tests/PackageManagerServiceTests/unit/src/com/android/server/pm/test/parsing/parcelling/AndroidPackageTest.kt @@ -238,6 +238,7 @@ class AndroidPackageTest : ParcelableComponentTest(AndroidPackage::class, Packag AndroidPackage::isVendor, AndroidPackage::isVisibleToInstantApps, AndroidPackage::isVmSafeMode, + AndroidPackage::isLeavingSharedUid, AndroidPackage::isResetEnabledSettingsOnAppDataCleared, AndroidPackage::getMaxAspectRatio, AndroidPackage::getMinAspectRatio,