< prev index next >

src/hotspot/cpu/aarch64/aarch64.ad

Print this page
rev 54670 : Port of valuetypes to aarch64


1596   if (C->need_stack_bang(framesize))
1597     st->print("# stack bang size=%d\n\t", framesize);
1598 
1599   if (framesize < ((1 << 9) + 2 * wordSize)) {
1600     st->print("sub  sp, sp, #%d\n\t", framesize);
1601     st->print("stp  rfp, lr, [sp, #%d]", framesize - 2 * wordSize);
1602     if (PreserveFramePointer) st->print("\n\tadd  rfp, sp, #%d", framesize - 2 * wordSize);
1603   } else {
1604     st->print("stp  lr, rfp, [sp, #%d]!\n\t", -(2 * wordSize));
1605     if (PreserveFramePointer) st->print("mov  rfp, sp\n\t");
1606     st->print("mov  rscratch1, #%d\n\t", framesize - 2 * wordSize);
1607     st->print("sub  sp, sp, rscratch1");
1608   }
1609 }
1610 #endif
1611 
1612 void MachPrologNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1613   Compile* C = ra_->C;
1614   MacroAssembler _masm(&cbuf);
1615 
1616   // n.b. frame size includes space for return pc and rfp
1617   const long framesize = C->frame_size_in_bytes();
1618   assert(framesize%(2*wordSize) == 0, "must preserve 2*wordSize alignment");
1619 
1620   // insert a nop at the start of the prolog so we can patch in a
1621   // branch if we need to invalidate the method later
1622   __ nop();
1623 
1624   int bangsize = C->bang_size_in_bytes();
1625   if (C->need_stack_bang(bangsize) && UseStackBanging)
1626     __ generate_stack_overflow_check(bangsize);
1627 
1628   __ build_frame(framesize);
1629 
1630   if (NotifySimulator) {
1631     __ notify(Assembler::method_entry);
1632   }
1633 
1634   if (VerifyStackAtCalls) {
1635     Unimplemented();
1636   }
1637 
1638   C->set_frame_complete(cbuf.insts_size());
1639 
1640   if (C->has_mach_constant_base_node()) {
1641     // NOTE: We set the table base offset here because users might be
1642     // emitted before MachConstantBaseNode.
1643     Compile::ConstantTable& constant_table = C->constant_table();
1644     constant_table.set_table_base_offset(constant_table.calculate_table_base_offset());
1645   }
1646 }
1647 
1648 uint MachPrologNode::size(PhaseRegAlloc* ra_) const
1649 {
1650   return MachNode::size(ra_); // too many variables; just compute it
1651                               // the hard way
1652 }
1653 
1654 int MachPrologNode::reloc() const
1655 {
1656   return 0;


1938 
1939 void BoxLockNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1940   MacroAssembler _masm(&cbuf);
1941 
1942   int offset = ra_->reg2offset(in_RegMask(0).find_first_elem());
1943   int reg    = ra_->get_encode(this);
1944 
1945   if (Assembler::operand_valid_for_add_sub_immediate(offset)) {
1946     __ add(as_Register(reg), sp, offset);
1947   } else {
1948     ShouldNotReachHere();
1949   }
1950 }
1951 
1952 uint BoxLockNode::size(PhaseRegAlloc *ra_) const {
1953   // BoxLockNode is not a MachNode, so we can't just call MachNode::size(ra_).
1954   return 4;
1955 }
1956 
1957 //=============================================================================







































