Support for unresolved types in new-instance during verification.

Also, ensure that classes that don't load are erroneous, warn early
about exceptions left on a thread by the verifier/compiler, factor out
slowpath checks for the compiler and fix the slowpath selector for
const-class.

This change causes more dex cache misses at runtime (more slowpath
execution). It also requires a "mm clean-oat".

Change-Id: I014b49ebdd7d8f7dd2e39cc0958fc0b708d58c4c
diff --git a/src/object.cc b/src/object.cc
index e59e79a..45fc781 100644
--- a/src/object.cc
+++ b/src/object.cc
@@ -668,7 +668,6 @@
 
 uint32_t Method::FindCatchBlock(Class* exception_type, uint32_t dex_pc) const {
   DexCache* dex_cache = GetDeclaringClass()->GetDexCache();
-  const ClassLoader* class_loader = GetDeclaringClass()->GetClassLoader();
   ClassLinker* class_linker = Runtime::Current()->GetClassLinker();
   const DexFile& dex_file = class_linker->FindDexFile(dex_cache);
   const DexFile::CodeItem* code_item = dex_file.GetCodeItem(GetCodeItemOffset());
@@ -681,9 +680,12 @@
       return iter.Get().address_;
     }
     // Does this catch exception type apply?
-    Class* iter_exception_type =
-        class_linker->ResolveType(dex_file, iter_type_idx, dex_cache, class_loader);
-    if (iter_exception_type->IsAssignableFrom(exception_type)) {
+    Class* iter_exception_type = dex_cache->GetResolvedType(iter_type_idx);
+    if (iter_exception_type == NULL) {
+      // The verifier should take care of resolving all exception classes early
+      LOG(WARNING) << "Unresolved exception class when finding catch block: "
+          << dex_file.GetTypeDescriptor(dex_file.GetTypeId(iter_type_idx));
+    } else if (iter_exception_type->IsAssignableFrom(exception_type)) {
       return iter.Get().address_;
     }
   }
@@ -764,10 +766,8 @@
 }
 
 Object* Class::AllocObject() {
-  DCHECK(!IsAbstract()) << PrettyClass(this);
-  DCHECK(!IsInterface()) << PrettyClass(this);
-  DCHECK(!IsPrimitive()) << PrettyClass(this);
   DCHECK(!IsArrayClass()) << PrettyClass(this);
+  DCHECK(IsInstantiable()) << PrettyClass(this);
   DCHECK(!Runtime::Current()->IsStarted() || IsInitializing()) << PrettyClass(this);
   DCHECK_GE(this->object_size_, sizeof(Object));
   return Heap::AllocObject(this, this->object_size_);