RFR (S): 8146246: JVMCICompiler::abort_on_pending_exception: assert(!thread->owns_locks()) failed: must release all locks when leaving VM

Christian Thalinger christian.thalinger at oracle.com
Wed Jan 6 19:19:35 UTC 2016


https://bugs.openjdk.java.net/browse/JDK-8146246

The problem is that https://bugs.openjdk.java.net/browse/JDK-8145435 introduced ttyLocker to synchronize the exception output but java_lang_Throwable::print_stack_trace can call out to Java to get the cause.

There are two solutions:

1) Remove ttyLocker and deal with some possible scrambling in the rare case of an exception:

diff -r df8d635f2296 -r e87e187552fb src/share/vm/jvmci/jvmciCompiler.cpp
--- a/src/share/vm/jvmci/jvmciCompiler.cpp	Tue Dec 29 11:24:01 2015 -0800
+++ b/src/share/vm/jvmci/jvmciCompiler.cpp	Thu Dec 31 09:20:16 2015 -0800
@@ -162,10 +162,7 @@ void JVMCICompiler::compile_method(const
     Handle exception(THREAD, PENDING_EXCEPTION);
     CLEAR_PENDING_EXCEPTION;
 
-    {
-      ttyLocker ttyl;
-      java_lang_Throwable::print_stack_trace(exception, tty);
-    }
+    java_lang_Throwable::print_stack_trace(exception, tty);
 
     // Something went wrong so disable compilation at this level
     method->set_not_compilable(CompLevel_full_optimization);
@@ -181,11 +178,8 @@ void JVMCICompiler::abort_on_pending_exc
   Thread* THREAD = Thread::current();
   CLEAR_PENDING_EXCEPTION;
 
-  {
-    ttyLocker ttyl;
-    tty->print_raw_cr(message);
-    java_lang_Throwable::print_stack_trace(exception, tty);
-  }
+  tty->print_raw_cr(message);
+  java_lang_Throwable::print_stack_trace(exception, tty);
 
   // Give other aborting threads to also print their stack traces.
   // This can be very useful when debugging class initialization
diff -r df8d635f2296 -r e87e187552fb src/share/vm/runtime/java.cpp
--- a/src/share/vm/runtime/java.cpp	Tue Dec 29 11:24:01 2015 -0800
+++ b/src/share/vm/runtime/java.cpp	Thu Dec 31 09:20:16 2015 -0800
@@ -432,7 +432,6 @@ void before_exit(JavaThread* thread) {
   if (HAS_PENDING_EXCEPTION) {
     Handle exception(THREAD, PENDING_EXCEPTION);
     CLEAR_PENDING_EXCEPTION;
-    ttyLocker ttyl;
     java_lang_Throwable::print_stack_trace(exception, tty);
   }
 #endif

or

2) Call out to Java and let the Java code do the printing:

diff -r 0fcfe4b07f7e src/share/vm/classfile/javaClasses.cpp
--- a/src/share/vm/classfile/javaClasses.cpp	Tue Dec 29 18:30:51 2015 +0100
+++ b/src/share/vm/classfile/javaClasses.cpp	Wed Jan 06 09:12:00 2016 -1000
@@ -1784,6 +1784,20 @@ void java_lang_Throwable::print_stack_tr
   }
 }
 
+/**
+ * Print the throwable stack trace by calling the Java method java.lang.Throwable.printStackTrace().
+ */
+void java_lang_Throwable::java_printStackTrace(Handle throwable, TRAPS) {
+  assert(throwable->is_a(SystemDictionary::Throwable_klass()), "Throwable instance expected");
+  JavaValue result(T_VOID);
+  JavaCalls::call_virtual(&result,
+                          throwable,
+                          KlassHandle(THREAD, SystemDictionary::Throwable_klass()),
+                          vmSymbols::printStackTrace_name(),
+                          vmSymbols::void_method_signature(),
+                          THREAD);
+}
+
 void java_lang_Throwable::fill_in_stack_trace(Handle throwable, const methodHandle& method, TRAPS) {
   if (!StackTraceInThrowable) return;
   ResourceMark rm(THREAD);
diff -r 0fcfe4b07f7e src/share/vm/classfile/javaClasses.hpp
--- a/src/share/vm/classfile/javaClasses.hpp	Tue Dec 29 18:30:51 2015 +0100
+++ b/src/share/vm/classfile/javaClasses.hpp	Wed Jan 06 09:12:00 2016 -1000
@@ -554,6 +554,7 @@ class java_lang_Throwable: AllStatic {
   // Printing
   static void print(Handle throwable, outputStream* st);
   static void print_stack_trace(Handle throwable, outputStream* st);
+  static void java_printStackTrace(Handle throwable, TRAPS);
   // Debugging
   friend class JavaClasses;
 };
diff -r 0fcfe4b07f7e src/share/vm/jvmci/jvmciCompiler.cpp
--- a/src/share/vm/jvmci/jvmciCompiler.cpp	Tue Dec 29 18:30:51 2015 +0100
+++ b/src/share/vm/jvmci/jvmciCompiler.cpp	Wed Jan 06 09:12:00 2016 -1000
@@ -162,10 +162,7 @@ void JVMCICompiler::compile_method(const
     Handle exception(THREAD, PENDING_EXCEPTION);
     CLEAR_PENDING_EXCEPTION;
 
-    {
-      ttyLocker ttyl;
-      java_lang_Throwable::print_stack_trace(exception, tty);
-    }
+    java_lang_Throwable::java_printStackTrace(exception, THREAD);
 
     // Something went wrong so disable compilation at this level
     method->set_not_compilable(CompLevel_full_optimization);
@@ -181,11 +178,7 @@ void JVMCICompiler::abort_on_pending_exc
   Thread* THREAD = Thread::current();
   CLEAR_PENDING_EXCEPTION;
 
-  {
-    ttyLocker ttyl;
-    tty->print_raw_cr(message);
-    java_lang_Throwable::print_stack_trace(exception, tty);
-  }
+  java_lang_Throwable::java_printStackTrace(exception, THREAD);
 
   // Give other aborting threads to also print their stack traces.
   // This can be very useful when debugging class initialization
diff -r 0fcfe4b07f7e src/share/vm/runtime/java.cpp
--- a/src/share/vm/runtime/java.cpp	Tue Dec 29 18:30:51 2015 +0100
+++ b/src/share/vm/runtime/java.cpp	Wed Jan 06 09:12:00 2016 -1000
@@ -433,7 +433,7 @@ void before_exit(JavaThread* thread) {
     Handle exception(THREAD, PENDING_EXCEPTION);
     CLEAR_PENDING_EXCEPTION;
     ttyLocker ttyl;
-    java_lang_Throwable::print_stack_trace(exception, tty);
+    java_lang_Throwable::java_printStackTrace(exception, THREAD);
   }
 #endif



More information about the hotspot-compiler-dev mailing list