예제 #1
0
void InlineCacheBuffer::assemble_ic_buffer_code(address code_begin, void* cached_value, address entry_point) {
  ResourceMark rm;
  CodeBuffer      code(code_begin, ic_stub_code_size());
  MacroAssembler* masm            = new MacroAssembler(&code);
  // note: even though the code contains an embedded value, we do not need reloc info
  // because
  // (1) the value is old (i.e., doesn't matter for scavenges)
  // (2) these ICStubs are removed *before* a GC happens, so the roots disappear
  // assert(cached_value == NULL || cached_oop->is_perm(), "must be perm oop");
  masm->lea(rax, AddressLiteral((address) cached_value, relocInfo::metadata_type));
  masm->jump(ExternalAddress(entry_point));
}
예제 #2
0
void NativeFarCall::set_destination(address dest) {
  // Address materialized in the instruction stream, so nothing to do.
  return;
#if 0 // What we'd do if we really did want to change the destination
  if (destination() == dest) {
    return;
  }
  ResourceMark rm;
  CodeBuffer buf(addr_at(0), instruction_size + 1);
  MacroAssembler* _masm = new MacroAssembler(&buf);
  // Generate the new sequence
  AddressLiteral(dest);
  _masm->jumpl_to(dest, O7, O7);
  ICache::invalidate_range(addr_at(0), instruction_size );
#endif
}
예제 #3
0
// Code generation
address MethodHandles::generate_method_handle_interpreter_entry(MacroAssembler* _masm) {
  // I5_savedSP: sender SP (must preserve)
  // G4 (Gargs): incoming argument list (must preserve)
  // G5_method:  invoke methodOop; becomes method type.
  // G3_method_handle: receiver method handle (must load from sp[MethodTypeForm.vmslots])
  // O0, O1: garbage temps, blown away
  Register O0_argslot = O0;
  Register O1_scratch = O1;

  // emit WrongMethodType path first, to enable back-branch from main path
  Label wrong_method_type;
  __ bind(wrong_method_type);
  __ jump_to(AddressLiteral(Interpreter::throw_WrongMethodType_entry()), O1_scratch);
  __ delayed()->nop();

  // here's where control starts out:
  __ align(CodeEntryAlignment);
  address entry_point = __ pc();

  // fetch the MethodType from the method handle into G5_method_type
  {
    Register tem = G5_method;
    assert(tem == G5_method_type, "yes, it's the same register");
    for (jint* pchase = methodOopDesc::method_type_offsets_chain(); (*pchase) != -1; pchase++) {
      __ ld_ptr(Address(tem, *pchase), G5_method_type);
    }
  }

  // given the MethodType, find out where the MH argument is buried
  __ ld_ptr(Address(G5_method_type, __ delayed_value(java_dyn_MethodType::form_offset_in_bytes, O1_scratch)),        O0_argslot);
  __ ldsw(  Address(O0_argslot,     __ delayed_value(java_dyn_MethodTypeForm::vmslots_offset_in_bytes, O1_scratch)), O0_argslot);
  __ ld_ptr(__ argument_address(O0_argslot), G3_method_handle);

  __ check_method_handle_type(G5_method_type, G3_method_handle, O1_scratch, wrong_method_type);
  __ jump_to_method_handle_entry(G3_method_handle, O1_scratch);

  return entry_point;
}
예제 #4
0
void C1_MacroAssembler::inline_cache_check(Register receiver, Register iCache) {
  Label ic_miss, ic_hit;
  verify_oop(receiver);
  int klass_offset = oopDesc::klass_offset_in_bytes();

  if (!ImplicitNullChecks || MacroAssembler::needs_explicit_null_check(klass_offset)) {
    if (VM_Version::has_CompareBranch()) {
      z_cgij(receiver, 0, Assembler::bcondEqual, ic_miss);
    } else {
      z_ltgr(receiver, receiver);
      z_bre(ic_miss);
    }
  }

  compare_klass_ptr(iCache, klass_offset, receiver, false);
  z_bre(ic_hit);

  // If icache check fails, then jump to runtime routine.
  // Note: RECEIVER must still contain the receiver!
  load_const_optimized(Z_R1_scratch, AddressLiteral(SharedRuntime::get_ic_miss_stub()));
  z_br(Z_R1_scratch);
  align(CodeEntryAlignment);
  bind(ic_hit);
}