Recompile packages with cdex in vdex'es in background dexopt when the
disable cdex experiment is enabled.

Test: adb install out/dist/com.google.android.art.apex
      adb reboot && adb wait-for-device
      m AppUsedByOtherApp
      adb install-multiple out/target/product/vsoc_x86_64/testcases/AppUsedByOtherApp/x86_64/AppUsedByOtherApp.apk AppUsedByOtherApp.dm
      # where AppUsedByOtherApp.dm is created from a non-empty profile
      adb root && adb wait-for-device
      adb shell pm bg-dexopt-job
      adb shell find data/app data/dalvik-cache -name \*.vdex \
        \| xargs grep cdex001
      # -> matches are found, e.g. in system apps
      adb shell pm compile -f -m speed-profile \
        android.compilation.cts.appusedbyotherapp
      adb shell grep cdex001 \
        /data/app/\*/android.compilation.cts.appusedbyotherapp-\*/oat/x86_64/base.vdex
      # -> check that a match is found
      adb shell setprop \
        persist.device_config.runtime_native_boot.disable_compact_dex \
        true
      adb shell pm bg-dexopt-job
      adb shell find data/app data/dalvik-cache -name \*.vdex \
        \| xargs grep cdex001
      # -> check that no matches are found
  on SC, TM and UDC platform images
Bug: 256664509
Bug: 282137215
Change-Id: I720ffc5861768dc43f70789c0dfbad7ceedc5c9a
(cherry picked from commit 35ea7e066db64f4c9c740894d2c428707015a8c0)
Merged-In: I720ffc5861768dc43f70789c0dfbad7ceedc5c9a
diff --git a/runtime/oat_file_assistant.cc b/runtime/oat_file_assistant.cc
index 1b0f0bc..9e16e49 100644
--- a/runtime/oat_file_assistant.cc
+++ b/runtime/oat_file_assistant.cc
@@ -25,6 +25,7 @@
 
 #include "android-base/file.h"
 #include "android-base/logging.h"
+#include "android-base/properties.h"
 #include "android-base/stringprintf.h"
 #include "android-base/strings.h"
 #include "arch/instruction_set.h"
@@ -309,6 +310,9 @@
                                       bool profile_changed,
                                       bool downgrade) {
   OatFileInfo& info = GetBestInfo();
+  if (info.CheckDisableCompactDexExperiment()) {  // TODO(b/256664509): Clean this up.
+    return kDex2OatFromScratch;
+  }
   DexOptNeeded dexopt_needed = info.GetDexOptNeeded(
       target_compiler_filter, GetDexOptTrigger(target_compiler_filter, profile_changed, downgrade));
   if (dexopt_needed != kNoDexOptNeeded && (&info == &dm_for_oat_ || &info == &dm_for_odex_)) {
@@ -327,6 +331,10 @@
                                        DexOptTrigger dexopt_trigger,
                                        /*out*/ DexOptStatus* dexopt_status) {
   OatFileInfo& info = GetBestInfo();
+  if (info.CheckDisableCompactDexExperiment()) {  // TODO(b/256664509): Clean this up.
+    dexopt_status->location_ = kLocationNoneOrError;
+    return true;
+  }
   DexOptNeeded dexopt_needed = info.GetDexOptNeeded(target_compiler_filter, dexopt_trigger);
   if (info.IsUseable()) {
     if (&info == &dm_for_oat_ || &info == &dm_for_odex_) {
@@ -1262,6 +1270,23 @@
   return std::unique_ptr<OatFile>();
 }
 
+// Check if we should reject vdex containing cdex code as part of the
+// disable_cdex experiment.
+// TODO(b/256664509): Clean this up.
+bool OatFileAssistant::OatFileInfo::CheckDisableCompactDexExperiment() {
+  std::string ph_disable_compact_dex = android::base::GetProperty(kPhDisableCompactDex, "false");
+  if (ph_disable_compact_dex != "true") {
+    return false;
+  }
+  const OatFile* oat_file = GetFile();
+  if (oat_file == nullptr) {
+    return false;
+  }
+  const VdexFile* vdex_file = oat_file->GetVdexFile();
+  return vdex_file != nullptr && vdex_file->HasDexSection() &&
+         !vdex_file->HasOnlyStandardDexFiles();
+}
+
 // TODO(calin): we could provide a more refined status here
 // (e.g. run from uncompressed apk, run with vdex but not oat etc). It will allow us to
 // track more experiments but adds extra complexity.