ClassLinker can now FindClass all libcore classes

Summary:
- added ClassLinkerTest/LibCore test of finding all libcore classes
- fixed bug in LinkInterfaceMethods appending mirant methods to vtable_
- fixed bug in LinkVirtualMethods allocating subclass vtable_
- fixed mmap bug in MarkStack::Init
- bumped default (and max) heap sizes to handle ClassLinkerTest/LibCore
- made ObjectArray a templated class
- heap allocate Class::vtable_
- "mm test-art" and "mm test-art-target" added
- new is_host_ for use by tests

Details:

    Added support for "mm test-art" and "mm test-art-target" in addition to test-art-host
	Android.mk

    Made ObjectArray a template class for clearer declarations and to
    remove need the need for down_cast.

	src/object.h
	src/object_test.cc
	src/class_linker.cc
	src/class_linker.h
	src/dex_cache.cc
	src/dex_cache.h
	src/dex_cache_test.cc
	src/mark_sweep.cc

    Made Class::vtable_ a heap allocated ObjectArray<Method>

	src/class_linker.cc

    Fix bug in ClassLinker::LinkInterfaceMethods where we were not
    extending the vtable_ before appending miranda methods.

	src/class_linker.cc

    Changed all uses of DexFile* in ClassLinker to be const

	src/class_linker.cc
	src/class_linker.h

    Fix bug in ClassLinker::LinkVirtualMethods where we were using
    NumVirtualMethods vs vtable->GetLength when determining new max
    vtable_ length.

	src/class_linker.cc

    New ClassLinkerTest/LibCore that enumerates the libcore dex file
    and tries to FindClass every descriptor found.

	src/class_linker_test.cc

    Added if_host_ check for host only tests. In the future will use
    for picking proper location of files, etc. on host vs target.

	src/common_test.h

    Fixed test to use ClassLinker::AllocDexCache

	src/dex_cache_test.cc

    Fixed fooIds comments to foo_ids_

	src/dex_file.h

    Bumped default heap size (and max as well) to make ClassLinkerTest/LibCore run

	src/heap.h

    Fixed bug where we were not using MAP_ANONYMOUS for MarkStack
    allocation found running ClassLinkerTest/LibCore.

	src/mark_stack.cc

Change-Id: I204e2ec7205210e2b60f5b81d126ab6e1da5a71c
diff --git a/src/class_linker.cc b/src/class_linker.cc
index 78b6d33..22bcca6 100644
--- a/src/class_linker.cc
+++ b/src/class_linker.cc
@@ -86,7 +86,7 @@
   CHECK(java_io_Serializable_ != NULL);
   java_io_Serializable_->descriptor_ = "Ljava/io/Serializable;";
 
-  array_interfaces_ = AllocObjectArray(2);
+  array_interfaces_ = AllocObjectArray<Class>(2);
   CHECK(array_interfaces_ != NULL);
   array_interfaces_->Set(0, java_lang_Cloneable_);
   array_interfaces_->Set(1, java_io_Serializable_);
@@ -98,8 +98,8 @@
   array_iftable_ = new InterfaceEntry[2];
   CHECK(array_iftable_ != NULL);
   memset(array_iftable_, 0, sizeof(InterfaceEntry) * 2);
-  array_iftable_[0].SetClass(down_cast<Class*>(array_interfaces_->Get(0)));
-  array_iftable_[1].SetClass(down_cast<Class*>(array_interfaces_->Get(1)));
+  array_iftable_[0].SetClass(array_interfaces_->Get(0));
+  array_iftable_[1].SetClass(array_interfaces_->Get(1));
 
   char_array_class_ = FindSystemClass("[C");
   CHECK(char_array_class_ != NULL);
@@ -113,7 +113,7 @@
 }
 
 DexCache* ClassLinker::AllocDexCache() {
-  return down_cast<DexCache*>(Heap::AllocObjectArray(object_array_class_, DexCache::kMax));
+  return down_cast<DexCache*>(Heap::AllocObjectArray<Object>(object_array_class_, DexCache::kMax));
 }
 
 Class* ClassLinker::AllocClass(DexCache* dex_cache) {
@@ -137,10 +137,6 @@
                                               sizeof(Method)));
 }
 
