< prev index next >

src/hotspot/cpu/x86/c1_LIRAssembler_x86.cpp

Print this page

  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "asm/macroAssembler.hpp"
  27 #include "asm/macroAssembler.inline.hpp"
  28 #include "c1/c1_CodeStubs.hpp"
  29 #include "c1/c1_Compilation.hpp"
  30 #include "c1/c1_LIRAssembler.hpp"
  31 #include "c1/c1_MacroAssembler.hpp"
  32 #include "c1/c1_Runtime1.hpp"
  33 #include "c1/c1_ValueStack.hpp"
  34 #include "ci/ciArrayKlass.hpp"
  35 #include "ci/ciInstance.hpp"


  36 #include "compiler/oopMap.hpp"
  37 #include "gc/shared/collectedHeap.hpp"
  38 #include "gc/shared/gc_globals.hpp"
  39 #include "nativeInst_x86.hpp"
  40 #include "oops/objArrayKlass.hpp"
  41 #include "runtime/frame.inline.hpp"
  42 #include "runtime/safepointMechanism.hpp"
  43 #include "runtime/sharedRuntime.hpp"
  44 #include "runtime/stubRoutines.hpp"
  45 #include "utilities/powerOfTwo.hpp"
  46 #include "vmreg_x86.inline.hpp"
  47 
  48 
  49 // These masks are used to provide 128-bit aligned bitmasks to the XMM
  50 // instructions, to allow sign-masking or sign-bit flipping.  They allow
  51 // fast versions of NegF/NegD and AbsF/AbsD.
  52 
  53 // Note: 'double' and 'long long' have 32-bits alignment on x86.
  54 static jlong* double_quadword(jlong *adr, jlong lo, jlong hi) {
  55   // Use the expression (adr)&(~0xF) to provide 128-bits aligned address
  56   // of 128-bits operands for SSE instructions.
  57   jlong *operand = (jlong*)(((intptr_t)adr) & ((intptr_t)(~0xF)));
  58   // Store the value to a 128-bits operand.
  59   operand[0] = lo;
  60   operand[1] = hi;
  61   return operand;
  62 }
  63 
  64 // Buffer for 128-bits masks used by SSE instructions.
  65 static jlong fp_signmask_pool[(4+1)*2]; // 4*128bits(data) + 128bits(alignment)
  66 
  67 // Static initialization during VM startup.
  68 static jlong *float_signmask_pool  = double_quadword(&fp_signmask_pool[1*2],         CONST64(0x7FFFFFFF7FFFFFFF),         CONST64(0x7FFFFFFF7FFFFFFF));
  69 static jlong *double_signmask_pool = double_quadword(&fp_signmask_pool[2*2],         CONST64(0x7FFFFFFFFFFFFFFF),         CONST64(0x7FFFFFFFFFFFFFFF));
  70 static jlong *float_signflip_pool  = double_quadword(&fp_signmask_pool[3*2], (jlong)UCONST64(0x8000000080000000), (jlong)UCONST64(0x8000000080000000));
  71 static jlong *double_signflip_pool = double_quadword(&fp_signmask_pool[4*2], (jlong)UCONST64(0x8000000000000000), (jlong)UCONST64(0x8000000000000000));
  72 
  73 
  74 NEEDS_CLEANUP // remove this definitions ?
  75 const Register IC_Klass    = rax;   // where the IC klass is cached
  76 const Register SYNC_header = rax;   // synchronization header
  77 const Register SHIFT_count = rcx;   // where count for shift operations must be
  78 
  79 #define __ _masm->
  80 
  81 
  82 static void select_different_registers(Register preserve,
  83                                        Register extra,
  84                                        Register &tmp1,
  85                                        Register &tmp2) {
  86   if (tmp1 == preserve) {
  87     assert_different_registers(tmp1, tmp2, extra);
  88     tmp1 = extra;
  89   } else if (tmp2 == preserve) {
  90     assert_different_registers(tmp1, tmp2, extra);
  91     tmp2 = extra;

 575   assert(src->is_constant(), "should not call otherwise");
 576   assert(dest->is_register(), "should not call otherwise");
 577   LIR_Const* c = src->as_constant_ptr();
 578 
 579   switch (c->type()) {
 580     case T_INT: {
 581       assert(patch_code == lir_patch_none, "no patching handled here");
 582       __ movl(dest->as_register(), c->as_jint());
 583       break;
 584     }
 585 
 586     case T_ADDRESS: {
 587       assert(patch_code == lir_patch_none, "no patching handled here");
 588       __ movptr(dest->as_register(), c->as_jint());
 589       break;
 590     }
 591 
 592     case T_LONG: {
 593       assert(patch_code == lir_patch_none, "no patching handled here");
 594 #ifdef _LP64








 595       __ movptr(dest->as_register_lo(), (intptr_t)c->as_jlong());
 596 #else
 597       __ movptr(dest->as_register_lo(), c->as_jint_lo());
 598       __ movptr(dest->as_register_hi(), c->as_jint_hi());
 599 #endif // _LP64
 600       break;
 601     }
 602 
 603     case T_OBJECT: {
 604       if (patch_code != lir_patch_none) {
 605         jobject2reg_with_patching(dest->as_register(), info);
 606       } else {
 607         __ movoop(dest->as_register(), c->as_jobject());
 608       }
 609       break;
 610     }
 611 
 612     case T_METADATA: {
 613       if (patch_code != lir_patch_none) {
 614         klass2reg_with_patching(dest->as_register(), info);

2406 #endif // _LP64
2407 
2408 
2409 void LIR_Assembler::intrinsic_op(LIR_Code code, LIR_Opr value, LIR_Opr tmp, LIR_Opr dest, LIR_Op* op) {
2410   if (value->is_double_xmm()) {
2411     switch(code) {
2412       case lir_abs :
2413         {
2414 #ifdef _LP64
2415           if (UseAVX > 2 && !VM_Version::supports_avx512vl()) {
2416             assert(tmp->is_valid(), "need temporary");
2417             __ vpandn(dest->as_xmm_double_reg(), tmp->as_xmm_double_reg(), value->as_xmm_double_reg(), 2);
2418           } else
2419 #endif
2420           {
2421             if (dest->as_xmm_double_reg() != value->as_xmm_double_reg()) {
2422               __ movdbl(dest->as_xmm_double_reg(), value->as_xmm_double_reg());
2423             }
2424             assert(!tmp->is_valid(), "do not need temporary");
2425             __ andpd(dest->as_xmm_double_reg(),
2426                      ExternalAddress((address)double_signmask_pool),
2427                      rscratch1);
2428           }
2429         }
2430         break;
2431 
2432       case lir_sqrt: __ sqrtsd(dest->as_xmm_double_reg(), value->as_xmm_double_reg()); break;
2433       // all other intrinsics are not available in the SSE instruction set, so FPU is used
2434       default      : ShouldNotReachHere();
2435     }
2436 
2437 #ifndef _LP64
2438   } else if (value->is_double_fpu()) {
2439     assert(value->fpu_regnrLo() == 0 && dest->fpu_regnrLo() == 0, "both must be on TOS");
2440     switch(code) {
2441       case lir_abs   : __ fabs() ; break;
2442       case lir_sqrt  : __ fsqrt(); break;
2443       default      : ShouldNotReachHere();
2444     }
2445 #endif // !_LP64
2446   } else if (code == lir_f2hf) {

3827       move_regs(lo, dest->as_register_lo());
3828       move_regs(hi, dest->as_register_hi());
3829     }
3830 #endif // _LP64
3831 
3832   } else if (dest->is_single_xmm()) {
3833 #ifdef _LP64
3834     if (UseAVX > 2 && !VM_Version::supports_avx512vl()) {
3835       assert(tmp->is_valid(), "need temporary");
3836       assert_different_registers(left->as_xmm_float_reg(), tmp->as_xmm_float_reg());
3837       __ vpxor(dest->as_xmm_float_reg(), tmp->as_xmm_float_reg(), left->as_xmm_float_reg(), 2);
3838     }
3839     else
3840 #endif
3841     {
3842       assert(!tmp->is_valid(), "do not need temporary");
3843       if (left->as_xmm_float_reg() != dest->as_xmm_float_reg()) {
3844         __ movflt(dest->as_xmm_float_reg(), left->as_xmm_float_reg());
3845       }
3846       __ xorps(dest->as_xmm_float_reg(),
3847                ExternalAddress((address)float_signflip_pool),
3848                rscratch1);
3849     }
3850   } else if (dest->is_double_xmm()) {
3851 #ifdef _LP64
3852     if (UseAVX > 2 && !VM_Version::supports_avx512vl()) {
3853       assert(tmp->is_valid(), "need temporary");
3854       assert_different_registers(left->as_xmm_double_reg(), tmp->as_xmm_double_reg());
3855       __ vpxor(dest->as_xmm_double_reg(), tmp->as_xmm_double_reg(), left->as_xmm_double_reg(), 2);
3856     }
3857     else
3858 #endif
3859     {
3860       assert(!tmp->is_valid(), "do not need temporary");
3861       if (left->as_xmm_double_reg() != dest->as_xmm_double_reg()) {
3862         __ movdbl(dest->as_xmm_double_reg(), left->as_xmm_double_reg());
3863       }
3864       __ xorpd(dest->as_xmm_double_reg(),
3865                ExternalAddress((address)double_signflip_pool),
3866                rscratch1);
3867     }
3868 #ifndef _LP64
3869   } else if (left->is_single_fpu() || left->is_double_fpu()) {
3870     assert(left->fpu() == 0, "arg must be on TOS");
3871     assert(dest->fpu() == 0, "dest must be TOS");
3872     __ fchs();
3873 #endif // !_LP64
3874 
3875   } else {
3876     ShouldNotReachHere();
3877   }
3878 }
3879 
3880 
3881 void LIR_Assembler::leal(LIR_Opr src, LIR_Opr dest, LIR_PatchCode patch_code, CodeEmitInfo* info) {
3882   assert(src->is_address(), "must be an address");
3883   assert(dest->is_register(), "must be a register");
3884 
3885   PatchingStub* patch = nullptr;

  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "asm/macroAssembler.hpp"
  27 #include "asm/macroAssembler.inline.hpp"
  28 #include "c1/c1_CodeStubs.hpp"
  29 #include "c1/c1_Compilation.hpp"
  30 #include "c1/c1_LIRAssembler.hpp"
  31 #include "c1/c1_MacroAssembler.hpp"
  32 #include "c1/c1_Runtime1.hpp"
  33 #include "c1/c1_ValueStack.hpp"
  34 #include "ci/ciArrayKlass.hpp"
  35 #include "ci/ciInstance.hpp"
  36 #include "ci/ciUtilities.hpp"
  37 #include "code/SCCache.hpp"
  38 #include "compiler/oopMap.hpp"
  39 #include "gc/shared/collectedHeap.hpp"
  40 #include "gc/shared/gc_globals.hpp"
  41 #include "nativeInst_x86.hpp"
  42 #include "oops/objArrayKlass.hpp"
  43 #include "runtime/frame.inline.hpp"
  44 #include "runtime/safepointMechanism.hpp"
  45 #include "runtime/sharedRuntime.hpp"
  46 #include "runtime/stubRoutines.hpp"
  47 #include "utilities/powerOfTwo.hpp"
  48 #include "vmreg_x86.inline.hpp"
  49 
  50 
  51 // These masks are used to provide 128-bit aligned bitmasks to the XMM
  52 // instructions, to allow sign-masking or sign-bit flipping.  They allow
  53 // fast versions of NegF/NegD and AbsF/AbsD.
  54 
  55 // Note: 'double' and 'long long' have 32-bits alignment on x86.
  56 static address double_quadword(jlong *adr, jlong lo, jlong hi) {
  57   // Use the expression (adr)&(~0xF) to provide 128-bits aligned address
  58   // of 128-bits operands for SSE instructions.
  59   jlong *operand = (jlong*)(((intptr_t)adr) & ((intptr_t)(~0xF)));
  60   // Store the value to a 128-bits operand.
  61   operand[0] = lo;
  62   operand[1] = hi;
  63   return (address)operand;
  64 }
  65 
  66 // Buffer for 128-bits masks used by SSE instructions.
  67 static jlong fp_signmask_pool[(4+1)*2]; // 4*128bits(data) + 128bits(alignment)
  68 
  69 // Static initialization during VM startup.
  70 address LIR_Assembler::float_signmask_pool  = double_quadword(&fp_signmask_pool[1*2],         CONST64(0x7FFFFFFF7FFFFFFF),         CONST64(0x7FFFFFFF7FFFFFFF));
  71 address LIR_Assembler::double_signmask_pool = double_quadword(&fp_signmask_pool[2*2],         CONST64(0x7FFFFFFFFFFFFFFF),         CONST64(0x7FFFFFFFFFFFFFFF));
  72 address LIR_Assembler::float_signflip_pool  = double_quadword(&fp_signmask_pool[3*2], (jlong)UCONST64(0x8000000080000000), (jlong)UCONST64(0x8000000080000000));
  73 address LIR_Assembler::double_signflip_pool = double_quadword(&fp_signmask_pool[4*2], (jlong)UCONST64(0x8000000000000000), (jlong)UCONST64(0x8000000000000000));
  74 
  75 
  76 NEEDS_CLEANUP // remove this definitions ?
  77 const Register IC_Klass    = rax;   // where the IC klass is cached
  78 const Register SYNC_header = rax;   // synchronization header
  79 const Register SHIFT_count = rcx;   // where count for shift operations must be
  80 
  81 #define __ _masm->
  82 
  83 
  84 static void select_different_registers(Register preserve,
  85                                        Register extra,
  86                                        Register &tmp1,
  87                                        Register &tmp2) {
  88   if (tmp1 == preserve) {
  89     assert_different_registers(tmp1, tmp2, extra);
  90     tmp1 = extra;
  91   } else if (tmp2 == preserve) {
  92     assert_different_registers(tmp1, tmp2, extra);
  93     tmp2 = extra;

 577   assert(src->is_constant(), "should not call otherwise");
 578   assert(dest->is_register(), "should not call otherwise");
 579   LIR_Const* c = src->as_constant_ptr();
 580 
 581   switch (c->type()) {
 582     case T_INT: {
 583       assert(patch_code == lir_patch_none, "no patching handled here");
 584       __ movl(dest->as_register(), c->as_jint());
 585       break;
 586     }
 587 
 588     case T_ADDRESS: {
 589       assert(patch_code == lir_patch_none, "no patching handled here");
 590       __ movptr(dest->as_register(), c->as_jint());
 591       break;
 592     }
 593 
 594     case T_LONG: {
 595       assert(patch_code == lir_patch_none, "no patching handled here");
 596 #ifdef _LP64
 597       if (SCCache::is_on_for_write()) {
 598         // SCA needs relocation info for card table base
 599         address b = c->as_pointer();
 600         if (is_card_table_address(b)) {
 601           __ lea(dest->as_register_lo(), ExternalAddress(b));
 602           break;
 603         }
 604       }
 605       __ movptr(dest->as_register_lo(), (intptr_t)c->as_jlong());
 606 #else
 607       __ movptr(dest->as_register_lo(), c->as_jint_lo());
 608       __ movptr(dest->as_register_hi(), c->as_jint_hi());
 609 #endif // _LP64
 610       break;
 611     }
 612 
 613     case T_OBJECT: {
 614       if (patch_code != lir_patch_none) {
 615         jobject2reg_with_patching(dest->as_register(), info);
 616       } else {
 617         __ movoop(dest->as_register(), c->as_jobject());
 618       }
 619       break;
 620     }
 621 
 622     case T_METADATA: {
 623       if (patch_code != lir_patch_none) {
 624         klass2reg_with_patching(dest->as_register(), info);

2416 #endif // _LP64
2417 
2418 
2419 void LIR_Assembler::intrinsic_op(LIR_Code code, LIR_Opr value, LIR_Opr tmp, LIR_Opr dest, LIR_Op* op) {
2420   if (value->is_double_xmm()) {
2421     switch(code) {
2422       case lir_abs :
2423         {
2424 #ifdef _LP64
2425           if (UseAVX > 2 && !VM_Version::supports_avx512vl()) {
2426             assert(tmp->is_valid(), "need temporary");
2427             __ vpandn(dest->as_xmm_double_reg(), tmp->as_xmm_double_reg(), value->as_xmm_double_reg(), 2);
2428           } else
2429 #endif
2430           {
2431             if (dest->as_xmm_double_reg() != value->as_xmm_double_reg()) {
2432               __ movdbl(dest->as_xmm_double_reg(), value->as_xmm_double_reg());
2433             }
2434             assert(!tmp->is_valid(), "do not need temporary");
2435             __ andpd(dest->as_xmm_double_reg(),
2436                      ExternalAddress(LIR_Assembler::double_signmask_pool),
2437                      rscratch1);
2438           }
2439         }
2440         break;
2441 
2442       case lir_sqrt: __ sqrtsd(dest->as_xmm_double_reg(), value->as_xmm_double_reg()); break;
2443       // all other intrinsics are not available in the SSE instruction set, so FPU is used
2444       default      : ShouldNotReachHere();
2445     }
2446 
2447 #ifndef _LP64
2448   } else if (value->is_double_fpu()) {
2449     assert(value->fpu_regnrLo() == 0 && dest->fpu_regnrLo() == 0, "both must be on TOS");
2450     switch(code) {
2451       case lir_abs   : __ fabs() ; break;
2452       case lir_sqrt  : __ fsqrt(); break;
2453       default      : ShouldNotReachHere();
2454     }
2455 #endif // !_LP64
2456   } else if (code == lir_f2hf) {

3837       move_regs(lo, dest->as_register_lo());
3838       move_regs(hi, dest->as_register_hi());
3839     }
3840 #endif // _LP64
3841 
3842   } else if (dest->is_single_xmm()) {
3843 #ifdef _LP64
3844     if (UseAVX > 2 && !VM_Version::supports_avx512vl()) {
3845       assert(tmp->is_valid(), "need temporary");
3846       assert_different_registers(left->as_xmm_float_reg(), tmp->as_xmm_float_reg());
3847       __ vpxor(dest->as_xmm_float_reg(), tmp->as_xmm_float_reg(), left->as_xmm_float_reg(), 2);
3848     }
3849     else
3850 #endif
3851     {
3852       assert(!tmp->is_valid(), "do not need temporary");
3853       if (left->as_xmm_float_reg() != dest->as_xmm_float_reg()) {
3854         __ movflt(dest->as_xmm_float_reg(), left->as_xmm_float_reg());
3855       }
3856       __ xorps(dest->as_xmm_float_reg(),
3857                ExternalAddress(LIR_Assembler::float_signflip_pool),
3858                rscratch1);
3859     }
3860   } else if (dest->is_double_xmm()) {
3861 #ifdef _LP64
3862     if (UseAVX > 2 && !VM_Version::supports_avx512vl()) {
3863       assert(tmp->is_valid(), "need temporary");
3864       assert_different_registers(left->as_xmm_double_reg(), tmp->as_xmm_double_reg());
3865       __ vpxor(dest->as_xmm_double_reg(), tmp->as_xmm_double_reg(), left->as_xmm_double_reg(), 2);
3866     }
3867     else
3868 #endif
3869     {
3870       assert(!tmp->is_valid(), "do not need temporary");
3871       if (left->as_xmm_double_reg() != dest->as_xmm_double_reg()) {
3872         __ movdbl(dest->as_xmm_double_reg(), left->as_xmm_double_reg());
3873       }
3874       __ xorpd(dest->as_xmm_double_reg(),
3875                ExternalAddress(LIR_Assembler::double_signflip_pool),
3876                rscratch1);
3877     }
3878 #ifndef _LP64
3879   } else if (left->is_single_fpu() || left->is_double_fpu()) {
3880     assert(left->fpu() == 0, "arg must be on TOS");
3881     assert(dest->fpu() == 0, "dest must be TOS");
3882     __ fchs();
3883 #endif // !_LP64
3884 
3885   } else {
3886     ShouldNotReachHere();
3887   }
3888 }
3889 
3890 
3891 void LIR_Assembler::leal(LIR_Opr src, LIR_Opr dest, LIR_PatchCode patch_code, CodeEmitInfo* info) {
3892   assert(src->is_address(), "must be an address");
3893   assert(dest->is_register(), "must be a register");
3894 
3895   PatchingStub* patch = nullptr;
< prev index next >