src/cpu/x86/vm/x86_64.ad
Index Unified diffs Context diffs Sdiffs Wdiffs Patch New Old Previous File Next File bug_8003424.4 Sdiff src/cpu/x86/vm

src/cpu/x86/vm/x86_64.ad

Print this page




1376     emit_opcode(cbuf, reg < 8 ? Assembler::REX_W : Assembler::REX_WR);
1377     emit_opcode(cbuf, 0x8D); // LEA  reg,[SP+offset]
1378     emit_rm(cbuf, 0x1, reg & 7, 0x04);
1379     emit_rm(cbuf, 0x0, 0x04, RSP_enc);
1380     emit_d8(cbuf, offset);
1381   }
1382 }
1383 
1384 uint BoxLockNode::size(PhaseRegAlloc *ra_) const
1385 {
1386   int offset = ra_->reg2offset(in_RegMask(0).find_first_elem());
1387   return (offset < 0x80) ? 5 : 8; // REX
1388 }
1389 
1390 //=============================================================================
1391 #ifndef PRODUCT
1392 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const
1393 {
1394   if (UseCompressedKlassPointers) {
1395     st->print_cr("movl    rscratch1, [j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");
1396     if (Universe::narrow_klass_shift() != 0) {
1397       st->print_cr("\tdecode_klass_not_null rscratch1, rscratch1");
1398     }
1399     st->print_cr("\tcmpq    rax, rscratch1\t # Inline cache check");
1400   } else {
1401     st->print_cr("\tcmpq    rax, [j_rarg0 + oopDesc::klass_offset_in_bytes()]\t"
1402                  "# Inline cache check");
1403   }
1404   st->print_cr("\tjne     SharedRuntime::_ic_miss_stub");
1405   st->print_cr("\tnop\t# nops to align entry point");
1406 }
1407 #endif
1408 
1409 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const
1410 {
1411   MacroAssembler masm(&cbuf);
1412   uint insts_size = cbuf.insts_size();
1413   if (UseCompressedKlassPointers) {
1414     masm.load_klass(rscratch1, j_rarg0);
1415     masm.cmpptr(rax, rscratch1);
1416   } else {
1417     masm.cmpptr(rax, Address(j_rarg0, oopDesc::klass_offset_in_bytes()));
1418   }


4018   %}
4019 %}
4020 
4021 // Indirect Memory Times Scale Plus Positive Index Register Plus Offset Operand
4022 operand indPosIndexScaleOffsetNarrow(rRegN reg, immL32 off, rRegI idx, immI2 scale)
4023 %{
4024   constraint(ALLOC_IN_RC(ptr_reg));
4025   predicate(Universe::narrow_oop_shift() == 0 && n->in(2)->in(3)->in(1)->as_Type()->type()->is_long()->_lo >= 0);
4026   match(AddP (AddP (DecodeN reg) (LShiftL (ConvI2L idx) scale)) off);
4027 
4028   op_cost(10);
4029   format %{"[$reg + $off + $idx << $scale]" %}
4030   interface(MEMORY_INTER) %{
4031     base($reg);
4032     index($idx);
4033     scale($scale);
4034     disp($off);
4035   %}
4036 %}
4037 
4038 operand indirectNarrowKlass(rRegN reg)
4039 %{
4040   predicate(Universe::narrow_klass_shift() == 0);
4041   constraint(ALLOC_IN_RC(ptr_reg));
4042   match(DecodeNKlass reg);
4043 
4044   format %{ "[$reg]" %}
4045   interface(MEMORY_INTER) %{
4046     base($reg);
4047     index(0x4);
4048     scale(0x0);
4049     disp(0x0);
4050   %}
4051 %}
4052 
4053 operand indOffset8NarrowKlass(rRegN reg, immL8 off)
4054 %{
4055   predicate(Universe::narrow_klass_shift() == 0);
4056   constraint(ALLOC_IN_RC(ptr_reg));
4057   match(AddP (DecodeNKlass reg) off);
4058 
4059   format %{ "[$reg + $off (8-bit)]" %}
4060   interface(MEMORY_INTER) %{
4061     base($reg);
4062     index(0x4);
4063     scale(0x0);
4064     disp($off);
4065   %}
4066 %}
4067 
4068 operand indOffset32NarrowKlass(rRegN reg, immL32 off)
4069 %{
4070   predicate(Universe::narrow_klass_shift() == 0);
4071   constraint(ALLOC_IN_RC(ptr_reg));
4072   match(AddP (DecodeNKlass reg) off);
4073 
4074   format %{ "[$reg + $off (32-bit)]" %}
4075   interface(MEMORY_INTER) %{
4076     base($reg);
4077     index(0x4);
4078     scale(0x0);
4079     disp($off);
4080   %}
4081 %}
4082 
4083 operand indIndexOffsetNarrowKlass(rRegN reg, rRegL lreg, immL32 off)
4084 %{
4085   predicate(Universe::narrow_klass_shift() == 0);
4086   constraint(ALLOC_IN_RC(ptr_reg));
4087   match(AddP (AddP (DecodeNKlass reg) lreg) off);
4088 
4089   op_cost(10);
4090   format %{"[$reg + $off + $lreg]" %}
4091   interface(MEMORY_INTER) %{
4092     base($reg);
4093     index($lreg);
4094     scale(0x0);
4095     disp($off);
4096   %}
4097 %}
4098 
4099 operand indIndexNarrowKlass(rRegN reg, rRegL lreg)
4100 %{
4101   predicate(Universe::narrow_klass_shift() == 0);
4102   constraint(ALLOC_IN_RC(ptr_reg));
4103   match(AddP (DecodeNKlass reg) lreg);
4104 
4105   op_cost(10);
4106   format %{"[$reg + $lreg]" %}
4107   interface(MEMORY_INTER) %{
4108     base($reg);
4109     index($lreg);
4110     scale(0x0);
4111     disp(0x0);
4112   %}
4113 %}
4114 
4115 operand indIndexScaleNarrowKlass(rRegN reg, rRegL lreg, immI2 scale)
4116 %{
4117   predicate(Universe::narrow_klass_shift() == 0);
4118   constraint(ALLOC_IN_RC(ptr_reg));
4119   match(AddP (DecodeNKlass reg) (LShiftL lreg scale));
4120 
4121   op_cost(10);
4122   format %{"[$reg + $lreg << $scale]" %}
4123   interface(MEMORY_INTER) %{
4124     base($reg);
4125     index($lreg);
4126     scale($scale);
4127     disp(0x0);
4128   %}
4129 %}
4130 
4131 operand indIndexScaleOffsetNarrowKlass(rRegN reg, immL32 off, rRegL lreg, immI2 scale)
4132 %{
4133   predicate(Universe::narrow_klass_shift() == 0);
4134   constraint(ALLOC_IN_RC(ptr_reg));
4135   match(AddP (AddP (DecodeNKlass reg) (LShiftL lreg scale)) off);
4136 
4137   op_cost(10);
4138   format %{"[$reg + $off + $lreg << $scale]" %}
4139   interface(MEMORY_INTER) %{
4140     base($reg);
4141     index($lreg);
4142     scale($scale);
4143     disp($off);
4144   %}
4145 %}
4146 
4147 operand indCompressedKlassOffset(rRegN reg, immL32 off) %{
4148   predicate(UseCompressedKlassPointers && (Universe::narrow_klass_shift() == Address::times_8));
4149   constraint(ALLOC_IN_RC(ptr_reg));
4150   match(AddP (DecodeNKlass reg) off);
4151 
4152   op_cost(10);
4153   format %{"[R12 + $reg << 3 + $off] (compressed klass addressing)" %}
4154   interface(MEMORY_INTER) %{
4155     base(0xc); // R12
4156     index($reg);
4157     scale(0x3);
4158     disp($off);
4159   %}
4160 %}
4161 
4162 operand indPosIndexScaleOffsetNarrowKlass(rRegN reg, immL32 off, rRegI idx, immI2 scale)
4163 %{
4164   constraint(ALLOC_IN_RC(ptr_reg));
4165   predicate(Universe::narrow_klass_shift() == 0 && n->in(2)->in(3)->in(1)->as_Type()->type()->is_long()->_lo >= 0);
4166   match(AddP (AddP (DecodeNKlass reg) (LShiftL (ConvI2L idx) scale)) off);
4167 
4168   op_cost(10);
4169   format %{"[$reg + $off + $idx << $scale]" %}
4170   interface(MEMORY_INTER) %{
4171     base($reg);
4172     index($idx);
4173     scale($scale);
4174     disp($off);
4175   %}
4176 %}
4177 
4178 //----------Special Memory Operands--------------------------------------------
4179 // Stack Slot Operand - This operand is used for loading and storing temporary
4180 //                      values on the stack where a match requires a value to
4181 //                      flow through memory.
4182 operand stackSlotP(sRegP reg)
4183 %{
4184   constraint(ALLOC_IN_RC(stack_slots));
4185   // No match rule because this operand is only generated in matching
4186 
4187   format %{ "[$reg]" %}
4188   interface(MEMORY_INTER) %{
4189     base(0x4);   // RSP
4190     index(0x4);  // No Index
4191     scale(0x0);  // No Scale
4192     disp($reg);  // Stack Offset
4193   %}
4194 %}
4195 
4196 operand stackSlotI(sRegI reg)
4197 %{


4328     less(0x2, "b");
4329     greater_equal(0x3, "nb");
4330     less_equal(0x6, "be");
4331     greater(0x7, "nbe");
4332   %}
4333 %}
4334 
4335 
4336 //----------OPERAND CLASSES----------------------------------------------------
4337 // Operand Classes are groups of operands that are used as to simplify
4338 // instruction definitions by not requiring the AD writer to specify separate
4339 // instructions for every form of operand when the instruction accepts
4340 // multiple operand types with the same basic encoding and format.  The classic
4341 // case of this is memory operands.
4342 
4343 opclass memory(indirect, indOffset8, indOffset32, indIndexOffset, indIndex,
4344                indIndexScale, indIndexScaleOffset, indPosIndexScaleOffset,
4345                indCompressedOopOffset,
4346                indirectNarrow, indOffset8Narrow, indOffset32Narrow,
4347                indIndexOffsetNarrow, indIndexNarrow, indIndexScaleNarrow,
4348                indIndexScaleOffsetNarrow, indPosIndexScaleOffsetNarrow,
4349                indCompressedKlassOffset,
4350                indirectNarrowKlass, indOffset8NarrowKlass, indOffset32NarrowKlass,
4351                indIndexOffsetNarrowKlass, indIndexNarrowKlass, indIndexScaleNarrowKlass,
4352                indIndexScaleOffsetNarrowKlass, indPosIndexScaleOffsetNarrowKlass);
4353 
4354 //----------PIPELINE-----------------------------------------------------------
4355 // Rules which define the behavior of the target architectures pipeline.
4356 pipeline %{
4357 
4358 //----------ATTRIBUTES---------------------------------------------------------
4359 attributes %{
4360   variable_size_instructions;        // Fixed size instructions
4361   max_instructions_per_bundle = 3;   // Up to 3 instructions per bundle
4362   instruction_unit_size = 1;         // An instruction is 1 bytes long
4363   instruction_fetch_unit_size = 16;  // The processor fetches one line
4364   instruction_fetch_units = 1;       // of 16 bytes
4365 
4366   // List of nop instructions
4367   nops( MachNop );
4368 %}
4369 
4370 //----------RESOURCES----------------------------------------------------------
4371 // Resources are the functional units available to the machine
4372 


6648   predicate(n->bottom_type()->is_ptr()->ptr() == TypePtr::NotNull ||
6649             n->bottom_type()->is_ptr()->ptr() == TypePtr::Constant);
6650   match(Set dst (DecodeN src));
6651   effect(KILL cr);
6652   format %{ "decode_heap_oop_not_null $dst,$src" %}
6653   ins_encode %{
6654     Register s = $src$$Register;
6655     Register d = $dst$$Register;
6656     if (s != d) {
6657       __ decode_heap_oop_not_null(d, s);
6658     } else {
6659       __ decode_heap_oop_not_null(d);
6660     }
6661   %}
6662   ins_pipe(ialu_reg_long);
6663 %}
6664 
6665 instruct encodeKlass_not_null(rRegN dst, rRegP src, rFlagsReg cr) %{
6666   match(Set dst (EncodePKlass src));
6667   effect(KILL cr);
6668   format %{ "encode_heap_oop_not_null $dst,$src" %}
6669   ins_encode %{
6670     __ encode_klass_not_null($dst$$Register, $src$$Register);
6671   %}
6672   ins_pipe(ialu_reg_long);
6673 %}
6674 
6675 instruct decodeKlass_not_null(rRegP dst, rRegN src, rFlagsReg cr) %{
6676   match(Set dst (DecodeNKlass src));
6677   effect(KILL cr);
6678   format %{ "decode_heap_oop_not_null $dst,$src" %}
6679   ins_encode %{
6680     Register s = $src$$Register;
6681     Register d = $dst$$Register;
6682     if (s != d) {
6683       __ decode_klass_not_null(d, s);
6684     } else {
6685       __ decode_klass_not_null(d);
6686     }
6687   %}
6688   ins_pipe(ialu_reg_long);
6689 %}
6690 
6691 
6692 //----------Conditional Move---------------------------------------------------
6693 // Jump
6694 // dummy instruction for generating temp registers
6695 instruct jumpXtnd_offset(rRegL switch_val, immI2 shift, rRegI dest) %{
6696   match(Jump (LShiftL switch_val shift));
6697   ins_cost(350);
6698   predicate(false);




1376     emit_opcode(cbuf, reg < 8 ? Assembler::REX_W : Assembler::REX_WR);
1377     emit_opcode(cbuf, 0x8D); // LEA  reg,[SP+offset]
1378     emit_rm(cbuf, 0x1, reg & 7, 0x04);
1379     emit_rm(cbuf, 0x0, 0x04, RSP_enc);
1380     emit_d8(cbuf, offset);
1381   }
1382 }
1383 
1384 uint BoxLockNode::size(PhaseRegAlloc *ra_) const
1385 {
1386   int offset = ra_->reg2offset(in_RegMask(0).find_first_elem());
1387   return (offset < 0x80) ? 5 : 8; // REX
1388 }
1389 
1390 //=============================================================================
1391 #ifndef PRODUCT
1392 void MachUEPNode::format(PhaseRegAlloc* ra_, outputStream* st) const
1393 {
1394   if (UseCompressedKlassPointers) {
1395     st->print_cr("movl    rscratch1, [j_rarg0 + oopDesc::klass_offset_in_bytes()]\t# compressed klass");

1396     st->print_cr("\tdecode_klass_not_null rscratch1, rscratch1");

1397     st->print_cr("\tcmpq    rax, rscratch1\t # Inline cache check");
1398   } else {
1399     st->print_cr("\tcmpq    rax, [j_rarg0 + oopDesc::klass_offset_in_bytes()]\t"
1400                  "# Inline cache check");
1401   }
1402   st->print_cr("\tjne     SharedRuntime::_ic_miss_stub");
1403   st->print_cr("\tnop\t# nops to align entry point");
1404 }
1405 #endif
1406 
1407 void MachUEPNode::emit(CodeBuffer& cbuf, PhaseRegAlloc* ra_) const
1408 {
1409   MacroAssembler masm(&cbuf);
1410   uint insts_size = cbuf.insts_size();
1411   if (UseCompressedKlassPointers) {
1412     masm.load_klass(rscratch1, j_rarg0);
1413     masm.cmpptr(rax, rscratch1);
1414   } else {
1415     masm.cmpptr(rax, Address(j_rarg0, oopDesc::klass_offset_in_bytes()));
1416   }


4016   %}
4017 %}
4018 
4019 // Indirect Memory Times Scale Plus Positive Index Register Plus Offset Operand
4020 operand indPosIndexScaleOffsetNarrow(rRegN reg, immL32 off, rRegI idx, immI2 scale)
4021 %{
4022   constraint(ALLOC_IN_RC(ptr_reg));
4023   predicate(Universe::narrow_oop_shift() == 0 && n->in(2)->in(3)->in(1)->as_Type()->type()->is_long()->_lo >= 0);
4024   match(AddP (AddP (DecodeN reg) (LShiftL (ConvI2L idx) scale)) off);
4025 
4026   op_cost(10);
4027   format %{"[$reg + $off + $idx << $scale]" %}
4028   interface(MEMORY_INTER) %{
4029     base($reg);
4030     index($idx);
4031     scale($scale);
4032     disp($off);
4033   %}
4034 %}
4035 












































































































































