Merge "Allow RollbackManager to downgrade apks on user builds"
diff --git a/core/java/android/content/pm/PackageInstaller.java b/core/java/android/content/pm/PackageInstaller.java
index 0304f19..b20cce9 100644
--- a/core/java/android/content/pm/PackageInstaller.java
+++ b/core/java/android/content/pm/PackageInstaller.java
@@ -1343,6 +1343,7 @@
*/
public boolean areHiddenOptionsSet() {
return (installFlags & (PackageManager.INSTALL_ALLOW_DOWNGRADE
+ | PackageManager.INSTALL_RESPECT_ALLOW_DOWNGRADE
| PackageManager.INSTALL_DONT_KILL_APP
| PackageManager.INSTALL_INSTANT_APP
| PackageManager.INSTALL_FULL_APP
diff --git a/core/java/android/content/pm/PackageManager.java b/core/java/android/content/pm/PackageManager.java
index a5464c2..c133fba 100644
--- a/core/java/android/content/pm/PackageManager.java
+++ b/core/java/android/content/pm/PackageManager.java
@@ -721,6 +721,7 @@
INSTALL_VIRTUAL_PRELOAD,
INSTALL_APEX,
INSTALL_ENABLE_ROLLBACK,
+ INSTALL_RESPECT_ALLOW_DOWNGRADE,
})
@Retention(RetentionPolicy.SOURCE)
public @interface InstallFlags {}
@@ -865,6 +866,15 @@
*/
public static final int INSTALL_DISABLE_VERIFICATION = 0x00080000;
+ /**
+ * Flag parameter for {@link #installPackage} to indicate that
+ * {@link #INSTALL_ALLOW_DOWNGRADE} should be respected.
+ *
+ * @hide
+ */
+ // TODO(b/127322579): rename
+ public static final int INSTALL_RESPECT_ALLOW_DOWNGRADE = 0x00100000;
+
/** @hide */
@IntDef(flag = true, prefix = { "DONT_KILL_APP" }, value = {
DONT_KILL_APP
diff --git a/services/core/java/com/android/server/pm/PackageInstallerService.java b/services/core/java/com/android/server/pm/PackageInstallerService.java
index b72e836..a3b72fd 100644
--- a/services/core/java/com/android/server/pm/PackageInstallerService.java
+++ b/services/core/java/com/android/server/pm/PackageInstallerService.java
@@ -481,6 +481,12 @@
}
}
+ if (callingUid == Process.SYSTEM_UID) {
+ params.installFlags |= PackageManager.INSTALL_RESPECT_ALLOW_DOWNGRADE;
+ } else {
+ params.installFlags &= ~PackageManager.INSTALL_RESPECT_ALLOW_DOWNGRADE;
+ }
+
boolean isApex = (params.installFlags & PackageManager.INSTALL_APEX) != 0;
if (params.isStaged || isApex) {
mContext.enforceCallingOrSelfPermission(Manifest.permission.INSTALL_PACKAGES, TAG);
diff --git a/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java b/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java
index 3218c86..ff81ad5 100644
--- a/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java
+++ b/services/core/java/com/android/server/pm/PackageManagerServiceUtils.java
@@ -806,7 +806,7 @@
*/
public static boolean isDowngradePermitted(int installFlags, int applicationFlags) {
// If installed, the package will get access to data left on the device by its
- // predecessor. As a security measure, this is permited only if this is not a
+ // predecessor. As a security measure, this is permitted only if this is not a
// version downgrade or if the predecessor package is marked as debuggable and
// a downgrade is explicitly requested.
//
@@ -818,12 +818,21 @@
// installFlags. This is because we aim to keep the behavior of debuggable
// platform builds as close as possible to the behavior of non-debuggable
// platform builds.
+ //
+ // In case of user builds, downgrade is permitted only for the system server initiated
+ // sessions. This is enforced by INSTALL_RESPECT_ALLOW_DOWNGRADE flag parameter.
final boolean downgradeRequested =
(installFlags & PackageManager.INSTALL_ALLOW_DOWNGRADE) != 0;
- final boolean packageDebuggable =
- (applicationFlags
- & ApplicationInfo.FLAG_DEBUGGABLE) != 0;
- return (downgradeRequested) && ((Build.IS_DEBUGGABLE) || (packageDebuggable));
+ if (!downgradeRequested) {
+ return false;
+ }
+ final boolean isDebuggable =
+ Build.IS_DEBUGGABLE || ((applicationFlags
+ & ApplicationInfo.FLAG_DEBUGGABLE) != 0);
+ if (isDebuggable) {
+ return true;
+ }
+ return (installFlags & PackageManager.INSTALL_RESPECT_ALLOW_DOWNGRADE) != 0;
}
/**