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

Commit 8a7f93bb authored by Joanne Chung's avatar Joanne Chung
Browse files

Refactor dexopt related code to DexOptHelper

This change is a preparation change for moving dex package ealier.
The logic will be used for both flag is on/off, moving the common
code that will be used in both places to helper class, no code logic
is changed.

Bug: 321139675
Test: manual. Install app and launch app

Change-Id: I243afc60f7554d2952247419c531d1da6c7790bd
parent 976c29c7
Loading
Loading
Loading
Loading
+77 −0
Original line number Diff line number Diff line
@@ -16,7 +16,10 @@

package com.android.server.pm;

import static android.content.pm.PackageManager.INSTALL_REASON_DEVICE_RESTORE;
import static android.content.pm.PackageManager.INSTALL_REASON_DEVICE_SETUP;
import static android.os.Trace.TRACE_TAG_DALVIK;
import static android.os.incremental.IncrementalManager.isIncrementalPath;

import static com.android.server.LocalManagerRegistry.ManagerNotFoundException;
import static com.android.server.pm.ApexManager.ActiveApexInfo;
@@ -27,6 +30,8 @@ import static com.android.server.pm.PackageManagerService.REASON_BOOT_AFTER_MAIN
import static com.android.server.pm.PackageManagerService.REASON_BOOT_AFTER_OTA;
import static com.android.server.pm.PackageManagerService.REASON_CMDLINE;
import static com.android.server.pm.PackageManagerService.REASON_FIRST_BOOT;
import static com.android.server.pm.PackageManagerService.SCAN_AS_APEX;
import static com.android.server.pm.PackageManagerService.SCAN_AS_INSTANT_APP;
import static com.android.server.pm.PackageManagerService.STUB_SUFFIX;
import static com.android.server.pm.PackageManagerService.TAG;
import static com.android.server.pm.PackageManagerServiceCompilerMapping.getCompilerFilterForReason;
@@ -45,6 +50,8 @@ import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.Flags;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.content.pm.SharedLibraryInfo;
import android.content.pm.dex.ArtManager;
@@ -54,6 +61,7 @@ import android.os.SystemClock;
import android.os.SystemProperties;
import android.os.Trace;
import android.os.UserHandle;
import android.provider.Settings.Global;
import android.text.TextUtils;
import android.util.ArraySet;
import android.util.Log;
@@ -1091,4 +1099,73 @@ public final class DexOptHelper {
                        + " has unsupported status " + status);
        }
    }

    /**
     * Returns DexoptOptions by the given InstallRequest.
     */
    static DexoptOptions getDexoptOptionsByInstallRequest(InstallRequest installRequest,
            DexManager dexManager) {
        final PackageSetting ps = installRequest.getScannedPackageSetting();
        final String packageName = ps.getPackageName();
        final boolean isBackupOrRestore =
                installRequest.getInstallReason() == INSTALL_REASON_DEVICE_RESTORE
                        || installRequest.getInstallReason() == INSTALL_REASON_DEVICE_SETUP;
        final int dexoptFlags = DexoptOptions.DEXOPT_BOOT_COMPLETE
                | DexoptOptions.DEXOPT_CHECK_FOR_PROFILES_UPDATES
                | DexoptOptions.DEXOPT_INSTALL_WITH_DEX_METADATA_FILE
                | (isBackupOrRestore ? DexoptOptions.DEXOPT_FOR_RESTORE : 0);
        // Compute the compilation reason from the installation scenario.
        final int compilationReason =
                dexManager.getCompilationReasonForInstallScenario(
                        installRequest.getInstallScenario());
        return new DexoptOptions(packageName, compilationReason, dexoptFlags);
    }

    /**
     * Use ArtService to perform dexopt by the given InstallRequest.
     */
    static DexoptResult dexoptPackageUsingArtService(InstallRequest installRequest,
            DexoptOptions dexoptOptions) {
        final PackageSetting ps = installRequest.getScannedPackageSetting();
        final String packageName = ps.getPackageName();

        PackageManagerLocal packageManagerLocal =
                LocalManagerRegistry.getManager(PackageManagerLocal.class);
        try (PackageManagerLocal.FilteredSnapshot snapshot =
                     packageManagerLocal.withFilteredSnapshot()) {
            boolean ignoreDexoptProfile =
                    (installRequest.getInstallFlags()
                            & PackageManager.INSTALL_IGNORE_DEXOPT_PROFILE)
                            != 0;
            /*@DexoptFlags*/ int extraFlags =
                    ignoreDexoptProfile && Flags.useArtServiceV2()
                            ? ArtFlags.FLAG_IGNORE_PROFILE
                            : 0;
            DexoptParams params = dexoptOptions.convertToDexoptParams(extraFlags);
            DexoptResult dexOptResult = getArtManagerLocal().dexoptPackage(
                    snapshot, packageName, params);

            return dexOptResult;
        }
    }

    /**
     * Returns whether to perform dexopt by the given InstallRequest.
     */
    static boolean shouldPerformDexopt(InstallRequest installRequest, DexoptOptions dexoptOptions,
            Context context) {
        final boolean isApex = ((installRequest.getScanFlags() & SCAN_AS_APEX) != 0);
        final boolean instantApp = ((installRequest.getScanFlags() & SCAN_AS_INSTANT_APP) != 0);
        final PackageSetting ps = installRequest.getScannedPackageSetting();
        final AndroidPackage pkg = ps.getPkg();
        final boolean onIncremental = isIncrementalPath(ps.getPathString());

        return (!instantApp || Global.getInt(context.getContentResolver(),
                Global.INSTANT_APP_DEXOPT_ENABLED, 0) != 0)
                && pkg != null
                && !pkg.isDebuggable()
                && (!onIncremental)
                && dexoptOptions.isCompilationEnabled()
                && !isApex;
    }
}
+7 −49
Original line number Diff line number Diff line
@@ -32,8 +32,6 @@ import static android.content.pm.PackageManager.INSTALL_FAILED_SESSION_INVALID;
import static android.content.pm.PackageManager.INSTALL_FAILED_TEST_ONLY;
import static android.content.pm.PackageManager.INSTALL_FAILED_UID_CHANGED;
import static android.content.pm.PackageManager.INSTALL_FAILED_UPDATE_INCOMPATIBLE;
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_STAGED;
import static android.content.pm.PackageManager.INSTALL_SUCCEEDED;
import static android.content.pm.PackageManager.UNINSTALL_REASON_UNKNOWN;
@@ -170,10 +168,7 @@ import com.android.internal.security.VerityUtils;
import com.android.internal.util.ArrayUtils;
import com.android.internal.util.CollectionUtils;
import com.android.server.EventLogTags;
import com.android.server.LocalManagerRegistry;
import com.android.server.SystemConfig;
import com.android.server.art.model.ArtFlags;
import com.android.server.art.model.DexoptParams;
import com.android.server.art.model.DexoptResult;
import com.android.server.criticalevents.CriticalEventLog;
import com.android.server.pm.Installer.LegacyDexoptDisabledException;
@@ -2464,8 +2459,6 @@ final class InstallPackageHelper {
        final ArraySet<IncrementalStorage> incrementalStorages = new ArraySet<>();
        for (ReconciledPackage reconciledPkg : reconciledPackages) {
            final InstallRequest installRequest = reconciledPkg.mInstallRequest;
            final boolean instantApp = ((installRequest.getScanFlags() & SCAN_AS_INSTANT_APP) != 0);
            final boolean isApex = ((installRequest.getScanFlags() & SCAN_AS_APEX) != 0);
            final PackageSetting ps = installRequest.getScannedPackageSetting();
            final String packageName = ps.getPackageName();
            final String codePath = ps.getPathString();
@@ -2507,28 +2500,14 @@ final class InstallPackageHelper {
                }
            }

            // Compute the compilation reason from the installation scenario.
            final int compilationReason =
                    mDexManager.getCompilationReasonForInstallScenario(
                            installRequest.getInstallScenario());

            // Construct the DexoptOptions early to see if we should skip running dexopt.
            //
            // Do not run PackageDexOptimizer through the local performDexOpt
            // method because `pkg` may not be in `mPackages` yet.
            //
            // Also, don't fail application installs if the dexopt step fails.
            final boolean isBackupOrRestore =
                    installRequest.getInstallReason() == INSTALL_REASON_DEVICE_RESTORE
                            || installRequest.getInstallReason() == INSTALL_REASON_DEVICE_SETUP;

            final int dexoptFlags = DexoptOptions.DEXOPT_BOOT_COMPLETE
                    | DexoptOptions.DEXOPT_CHECK_FOR_PROFILES_UPDATES
                    | DexoptOptions.DEXOPT_INSTALL_WITH_DEX_METADATA_FILE
                    | (isBackupOrRestore ? DexoptOptions.DEXOPT_FOR_RESTORE : 0);
            DexoptOptions dexoptOptions =
                    new DexoptOptions(packageName, compilationReason, dexoptFlags);

            DexoptOptions dexoptOptions = DexOptHelper.getDexoptOptionsByInstallRequest(
                    installRequest, mDexManager);
            // Check whether we need to dexopt the app.
            //
            // NOTE: it is IMPORTANT to call dexopt:
@@ -2555,16 +2534,9 @@ final class InstallPackageHelper {
            //
            // TODO(b/174695087): instantApp and onIncremental should be removed and their install
            //       path moved to SCENARIO_FAST.
            final boolean performDexopt =
                    (!instantApp || android.provider.Settings.Global.getInt(
                            mContext.getContentResolver(),
                            android.provider.Settings.Global.INSTANT_APP_DEXOPT_ENABLED, 0) != 0)
                            && pkg != null
                            && !pkg.isDebuggable()
                            && (!onIncremental)
                            && dexoptOptions.isCompilationEnabled()
                            && !isApex;

            final boolean performDexopt = DexOptHelper.shouldPerformDexopt(installRequest,
                    dexoptOptions, mContext);
            if (performDexopt) {
                Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dexopt");

@@ -2579,23 +2551,9 @@ final class InstallPackageHelper {
                realPkgSetting.getPkgState().setUpdatedSystemApp(isUpdatedSystemApp);

                if (useArtService()) {
                    PackageManagerLocal packageManagerLocal =
                            LocalManagerRegistry.getManager(PackageManagerLocal.class);
                    try (PackageManagerLocal.FilteredSnapshot snapshot =
                                    packageManagerLocal.withFilteredSnapshot()) {
                        boolean ignoreDexoptProfile =
                                (installRequest.getInstallFlags()
                                        & PackageManager.INSTALL_IGNORE_DEXOPT_PROFILE)
                                != 0;
                        /*@DexoptFlags*/ int extraFlags =
                                ignoreDexoptProfile && Flags.useArtServiceV2()
                                ? ArtFlags.FLAG_IGNORE_PROFILE
                                : 0;
                        DexoptParams params = dexoptOptions.convertToDexoptParams(extraFlags);
                        DexoptResult dexOptResult = DexOptHelper.getArtManagerLocal().dexoptPackage(
                                snapshot, packageName, params);
                    DexoptResult dexOptResult = DexOptHelper.dexoptPackageUsingArtService(
                            installRequest, dexoptOptions);
                    installRequest.onDexoptFinished(dexOptResult);
                    }
                } else {
                    try {
                        mPackageDexOptimizer.performDexOpt(pkg, realPkgSetting,