src/share/vm/runtime/deoptimization.cpp
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File hotspot Sdiff src/share/vm/runtime

src/share/vm/runtime/deoptimization.cpp

Print this page
rev 6086 : 8032410: compiler/uncommontrap/TestStackBangRbp.java times out on Solaris-Sparc V9
Summary: make compiled code bang the stack by the worst case size of the interpreter frame at deoptimization points.
Reviewed-by:


 403   //
 404   // frame_sizes/frame_pcs[0] oldest frame (int or c2i)
 405   // frame_sizes/frame_pcs[1] next oldest frame (int)
 406   // frame_sizes/frame_pcs[n] youngest frame (int)
 407   //
 408   // Now a pc in frame_pcs is actually the return address to the frame's caller (a frame
 409   // owns the space for the return address to it's caller).  Confusing ain't it.
 410   //
 411   // The vframe array can address vframes with indices running from
 412   // 0.._frames-1. Index  0 is the youngest frame and _frame - 1 is the oldest (root) frame.
 413   // When we create the skeletal frames we need the oldest frame to be in the zero slot
 414   // in the frame_sizes/frame_pcs so the assembly code can do a trivial walk.
 415   // so things look a little strange in this loop.
 416   //
 417   int callee_parameters = 0;
 418   int callee_locals = 0;
 419   for (int index = 0; index < array->frames(); index++ ) {
 420     // frame[number_of_frames - 1 ] = on_stack_size(youngest)
 421     // frame[number_of_frames - 2 ] = on_stack_size(sender(youngest))
 422     // frame[number_of_frames - 3 ] = on_stack_size(sender(sender(youngest)))
 423     int caller_parms = callee_parameters;
 424     if ((index == array->frames() - 1) && caller_was_method_handle) {
 425       caller_parms = 0;
 426     }
 427     frame_sizes[number_of_frames - 1 - index] = BytesPerWord * array->element(index)->on_stack_size(caller_parms,
 428                                                                                                     callee_parameters,
 429                                                                                                     callee_locals,
 430                                                                                                     index == 0,
 431                                                                                                     index == array->frames() - 1,
 432                                                                                                     popframe_extra_args);
 433     // This pc doesn't have to be perfect just good enough to identify the frame
 434     // as interpreted so the skeleton frame will be walkable
 435     // The correct pc will be set when the skeleton frame is completely filled out
 436     // The final pc we store in the loop is wrong and will be overwritten below
 437     frame_pcs[number_of_frames - 1 - index ] = Interpreter::deopt_entry(vtos, 0) - frame::pc_return_offset;
 438 
 439     callee_parameters = array->element(index)->method()->size_of_parameters();
 440     callee_locals = array->element(index)->method()->max_locals();
 441     popframe_extra_args = 0;
 442   }
 443 
 444   // Compute whether the root vframe returns a float or double value.
 445   BasicType return_type;
 446   {
 447     HandleMark hm;
 448     methodHandle method(thread, array->element(0)->method());
 449     Bytecode_invoke invoke = Bytecode_invoke_check(method, array->element(0)->bci());
 450     return_type = invoke.is_valid() ? invoke.result_type() : T_ILLEGAL;




 403   //
 404   // frame_sizes/frame_pcs[0] oldest frame (int or c2i)
 405   // frame_sizes/frame_pcs[1] next oldest frame (int)
 406   // frame_sizes/frame_pcs[n] youngest frame (int)
 407   //
 408   // Now a pc in frame_pcs is actually the return address to the frame's caller (a frame
 409   // owns the space for the return address to it's caller).  Confusing ain't it.
 410   //
 411   // The vframe array can address vframes with indices running from
 412   // 0.._frames-1. Index  0 is the youngest frame and _frame - 1 is the oldest (root) frame.
 413   // When we create the skeletal frames we need the oldest frame to be in the zero slot
 414   // in the frame_sizes/frame_pcs so the assembly code can do a trivial walk.
 415   // so things look a little strange in this loop.
 416   //
 417   int callee_parameters = 0;
 418   int callee_locals = 0;
 419   for (int index = 0; index < array->frames(); index++ ) {
 420     // frame[number_of_frames - 1 ] = on_stack_size(youngest)
 421     // frame[number_of_frames - 2 ] = on_stack_size(sender(youngest))
 422     // frame[number_of_frames - 3 ] = on_stack_size(sender(sender(youngest)))
 423     frame_sizes[number_of_frames - 1 - index] = BytesPerWord * array->element(index)->on_stack_size(callee_parameters,





 424                                                                                                     callee_locals,

 425                                                                                                     index == array->frames() - 1,
 426                                                                                                     popframe_extra_args);
 427     // This pc doesn't have to be perfect just good enough to identify the frame
 428     // as interpreted so the skeleton frame will be walkable
 429     // The correct pc will be set when the skeleton frame is completely filled out
 430     // The final pc we store in the loop is wrong and will be overwritten below
 431     frame_pcs[number_of_frames - 1 - index ] = Interpreter::deopt_entry(vtos, 0) - frame::pc_return_offset;
 432 
 433     callee_parameters = array->element(index)->method()->size_of_parameters();
 434     callee_locals = array->element(index)->method()->max_locals();
 435     popframe_extra_args = 0;
 436   }
 437 
 438   // Compute whether the root vframe returns a float or double value.
 439   BasicType return_type;
 440   {
 441     HandleMark hm;
 442     methodHandle method(thread, array->element(0)->method());
 443     Bytecode_invoke invoke = Bytecode_invoke_check(method, array->element(0)->bci());
 444     return_type = invoke.is_valid() ? invoke.result_type() : T_ILLEGAL;


src/share/vm/runtime/deoptimization.cpp
Index Unified diffs Context diffs Sdiffs Patch New Old Previous File Next File