4036 //----------Special Memory Operands--------------------------------------------
4037 // Stack Slot Operand - This operand is used for loading and storing temporary
4038 //                      values on the stack where a match requires a value to
4039 //                      flow through memory.
4040 operand stackSlotP(sRegP reg)
4041 %{
4042   constraint(ALLOC_IN_RC(stack_slots));
4043   // No match rule because this operand is only generated in matching
4044 
4045   format %{ "[$reg]" %}
4046   interface(MEMORY_INTER) %{
4047     base(0x4);   // RSP
4048     index(0x4);  // No Index
4049     scale(0x0);  // No Scale
4050     disp($reg);  // Stack Offset
4051   %}
4052 %}
4053 
4054 operand stackSlotI(sRegI reg)
4055 %{


4186     less(0x2, "b");
4187     greater_equal(0x3, "nb");
4188     less_equal(0x6, "be");
4189     greater(0x7, "nbe");
4190   %}
4191 %}
4192 
4193 
4194 //----------OPERAND CLASSES----------------------------------------------------
4195 // Operand Classes are groups of operands that are used as to simplify
4196 // instruction definitions by not requiring the AD writer to specify separate
4197 // instructions for every form of operand when the instruction accepts
4198 // multiple operand types with the same basic encoding and format.  The classic
4199 // case of this is memory operands.
4200 
4201 opclass memory(indirect, indOffset8, indOffset32, indIndexOffset, indIndex,
4202                indIndexScale, indIndexScaleOffset, indPosIndexScaleOffset,
4203                indCompressedOopOffset,
4204                indirectNarrow, indOffset8Narrow, indOffset32Narrow,
4205                indIndexOffsetNarrow, indIndexNarrow, indIndexScaleNarrow,
4206                indIndexScaleOffsetNarrow, indPosIndexScaleOffsetNarrow);




