summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--services/core/java/com/android/server/pm/PackageManagerServiceUtils.java32
-rw-r--r--services/core/java/com/android/server/pm/ReconcilePackageUtils.java10
2 files changed, 28 insertions, 14 deletions
diff --git a/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java b/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java
index d0aa6c2b8726..703be169f14c 100644
--- a/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java
+++ b/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java
@@ -19,6 +19,7 @@ package com.android.server.pm;
import static android.content.pm.PackageManager.INSTALL_FAILED_SHARED_USER_INCOMPATIBLE;
import static android.content.pm.PackageManager.INSTALL_FAILED_UPDATE_INCOMPATIBLE;
import static android.content.pm.PackageManager.INSTALL_FAILED_VERSION_DOWNGRADE;
+import static android.content.pm.SigningDetails.CertCapabilities.SHARED_USER_ID;
import static android.system.OsConstants.O_CREAT;
import static android.system.OsConstants.O_RDWR;
@@ -565,13 +566,8 @@ public class PackageManagerServiceUtils {
// the older ones. We check to see if either the new package is signed by an older cert
// with which the current sharedUser is ok, or if it is signed by a newer one, and is ok
// with being sharedUser with the existing signing cert.
- boolean match =
- parsedSignatures.checkCapability(
- sharedUserSetting.getSigningDetails(),
- SigningDetails.CertCapabilities.SHARED_USER_ID)
- || sharedUserSetting.getSigningDetails().checkCapability(
- parsedSignatures,
- SigningDetails.CertCapabilities.SHARED_USER_ID);
+ boolean match = canJoinSharedUserId(parsedSignatures,
+ sharedUserSetting.getSigningDetails());
// Special case: if the sharedUserId capability check failed it could be due to this
// being the only package in the sharedUserId so far and the lineage being updated to
// deny the sharedUserId capability of the previous key in the lineage.
@@ -646,6 +642,28 @@ public class PackageManagerServiceUtils {
}
/**
+ * Returns whether the package with {@code packageSigningDetails} can join the sharedUserId
+ * with {@code sharedUserSigningDetails}.
+ * <p>
+ * A sharedUserId maintains a shared {@link SigningDetails} containing the full lineage and
+ * capabilities for each package in the sharedUserId. A package can join the sharedUserId if
+ * its current signer is the same as the shared signer, or if the current signer of either
+ * is in the signing lineage of the other with the {@link
+ * SigningDetails.CertCapabilities#SHARED_USER_ID} capability granted to that previous signer
+ * in the lineage.
+ *
+ * @param packageSigningDetails the {@code SigningDetails} of the package seeking to join the
+ * sharedUserId
+ * @param sharedUserSigningDetails the {@code SigningDetails} of the sharedUserId
+ * @return true if the package seeking to join the sharedUserId meets the requirements
+ */
+ public static boolean canJoinSharedUserId(@NonNull SigningDetails packageSigningDetails,
+ @NonNull SigningDetails sharedUserSigningDetails) {
+ return packageSigningDetails.checkCapability(sharedUserSigningDetails, SHARED_USER_ID)
+ || sharedUserSigningDetails.checkCapability(packageSigningDetails, SHARED_USER_ID);
+ }
+
+ /**
* Extract native libraries to a target path
*/
public static int extractNativeBinaries(File dstCodePath, String packageName) {
diff --git a/services/core/java/com/android/server/pm/ReconcilePackageUtils.java b/services/core/java/com/android/server/pm/ReconcilePackageUtils.java
index 5fc916f888f3..d6a133e43789 100644
--- a/services/core/java/com/android/server/pm/ReconcilePackageUtils.java
+++ b/services/core/java/com/android/server/pm/ReconcilePackageUtils.java
@@ -22,11 +22,9 @@ import static android.content.pm.SigningDetails.CapabilityMergeRule.MERGE_RESTRI
import static com.android.server.pm.PackageManagerService.SCAN_BOOTING;
import static com.android.server.pm.PackageManagerService.SCAN_DONT_KILL_APP;
-import static com.android.server.pm.PackageManagerServiceUtils.compareSignatures;
import android.content.pm.PackageManager;
import android.content.pm.SharedLibraryInfo;
-import android.content.pm.Signature;
import android.content.pm.SigningDetails;
import android.os.SystemProperties;
import android.util.ArrayMap;
@@ -212,12 +210,10 @@ final class ReconcilePackageUtils {
// the signatures on the first package scanned for the shared user (i.e. if the
// signaturesChanged state hasn't been initialized yet in SharedUserSetting).
if (sharedUserSetting != null) {
- final Signature[] sharedUserSignatures = sharedUserSetting
- .signatures.mSigningDetails.getSignatures();
if (sharedUserSetting.signaturesChanged != null
- && compareSignatures(sharedUserSignatures,
- parsedPackage.getSigningDetails().getSignatures())
- != PackageManager.SIGNATURE_MATCH) {
+ && !PackageManagerServiceUtils.canJoinSharedUserId(
+ parsedPackage.getSigningDetails(),
+ sharedUserSetting.getSigningDetails())) {
if (SystemProperties.getInt("ro.product.first_api_level", 0) <= 29) {
// Mismatched signatures is an error and silently skipping system
// packages will likely break the device in unforeseen ways.