summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Nick Kovacs <nrkovacs@google.com> 2022-12-20 00:11:58 +0000
committer Nick Kovacs <nrkovacs@google.com> 2023-01-06 20:42:39 +0000
commit7c710f62228fbc829eaa097204a00bccd8aa420d (patch)
tree957e70ad921d426f7b92151a3b2103a48223df10
parent1d7957fab8fc7e03b8ad02cdf21d2366852cfc60 (diff)
Add install flag --bypass-low-target-sdk-block
Added a PM shell install flag to bypass the low target sdk block for installing apps that are using low targetSdkVersion. When set, this flag will bypass the install block and allow the app to be installed. Added some additional broad exclusions that will allow this feature to be ramped up earlier. The plan will be to follow this up with changes that remove exceptions for skipping the install block when installed via adb, or when the package name isn't set. Will also follow up with a change that removes the bypass flag if the caller isn't root or shell. Bug: 237321649 Test: adb install app.apk Test: adb install --bypass-low-target-sdk-block Test: adb shell pm install app.apk Test: Sideloaded apk using the Files app Test: adb shell device_config put package_manager_service MinInstallableTargetSdk__install_block_enabled true Test: adb shell device_config put package_manager_service MinInstallableTargetSdk__min_installable_target_sdk 23 Test: atest PackageManagerTests Test: atest CtsPackageManagerParsingHostTestCases Change-Id: I88261b25e6d7360251385e15eb3a352e1213fe76
-rw-r--r--core/java/android/content/pm/PackageManager.java8
-rw-r--r--services/core/java/com/android/server/pm/InstallPackageHelper.java43
-rw-r--r--services/core/java/com/android/server/pm/PackageManagerShellCommand.java4
3 files changed, 50 insertions, 5 deletions
diff --git a/core/java/android/content/pm/PackageManager.java b/core/java/android/content/pm/PackageManager.java
index 4ad657e64fb3..7cc8af7fcab0 100644
--- a/core/java/android/content/pm/PackageManager.java
+++ b/core/java/android/content/pm/PackageManager.java
@@ -1545,6 +1545,14 @@ public abstract class PackageManager {
*/
public static final int INSTALL_DISABLE_ALLOWED_APEX_UPDATE_CHECK = 0x00800000;
+ /**
+ * Flag parameter for {@link #installPackage} to bypass the low targer sdk version block
+ * for this install.
+ *
+ * @hide
+ */
+ public static final int INSTALL_BYPASS_LOW_TARGET_SDK_BLOCK = 0x00800000;
+
/** @hide */
@IntDef(flag = true, value = {
DONT_KILL_APP,
diff --git a/services/core/java/com/android/server/pm/InstallPackageHelper.java b/services/core/java/com/android/server/pm/InstallPackageHelper.java
index 16bf0fe09b9e..0ee1bbfc190e 100644
--- a/services/core/java/com/android/server/pm/InstallPackageHelper.java
+++ b/services/core/java/com/android/server/pm/InstallPackageHelper.java
@@ -1032,15 +1032,48 @@ final class InstallPackageHelper {
DeviceConfig.getInt(DeviceConfig.NAMESPACE_PACKAGE_MANAGER_SERVICE,
"MinInstallableTargetSdk__min_installable_target_sdk",
0);
- if (parsedPackage.getTargetSdkVersion() < minInstallableTargetSdk) {
+
+ // Skip enforcement when the bypass flag is set
+ boolean bypassLowTargetSdkBlock =
+ ((installFlags & PackageManager.INSTALL_BYPASS_LOW_TARGET_SDK_BLOCK) != 0);
+
+ // Skip enforcement for tests that were installed from adb
+ if (!bypassLowTargetSdkBlock
+ && ((installFlags & PackageManager.INSTALL_FROM_ADB) != 0)) {
+ bypassLowTargetSdkBlock = true;
+ }
+
+ // Skip enforcement if the installer package name is not set
+ // (e.g. "pm install" from shell)
+ if (!bypassLowTargetSdkBlock) {
+ if (request.getInstallerPackageName() == null) {
+ bypassLowTargetSdkBlock = true;
+ } else {
+ // Also skip if the install is occurring from an app that was installed from adb
+ if (mContext
+ .getPackageManager()
+ .getInstallerPackageName(request.getInstallerPackageName()) == null) {
+ bypassLowTargetSdkBlock = true;
+ }
+ }
+ }
+
+ // Skip enforcement when the testOnly flag is set
+ if (!bypassLowTargetSdkBlock && parsedPackage.isTestOnly()) {
+ bypassLowTargetSdkBlock = true;
+ }
+
+ // Enforce the low target sdk install block except when
+ // the --bypass-low-target-sdk-block is set for the install
+ if (!bypassLowTargetSdkBlock
+ && parsedPackage.getTargetSdkVersion() < minInstallableTargetSdk) {
Slog.w(TAG, "App " + parsedPackage.getPackageName()
+ " targets deprecated sdk version");
throw new PrepareFailure(INSTALL_FAILED_DEPRECATED_SDK_VERSION,
- "App package must target at least version "
- + minInstallableTargetSdk);
+ "App package must target at least SDK version "
+ + minInstallableTargetSdk + ", but found "
+ + parsedPackage.getTargetSdkVersion());
}
- } else {
- Slog.i(TAG, "Minimum installable target sdk enforcement not enabled");
}
// Instant apps have several additional install-time checks.
diff --git a/services/core/java/com/android/server/pm/PackageManagerShellCommand.java b/services/core/java/com/android/server/pm/PackageManagerShellCommand.java
index 2138c205ee58..b53c75a9cd24 100644
--- a/services/core/java/com/android/server/pm/PackageManagerShellCommand.java
+++ b/services/core/java/com/android/server/pm/PackageManagerShellCommand.java
@@ -3243,6 +3243,10 @@ class PackageManagerShellCommand extends ShellCommand {
case "--skip-enable":
sessionParams.setKeepApplicationEnabledSetting();
break;
+ case "--bypass-low-target-sdk-block":
+ sessionParams.installFlags |=
+ PackageManager.INSTALL_BYPASS_LOW_TARGET_SDK_BLOCK;
+ break;
default:
throw new IllegalArgumentException("Unknown option " + opt);
}