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

Commit a2afebf9 authored by Dario Freni's avatar Dario Freni
Browse files

Allow persistent APKs updates using PM flags.

This is a different approach than
I346d772e1f4aed94f6faead3b6455efc4666b651, suggested during reviews.

Bug: 131046856
Test: marked the NetworkStack APK as persistent, verified that
  - adb install networkstack.apk fails
  - adb install --staged networkstack.apk succeds (after reboot)

Change-Id: I1facb24786431906a8056a50bff01745cebacf24
parent bc646622
Loading
Loading
Loading
Loading
+9 −0
Original line number Diff line number Diff line
@@ -730,6 +730,7 @@ public abstract class PackageManager {
            INSTALL_APEX,
            INSTALL_ENABLE_ROLLBACK,
            INSTALL_ALLOW_DOWNGRADE,
            INSTALL_STAGED,
    })
    @Retention(RetentionPolicy.SOURCE)
    public @interface InstallFlags {}
@@ -899,6 +900,14 @@ public abstract class PackageManager {
     */
    public static final int INSTALL_ALLOW_DOWNGRADE = 0x00100000;

    /**
     * Flag parameter for {@link #installPackage} to indicate that this package
     * is being installed as part of a staged install.
     *
     * @hide
     */
    public static final int INSTALL_STAGED = 0x00200000;

    /** @hide */
    @IntDef(flag = true, prefix = { "DONT_KILL_APP" }, value = {
            DONT_KILL_APP
+1 −4
Original line number Diff line number Diff line
@@ -939,7 +939,6 @@ public class PackageManagerService extends IPackageManager.Stub
    ComponentName mCustomResolverComponentName;
    boolean mResolverReplaced = false;
    boolean mOkToReplacePersistentPackages = false;
    private final @Nullable ComponentName mIntentFilterVerifierComponent;
    private final @Nullable IntentFilterVerifier<ActivityIntentInfo> mIntentFilterVerifier;
@@ -17327,7 +17326,7 @@ public class PackageManagerService extends IPackageManager.Stub
                    }
                    // Prevent persistent apps from being updated
                    if (((oldPackage.applicationInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0)
                            && !mOkToReplacePersistentPackages) {
                            && ((installFlags & PackageManager.INSTALL_STAGED) == 0)) {
                        throw new PrepareFailure(PackageManager.INSTALL_FAILED_INVALID_APK,
                                "Package " + oldPackage.packageName + " is a persistent app. "
                                        + "Persistent apps are not updateable.");
@@ -21507,12 +21506,10 @@ public class PackageManagerService extends IPackageManager.Stub
        mModuleInfoProvider.systemReady();
        mOkToReplacePersistentPackages = true;
        // Installer service might attempt to install some packages that have been staged for
        // installation on reboot. Make sure this is the last component to be call since the
        // installation might require other components to be ready.
        mInstallerService.restoreAndApplyStagedSessionIfNeeded();
        mOkToReplacePersistentPackages = false;
    }
    public void waitForAppDataPrepared() {
+1 −0
Original line number Diff line number Diff line
@@ -384,6 +384,7 @@ public class StagingManager {
        PackageInstaller.SessionParams params = originalSession.params.copy();
        params.isStaged = false;
        params.installFlags |= PackageManager.INSTALL_DISABLE_VERIFICATION;
        params.installFlags |= PackageManager.INSTALL_STAGED;
        // TODO(b/129744602): use the userid from the original session.
        int apkSessionId = mPi.createSession(
                params, originalSession.getInstallerPackageName(),