-ObjectArray* ClassLinker::AllocObjectArray(size_t length) {
-    return Heap::AllocObjectArray(object_array_class_, length);
-}
-
 Class* ClassLinker::FindClass(const StringPiece& descriptor,
                               Object* class_loader,
                               const DexFile* dex_file) {
@@ -290,7 +286,7 @@
   // Load static fields.
   DCHECK(klass->sfields_ == NULL);
   if (num_static_fields != 0) {
-    klass->sfields_ = AllocObjectArray(num_static_fields);
+    klass->sfields_ = AllocObjectArray<StaticField>(num_static_fields);
     uint32_t last_idx = 0;
     for (size_t i = 0; i < klass->NumStaticFields(); ++i) {
       DexFile::Field dex_field;
@@ -305,7 +301,7 @@
   DCHECK(klass->ifields_ == NULL);
   if (num_instance_fields != 0) {
     // TODO: allocate on the object heap.
-    klass->ifields_ = AllocObjectArray(num_instance_fields);
+    klass->ifields_ = AllocObjectArray<InstanceField>(num_instance_fields);
     uint32_t last_idx = 0;
     for (size_t i = 0; i < klass->NumInstanceFields(); ++i) {
       DexFile::Field dex_field;
@@ -320,7 +316,7 @@
   DCHECK(klass->direct_methods_ == NULL);
   if (num_direct_methods != 0) {
     // TODO: append direct methods to class object
-    klass->direct_methods_ = AllocObjectArray(num_direct_methods);
+    klass->direct_methods_ = AllocObjectArray<Method>(num_direct_methods);
     uint32_t last_idx = 0;
     for (size_t i = 0; i < klass->NumDirectMethods(); ++i) {
       DexFile::Method dex_method;
@@ -336,7 +332,7 @@
   DCHECK(klass->virtual_methods_ == NULL);
   if (num_virtual_methods != 0) {
     // TODO: append virtual methods to class object
-    klass->virtual_methods_ = AllocObjectArray(num_virtual_methods);
+    klass->virtual_methods_ = AllocObjectArray<Method>(num_virtual_methods);
     uint32_t last_idx = 0;
     for (size_t i = 0; i < klass->NumVirtualMethods(); ++i) {
       DexFile::Method dex_method;
@@ -355,7 +351,7 @@
   const DexFile::TypeList* list = dex_file.GetInterfacesList(dex_class_def);
   if (list != NULL) {
     DCHECK(klass->interfaces_ == NULL);
-    klass->interfaces_ = AllocObjectArray(list->Size());
+    klass->interfaces_ = AllocObjectArray<Class>(list->Size());
     DCHECK(klass->interfaces_idx_ == NULL);
     klass->interfaces_idx_ = new uint32_t[list->Size()];
     for (size_t i = 0; i < list->Size(); ++i) {
@@ -407,7 +403,7 @@
 
 ClassLinker::ClassPathEntry ClassLinker::FindInBootClassPath(const StringPiece& descriptor) {
   for (size_t i = 0; i != boot_class_path_.size(); ++i) {
-    DexFile* dex_file = boot_class_path_[i];
+    const DexFile* dex_file = boot_class_path_[i];
     const DexFile::ClassDef* dex_class_def = dex_file->FindClassDef(descriptor);
     if (dex_class_def != NULL) {
       return ClassPathEntry(dex_file, dex_class_def);
@@ -422,15 +418,15 @@
   RegisterDexFile(dex_file);
 }
 
-void ClassLinker::RegisterDexFile(DexFile* dex_file) {
+void ClassLinker::RegisterDexFile(const DexFile* dex_file) {
   CHECK(dex_file != NULL);
   dex_files_.push_back(dex_file);
   DexCache* dex_cache = AllocDexCache();
   CHECK(dex_cache != NULL);
-  dex_cache->Init(AllocObjectArray(dex_file->NumStringIds()),
-                  AllocObjectArray(dex_file->NumTypeIds()),
-                  AllocObjectArray(dex_file->NumMethodIds()),
-                  AllocObjectArray(dex_file->NumFieldIds()));
+  dex_cache->Init(AllocObjectArray<String>(dex_file->NumStringIds()),
+                  AllocObjectArray<Class>(dex_file->NumTypeIds()),
+                  AllocObjectArray<Method>(dex_file->NumMethodIds()),
+                  AllocObjectArray<Field>(dex_file->NumFieldIds()));
   dex_caches_.push_back(dex_cache);
 }
 
@@ -569,7 +565,6 @@
     new_class->descriptor_.set(new_class->descriptor_alloc_->data(),
                                new_class->descriptor_alloc_->size());
     new_class->super_class_ = java_lang_Object_;
-    new_class->vtable_count_ = java_lang_Object_->vtable_count_;
     new_class->vtable_ = java_lang_Object_->vtable_;
     new_class->primitive_type_ = Class::kPrimNot;
     new_class->component_type_ = component_type_;
@@ -1113,38 +1108,36 @@
 bool ClassLinker::LinkVirtualMethods(Class* klass) {
   uint32_t max_count = klass->NumVirtualMethods();
   if (klass->GetSuperClass() != NULL) {
-    max_count += klass->GetSuperClass()->NumVirtualMethods();
+    max_count += klass->GetSuperClass()->vtable_->GetLength();
   } else {
     CHECK(klass->GetDescriptor() == "Ljava/lang/Object;");
   }
   // TODO: do not assign to the vtable field until it is fully constructed.
-  // TODO: make this a vector<Method*> instead?
-  klass->vtable_ = new Method*[max_count];
+  klass->vtable_ = AllocObjectArray<Method>(max_count);
   if (klass->HasSuperClass()) {
-    memcpy(klass->vtable_,
-           klass->GetSuperClass()->vtable_,
-           klass->GetSuperClass()->vtable_count_ * sizeof(Method*));
-    size_t actual_count = klass->GetSuperClass()->vtable_count_;
+    size_t actual_count = klass->GetSuperClass()->vtable_->GetLength();
+    CHECK_LE(actual_count, max_count);
+    ObjectArray<Method>::Copy(klass->GetSuperClass()->vtable_, 0, klass->vtable_, 0, actual_count);
     // See if any of our virtual methods override the superclass.
     for (size_t i = 0; i < klass->NumVirtualMethods(); ++i) {
       Method* local_method = klass->GetVirtualMethod(i);
       size_t j = 0;
-      for (; j < klass->GetSuperClass()->vtable_count_; ++j) {
-        const Method* super_method = klass->vtable_[j];
+      for (; j < actual_count; ++j) {
+        Method* super_method = klass->vtable_->Get(j);
         if (HasSameNameAndPrototype(local_method, super_method)) {
           // Verify
           if (super_method->IsFinal()) {
             LG << "Method overrides final method";  // TODO: VirtualMachineError
             return false;
           }
-          klass->vtable_[j] = local_method;
+          klass->vtable_->Set(j, local_method);
           local_method->method_index_ = j;
           break;
         }
       }
-      if (j == klass->GetSuperClass()->vtable_count_) {
+      if (j == actual_count) {
         // Not overriding, append.
-        klass->vtable_[actual_count] = local_method;
+        klass->vtable_->Set(actual_count, local_method);
         local_method->method_index_ = actual_count;
         actual_count += 1;
       }
@@ -1155,15 +1148,13 @@
     }
     CHECK_LE(actual_count, max_count);
     if (actual_count < max_count) {
-      Method** new_vtable = new Method*[actual_count];
-      memcpy(new_vtable, klass->vtable_, actual_count * sizeof(Method*));
-      delete[] klass->vtable_;
+      ObjectArray<Method>* new_vtable = AllocObjectArray<Method>(actual_count);
+      ObjectArray<Method>::Copy(klass->vtable_, 0, new_vtable, 0, actual_count);
       klass->vtable_ = new_vtable;
       LG << "shrunk vtable: "
          << "was " << max_count << ", "
          << "now " << actual_count;
     }
-    klass->vtable_count_ = actual_count;
   } else {
     CHECK(klass->GetDescriptor() == "Ljava/lang/Object;");
     if (!IsUint(16, klass->NumVirtualMethods())) {
@@ -1171,10 +1162,9 @@
       return false;
     }
     for (size_t i = 0; i < klass->NumVirtualMethods(); ++i) {
-      klass->vtable_[i] = klass->GetVirtualMethod(i);
+      klass->vtable_->Set(i, klass->GetVirtualMethod(i));
       klass->GetVirtualMethod(i)->method_index_ = i & 0xFFFF;
     }
-    klass->vtable_count_ = klass->NumVirtualMethods();
   }
   return true;
 }
@@ -1241,9 +1231,9 @@
     for (size_t j = 0; j < interface->NumVirtualMethods(); ++j) {
       Method* interface_method = interface->GetVirtualMethod(j);
       int k;  // must be signed
-      for (k = klass->vtable_count_ - 1; k >= 0; --k) {
-        if (HasSameNameAndPrototype(interface_method, klass->vtable_[k])) {
-          if (!klass->vtable_[k]->IsPublic()) {
+      for (k = klass->vtable_->GetLength() - 1; k >= 0; --k) {
+        if (HasSameNameAndPrototype(interface_method, klass->vtable_->Get(k))) {
+          if (!klass->vtable_->Get(k)->IsPublic()) {
             LG << "Implementation not public";
             return false;
           }
@@ -1267,7 +1257,7 @@
           }
         }
         // point the interface table at a phantom slot index
-        klass->iftable_[i].method_index_array_[j] = klass->vtable_count_ + mir;
+        klass->iftable_[i].method_index_array_[j] = klass->vtable_->GetLength() + mir;
         if (mir == miranda_count) {
           miranda_list[miranda_count++] = interface_method;
         }
@@ -1277,17 +1267,20 @@
   if (miranda_count != 0) {
     int old_method_count = klass->NumVirtualMethods();
     int new_method_count = old_method_count + miranda_count;
-    ObjectArray* new_virtual_methods = AllocObjectArray(new_method_count);
-    if (klass->virtual_methods_ != NULL) {
-      ObjectArray::Copy(klass->virtual_methods_, 0,
-                        new_virtual_methods, 0,
-                        old_method_count);
-    }
+    ObjectArray<Method>* new_virtual_methods = AllocObjectArray<Method>(new_method_count);
+    ObjectArray<Method>::Copy(klass->virtual_methods_, 0,
+                              new_virtual_methods, 0,
+                              old_method_count);
     klass->virtual_methods_ = new_virtual_methods;
 
     CHECK(klass->vtable_ != NULL);
-    int old_vtable_count = klass->vtable_count_;
-    klass->vtable_count_ += miranda_count;
+    int old_vtable_count = klass->vtable_->GetLength();
+    int new_vtable_count = old_vtable_count + miranda_count;
+    ObjectArray<Method>* new_vtable = AllocObjectArray<Method>(new_vtable_count);
+    ObjectArray<Method>::Copy(klass->vtable_, 0,
+                              new_vtable, 0,
+                              old_vtable_count);
+    klass->vtable_ = new_vtable;
 
     for (int i = 0; i < miranda_count; i++) {
       Method* meth = AllocMethod();
@@ -1296,7 +1289,7 @@
       meth->access_flags_ |= kAccMiranda;
       meth->method_index_ = 0xFFFF & (old_vtable_count + i);
       klass->SetVirtualMethod(old_method_count + i, meth);
-      klass->vtable_[old_vtable_count + i] = meth;
+      klass->vtable_->Set(old_vtable_count + i, meth);
     }
   }
   return true;