Enable moving classes.

Slight reduction in Zygote size, memory savings are in the noise.
Before: Zygote size: 8739224
After: Zygote size: 8733568

Fixed a bug where we didn't set the concurrent start bytes after
switching the allocator from bump pointer to ROSAlloc in the
zygote. This caused excessive memory usage.

Added the method verifiers as roots to fix an issue caused by
RegTypes holding a Class*.

Added logic to clear card table in the SemiSpace collector, this
reduces DalvikOther from ~2400k -> ~1760k when using the SemiSpace
collector.

Added a missing lock to the timing loggers which caused a rare
one time crash in std::set.

Bug: 11771255
Bug: 8499494
Bug: 10802951

Change-Id: I99d2b528cd51c1c5ed7012e3220b3aefded680ae
diff --git a/runtime/mirror/array-inl.h b/runtime/mirror/array-inl.h
index a754b69..cf4b48c 100644
--- a/runtime/mirror/array-inl.h
+++ b/runtime/mirror/array-inl.h
@@ -108,6 +108,13 @@
                Runtime::Current()->GetHeap()->GetCurrentAllocator());
 }
 
+template<class T>
+inline void PrimitiveArray<T>::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (array_class_ != nullptr) {
+    array_class_ = down_cast<Class*>(visitor(array_class_, arg));
+  }
+}
+
 }  // namespace mirror
 }  // namespace art
 
diff --git a/runtime/mirror/array.h b/runtime/mirror/array.h
index a332f97..5265946 100644
--- a/runtime/mirror/array.h
+++ b/runtime/mirror/array.h
@@ -149,6 +149,9 @@
     array_class_ = NULL;
   }
 
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
+
  private:
   static Class* array_class_;
 
diff --git a/runtime/mirror/art_field.cc b/runtime/mirror/art_field.cc
index a8bbe4b..c3a4efb 100644
--- a/runtime/mirror/art_field.cc
+++ b/runtime/mirror/art_field.cc
@@ -52,5 +52,12 @@
   SetField32(OFFSET_OF_OBJECT_MEMBER(ArtField, offset_), num_bytes.Uint32Value(), false);
 }
 
+void ArtField::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (java_lang_reflect_ArtField_ != nullptr) {
+    java_lang_reflect_ArtField_ = down_cast<mirror::Class*>(
+        visitor(java_lang_reflect_ArtField_, arg));
+  }
+}
+
 }  // namespace mirror
 }  // namespace art