4207 
4208 //----------PIPELINE-----------------------------------------------------------
4209 // Rules which define the behavior of the target architectures pipeline.
4210 pipeline %{
4211 
4212 //----------ATTRIBUTES---------------------------------------------------------
4213 attributes %{
4214   variable_size_instructions;        // Fixed size instructions
4215   max_instructions_per_bundle = 3;   // Up to 3 instructions per bundle
4216   instruction_unit_size = 1;         // An instruction is 1 bytes long
4217   instruction_fetch_unit_size = 16;  // The processor fetches one line
4218   instruction_fetch_units = 1;       // of 16 bytes
4219 
4220   // List of nop instructions
4221   nops( MachNop );
4222 %}
4223 
4224 //----------RESOURCES----------------------------------------------------------
4225 // Resources are the functional units available to the machine
4226 


6502   predicate(n->bottom_type()->is_ptr()->ptr() == TypePtr::NotNull ||
6503             n->bottom_type()->is_ptr()->ptr() == TypePtr::Constant);
6504   match(Set dst (DecodeN src));
6505   effect(KILL cr);
6506   format %{ "decode_heap_oop_not_null $dst,$src" %}
6507   ins_encode %{
6508     Register s = $src$$Register;
6509     Register d = $dst$$Register;
6510     if (s != d) {
6511       __ decode_heap_oop_not_null(d, s);
6512     } else {
6513       __ decode_heap_oop_not_null(d);
6514     }
6515   %}
6516   ins_pipe(ialu_reg_long);
6517 %}
6518 
6519 instruct encodeKlass_not_null(rRegN dst, rRegP src, rFlagsReg cr) %{
6520   match(Set dst (EncodePKlass src));
6521   effect(KILL cr);
6522   format %{ "encode_klass_not_null $dst,$src" %}
6523   ins_encode %{
6524     __ encode_klass_not_null($dst$$Register, $src$$Register);
6525   %}
6526   ins_pipe(ialu_reg_long);
6527 %}
6528 
6529 instruct decodeKlass_not_null(rRegP dst, rRegN src, rFlagsReg cr) %{
6530   match(Set dst (DecodeNKlass src));
6531   effect(KILL cr);
6532   format %{ "decode_klass_not_null $dst,$src" %}
6533   ins_encode %{
6534     Register s = $src$$Register;
6535     Register d = $dst$$Register;
6536     if (s != d) {
6537       __ decode_klass_not_null(d, s);
6538     } else {
6539       __ decode_klass_not_null(d);
6540     }
6541   %}
6542   ins_pipe(ialu_reg_long);
6543 %}
6544 
6545 
6546 //----------Conditional Move---------------------------------------------------
6547 // Jump
6548 // dummy instruction for generating temp registers
6549 instruct jumpXtnd_offset(rRegL switch_val, immI2 shift, rRegI dest) %{
6550   match(Jump (LShiftL switch_val shift));
6551   ins_cost(350);
6552   predicate(false);


src/cpu/x86/vm/x86_64.ad
Index Unified diffs Context diffs Sdiffs Wdiffs Patch New Old Previous File Next File