diff src/cpu/sparc/vm/templateInterpreter_sparc.cpp @ 4743:dca455dea3a7

7116216: StackOverflow GC crash Summary: GC crash for explicit stack overflow checks after a C2I transition. Reviewed-by: coleenp, never Contributed-by: yang02.wang@sap.com, bertrand.delsart@oracle.com
author bdelsart
date Tue, 20 Dec 2011 12:33:05 +0100
parents 3d42f82cd811
children 22cee0ee8927
line wrap: on
line diff
--- a/src/cpu/sparc/vm/templateInterpreter_sparc.cpp	Fri Dec 16 17:33:08 2011 -0500
+++ b/src/cpu/sparc/vm/templateInterpreter_sparc.cpp	Tue Dec 20 12:33:05 2011 +0100
@@ -396,7 +396,6 @@
                                                          Register Rscratch,
                                                          Register Rscratch2) {
   const int page_size = os::vm_page_size();
-  Address saved_exception_pc(G2_thread, JavaThread::saved_exception_pc_offset());
   Label after_frame_check;
 
   assert_different_registers(Rframe_size, Rscratch, Rscratch2);
@@ -436,11 +435,19 @@
   // the bottom of the stack
   __ cmp_and_brx_short(SP, Rscratch, Assembler::greater, Assembler::pt, after_frame_check);
 
-  // Save the return address as the exception pc
-  __ st_ptr(O7, saved_exception_pc);
+  // the stack will overflow, throw an exception
+
+  // Note that SP is restored to sender's sp (in the delay slot). This
+  // is necessary if the sender's frame is an extended compiled frame
+  // (see gen_c2i_adapter()) and safer anyway in case of JSR292
+  // adaptations.
 
-  // the stack will overflow, throw an exception
-  __ call_VM(noreg, CAST_FROM_FN_PTR(address, InterpreterRuntime::throw_StackOverflowError));
+  // Note also that the restored frame is not necessarily interpreted.
+  // Use the shared runtime version of the StackOverflowError.
+  assert(StubRoutines::throw_StackOverflowError_entry() != NULL, "stub not yet generated");
+  AddressLiteral stub(StubRoutines::throw_StackOverflowError_entry());
+  __ jump_to(stub, Rscratch);
+  __ delayed()->mov(O5_savedSP, SP);
 
   // if you get to here, then there is enough stack space
   __ bind( after_frame_check );