src/cpu/mips/vm/c1_Runtime1_mips.cpp

changeset 8865
ffcdff41a92f
parent 6880
52ea28d233d2
child 9132
0f025dcc49cc
     1.1 --- a/src/cpu/mips/vm/c1_Runtime1_mips.cpp	Sat Jan 06 16:30:58 2018 +0800
     1.2 +++ b/src/cpu/mips/vm/c1_Runtime1_mips.cpp	Thu May 24 19:49:50 2018 +0800
     1.3 @@ -60,9 +60,7 @@
     1.4  
     1.5  
     1.6    // push java thread (becomes first argument of C function)
     1.7 -#ifndef OPT_THREAD
     1.8    get_thread(thread);
     1.9 -#endif
    1.10    move(A0, thread);
    1.11  
    1.12    set_last_Java_frame(thread, NOREG, FP, NULL);
    1.13 @@ -139,8 +137,7 @@
    1.14      } else if (_stub_id == Runtime1::forward_exception_id) {
    1.15        should_not_reach_here();
    1.16      } else {
    1.17 -      jmp(Runtime1::entry_for(Runtime1::forward_exception_id),
    1.18 -          relocInfo::runtime_call_type);
    1.19 +      jmp(Runtime1::entry_for(Runtime1::forward_exception_id), relocInfo::runtime_call_type);
    1.20        delayed()->nop();
    1.21      }
    1.22      bind(L);
    1.23 @@ -327,9 +324,10 @@
    1.24  static OopMap* generate_oop_map(StubAssembler* sasm, int num_rt_args,
    1.25                                  bool save_fpu_registers = true, bool describe_fpu_registers = false) {
    1.26  
    1.27 -  /* Jin: num_rt_args is caculated by 8 bytes. */
    1.28 -  int frame_size_in_slots = reg_save_frame_size + num_rt_args * wordSize / SLOT_PER_WORD;   // args + thread
    1.29 -  sasm->set_frame_size(frame_size_in_slots / SLOT_PER_WORD);
    1.30 +  LP64_ONLY(num_rt_args = 0);
    1.31 +  LP64_ONLY(assert((reg_save_frame_size * VMRegImpl::stack_slot_size) % 16 == 0, "must be 16 byte aligned");)
    1.32 +  int frame_size_in_slots = reg_save_frame_size + num_rt_args * wordSize / VMRegImpl::slots_per_word;   // args + thread
    1.33 +  sasm->set_frame_size(frame_size_in_slots / VMRegImpl::slots_per_word);
    1.34  
    1.35    // record saved value locations in an OopMap
    1.36    // locations are offsets from sp after runtime call; num_rt_args is number of arguments
    1.37 @@ -407,9 +405,8 @@
    1.38  }
    1.39  
    1.40  //FIXME, Is it enough to save this registers  by yyq
    1.41 -static OopMap* save_live_registers(StubAssembler* sasm,
    1.42 -                                   int num_rt_args,
    1.43 -                       bool save_fpu_registers = true,
    1.44 +static OopMap* save_live_registers(StubAssembler* sasm, int num_rt_args,
    1.45 +                                   bool save_fpu_registers = true,
    1.46                                     bool describe_fpu_registers = false) {
    1.47    //const int reg_save_frame_size = return_off + 1 + num_rt_args;
    1.48    __ block_comment("save_live_registers");
    1.49 @@ -607,57 +604,59 @@
    1.50  
    1.51  //FIXME I do not know which reigster to use.should use T3 as real_return_addr @jerome
    1.52  OopMapSet* Runtime1::generate_handle_exception(StubID id, StubAssembler *sasm) {
    1.53 -        __ block_comment("generate_handle_exception");
    1.54 - // incoming parameters
    1.55 +  __ block_comment("generate_handle_exception");
    1.56 +
    1.57 +  // incoming parameters
    1.58    const Register exception_oop = V0;
    1.59    const Register exception_pc = V1;
    1.60    // other registers used in this stub
    1.61 -//  const Register real_return_addr = T3;
    1.62 -  const Register thread = T8;
    1.63 +  // const Register real_return_addr = T3;
    1.64 +  const Register thread = TREG;
    1.65 +#ifndef OPT_THREAD
    1.66 +  __ get_thread(thread);
    1.67 +#endif
    1.68    // Save registers, if required.
    1.69 -   OopMapSet* oop_maps = new OopMapSet();
    1.70 -   OopMap* oop_map = NULL;
    1.71 -   switch (id) {
    1.72 -   case forward_exception_id:
    1.73 -     // We're handling an exception in the context of a compiled frame.
    1.74 -     // The registers have been saved in the standard places.  Perform
    1.75 -     // an exception lookup in the caller and dispatch to the handler
    1.76 -     // if found.  Otherwise unwind and dispatch to the callers
    1.77 -     // exception handler.
    1.78 -     oop_map = generate_oop_map(sasm, 1 /*thread*/);
    1.79 +  OopMapSet* oop_maps = new OopMapSet();
    1.80 +  OopMap* oop_map = NULL;
    1.81 +  switch (id) {
    1.82 +  case forward_exception_id:
    1.83 +    // We're handling an exception in the context of a compiled frame.
    1.84 +    // The registers have been saved in the standard places.  Perform
    1.85 +    // an exception lookup in the caller and dispatch to the handler
    1.86 +    // if found.  Otherwise unwind and dispatch to the callers
    1.87 +    // exception handler.
    1.88 +    oop_map = generate_oop_map(sasm, 1 /*thread*/);
    1.89  
    1.90 -     // load and clear pending exception oop into RAX
    1.91 -     __ ld(exception_oop, Address(thread, Thread::pending_exception_offset()));
    1.92 -     __ sw(R0,Address(thread, Thread::pending_exception_offset()));
    1.93 +    // load and clear pending exception oop into RAX
    1.94 +    __ ld_ptr(exception_oop, Address(thread, Thread::pending_exception_offset()));
    1.95 +    __ st_ptr(R0, Address(thread, Thread::pending_exception_offset()));
    1.96  
    1.97 -     // load issuing PC (the return address for this stub) into rdx
    1.98 -     __ ld(exception_pc, Address(FP, 1*BytesPerWord));
    1.99 +    // load issuing PC (the return address for this stub) into rdx
   1.100 +    __ ld_ptr(exception_pc, Address(FP, 1*BytesPerWord));
   1.101  
   1.102 -     // make sure that the vm_results are cleared (may be unnecessary)
   1.103 -     __ sw(R0,Address(thread, JavaThread::vm_result_offset()));
   1.104 -     __ sw(R0,Address(thread, JavaThread::vm_result_2_offset()));
   1.105 -     break;
   1.106 -   case handle_exception_nofpu_id:
   1.107 -   case handle_exception_id:
   1.108 -     // At this point all registers MAY be live.
   1.109 -     oop_map = save_live_registers(sasm, 1 /*thread*/, id == handle_exception_nofpu_id);
   1.110 -     break;
   1.111 -   case handle_exception_from_callee_id: {
   1.112 -     // At this point all registers except exception oop (RAX) and
   1.113 -     // exception pc (RDX) are dead.
   1.114 -     const int frame_size = 2 /*BP, return address*/ NOT_LP64(+ 1 /*thread*/) WIN64_ONLY(+ frame::arg_reg_save_area_by     tes / BytesPerWord);
   1.115 -     oop_map = new OopMap(frame_size * VMRegImpl::slots_per_word, 0);
   1.116 -     sasm->set_frame_size(frame_size);
   1.117 -     WIN64_ONLY(__ subq(rsp, frame::arg_reg_save_area_bytes));
   1.118 -     break;
   1.119 -   }
   1.120 -   default:  ShouldNotReachHere();
   1.121 -   }
   1.122 +    // make sure that the vm_results are cleared (may be unnecessary)
   1.123 +    __ st_ptr(R0, Address(thread, JavaThread::vm_result_offset()));
   1.124 +    __ st_ptr(R0, Address(thread, JavaThread::vm_result_2_offset()));
   1.125 +    break;
   1.126 +  case handle_exception_nofpu_id:
   1.127 +  case handle_exception_id:
   1.128 +    // At this point all registers MAY be live.
   1.129 +    oop_map = save_live_registers(sasm, 1 /*thread*/, id != handle_exception_nofpu_id);
   1.130 +    break;
   1.131 +  case handle_exception_from_callee_id: {
   1.132 +    // At this point all registers except exception oop (RAX) and
   1.133 +    // exception pc (RDX) are dead.
   1.134 +    const int frame_size = 2 /*BP, return address*/ NOT_LP64(+ 1 /*thread*/);
   1.135 +    oop_map = new OopMap(frame_size * VMRegImpl::slots_per_word, 0);
   1.136 +    sasm->set_frame_size(frame_size);
   1.137 +    break;
   1.138 +  }
   1.139 +  default:  ShouldNotReachHere();
   1.140 +  }
   1.141  
   1.142  #ifdef TIERED
   1.143    // C2 can leave the fpu stack dirty
   1.144    __ empty_FPU_stack();
   1.145 -  //}
   1.146  #endif // TIERED
   1.147  
   1.148    // verify that only V0 and V1 is valid at this time
   1.149 @@ -689,16 +688,12 @@
   1.150    __ st_ptr(exception_oop, Address(thread, in_bytes(JavaThread::exception_oop_offset())));
   1.151    __ st_ptr(exception_pc, Address(thread, in_bytes(JavaThread::exception_pc_offset())));
   1.152  
   1.153 -  // save real return address (pc that called this stub)
   1.154 -//  __ ld_ptr(real_return_addr, FP, 1*BytesPerWord);
   1.155 -//  __ st_ptr(real_return_addr, SP, temp_1_off * BytesPerWord / SLOT_PER_WORD);
   1.156 +  // patch throwing pc into return address (has bci & oop map)
   1.157 +  __ st_ptr(exception_pc, Address(FP, 1*BytesPerWord));
   1.158  
   1.159 -  // patch throwing pc into return address (has bci & oop map)
   1.160 -  __ st_ptr(exception_pc, FP, 1*BytesPerWord);
   1.161    // compute the exception handler.
   1.162    // the exception oop and the throwing pc are read from the fields in JavaThread
   1.163 -  int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address,
   1.164 -        exception_handler_for_pc));
   1.165 +  int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, exception_handler_for_pc));
   1.166    oop_maps->add_gc_map(call_offset, oop_map);
   1.167    // V0:  handler address or NULL if no handler exists
   1.168    //      will be the deopt blob if nmethod was deoptimized while we looked up
   1.169 @@ -707,75 +702,38 @@
   1.170    // only V0 is valid at this time, all other registers have been destroyed by the
   1.171    // runtime call
   1.172  
   1.173 -  // Do we have an exception handler in the nmethod?
   1.174 -  /*Label no_handler;
   1.175 -  Label done;
   1.176 -  __ beq(V0, R0, no_handler);
   1.177 -  __ delayed()->nop(); */
   1.178 -  // exception handler found
   1.179    // patch the return address -> the stub will directly return to the exception handler
   1.180 -  __ st_ptr(V0, FP, 1 * BytesPerWord);
   1.181 +  __ st_ptr(V0, Address(FP, 1 * BytesPerWord));
   1.182  
   1.183 -  // restore registers
   1.184 -//  restore_live_registers(sasm, save_fpu_registers);
   1.185 +  switch (id) {
   1.186 +  case forward_exception_id:
   1.187 +  case handle_exception_nofpu_id:
   1.188 +  case handle_exception_id:
   1.189 +    // Restore the registers that were saved at the beginning.
   1.190 +    restore_live_registers(sasm, id != handle_exception_nofpu_id);
   1.191 +    break;
   1.192 +  case handle_exception_from_callee_id:
   1.193 +    // WIN64_ONLY: No need to add frame::arg_reg_save_area_bytes to SP
   1.194 +    // since we do a leave anyway.
   1.195  
   1.196 -  // return to exception handler
   1.197 -//  __ leave();
   1.198 -//  __ jr(RA);
   1.199 -//  __ delayed()->nop();
   1.200 -//  __ bind(no_handler);
   1.201 -  // no exception handler found in this method, so the exception is
   1.202 -  // forwarded to the caller (using the unwind code of the nmethod)
   1.203 -  // there is no need to restore the registers
   1.204 +    // Pop the return address since we are possibly changing SP (restoring from BP).
   1.205 +    __ leave();
   1.206 +    // Restore SP from BP if the exception PC is a method handle call site.
   1.207 +    {
   1.208 +      Label done;
   1.209 +      __ ld(AT, Address(thread, JavaThread::is_method_handle_return_offset()));
   1.210 +      __ beq(AT, R0, done);
   1.211 +      __ delayed()->nop();
   1.212 +      __ bind(done);
   1.213 +    }
   1.214 +    __ jr(RA);  // jump to exception handler
   1.215 +    __ delayed()->nop();
   1.216 +    break;
   1.217 +   default:  ShouldNotReachHere();
   1.218 +  }
   1.219  
   1.220 -  // restore the real return address that was saved before the RT-call
   1.221 -//  __ ld_ptr(real_return_addr, SP, temp_1_off * BytesPerWord / SLOT_PER_WORD);
   1.222 -//  __ st_ptr(real_return_addr, FP, 1 * BytesPerWord);
   1.223 -  // load address of JavaThread object for thread-local data
   1.224 -//  __ get_thread(thread);
   1.225 -  // restore exception oop into eax (convention for unwind code)
   1.226 -//  __ ld_ptr(exception_oop, thread, in_bytes(JavaThread::exception_oop_offset()));
   1.227 -
   1.228 -  // clear exception fields in JavaThread because they are no longer needed
   1.229 -  // (fields must be cleared because they are processed by GC otherwise)
   1.230 -//  __ st_ptr(R0, thread, in_bytes(JavaThread::exception_oop_offset()));
   1.231 -//  __ st_ptr(R0,thread, in_bytes(JavaThread::exception_pc_offset()));
   1.232 -  // pop the stub frame off
   1.233 -//  __ leave();
   1.234 -//  generate_unwind_exception(sasm);
   1.235 -//  __ stop("should not reach here");
   1.236 -//}
   1.237 -   switch (id) {
   1.238 -   case forward_exception_id:
   1.239 -   case handle_exception_nofpu_id:
   1.240 -   case handle_exception_id:
   1.241 -     // Restore the registers that were saved at the beginning.
   1.242 -     restore_live_registers(sasm, id == handle_exception_nofpu_id);
   1.243 -     break;
   1.244 -   case handle_exception_from_callee_id:
   1.245 -     // WIN64_ONLY: No need to add frame::arg_reg_save_area_bytes to SP
   1.246 -     // since we do a leave anyway.
   1.247 -
   1.248 -     // Pop the return address since we are possibly changing SP (restoring from BP).
   1.249 -     __ leave();
   1.250 -     // Restore SP from BP if the exception PC is a method handle call site.
   1.251 -     NOT_LP64(__ get_thread(thread);)
   1.252 -     /*__ ld(AT, Address(thread, JavaThread::is_method_handle_return_offset()));
   1.253 -     __ beq(AT, R0, done);
   1.254 -     __ move(SP, rbp_mh_SP_save);
   1.255 -     __ bind(done);
   1.256 -     __ jr(RA);  // jump to exception handler
   1.257 -     __ delayed()->nop();*/
   1.258 -// 759     __ cmpl(Address(thread, JavaThread::is_method_handle_return_offset()), 0);
   1.259 -// 760     __ cmovptr(Assembler::notEqual, rsp, rbp_mh_SP_save);
   1.260 -// 761     __ jmp(rcx);  // jump to exception handler
   1.261 -
   1.262 -     break;
   1.263 -   default:  ShouldNotReachHere();
   1.264 -   }
   1.265 -
   1.266 -   return oop_maps;
   1.267 - }
   1.268 +  return oop_maps;
   1.269 +}
   1.270  
   1.271  
   1.272  
   1.273 @@ -784,10 +742,12 @@
   1.274  void Runtime1::generate_unwind_exception(StubAssembler *sasm) {
   1.275    // incoming parameters
   1.276    const Register exception_oop = V0;
   1.277 +  // callee-saved copy of exception_oop during runtime call
   1.278 +  const Register exception_oop_callee_saved = S0;
   1.279    // other registers used in this stub
   1.280    const Register exception_pc = V1;
   1.281    const Register handler_addr = T3;
   1.282 -  const Register thread = T8;
   1.283 +  const Register thread = TREG;
   1.284  
   1.285    // verify that only eax is valid at this time
   1.286    //  __ invalidate_registers(false, true, true, true, true, true);
   1.287 @@ -804,7 +764,7 @@
   1.288  
   1.289    Label pc_empty;
   1.290    __ ld_ptr(AT, thread, in_bytes(JavaThread::exception_pc_offset()));
   1.291 -  __ beq(AT,R0, pc_empty);
   1.292 +  __ beq(AT, R0, pc_empty);
   1.293    __ delayed()->nop();
   1.294    __ stop("exception pc must be empty");
   1.295    __ bind(pc_empty);
   1.296 @@ -812,35 +772,37 @@
   1.297    // clear the FPU stack in case any FPU results are left behind
   1.298    __ empty_FPU_stack();
   1.299  
   1.300 -  // leave activation of nmethod
   1.301 -  __ addi(SP, FP, wordSize);
   1.302 -  __ ld_ptr(FP, SP, - wordSize);
   1.303 +  // save exception_oop in callee-saved register to preserve it during runtime calls
   1.304 +  __ verify_not_null_oop(exception_oop);
   1.305 +  __ move(exception_oop_callee_saved, exception_oop);
   1.306 +
   1.307 +#ifndef OPT_THREAD
   1.308 +  __ get_thread(thread);
   1.309 +#endif
   1.310 +  // Get return address (is on top of stack after leave).
   1.311    // store return address (is on top of stack after leave)
   1.312 +
   1.313    __ ld_ptr(exception_pc, SP, 0);
   1.314 -  __ verify_oop(exception_oop);
   1.315  
   1.316 -  // save exception oop from eax to stack before call
   1.317 -  __ push(exception_oop);
   1.318    // search the exception handler address of the caller (using the return address)
   1.319 -  __ call_VM_leaf(CAST_FROM_FN_PTR(address,
   1.320 -      SharedRuntime::exception_handler_for_return_address), exception_pc);
   1.321 -  // eax: exception handler address of the caller
   1.322 +  __ call_VM_leaf(CAST_FROM_FN_PTR(address, SharedRuntime::exception_handler_for_return_address), thread, exception_pc);
   1.323 +  // V0: exception handler address of the caller
   1.324  
   1.325    // only eax is valid at this time, all other registers have been destroyed by the call
   1.326  
   1.327    // move result of call into correct register
   1.328    __ move(handler_addr, V0);
   1.329 -  // restore exception oop in eax (required convention of exception handler)
   1.330 -  __ super_pop(exception_oop);
   1.331  
   1.332 +  // Restore exception oop to V0 (required convention of exception handler).
   1.333 +  __ move(exception_oop, exception_oop_callee_saved);
   1.334 +
   1.335 +  // verify that there is really a valid exception in V0
   1.336    __ verify_oop(exception_oop);
   1.337  
   1.338    // get throwing pc (= return address).
   1.339 -  // edx has been destroyed by the call, so it must be set again
   1.340 +  // V1 has been destroyed by the call, so it must be set again
   1.341    // the pop is also necessary to simulate the effect of a ret(0)
   1.342    __ super_pop(exception_pc);
   1.343 -  // verify that that there is really a valid exception in eax
   1.344 -  __ verify_not_null_oop(exception_oop);
   1.345  
   1.346    // continue at exception handler (return address removed)
   1.347    // note: do *not* remove arguments when unwinding the
   1.348 @@ -848,9 +810,9 @@
   1.349    //       all arguments on the stack when entering the
   1.350    //       runtime to determine the exception handler
   1.351    //       (GC happens at call site with arguments!)
   1.352 -  // eax: exception oop
   1.353 -  // edx: throwing pc
   1.354 -  // ebx: exception handler
   1.355 +  // V0: exception oop
   1.356 +  // V1: throwing pc
   1.357 +  // T3: exception handler
   1.358    __ jr(handler_addr);
   1.359    __ delayed()->nop();
   1.360  }
   1.361 @@ -867,9 +829,6 @@
   1.362    // Note: This number affects also the RT-Call in generate_handle_exception because
   1.363    //       the oop-map is shared for all calls.
   1.364  
   1.365 -
   1.366 -
   1.367 -
   1.368    DeoptimizationBlob* deopt_blob = SharedRuntime::deopt_blob();
   1.369    assert(deopt_blob != NULL, "deoptimization blob must have been created");
   1.370    // assert(deopt_with_exception_entry_for_patch != NULL,
   1.371 @@ -877,13 +836,9 @@
   1.372  
   1.373    //OopMap* oop_map = save_live_registers(sasm, num_rt_args);
   1.374    OopMap* oop_map = save_live_registers(sasm, 0);
   1.375 -#ifndef OPT_THREAD
   1.376    const Register thread = T8;
   1.377    // push java thread (becomes first argument of C function)
   1.378    __ get_thread(thread);
   1.379 -#else
   1.380 -  const Register thread = TREG;
   1.381 -#endif
   1.382    __ move(A0, thread);
   1.383  
   1.384  
   1.385 @@ -922,9 +877,7 @@
   1.386    OopMapSet*  oop_maps = new OopMapSet();
   1.387    oop_maps->add_gc_map(__ offset(),  oop_map);
   1.388  
   1.389 -#ifndef OPT_THREAD
   1.390    __ get_thread(thread);
   1.391 -#endif
   1.392  
   1.393    __ ld_ptr (SP, thread, in_bytes(JavaThread::last_Java_sp_offset()));
   1.394    __ reset_last_Java_frame(thread, true,true);
   1.395 @@ -938,9 +891,8 @@
   1.396      __ delayed()->nop();
   1.397      // exception pending => remove activation and forward to exception handler
   1.398  
   1.399 -    __ bne(V0,R0, skip);
   1.400 +    __ bne(V0, R0, skip);
   1.401      __ delayed()->nop();
   1.402 -    //      relocInfo::runtime_call_type);
   1.403      __ jmp(Runtime1::entry_for(Runtime1::forward_exception_id),
   1.404          relocInfo::runtime_call_type);
   1.405      __ delayed()->nop();
   1.406 @@ -1039,40 +991,10 @@
   1.407    switch (id) {
   1.408      case forward_exception_id:
   1.409        {
   1.410 -        // we're handling an exception in the context of a compiled
   1.411 -        // frame.  The registers have been saved in the standard
   1.412 -        // places.  Perform an exception lookup in the caller and
   1.413 -        // dispatch to the handler if found.  Otherwise unwind and
   1.414 -        // dispatch to the callers exception handler.
   1.415 -
   1.416 -        const Register exception_oop = V0;
   1.417 -        const Register exception_pc = V1;
   1.418 -#ifndef OPT_THREAD
   1.419 -  const Register thread = T8;
   1.420 -  __ get_thread(thread);
   1.421 -#else
   1.422 -  const Register thread = TREG;
   1.423 -#endif
   1.424 -        // load pending exception oop into eax
   1.425 -        __ ld_ptr(exception_oop, thread, in_bytes(Thread::pending_exception_offset()));
   1.426 -        // clear pending exception
   1.427 -        __ st_ptr(R0, thread, in_bytes(Thread::pending_exception_offset()));
   1.428 -
   1.429 -        // load issuing PC (the return address for this stub) into V1
   1.430 -        __ ld_ptr(exception_pc, FP, 1*BytesPerWord);
   1.431 -
   1.432 -        // make sure that the vm_results are cleared (may be unnecessary)
   1.433 -        __ st_ptr(R0, Address(thread, in_bytes(JavaThread::vm_result_offset())));
   1.434 -        __ st_ptr(R0, Address(thread, in_bytes(JavaThread::vm_result_2_offset())));
   1.435 -
   1.436 -        // verify that that there is really a valid exception in eax
   1.437 -        __ verify_not_null_oop(exception_oop);
   1.438 -
   1.439 -
   1.440 -        oop_maps = new OopMapSet();
   1.441 -        OopMap* oop_map = generate_oop_map(sasm, 0);
   1.442 -        generate_handle_exception(id, sasm);
   1.443 -        __ stop("should not reach here");
   1.444 +        oop_maps = generate_handle_exception(id, sasm);
   1.445 +        __ leave();
   1.446 +        __ jr(RA);
   1.447 +        __ delayed()->nop();
   1.448        }
   1.449        break;
   1.450  
   1.451 @@ -1080,12 +1002,7 @@
   1.452      case fast_new_instance_id:
   1.453      case fast_new_instance_init_check_id:
   1.454        {
   1.455 -        // i use T4 as klass register, V0 as result register. MUST accord with NewInstanceStub::emit_code
   1.456 -#ifndef _LP64
   1.457 -        Register klass = T4; // Incoming
   1.458 -#else
   1.459          Register klass = A4; // Incoming
   1.460 -#endif
   1.461          Register obj   = V0; // Result
   1.462  
   1.463          if (id == new_instance_id) {
   1.464 @@ -1106,7 +1023,7 @@
   1.465            assert_different_registers(klass, obj, obj_size, t1, t2);
   1.466            if (id == fast_new_instance_init_check_id) {
   1.467              // make sure the klass is initialized
   1.468 -            __ lw(AT, klass, in_bytes(InstanceKlass::init_state_offset()));
   1.469 +            __ ld_ptr(AT, Address(klass, in_bytes(InstanceKlass::init_state_offset())));
   1.470              __ move(t1, InstanceKlass::fully_initialized);
   1.471              __ bne(AT, t1, slow_path);
   1.472              __ delayed()->nop();
   1.473 @@ -1180,11 +1097,13 @@
   1.474  #else
   1.475          Register bci = A5;
   1.476  #endif
   1.477 +        Register method = AT;
   1.478          __ enter();
   1.479          OopMap* map = save_live_registers(sasm, 0);
   1.480          // Retrieve bci
   1.481          __ lw(bci, Address(FP, 2*BytesPerWord));// FIXME:wuhui.ebp==??
   1.482 -  int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, counter_overflow), bci);
   1.483 +        __ ld(method, Address(FP, 3*BytesPerWord));
   1.484 +        int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, counter_overflow), bci, method);
   1.485          oop_maps = new OopMapSet();
   1.486          oop_maps->add_gc_map(call_offset, map);
   1.487          restore_live_registers(sasm);
   1.488 @@ -1379,7 +1298,8 @@
   1.489  
   1.490  //  case range_check_failed_id:
   1.491    case throw_range_check_failed_id:
   1.492 -      { StubFrame f(sasm, "range_check_failed", dont_gc_arguments);
   1.493 +      {
   1.494 +        StubFrame f(sasm, "range_check_failed", dont_gc_arguments);
   1.495          oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address,
   1.496                throw_range_check_exception),true);
   1.497        }
   1.498 @@ -1402,42 +1322,40 @@
   1.499        break;
   1.500  
   1.501    case throw_null_pointer_exception_id:
   1.502 -      { StubFrame f(sasm, "throw_null_pointer_exception", dont_gc_arguments);
   1.503 +      {
   1.504 +        StubFrame f(sasm, "throw_null_pointer_exception", dont_gc_arguments);
   1.505          oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address,
   1.506                throw_null_pointer_exception),false);
   1.507        }
   1.508        break;
   1.509  
   1.510 -        case handle_exception_nofpu_id:
   1.511 +  case handle_exception_nofpu_id:
   1.512      save_fpu_registers = false;
   1.513       // fall through
   1.514    case handle_exception_id:
   1.515      {
   1.516 -
   1.517 -
   1.518        StubFrame f(sasm, "handle_exception", dont_gc_arguments);
   1.519 -
   1.520        //OopMap* oop_map = save_live_registers(sasm, 1, save_fpu_registers);
   1.521        oop_maps = generate_handle_exception(id, sasm);
   1.522      }
   1.523      break;
   1.524 -        case handle_exception_from_callee_id:
   1.525 -                {
   1.526 -                        StubFrame f(sasm, "handle_exception_from_callee", dont_gc_arguments);
   1.527 -                        oop_maps = generate_handle_exception(id, sasm);
   1.528 -                }
   1.529 -                break;
   1.530 +  case handle_exception_from_callee_id:
   1.531 +    {
   1.532 +      StubFrame f(sasm, "handle_exception_from_callee", dont_gc_arguments);
   1.533 +      oop_maps = generate_handle_exception(id, sasm);
   1.534 +    }
   1.535 +    break;
   1.536    case unwind_exception_id:
   1.537      {
   1.538        __ set_info("unwind_exception", dont_gc_arguments);
   1.539 -
   1.540        generate_unwind_exception(sasm);
   1.541      }
   1.542      break;
   1.543  
   1.544  
   1.545    case throw_array_store_exception_id:
   1.546 -    { StubFrame f(sasm, "throw_array_store_exception", dont_gc_arguments);
   1.547 +    {
   1.548 +      StubFrame f(sasm, "throw_array_store_exception", dont_gc_arguments);
   1.549        // tos + 0: link
   1.550        //     + 1: return address
   1.551        oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address,
   1.552 @@ -1446,17 +1364,18 @@
   1.553      break;
   1.554  
   1.555    case throw_class_cast_exception_id:
   1.556 -    { StubFrame f(sasm, "throw_class_cast_exception", dont_gc_arguments);
   1.557 +    {
   1.558 +      StubFrame f(sasm, "throw_class_cast_exception", dont_gc_arguments);
   1.559        oop_maps = generate_exception_throw(sasm, CAST_FROM_FN_PTR(address,
   1.560 -            throw_class_cast_exception), V0);
   1.561 +            throw_class_cast_exception), true);
   1.562      }
   1.563      break;
   1.564  
   1.565    case throw_incompatible_class_change_error_id:
   1.566      {
   1.567 -    StubFrame f(sasm, "throw_incompatible_class_cast_exception", dont_gc_arguments);
   1.568 -    oop_maps = generate_exception_throw(sasm,
   1.569 -      CAST_FROM_FN_PTR(address, throw_incompatible_class_change_error), false);
   1.570 +      StubFrame f(sasm, "throw_incompatible_class_cast_exception", dont_gc_arguments);
   1.571 +      oop_maps = generate_exception_throw(sasm,
   1.572 +            CAST_FROM_FN_PTR(address, throw_incompatible_class_change_error), false);
   1.573      }
   1.574      break;
   1.575  
   1.576 @@ -1600,12 +1519,21 @@
   1.577        oop_maps->add_gc_map(call_offset,  map);
   1.578        restore_live_registers(sasm);
   1.579      }*/
   1.580 -        case load_mirror_patching_id:
   1.581 -                {
   1.582 -                     StubFrame f(sasm, "load_mirror_patching" , dont_gc_arguments);
   1.583 -                     oop_maps = generate_patching(sasm, CAST_FROM_FN_PTR(address, move_mirror_patching));
   1.584 -                }
   1.585 +  case load_mirror_patching_id:
   1.586 +    {
   1.587 +      StubFrame f(sasm, "load_mirror_patching" , dont_gc_arguments);
   1.588 +      oop_maps = generate_patching(sasm, CAST_FROM_FN_PTR(address, move_mirror_patching));
   1.589 +    }
   1.590      break;
   1.591 +
   1.592 +  case load_appendix_patching_id:
   1.593 +    {
   1.594 +      StubFrame f(sasm, "load_appendix_patching", dont_gc_arguments);
   1.595 +      // we should set up register map
   1.596 +      oop_maps = generate_patching(sasm, CAST_FROM_FN_PTR(address, move_appendix_patching));
   1.597 +    }
   1.598 +    break;
   1.599 +
   1.600    case dtrace_object_alloc_id:
   1.601      {
   1.602        // V0:object
   1.603 @@ -1615,6 +1543,7 @@
   1.604        save_live_registers(sasm, 0);
   1.605  
   1.606        __ push_reg(V0);
   1.607 +      __ move(A0, V0);
   1.608        __ call(CAST_FROM_FN_PTR(address, SharedRuntime::dtrace_object_alloc),
   1.609            relocInfo::runtime_call_type);
   1.610        __ super_pop(V0);
   1.611 @@ -1622,12 +1551,51 @@
   1.612        restore_live_registers(sasm);
   1.613      }
   1.614      break;
   1.615 +
   1.616    case fpu2long_stub_id:
   1.617      {
   1.618 -                   //FIXME, I hava no idea how to port this
   1.619 +      //FIXME, I hava no idea how to port this
   1.620 +      //tty->print_cr("fpu2long_stub_id unimplemented yet!");
   1.621      }
   1.622 +    break;
   1.623 +
   1.624 +  case deoptimize_id:
   1.625 +    {
   1.626 +      StubFrame f(sasm, "deoptimize", dont_gc_arguments);
   1.627 +      const int num_rt_args = 1;  // thread
   1.628 +      OopMap* oop_map = save_live_registers(sasm, num_rt_args);
   1.629 +      int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, deoptimize));
   1.630 +      oop_maps = new OopMapSet();
   1.631 +      oop_maps->add_gc_map(call_offset, oop_map);
   1.632 +      restore_live_registers(sasm);
   1.633 +      DeoptimizationBlob* deopt_blob = SharedRuntime::deopt_blob();
   1.634 +      assert(deopt_blob != NULL, "deoptimization blob must have been created");
   1.635 +      __ leave();
   1.636 +      __ jmp(deopt_blob->unpack_with_reexecution(), relocInfo::runtime_call_type);
   1.637 +    }
   1.638 +   break;
   1.639 +
   1.640 +  case predicate_failed_trap_id:
   1.641 +    {
   1.642 +      StubFrame f(sasm, "predicate_failed_trap", dont_gc_arguments);
   1.643 +
   1.644 +      OopMap* map = save_live_registers(sasm, 1);
   1.645 +
   1.646 +      int call_offset = __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, predicate_failed_trap));
   1.647 +      oop_maps = new OopMapSet();
   1.648 +      oop_maps->add_gc_map(call_offset, map);
   1.649 +      restore_live_registers(sasm);
   1.650 +      __ leave();
   1.651 +      DeoptimizationBlob* deopt_blob = SharedRuntime::deopt_blob();
   1.652 +      assert(deopt_blob != NULL, "deoptimization blob must have been created");
   1.653 +
   1.654 +      __ jmp(deopt_blob->unpack_with_reexecution(), relocInfo::runtime_call_type);
   1.655 +    }
   1.656 +   break;
   1.657 +
   1.658    default:
   1.659 -    { StubFrame f(sasm, "unimplemented entry", dont_gc_arguments);
   1.660 +    {
   1.661 +      StubFrame f(sasm, "unimplemented entry", dont_gc_arguments);
   1.662        __ move(A1, (int)id);
   1.663        __ call_RT(noreg, noreg, CAST_FROM_FN_PTR(address, unimplemented_entry), A1);
   1.664        __ should_not_reach_here();

mercurial