BaseAssembler-x86.h (6105B)
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- 2 * vim: set ts=8 sts=2 et sw=2 tw=80: 3 * This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #ifndef jit_x86_BaseAssembler_x86_h 8 #define jit_x86_BaseAssembler_x86_h 9 10 #include "jit/x86-shared/BaseAssembler-x86-shared.h" 11 12 namespace js { 13 namespace jit { 14 15 namespace X86Encoding { 16 17 class BaseAssemblerX86 : public BaseAssembler { 18 public: 19 // Arithmetic operations: 20 21 void adcl_ir(int32_t imm, RegisterID dst) { 22 spew("adcl $%d, %s", imm, GPReg32Name(dst)); 23 if (CAN_SIGN_EXTEND_8_32(imm)) { 24 m_formatter.oneByteOp(OP_GROUP1_EvIb, dst, GROUP1_OP_ADC); 25 m_formatter.immediate8s(imm); 26 } else { 27 m_formatter.oneByteOp(OP_GROUP1_EvIz, dst, GROUP1_OP_ADC); 28 m_formatter.immediate32(imm); 29 } 30 } 31 32 void adcl_im(int32_t imm, const void* addr) { 33 spew("adcl %d, %p", imm, addr); 34 if (CAN_SIGN_EXTEND_8_32(imm)) { 35 m_formatter.oneByteOp(OP_GROUP1_EvIb, addr, GROUP1_OP_ADC); 36 m_formatter.immediate8s(imm); 37 } else { 38 m_formatter.oneByteOp(OP_GROUP1_EvIz, addr, GROUP1_OP_ADC); 39 m_formatter.immediate32(imm); 40 } 41 } 42 43 void adcl_rr(RegisterID src, RegisterID dst) { 44 spew("adcl %s, %s", GPReg32Name(src), GPReg32Name(dst)); 45 m_formatter.oneByteOp(OP_ADC_GvEv, src, dst); 46 } 47 48 void adcl_mr(int32_t offset, RegisterID base, RegisterID dst) { 49 spew("adcl " MEM_ob ", %s", ADDR_ob(offset, base), GPReg32Name(dst)); 50 m_formatter.oneByteOp(OP_ADC_GvEv, offset, base, dst); 51 } 52 53 void adcl_mr(int32_t offset, RegisterID base, RegisterID index, int scale, 54 RegisterID dst) { 55 spew("adcl " MEM_obs ", %s", ADDR_obs(offset, base, index, scale), 56 GPReg32Name(dst)); 57 m_formatter.oneByteOp(OP_ADC_GvEv, offset, base, index, scale, dst); 58 } 59 60 void sbbl_ir(int32_t imm, RegisterID dst) { 61 spew("sbbl $%d, %s", imm, GPReg32Name(dst)); 62 if (CAN_SIGN_EXTEND_8_32(imm)) { 63 m_formatter.oneByteOp(OP_GROUP1_EvIb, dst, GROUP1_OP_SBB); 64 m_formatter.immediate8s(imm); 65 } else { 66 m_formatter.oneByteOp(OP_GROUP1_EvIz, dst, GROUP1_OP_SBB); 67 m_formatter.immediate32(imm); 68 } 69 } 70 71 void sbbl_rr(RegisterID src, RegisterID dst) { 72 spew("sbbl %s, %s", GPReg32Name(src), GPReg32Name(dst)); 73 m_formatter.oneByteOp(OP_SBB_GvEv, src, dst); 74 } 75 76 void sbbl_mr(int32_t offset, RegisterID base, RegisterID dst) { 77 spew("sbbl " MEM_ob ", %s", ADDR_ob(offset, base), GPReg32Name(dst)); 78 m_formatter.oneByteOp(OP_SBB_GvEv, offset, base, dst); 79 } 80 81 void sbbl_mr(int32_t offset, RegisterID base, RegisterID index, int scale, 82 RegisterID dst) { 83 spew("sbbl " MEM_obs ", %s", ADDR_obs(offset, base, index, scale), 84 GPReg32Name(dst)); 85 m_formatter.oneByteOp(OP_SBB_GvEv, offset, base, index, scale, dst); 86 } 87 88 using BaseAssembler::andl_im; 89 void andl_im(int32_t imm, const void* addr) { 90 spew("andl $0x%x, %p", imm, addr); 91 if (CAN_SIGN_EXTEND_8_32(imm)) { 92 m_formatter.oneByteOp(OP_GROUP1_EvIb, addr, GROUP1_OP_AND); 93 m_formatter.immediate8s(imm); 94 } else { 95 m_formatter.oneByteOp(OP_GROUP1_EvIz, addr, GROUP1_OP_AND); 96 m_formatter.immediate32(imm); 97 } 98 } 99 100 using BaseAssembler::orl_im; 101 void orl_im(int32_t imm, const void* addr) { 102 spew("orl $0x%x, %p", imm, addr); 103 if (CAN_SIGN_EXTEND_8_32(imm)) { 104 m_formatter.oneByteOp(OP_GROUP1_EvIb, addr, GROUP1_OP_OR); 105 m_formatter.immediate8s(imm); 106 } else { 107 m_formatter.oneByteOp(OP_GROUP1_EvIz, addr, GROUP1_OP_OR); 108 m_formatter.immediate32(imm); 109 } 110 } 111 112 using BaseAssembler::subl_im; 113 void subl_im(int32_t imm, const void* addr) { 114 spew("subl $%d, %p", imm, addr); 115 if (CAN_SIGN_EXTEND_8_32(imm)) { 116 m_formatter.oneByteOp(OP_GROUP1_EvIb, addr, GROUP1_OP_SUB); 117 m_formatter.immediate8s(imm); 118 } else { 119 m_formatter.oneByteOp(OP_GROUP1_EvIz, addr, GROUP1_OP_SUB); 120 m_formatter.immediate32(imm); 121 } 122 } 123 124 void shldl_irr(int32_t imm, RegisterID src, RegisterID dst) { 125 MOZ_ASSERT(imm < 32); 126 spew("shldl $%d, %s, %s", imm, GPReg32Name(src), GPReg32Name(dst)); 127 m_formatter.twoByteOp8(OP2_SHLD, dst, src); 128 m_formatter.immediate8u(imm); 129 } 130 131 void shrdl_irr(int32_t imm, RegisterID src, RegisterID dst) { 132 MOZ_ASSERT(imm < 32); 133 spew("shrdl $%d, %s, %s", imm, GPReg32Name(src), GPReg32Name(dst)); 134 m_formatter.twoByteOp8(OP2_SHRD, dst, src); 135 m_formatter.immediate8u(imm); 136 } 137 138 // SSE operations: 139 140 using BaseAssembler::vcvtsi2sd_mr; 141 void vcvtsi2sd_mr(const void* address, XMMRegisterID src0, 142 XMMRegisterID dst) { 143 twoByteOpSimd("vcvtsi2sd", VEX_SD, OP2_CVTSI2SD_VsdEd, address, src0, dst); 144 } 145 146 using BaseAssembler::vmovaps_mr; 147 void vmovaps_mr(const void* address, XMMRegisterID dst) { 148 twoByteOpSimd("vmovaps", VEX_PS, OP2_MOVAPS_VsdWsd, address, invalid_xmm, 149 dst); 150 } 151 152 using BaseAssembler::vmovdqa_mr; 153 void vmovdqa_mr(const void* address, XMMRegisterID dst) { 154 twoByteOpSimd("vmovdqa", VEX_PD, OP2_MOVDQ_VdqWdq, address, invalid_xmm, 155 dst); 156 } 157 158 void vhaddpd_rr(XMMRegisterID src1, XMMRegisterID src0, XMMRegisterID dst) { 159 twoByteOpSimd("vhaddpd", VEX_PD, OP2_HADDPD, src1, src0, dst); 160 } 161 162 void vsubpd_rr(XMMRegisterID src1, XMMRegisterID src0, XMMRegisterID dst) { 163 twoByteOpSimd("vsubpd", VEX_PD, OP2_SUBPS_VpsWps, src1, src0, dst); 164 } 165 166 void fild_m(int32_t offset, RegisterID base) { 167 m_formatter.oneByteOp(OP_FILD, offset, base, FILD_OP_64); 168 } 169 170 // Misc instructions: 171 172 void pusha() { 173 spew("pusha"); 174 m_formatter.oneByteOp(OP_PUSHA); 175 } 176 177 void popa() { 178 spew("popa"); 179 m_formatter.oneByteOp(OP_POPA); 180 } 181 }; 182 183 using BaseAssemblerSpecific = BaseAssemblerX86; 184 185 } // namespace X86Encoding 186 187 } // namespace jit 188 } // namespace js 189 190 #endif /* jit_x86_BaseAssembler_x86_h */