Hash-based dex cache type array.

Test: m test-art-host (Interpreter, Optimizing, JIT)
Test: m test-art-target on Nexus 6P (Interpreter, Optimizing, JIT)
Test: Nexus 6P boots
Test: m valgrind-test-art-host
Bug: 30627598
Bug: 34659969
Bug: 30419309
Change-Id: Ic00eda89e58088a3573fc9ec0ad04c0e69e161d1
diff --git a/compiler/image_writer.cc b/compiler/image_writer.cc
index c72edb1..3e9ae08 100644
--- a/compiler/image_writer.cc
+++ b/compiler/image_writer.cc
@@ -940,9 +940,11 @@
     }
     ObjPtr<mirror::DexCache> dex_cache = self->DecodeJObject(data.weak_root)->AsDexCache();
     for (size_t i = 0; i < dex_cache->NumResolvedTypes(); i++) {
-      Class* klass = dex_cache->GetResolvedType(dex::TypeIndex(i));
+      mirror::TypeDexCachePair pair =
+          dex_cache->GetResolvedTypes()[i].load(std::memory_order_relaxed);
+      mirror::Class* klass = pair.object.Read();
       if (klass != nullptr && !KeepClass(klass)) {
-        dex_cache->SetResolvedType(dex::TypeIndex(i), nullptr);
+        dex_cache->ClearResolvedType(dex::TypeIndex(pair.index));
       }
     }
     ArtMethod** resolved_methods = dex_cache->GetResolvedMethods();
@@ -1922,8 +1924,7 @@
     // above comment for intern tables.
     ClassTable temp_class_table;
     temp_class_table.ReadFromMemory(class_table_memory_ptr);
-    CHECK_EQ(class_loaders_.size(), compile_app_image_ ? 1u : 0u);
-    mirror::ClassLoader* class_loader = compile_app_image_ ? *class_loaders_.begin() : nullptr;
+    ObjPtr<mirror::ClassLoader> class_loader = GetClassLoader();
     CHECK_EQ(temp_class_table.NumZygoteClasses(class_loader),
              table->NumNonZygoteClasses(class_loader) + table->NumZygoteClasses(class_loader));
     UnbufferedRootVisitor visitor(&root_visitor, RootInfo(kRootUnknown));
@@ -2213,7 +2214,7 @@
     orig_dex_cache->FixupStrings(NativeCopyLocation(orig_strings, orig_dex_cache),
                                  ImageAddressVisitor(this));
   }
-  GcRoot<mirror::Class>* orig_types = orig_dex_cache->GetResolvedTypes();
+  mirror::TypeDexCacheType* orig_types = orig_dex_cache->GetResolvedTypes();
   if (orig_types != nullptr) {
     copy_dex_cache->SetFieldPtrWithSize<false>(mirror::DexCache::ResolvedTypesOffset(),
                                                NativeLocationInImage(orig_types),