1958 
1959 #ifndef PRODUCT
1960 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const
1961 {
1962   st->print_cr("# MachUEPNode");
1963   if (UseCompressedClassPointers) {
1964     st->print_cr("\tldrw rscratch1, j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1965     if (Universe::narrow_klass_shift() != 0) {
1966       st->print_cr("\tdecode_klass_not_null rscratch1, rscratch1");
1967     }
1968   } else {
1969    st->print_cr("\tldr rscratch1, j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1970   }
1971   st->print_cr("\tcmp r0, rscratch1\t # Inline cache check");
1972   st->print_cr("\tbne, SharedRuntime::_ic_miss_stub");
1973 }
1974 #endif
1975 
1976 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const
1977 {


2350     mstack.push(m->in(AddPNode::Base), Pre_Visit);
2351     return true;
2352   }
2353   return false;
2354 }
2355 
2356 void Compile::reshape_address(AddPNode* addp) {
2357 }
2358 
2359 // helper for encoding java_to_runtime calls on sim
2360 //
2361 // this is needed to compute the extra arguments required when
2362 // planting a call to the simulator blrt instruction. the TypeFunc
2363 // can be queried to identify the counts for integral, and floating
2364 // arguments and the return type
2365 
2366 static void getCallInfo(const TypeFunc *tf, int &gpcnt, int &fpcnt, int &rtype)
2367 {
2368   int gps = 0;
2369   int fps = 0;
2370   const TypeTuple *domain = tf->domain();
2371   int max = domain->cnt();
2372   for (int i = TypeFunc::Parms; i < max; i++) {
2373     const Type *t = domain->field_at(i);
2374     switch(t->basic_type()) {
2375     case T_FLOAT:
2376     case T_DOUBLE:
2377       fps++;
2378     default:
2379       gps++;
2380     }
2381   }
2382   gpcnt = gps;
2383   fpcnt = fps;
2384   BasicType rt = tf->return_type();
2385   switch (rt) {
2386   case T_VOID:
2387     rtype = MacroAssembler::ret_type_void;
2388     break;
2389   default:
2390     rtype = MacroAssembler::ret_type_integral;


7771 %}
7772 
7773 // ============================================================================
7774 // Cast/Convert Instructions
7775 
7776 instruct castX2P(iRegPNoSp dst, iRegL src) %{
7777   match(Set dst (CastX2P src));
7778 
7779   ins_cost(INSN_COST);
7780   format %{ "mov $dst, $src\t# long -> ptr" %}
7781 
7782   ins_encode %{
7783     if ($dst$$reg != $src$$reg) {
7784       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7785     }
7786   %}
7787 
7788   ins_pipe(ialu_reg);
7789 %}
7790 















7791 instruct castP2X(iRegLNoSp dst, iRegP src) %{
7792   match(Set dst (CastP2X src));
7793 
7794   ins_cost(INSN_COST);
7795   format %{ "mov $dst, $src\t# ptr -> long" %}
7796 
7797   ins_encode %{
7798     if ($dst$$reg != $src$$reg) {
7799       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7800     }
7801   %}
7802 
7803   ins_pipe(ialu_reg);
7804 %}
7805 
7806 // Convert oop into int for vectors alignment masking
7807 instruct convP2I(iRegINoSp dst, iRegP src) %{
7808   match(Set dst (ConvL2I (CastP2X src)));
7809 
7810   ins_cost(INSN_COST);


13284 
13285   match(Set dst (MoveL2D src));
13286 
13287   effect(DEF dst, USE src);
13288 
13289   ins_cost(INSN_COST);
13290 
13291   format %{ "fmovd $dst, $src\t# MoveL2D_reg_reg" %}
13292 
13293   ins_encode %{
13294     __ fmovd(as_FloatRegister($dst$$reg), $src$$Register);
13295   %}
13296 
13297   ins_pipe(fp_l2d);
13298 
13299 %}
13300 
13301 // ============================================================================
13302 // clearing of an array
13303 
13304 instruct clearArray_reg_reg(iRegL_R11 cnt, iRegP_R10 base, Universe dummy, rFlagsReg cr)
13305 %{
13306   match(Set dummy (ClearArray cnt base));
13307   effect(USE_KILL cnt, USE_KILL base);
13308 
13309   ins_cost(4 * INSN_COST);
13310   format %{ "ClearArray $cnt, $base" %}
13311 
13312   ins_encode %{
13313     __ zero_words($base$$Register, $cnt$$Register);
13314   %}
13315 
13316   ins_pipe(pipe_class_memory);
13317 %}
13318 
13319 instruct clearArray_imm_reg(immL cnt, iRegP_R10 base, Universe dummy, rFlagsReg cr)
13320 %{
13321   predicate((u_int64_t)n->in(2)->get_long()
13322             < (u_int64_t)(BlockZeroingLowLimit >> LogBytesPerWord));
13323   match(Set dummy (ClearArray cnt base));
13324   effect(USE_KILL base);
13325 
13326   ins_cost(4 * INSN_COST);
13327   format %{ "ClearArray $cnt, $base" %}
13328 
13329   ins_encode %{
13330     __ zero_words($base$$Register, (u_int64_t)$cnt$$constant);
13331   %}
13332 
13333   ins_pipe(pipe_class_memory);
13334 %}
13335 
13336 // ============================================================================
13337 // Overflow Math Instructions
13338 
13339 instruct overflowAddI_reg_reg(rFlagsReg cr, iRegIorL2I op1, iRegIorL2I op2)
13340 %{
13341   match(Set cr (OverflowAddI op1 op2));
13342 
13343   format %{ "cmnw  $op1, $op2\t# overflow check int" %}
13344   ins_cost(INSN_COST);
13345   ins_encode %{
13346     __ cmnw($op1$$Register, $op2$$Register);
13347   %}
13348 
13349   ins_pipe(icmp_reg_reg);
13350 %}




1596   if (C->need_stack_bang(framesize))
1597     st->print("# stack bang size=%d\n\t", framesize);
1598 
1599   if (framesize < ((1 << 9) + 2 * wordSize)) {
1600     st->print("sub  sp, sp, #%d\n\t", framesize);
1601     st->print("stp  rfp, lr, [sp, #%d]", framesize - 2 * wordSize);
1602     if (PreserveFramePointer) st->print("\n\tadd  rfp, sp, #%d", framesize - 2 * wordSize);
1603   } else {
1604     st->print("stp  lr, rfp, [sp, #%d]!\n\t", -(2 * wordSize));
1605     if (PreserveFramePointer) st->print("mov  rfp, sp\n\t");
1606     st->print("mov  rscratch1, #%d\n\t", framesize - 2 * wordSize);
1607     st->print("sub  sp, sp, rscratch1");
1608   }
1609 }
1610 #endif
1611 
1612 void MachPrologNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1613   Compile* C = ra_->C;
1614   MacroAssembler _masm(&cbuf);
1615 
1616   __ verified_entry(C, 0);
1617   __ bind(*_verified_entry);



















1618 
1619   C->set_frame_complete(cbuf.insts_size());
1620 
1621   if (C->has_mach_constant_base_node()) {
1622     // NOTE: We set the table base offset here because users might be
1623     // emitted before MachConstantBaseNode.
1624     Compile::ConstantTable& constant_table = C->constant_table();
1625     constant_table.set_table_base_offset(constant_table.calculate_table_base_offset());
1626   }
1627 }
1628 
1629 uint MachPrologNode::size(PhaseRegAlloc* ra_) const
1630 {
1631   return MachNode::size(ra_); // too many variables; just compute it
1632                               // the hard way
1633 }
1634 
1635 int MachPrologNode::reloc() const
1636 {
1637   return 0;


1919 
1920 void BoxLockNode::emit(CodeBuffer &cbuf, PhaseRegAlloc *ra_) const {
1921   MacroAssembler _masm(&cbuf);
1922 
1923   int offset = ra_->reg2offset(in_RegMask(0).find_first_elem());
1924   int reg    = ra_->get_encode(this);
1925 
1926   if (Assembler::operand_valid_for_add_sub_immediate(offset)) {
1927     __ add(as_Register(reg), sp, offset);
1928   } else {
1929     ShouldNotReachHere();
1930   }
1931 }
1932 
1933 uint BoxLockNode::size(PhaseRegAlloc *ra_) const {
1934   // BoxLockNode is not a MachNode, so we can't just call MachNode::size(ra_).
1935   return 4;
1936 }
1937 
1938 //=============================================================================
1939 #ifndef PRODUCT
1940 void MachVEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const
1941 {
1942   st->print_cr("# MachVEPNode");
1943   if (!_verified) {
1944     st->print_cr("\t load_class");
1945   } else {
1946     st->print_cr("\t unpack_value_arg");
1947   }
1948 }
1949 #endif
1950 
1951 void MachVEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const
1952 {
1953   MacroAssembler _masm(&cbuf);
1954 
1955   if (!_verified) {
1956     Label skip;
1957     __ cmp_klass(j_rarg0, rscratch2, rscratch1);
1958     __ br(Assembler::EQ, skip);
1959       __ far_jump(RuntimeAddress(SharedRuntime::get_ic_miss_stub()));
1960     __ bind(skip);
1961 
1962   } else {
1963     // Unpack value type args passed as oop and then jump to
1964     // the verified entry point (skipping the unverified entry).
1965     __ unpack_value_args(ra_->C, _receiver_only);
1966     __ b(*_verified_entry);
1967   }
1968 }
1969 
1970 
1971 uint MachVEPNode::size(PhaseRegAlloc* ra_) const
1972 {
1973   return MachNode::size(ra_); // too many variables; just compute it the hard way
1974 }
1975 
1976 
1977 //=============================================================================
1978 
1979 #ifndef PRODUCT
1980 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const
1981 {
1982   st->print_cr("# MachUEPNode");
1983   if (UseCompressedClassPointers) {
1984     st->print_cr("\tldrw rscratch1, j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1985     if (Universe::narrow_klass_shift() != 0) {
1986       st->print_cr("\tdecode_klass_not_null rscratch1, rscratch1");
1987     }
1988   } else {
1989    st->print_cr("\tldr rscratch1, j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1990   }
1991   st->print_cr("\tcmp r0, rscratch1\t # Inline cache check");
1992   st->print_cr("\tbne, SharedRuntime::_ic_miss_stub");
1993 }
1994 #endif
1995 
1996 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const
1997 {


2370     mstack.push(m->in(AddPNode::Base), Pre_Visit);
2371     return true;
2372   }
2373   return false;
2374 }
2375 
2376 void Compile::reshape_address(AddPNode* addp) {
2377 }
2378 
2379 // helper for encoding java_to_runtime calls on sim
2380 //
2381 // this is needed to compute the extra arguments required when
2382 // planting a call to the simulator blrt instruction. the TypeFunc
2383 // can be queried to identify the counts for integral, and floating
2384 // arguments and the return type
2385 
2386 static void getCallInfo(const TypeFunc *tf, int &gpcnt, int &fpcnt, int &rtype)
2387 {
2388   int gps = 0;
2389   int fps = 0;
2390   const TypeTuple *domain = tf->domain_cc();
2391   int max = domain->cnt();
2392   for (int i = TypeFunc::Parms; i < max; i++) {
2393     const Type *t = domain->field_at(i);
2394     switch(t->basic_type()) {
2395     case T_FLOAT:
2396     case T_DOUBLE:
2397       fps++;
2398     default:
2399       gps++;
2400     }
2401   }
2402   gpcnt = gps;
2403   fpcnt = fps;
2404   BasicType rt = tf->return_type();
2405   switch (rt) {
2406   case T_VOID:
2407     rtype = MacroAssembler::ret_type_void;
2408     break;
2409   default:
2410     rtype = MacroAssembler::ret_type_integral;


7791 %}
7792 
7793 // ============================================================================
7794 // Cast/Convert Instructions
7795 
7796 instruct castX2P(iRegPNoSp dst, iRegL src) %{
7797   match(Set dst (CastX2P src));
7798 
7799   ins_cost(INSN_COST);
7800   format %{ "mov $dst, $src\t# long -> ptr" %}
7801 
7802   ins_encode %{
7803     if ($dst$$reg != $src$$reg) {
7804       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7805     }
7806   %}
7807 
7808   ins_pipe(ialu_reg);
7809 %}
7810 
7811 instruct castN2X(iRegLNoSp dst, iRegN src) %{
7812   match(Set dst (CastP2X src));
7813 
7814   ins_cost(INSN_COST);
7815   format %{ "mov $dst, $src\t# ptr -> long" %}
7816 
7817   ins_encode %{
7818     if ($dst$$reg != $src$$reg) {
7819       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7820     }
7821   %}
7822 
7823   ins_pipe(ialu_reg);
7824 %}
7825 
7826 instruct castP2X(iRegLNoSp dst, iRegP src) %{
7827   match(Set dst (CastP2X src));
7828 
7829   ins_cost(INSN_COST);
7830   format %{ "mov $dst, $src\t# ptr -> long" %}
7831 
7832   ins_encode %{
7833     if ($dst$$reg != $src$$reg) {
7834       __ mov(as_Register($dst$$reg), as_Register($src$$reg));
7835     }
7836   %}
7837 
7838   ins_pipe(ialu_reg);
7839 %}
7840 
7841 // Convert oop into int for vectors alignment masking
7842 instruct convP2I(iRegINoSp dst, iRegP src) %{
7843   match(Set dst (ConvL2I (CastP2X src)));
7844 
7845   ins_cost(INSN_COST);


13319 
13320   match(Set dst (MoveL2D src));
13321 
13322   effect(DEF dst, USE src);
13323 
13324   ins_cost(INSN_COST);
13325 
13326   format %{ "fmovd $dst, $src\t# MoveL2D_reg_reg" %}
13327 
13328   ins_encode %{
13329     __ fmovd(as_FloatRegister($dst$$reg), $src$$Register);
13330   %}
13331 
13332   ins_pipe(fp_l2d);
13333 
13334 %}
13335 
13336 // ============================================================================
13337 // clearing of an array
13338 
13339 instruct clearArray_reg_reg(iRegL_R11 cnt, iRegP_R10 base, iRegL val, Universe dummy, rFlagsReg cr)
13340 %{
13341   match(Set dummy (ClearArray (Binary cnt base) val));
13342   effect(USE_KILL cnt, USE_KILL base);
13343 
13344   ins_cost(4 * INSN_COST);
13345   format %{ "ClearArray $cnt, $base, $val" %}

















13346 
13347   ins_encode %{
13348     __ fill_words($base$$Register, $cnt$$Register, $val$$Register);
13349   %}
13350 
13351   ins_pipe(pipe_class_memory);
13352 %}
13353 
13354 // ============================================================================
13355 // Overflow Math Instructions
13356 
13357 instruct overflowAddI_reg_reg(rFlagsReg cr, iRegIorL2I op1, iRegIorL2I op2)
13358 %{
13359   match(Set cr (OverflowAddI op1 op2));
13360 
13361   format %{ "cmnw  $op1, $op2\t# overflow check int" %}
13362   ins_cost(INSN_COST);
13363   ins_encode %{
13364     __ cmnw($op1$$Register, $op2$$Register);
13365   %}
13366 
13367   ins_pipe(icmp_reg_reg);
13368 %}


< prev index next >