diff --git a/runtime/mirror/art_field.h b/runtime/mirror/art_field.h
index ae34cb1..62bcf06 100644
--- a/runtime/mirror/art_field.h
+++ b/runtime/mirror/art_field.h
@@ -130,6 +130,8 @@
 
   static void SetClass(Class* java_lang_reflect_ArtField);
   static void ResetClass();
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
   bool IsVolatile() const {
     return (GetAccessFlags() & kAccVolatile) != 0;
diff --git a/runtime/mirror/art_method.cc b/runtime/mirror/art_method.cc
index f5c0e9f..a4f6b3b 100644
--- a/runtime/mirror/art_method.cc
+++ b/runtime/mirror/art_method.cc
@@ -40,6 +40,13 @@
 // TODO: get global references for these
 Class* ArtMethod::java_lang_reflect_ArtMethod_ = NULL;
 
+void ArtMethod::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (java_lang_reflect_ArtMethod_ != nullptr) {
+    java_lang_reflect_ArtMethod_ = down_cast<mirror::Class*>(
+        visitor(java_lang_reflect_ArtMethod_, arg));
+  }
+}
+
 InvokeType ArtMethod::GetInvokeType() const {
   // TODO: kSuper?
   if (GetDeclaringClass()->IsInterface()) {
diff --git a/runtime/mirror/art_method.h b/runtime/mirror/art_method.h
index f396fbe..d5524ec 100644
--- a/runtime/mirror/art_method.h
+++ b/runtime/mirror/art_method.h
@@ -23,6 +23,7 @@
 #include "locks.h"
 #include "modifiers.h"
 #include "object.h"
+#include "root_visitor.h"
 
 namespace art {
 
@@ -381,6 +382,9 @@
 
   static void ResetClass();
 
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
+
  protected:
   // Field order required by test "ValidateFieldOrderOfJavaCppUnionClasses".
   // The class we are a part of
diff --git a/runtime/mirror/class.cc b/runtime/mirror/class.cc
index cdc5ab2..2746e1e 100644
--- a/runtime/mirror/class.cc
+++ b/runtime/mirror/class.cc
@@ -50,6 +50,12 @@
   java_lang_Class_ = NULL;
 }
 
+void Class::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (java_lang_Class_ != nullptr) {
+    java_lang_Class_ = down_cast<Class*>(visitor(java_lang_Class_, arg));
+  }
+}
+
 void Class::SetStatus(Status new_status, Thread* self) {
   Status old_status = GetStatus();
   ClassLinker* class_linker = Runtime::Current()->GetClassLinker();
diff --git a/runtime/mirror/class.h b/runtime/mirror/class.h
index 5f64bb4..50ede66 100644
--- a/runtime/mirror/class.h
+++ b/runtime/mirror/class.h
@@ -787,6 +787,8 @@
   // Can't call this SetClass or else gets called instead of Object::SetClass in places.
   static void SetClassClass(Class* java_lang_Class);
   static void ResetClass();
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
   // When class is verified, set the kAccPreverified flag on each method.
   void SetPreverifiedFlagOnAllMethods() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
diff --git a/runtime/mirror/object.h b/runtime/mirror/object.h
index 0fb2039..fe89b7e 100644
--- a/runtime/mirror/object.h
+++ b/runtime/mirror/object.h
@@ -225,6 +225,11 @@
 
   void SetField64(MemberOffset field_offset, uint64_t new_value, bool is_volatile);
 
+  template<typename T>
+  void SetFieldPtr(MemberOffset field_offset, T new_value, bool is_volatile, bool this_is_valid = true) {
+    SetField32(field_offset, reinterpret_cast<uint32_t>(new_value), is_volatile, this_is_valid);
+  }
+
  protected:
   // Accessors for non-Java type fields
   template<class T>
@@ -232,11 +237,6 @@
     return reinterpret_cast<T>(GetField32(field_offset, is_volatile));
   }
 
-  template<typename T>
-  void SetFieldPtr(MemberOffset field_offset, T new_value, bool is_volatile, bool this_is_valid = true) {
-    SetField32(field_offset, reinterpret_cast<uint32_t>(new_value), is_volatile, this_is_valid);
-  }
-
  private:
   static void VerifyObject(const Object* obj) ALWAYS_INLINE;
   // Verify the type correctness of stores to fields.
diff --git a/runtime/mirror/stack_trace_element.cc b/runtime/mirror/stack_trace_element.cc
index 32a50fe..a7ebe07 100644
--- a/runtime/mirror/stack_trace_element.cc
+++ b/runtime/mirror/stack_trace_element.cc
@@ -58,5 +58,12 @@
   return trace;
 }
 
+void StackTraceElement::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (java_lang_StackTraceElement_ != nullptr) {
+    java_lang_StackTraceElement_ = down_cast<Class*>(visitor(java_lang_StackTraceElement_, arg));
+  }
+}
+
+
 }  // namespace mirror
 }  // namespace art
diff --git a/runtime/mirror/stack_trace_element.h b/runtime/mirror/stack_trace_element.h
index 2af5128..d1be4dc 100644
--- a/runtime/mirror/stack_trace_element.h
+++ b/runtime/mirror/stack_trace_element.h
@@ -57,8 +57,9 @@
       SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
   static void SetClass(Class* java_lang_StackTraceElement);
-
   static void ResetClass();
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
  private:
   // Field order required by test "ValidateFieldOrderOfJavaCppUnionClasses".
