Merge changes I240f8bb7,I27defaa7,Ib82d64cc

* changes:
  ART: Do not DCHECK in verifier when already aborting
  ART: Add debug exception check to JIT
  ART: Extend DumpRecursiveAbort
diff --git a/runtime/jit/jit.cc b/runtime/jit/jit.cc
index 803e9d5..dac2e60 100644
--- a/runtime/jit/jit.cc
+++ b/runtime/jit/jit.cc
@@ -274,6 +274,15 @@
               << ArtMethod::PrettyMethod(method_to_compile)
               << " osr=" << std::boolalpha << osr;
   }
+  if (kIsDebugBuild) {
+    if (self->IsExceptionPending()) {
+      mirror::Throwable* exception = self->GetException();
+      LOG(FATAL) << "No pending exception expected after compiling "
+                 << ArtMethod::PrettyMethod(method)
+                 << ": "
+                 << exception->Dump();
+    }
+  }
   return success;
 }
 
diff --git a/runtime/runtime.cc b/runtime/runtime.cc
index 771ac27..1490f05 100644
--- a/runtime/runtime.cc
+++ b/runtime/runtime.cc
@@ -372,9 +372,7 @@
   void Dump(std::ostream& os) const {
     if (gAborting > 1) {
       os << "Runtime aborting --- recursively, so no thread-specific detail!\n";
-      if (gAborting == 2) {
-        DumpRecursiveAbort(os);
-      }
+      DumpRecursiveAbort(os);
       return;
     }
     gAborting++;
@@ -434,8 +432,17 @@
 
   // For recursive aborts.
   void DumpRecursiveAbort(std::ostream& os) const NO_THREAD_SAFETY_ANALYSIS {
-    // The only thing we'll attempt is dumping the native stack of the current thread.
-    DumpNativeStack(os, GetTid());
+    // The only thing we'll attempt is dumping the native stack of the current thread. We will only
+    // try this if we haven't exceeded an arbitrary amount of recursions, to recover and actually
+    // die.
+    // Note: as we're using a global counter for the recursive abort detection, there is a potential
+    //       race here and it is not OK to just print when the counter is "2" (one from
+    //       Runtime::Abort(), one from previous Dump() call). Use a number that seems large enough.
+    static constexpr size_t kOnlyPrintWhenRecursionLessThan = 100u;
+    if (gAborting < kOnlyPrintWhenRecursionLessThan) {
+      gAborting++;
+      DumpNativeStack(os, GetTid());
+    }
   }
 };
 
diff --git a/runtime/verifier/method_verifier.cc b/runtime/verifier/method_verifier.cc
index d9e3ea7..ed24611 100644
--- a/runtime/verifier/method_verifier.cc
+++ b/runtime/verifier/method_verifier.cc
@@ -100,8 +100,18 @@
 ALWAYS_INLINE static inline bool FailOrAbort(MethodVerifier* verifier, bool condition,
                                              const char* error_msg, uint32_t work_insn_idx) {
   if (kIsDebugBuild) {
-    // In a debug build, abort if the error condition is wrong.
-    DCHECK(condition) << error_msg << work_insn_idx;
+    // In a debug build, abort if the error condition is wrong. Only warn if
+    // we are already aborting (as this verification is likely run to print
+    // lock information).
+    if (LIKELY(gAborting == 0)) {
+      DCHECK(condition) << error_msg << work_insn_idx;
+    } else {
+      if (!condition) {
+        LOG(ERROR) << error_msg << work_insn_idx;
+        verifier->Fail(VERIFY_ERROR_BAD_CLASS_HARD) << error_msg << work_insn_idx;
+        return true;
+      }
+    }
   } else {
     // In a non-debug build, just fail the class.
     if (!condition) {