From 0782f3ea80aaa0b9e8e47a1c511201323701f4fc Mon Sep 17 00:00:00 2001 From: Nikita Ioffe Date: Thu, 21 Apr 2022 00:10:12 +0100 Subject: [PATCH] Drop caches of apks-in-apex if APEX was updated When an APEX is updated, we need to drop the cache for the apks that belong to it. This change does that by making use of the new updatedDuringThisBoot field in ActiveApexInfo. With this change the apk-in-apex cache problem is almost solved, the only remaining piece is to clean up the stale cache entries after the APEX update has completed. It will be done in a separate cl. Bug: 225435110 Test: manual Test: stage mediaprovider APEX Test: crash system_server Test: reboot device Test: check MediaProvider apk inside was updated Change-Id: I080e9e21370fd9c44d4a45b3fe61d127066123d8 Merged-In: I080e9e21370fd9c44d4a45b3fe61d127066123d8 --- .../core/java/com/android/server/pm/InitAppsHelper.java | 7 ++++++- .../java/com/android/server/pm/InstallPackageHelper.java | 7 +++++++ .../java/com/android/server/pm/PackageManagerService.java | 1 + 3 files changed, 14 insertions(+), 1 deletion(-) diff --git a/services/core/java/com/android/server/pm/InitAppsHelper.java b/services/core/java/com/android/server/pm/InitAppsHelper.java index 154f32a2e436a..f6b22bc389394 100644 --- a/services/core/java/com/android/server/pm/InitAppsHelper.java +++ b/services/core/java/com/android/server/pm/InitAppsHelper.java @@ -24,6 +24,7 @@ import static com.android.server.pm.PackageManagerService.SCAN_AS_APK_IN_APEX; import static com.android.server.pm.PackageManagerService.SCAN_AS_PRIVILEGED; import static com.android.server.pm.PackageManagerService.SCAN_AS_SYSTEM; import static com.android.server.pm.PackageManagerService.SCAN_BOOTING; +import static com.android.server.pm.PackageManagerService.SCAN_DROP_CACHE; import static com.android.server.pm.PackageManagerService.SCAN_FIRST_BOOT_OR_UPGRADE; import static com.android.server.pm.PackageManagerService.SCAN_INITIAL; import static com.android.server.pm.PackageManagerService.SCAN_NO_DEX; @@ -167,7 +168,11 @@ final class InitAppsHelper { sp.getFolder().getAbsolutePath()) || apexInfo.preInstalledApexPath.getAbsolutePath().startsWith( sp.getFolder().getAbsolutePath() + File.separator)) { - return new ScanPartition(apexInfo.apexDirectory, sp, SCAN_AS_APK_IN_APEX); + int flags = SCAN_AS_APK_IN_APEX; + if (apexInfo.activeApexChanged) { + flags |= SCAN_DROP_CACHE; + } + return new ScanPartition(apexInfo.apexDirectory, sp, flags); } } return null; diff --git a/services/core/java/com/android/server/pm/InstallPackageHelper.java b/services/core/java/com/android/server/pm/InstallPackageHelper.java index f909feed80453..e753459985349 100644 --- a/services/core/java/com/android/server/pm/InstallPackageHelper.java +++ b/services/core/java/com/android/server/pm/InstallPackageHelper.java @@ -72,6 +72,7 @@ import static com.android.server.pm.PackageManagerService.SCAN_AS_VENDOR; import static com.android.server.pm.PackageManagerService.SCAN_AS_VIRTUAL_PRELOAD; import static com.android.server.pm.PackageManagerService.SCAN_BOOTING; import static com.android.server.pm.PackageManagerService.SCAN_DONT_KILL_APP; +import static com.android.server.pm.PackageManagerService.SCAN_DROP_CACHE; import static com.android.server.pm.PackageManagerService.SCAN_FIRST_BOOT_OR_UPGRADE; import static com.android.server.pm.PackageManagerService.SCAN_IGNORE_FROZEN; import static com.android.server.pm.PackageManagerService.SCAN_INITIAL; @@ -152,6 +153,7 @@ import com.android.server.pm.dex.ArtManagerService; import com.android.server.pm.dex.DexManager; import com.android.server.pm.dex.DexoptOptions; import com.android.server.pm.dex.ViewCompiler; +import com.android.server.pm.parsing.PackageCacher; import com.android.server.pm.parsing.PackageParser2; import com.android.server.pm.parsing.pkg.AndroidPackage; import com.android.server.pm.parsing.pkg.AndroidPackageUtils; @@ -3418,6 +3420,11 @@ final class InstallPackageHelper { // Ignore entries which are not packages continue; } + if ((scanFlags & SCAN_DROP_CACHE) != 0) { + final PackageCacher cacher = new PackageCacher(mPm.getCacheDir()); + Log.w(TAG, "Dropping cache of " + file.getAbsolutePath()); + cacher.cleanCachedResult(file); + } parallelPackageParser.submit(file, parseFlags); fileCount++; } diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java index 386c4372ca651..75a5ff61ee64a 100644 --- a/services/core/java/com/android/server/pm/PackageManagerService.java +++ b/services/core/java/com/android/server/pm/PackageManagerService.java @@ -376,6 +376,7 @@ public class PackageManagerService implements PackageSender, TestUtilityService static final int SCAN_AS_SYSTEM_EXT = 1 << 21; static final int SCAN_AS_ODM = 1 << 22; static final int SCAN_AS_APK_IN_APEX = 1 << 23; + static final int SCAN_DROP_CACHE = 1 << 24; @IntDef(flag = true, prefix = { "SCAN_" }, value = { SCAN_NO_DEX,