diff --git a/runtime/mirror/string.cc b/runtime/mirror/string.cc
index b372fe7..d6e509d 100644
--- a/runtime/mirror/string.cc
+++ b/runtime/mirror/string.cc
@@ -122,7 +122,7 @@
                                const uint16_t* utf16_data_in,
                                int32_t hash_code) {
   CHECK(utf16_data_in != NULL || utf16_length == 0);
-  String* string = Alloc(self, GetJavaLangString(), utf16_length);
+  String* string = Alloc(self, utf16_length);
   if (UNLIKELY(string == nullptr)) {
     return nullptr;
   }
@@ -152,7 +152,7 @@
 
 String* String::AllocFromModifiedUtf8(Thread* self, int32_t utf16_length,
                                       const char* utf8_data_in) {
-  String* string = Alloc(self, GetJavaLangString(), utf16_length);
+  String* string = Alloc(self, utf16_length);
   if (UNLIKELY(string == nullptr)) {
     return nullptr;
   }
@@ -163,21 +163,20 @@
   return string;
 }
 
-String* String::Alloc(Thread* self, Class* java_lang_String, int32_t utf16_length) {
-  CharArray* array = CharArray::Alloc(self, utf16_length);
-  if (UNLIKELY(array == nullptr)) {
+String* String::Alloc(Thread* self, int32_t utf16_length) {
+  SirtRef<CharArray> array(self, CharArray::Alloc(self, utf16_length));
+  if (UNLIKELY(array.get() == nullptr)) {
     return nullptr;
   }
-  return Alloc(self, java_lang_String, array);
+  return Alloc(self, array);
 }
 
-String* String::Alloc(Thread* self, Class* java_lang_String, CharArray* array) {
+String* String::Alloc(Thread* self, const SirtRef<CharArray>& array) {
   // Hold reference in case AllocObject causes GC.
-  SirtRef<CharArray> array_ref(self, array);
-  String* string = down_cast<String*>(java_lang_String->AllocObject(self));
+  String* string = down_cast<String*>(GetJavaLangString()->AllocObject(self));
   if (LIKELY(string != nullptr)) {
-    string->SetArray(array_ref.get());
-    string->SetCount(array_ref->GetLength());
+    string->SetArray(array.get());
+    string->SetCount(array->GetLength());
   }
   return string;
 }
@@ -287,5 +286,11 @@
   return countDiff;
 }
 
+void String::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (java_lang_String_ != nullptr) {
+    java_lang_String_ = down_cast<Class*>(visitor(java_lang_String_, arg));
+  }
+}
+
 }  // namespace mirror
 }  // namespace art
diff --git a/runtime/mirror/string.h b/runtime/mirror/string.h
index 7520c4d..4bbcb9c 100644
--- a/runtime/mirror/string.h
+++ b/runtime/mirror/string.h
@@ -19,6 +19,7 @@
 
 #include "class.h"
 #include "gtest/gtest.h"
+#include "root_visitor.h"
 
 namespace art {
 
@@ -77,12 +78,6 @@
                                        const char* utf8_data_in)
       SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
-  static String* Alloc(Thread* self, Class* java_lang_String, int32_t utf16_length)
-      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
-
-  static String* Alloc(Thread* self, Class* java_lang_String, CharArray* array)
-      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
-
   bool Equals(const char* modified_utf8) const
       SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
@@ -114,6 +109,8 @@
 
   static void SetClass(Class* java_lang_String);
   static void ResetClass();
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
  private:
   void SetHashCode(int32_t new_hash_code) {
@@ -132,6 +129,12 @@
     SetField32(OFFSET_OF_OBJECT_MEMBER(String, offset_), new_offset, false);
   }
 
+  static String* Alloc(Thread* self, int32_t utf16_length)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
+
+  static String* Alloc(Thread* self, const SirtRef<CharArray>& array)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
+
   void SetArray(CharArray* new_array) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
   // Field order required by test "ValidateFieldOrderOfJavaCppUnionClasses".
diff --git a/runtime/mirror/throwable.cc b/runtime/mirror/throwable.cc
index 961f6de..b55db72 100644
--- a/runtime/mirror/throwable.cc
+++ b/runtime/mirror/throwable.cc
@@ -93,5 +93,11 @@
   java_lang_Throwable_ = NULL;
 }
 
+void Throwable::VisitRoots(RootVisitor* visitor, void* arg) {
+  if (java_lang_Throwable_ != nullptr) {
+    java_lang_Throwable_ = down_cast<Class*>(visitor(java_lang_Throwable_, arg));
+  }
+}
+
 }  // namespace mirror
 }  // namespace art
diff --git a/runtime/mirror/throwable.h b/runtime/mirror/throwable.h
index 27f6e12..5a90599 100644
--- a/runtime/mirror/throwable.h
+++ b/runtime/mirror/throwable.h
@@ -18,6 +18,7 @@
 #define ART_RUNTIME_MIRROR_THROWABLE_H_
 
 #include "object.h"
+#include "root_visitor.h"
 #include "string.h"
 
 namespace art {
@@ -50,6 +51,8 @@
 
   static void SetClass(Class* java_lang_Throwable);
   static void ResetClass();
+  static void VisitRoots(RootVisitor* visitor, void* arg)
+      SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
 
  private:
   Object* GetStackState() const {