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

Commit 3ed22aea authored by Jiakai Zhang's avatar Jiakai Zhang
Browse files

Make dumpProfiles and reconcileSecondaryDexFiles throwing.

These two methods only uses the legacy implementation and are used by
the legacy shell command only. They should throw
LegacyDexoptDisabledException to prevent partners from accidentially
using them.

This change also moves the declaration of these two methods from
the IPackageManager interface to the PackageManagerInternal interface
because IPackageManager is in f/b/core and therefore cannot access
LegacyDexoptDisabledException.

Bug: 251903639
Bug: 263247832
Test: Presubmit
Change-Id: I9bc321292eb3f930afca18b960eb6ddee46d58c9
parent aaedfaf9
Loading
Loading
Loading
Loading
+0 −18
Original line number Diff line number Diff line
@@ -570,26 +570,8 @@ interface IPackageManager {
    boolean performDexOptSecondary(String packageName,
            String targetCompilerFilter, boolean force);

    /**
     * Ask the package manager to dump profiles associated with a package.
     *
     * @param packageName The name of the package to dump.
     * @param dumpClassesAndMethods If false, pass {@code --dump-only} to profman to dump the
     *   profile in a human readable form intended for debugging. If true, pass
     *   {@code --dump-classes-and-methods} to profman to dump a sorted list of classes and methods
     *   in a human readable form that is valid input for {@code profman --create-profile-from}.
     */
    void dumpProfiles(String packageName, boolean dumpClassesAndMethods);

    void forceDexOpt(String packageName);

    /**
     * Reconcile the information we have about the secondary dex files belonging to
     * {@code packagName} and the actual dex files. For all dex files that were
     * deleted, update the internal records and delete the generated oat files.
     */
    void reconcileSecondaryDexFiles(String packageName);

    int getMoveStatus(int moveId);

    void registerMoveCallback(in IPackageMoveObserver callback);
+11 −0
Original line number Diff line number Diff line
@@ -44,6 +44,7 @@ import android.util.ArraySet;
import android.util.SparseArray;

import com.android.internal.util.function.pooled.PooledLambda;
import com.android.server.pm.Installer.LegacyDexoptDisabledException;
import com.android.server.pm.KnownPackages;
import com.android.server.pm.PackageList;
import com.android.server.pm.PackageSetting;
@@ -1320,4 +1321,14 @@ public abstract class PackageManagerInternal {

    public abstract void setPackageStoppedState(@NonNull String packageName, boolean stopped,
            @UserIdInt int userId);

    /** @deprecated For legacy shell command only. */
    @Deprecated
    public abstract void legacyDumpProfiles(@NonNull String packageName,
            boolean dumpClassesAndMethods) throws LegacyDexoptDisabledException;

    /** @deprecated For legacy shell command only. */
    @Deprecated
    public abstract void legacyReconcileSecondaryDexFiles(String packageName)
            throws LegacyDexoptDisabledException;
}
+41 −56
Original line number Diff line number Diff line
@@ -4826,35 +4826,6 @@ public class PackageManagerService implements PackageSender, TestUtilityService
            });
        }

        @Override
        public void dumpProfiles(String packageName, boolean dumpClassesAndMethods) {
            /* Only the shell, root, or the app user should be able to dump profiles. */
            final int callingUid = Binder.getCallingUid();
            final Computer snapshot = snapshotComputer();
            final String[] callerPackageNames = snapshot.getPackagesForUid(callingUid);
            if (callingUid != Process.SHELL_UID
                    && callingUid != Process.ROOT_UID
                    && !ArrayUtils.contains(callerPackageNames, packageName)) {
                throw new SecurityException("dumpProfiles");
            }

            AndroidPackage pkg = snapshot.getPackage(packageName);
            if (pkg == null) {
                throw new IllegalArgumentException("Unknown package: " + packageName);
            }

            // TODO(b/251903639): Call into ART Service.
            synchronized (mInstallLock) {
                Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dump profiles");
                try {
                    mArtManagerService.dumpProfiles(pkg, dumpClassesAndMethods);
                } catch (LegacyDexoptDisabledException e) {
                    throw new RuntimeException(e);
                }
                Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
            }
        }

        @Override
        public void enterSafeMode() {
            PackageManagerServiceUtils.enforceSystemOrRoot(
@@ -5541,33 +5512,6 @@ public class PackageManagerService implements PackageSender, TestUtilityService
            return new ParceledListSlice<>(result);
        }

        /**
         * Reconcile the information we have about the secondary dex files belonging to
         * {@code packageName} and the actual dex files. For all dex files that were
         * deleted, update the internal records and delete the generated oat files.
         */
        @Override
        public void reconcileSecondaryDexFiles(String packageName) {
            if (useArtService()) {
                // ART Service currently relies on a GC to find stale oat files, including secondary
                // dex files. Hence it doesn't use this call for anything.
                return;
            }

            final Computer snapshot = snapshotComputer();
            if (snapshot.getInstantAppPackageName(Binder.getCallingUid()) != null) {
                return;
            } else if (snapshot.isInstantAppInternal(
                               packageName, UserHandle.getCallingUserId(), Process.SYSTEM_UID)) {
                return;
            }
            try {
                mDexManager.reconcileSecondaryDexFiles(packageName);
            } catch (LegacyDexoptDisabledException e) {
                throw new RuntimeException(e);
            }
        }

        @Override
        public void registerDexModule(String packageName, String dexModulePath,
                boolean isSharedModule,
@@ -6663,6 +6607,47 @@ public class PackageManagerService implements PackageSender, TestUtilityService
            }
        }

        /** @deprecated For legacy shell command only. */
        @Override
        @Deprecated
        public void legacyDumpProfiles(String packageName, boolean dumpClassesAndMethods)
                throws LegacyDexoptDisabledException {
            /* Only the shell, root, or the app user should be able to dump profiles. */
            final int callingUid = Binder.getCallingUid();
            final Computer snapshot = snapshotComputer();
            final String[] callerPackageNames = snapshot.getPackagesForUid(callingUid);
            if (callingUid != Process.SHELL_UID && callingUid != Process.ROOT_UID
                    && !ArrayUtils.contains(callerPackageNames, packageName)) {
                throw new SecurityException("dumpProfiles");
            }

            AndroidPackage pkg = snapshot.getPackage(packageName);
            if (pkg == null) {
                throw new IllegalArgumentException("Unknown package: " + packageName);
            }

            synchronized (mInstallLock) {
                Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "dump profiles");
                mArtManagerService.dumpProfiles(pkg, dumpClassesAndMethods);
                Trace.traceEnd(TRACE_TAG_PACKAGE_MANAGER);
            }
        }

        /** @deprecated For legacy shell command only. */
        @Override
        @Deprecated
        public void legacyReconcileSecondaryDexFiles(String packageName)
                throws LegacyDexoptDisabledException {
            final Computer snapshot = snapshotComputer();
            if (snapshot.getInstantAppPackageName(Binder.getCallingUid()) != null) {
                return;
            } else if (snapshot.isInstantAppInternal(
                               packageName, UserHandle.getCallingUserId(), Process.SYSTEM_UID)) {
                return;
            }
            mDexManager.reconcileSecondaryDexFiles(packageName);
        }

        @Override
        @SuppressWarnings("GuardedBy")
        public void updateRuntimePermissionsFingerprint(@UserIdInt int userId) {
+8 −6
Original line number Diff line number Diff line
@@ -179,6 +179,7 @@ class PackageManagerShellCommand extends ShellCommand {
            "cancel-bg-dexopt-job", "delete-dexopt", "dump-profiles", "snapshot-profile", "art");

    final IPackageManager mInterface;
    private final PackageManagerInternal mPm;
    final LegacyPermissionManagerInternal mLegacyPermissionManager;
    final PermissionManager mPermissionManager;
    final Context mContext;
@@ -195,6 +196,7 @@ class PackageManagerShellCommand extends ShellCommand {
    PackageManagerShellCommand(@NonNull IPackageManager packageManager,
            @NonNull Context context, @NonNull DomainVerificationShell domainVerificationShell) {
        mInterface = packageManager;
        mPm = LocalServices.getService(PackageManagerInternal.class);
        mLegacyPermissionManager = LocalServices.getService(LegacyPermissionManagerInternal.class);
        mPermissionManager = context.getSystemService(PermissionManager.class);
        mContext = context;
@@ -1968,9 +1970,10 @@ class PackageManagerShellCommand extends ShellCommand {
        }
    }

    private int runreconcileSecondaryDexFiles() throws RemoteException {
    private int runreconcileSecondaryDexFiles()
            throws RemoteException, LegacyDexoptDisabledException {
        String packageName = getNextArg();
        mInterface.reconcileSecondaryDexFiles(packageName);
        mPm.legacyReconcileSecondaryDexFiles(packageName);
        return 0;
    }

@@ -2035,8 +2038,7 @@ class PackageManagerShellCommand extends ShellCommand {
            pw.println("Error: no package name");
            return 1;
        }
        long freedBytes = LocalServices.getService(PackageManagerInternal.class)
                                  .deleteOatArtifactsOfPackage(packageName);
        long freedBytes = mPm.deleteOatArtifactsOfPackage(packageName);
        if (freedBytes < 0) {
            pw.println("Error: delete failed");
            return 1;
@@ -2046,7 +2048,7 @@ class PackageManagerShellCommand extends ShellCommand {
        return 0;
    }

    private int runDumpProfiles() throws RemoteException {
    private int runDumpProfiles() throws RemoteException, LegacyDexoptDisabledException {
        final PrintWriter pw = getOutPrintWriter();
        boolean dumpClassesAndMethods = false;

@@ -2063,7 +2065,7 @@ class PackageManagerShellCommand extends ShellCommand {
        }

        String packageName = getNextArg();
        mInterface.dumpProfiles(packageName, dumpClassesAndMethods);
        mPm.legacyDumpProfiles(packageName, dumpClassesAndMethods);
        return 0;
    }