Ignore image checksum for ExtractOnly oat files

Oat files compiled with --compiler-filter=verify-at-runtime contain
no compiled code and therefore are independent of the boot image.
This patch stores an ExtractOnly flag in the oat header and skips
the image checksum test if the flag is set, rendering the oat file
up to date even after OTAs.

Bug: 26813999

Change-Id: I25291d5b49d9e9d0018844e957a2dc88ef6bdc27
diff --git a/runtime/oat_file_assistant.cc b/runtime/oat_file_assistant.cc
index a8f84a2..6daade0 100644
--- a/runtime/oat_file_assistant.cc
+++ b/runtime/oat_file_assistant.cc
@@ -461,6 +461,23 @@
     }
   }
 
+  if (file.IsExtractOnly()) {
+    VLOG(oat) << "Oat file is extract-only. Image checksum test skipped.";
+    if (kIsDebugBuild) {
+      // Sanity check that no classes have compiled code. Does not test that
+      // the DEX code has not been quickened.
+      std::string error_msg;
+      for (const OatFile::OatDexFile* current : file.GetOatDexFiles()) {
+        const DexFile* const dex_file = current->OpenDexFile(&error_msg).release();
+        DCHECK(dex_file != nullptr);
+        for (size_t i = 0, e = dex_file->NumClassDefs(); i < e; ++i) {
+          DCHECK_EQ(current->GetOatClass(i).GetType(), kOatClassNoneCompiled);
+        }
+      }
+    }
+    return false;
+  }
+
   // Verify the image checksum
   const ImageInfo* image_info = GetImageInfo();
   if (image_info == nullptr) {
@@ -486,7 +503,10 @@
     return false;
   }
 
-  if (file.IsPic()) {
+  if (file.IsPic() || file.IsExtractOnly()) {
+    // Oat files compiled in PIC mode do not require relocation and extract-only
+    // oat files do not contain any compiled code. Skip the relocation test.
+    VLOG(oat) << "Oat relocation test skipped.";
     return true;
   }