diff options
Diffstat (limited to 'Source/JavaScriptCore/assembler')
-rw-r--r-- | Source/JavaScriptCore/assembler/MIPSAssembler.h | 25 | ||||
-rw-r--r-- | Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h | 12 | ||||
-rw-r--r-- | Source/JavaScriptCore/assembler/MacroAssemblerSH4.h | 202 | ||||
-rw-r--r-- | Source/JavaScriptCore/assembler/SH4Assembler.h | 46 |
4 files changed, 266 insertions, 19 deletions
diff --git a/Source/JavaScriptCore/assembler/MIPSAssembler.h b/Source/JavaScriptCore/assembler/MIPSAssembler.h index 30f172fb8..026f87e52 100644 --- a/Source/JavaScriptCore/assembler/MIPSAssembler.h +++ b/Source/JavaScriptCore/assembler/MIPSAssembler.h @@ -825,6 +825,31 @@ public: #endif } + static void revertJumpToMove(void* instructionStart, RegisterID rt, int imm) + { + MIPSWord* insn = static_cast<MIPSWord*>(instructionStart) + 1; + ASSERT((*insn & 0xfc000000) == 0x34000000); + *insn = (*insn & 0xfc1f0000) | (imm & 0xffff); + cacheFlush(insn, sizeof(MIPSWord)); + } + + static void replaceWithJump(void* instructionStart, void* to) + { + MIPSWord* instruction = reinterpret_cast<MIPSWord*>(instructionStart); + intptr_t jumpTo = reinterpret_cast<intptr_t>(to); + + // lui + instruction[0] = 0x3c000000 | (MIPSRegisters::t9 << OP_SH_RT) | ((jumpTo >> 16) & 0xffff); + // ori + instruction[1] = 0x34000000 | (MIPSRegisters::t9 << OP_SH_RT) | (MIPSRegisters::t9 << OP_SH_RS) | (jumpTo & 0xffff); + // jr + instruction[2] = 0x00000008 | (MIPSRegisters::t9 << OP_SH_RS); + // nop + instruction[3] = 0x0; + + cacheFlush(instruction, sizeof(MIPSWord) * 4); + } + static void replaceWithLoad(void* instructionStart) { MIPSWord* insn = reinterpret_cast<MIPSWord*>(instructionStart); diff --git a/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h b/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h index 5b6da9663..4f81b4599 100644 --- a/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h +++ b/Source/JavaScriptCore/assembler/MacroAssemblerMIPS.h @@ -2244,7 +2244,17 @@ public: static bool canJumpReplacePatchableBranchPtrWithPatch() { return false; } - static CodeLocationLabel startOfPatchableBranchPtrWithPatch(CodeLocationDataLabelPtr label) + static CodeLocationLabel startOfBranchPtrWithPatchOnRegister(CodeLocationDataLabelPtr label) + { + return label.labelAtOffset(0); + } + + static void revertJumpReplacementToBranchPtrWithPatch(CodeLocationLabel instructionStart, RegisterID, void* initialValue) + { + MIPSAssembler::revertJumpToMove(instructionStart.dataLocation(), immTempRegister, reinterpret_cast<int>(initialValue) & 0xffff); + } + + static CodeLocationLabel startOfPatchableBranchPtrWithPatchOnAddress(CodeLocationDataLabelPtr) { UNREACHABLE_FOR_PLATFORM(); return CodeLocationLabel(); diff --git a/Source/JavaScriptCore/assembler/MacroAssemblerSH4.h b/Source/JavaScriptCore/assembler/MacroAssemblerSH4.h index ca410afa8..b6f3e6d57 100644 --- a/Source/JavaScriptCore/assembler/MacroAssemblerSH4.h +++ b/Source/JavaScriptCore/assembler/MacroAssemblerSH4.h @@ -602,6 +602,16 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) releaseScratch(scr); } + void load8Signed(BaseIndex address, RegisterID dest) + { + RegisterID scr = claimScratch(); + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + load8Signed(scr, address.offset, dest); + releaseScratch(scr); + } + void load32(BaseIndex address, RegisterID dest) { RegisterID scr = claimScratch(); @@ -649,6 +659,32 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) releaseScratch(scr); } + void load8Signed(RegisterID base, int offset, RegisterID dest) + { + if (!offset) { + m_assembler.movbMemReg(base, dest); + return; + } + + if ((offset > 0) && (offset < 64) && (dest == SH4Registers::r0)) { + m_assembler.movbMemReg(offset, base, dest); + return; + } + + if (base != dest) { + m_assembler.loadConstant((offset), dest); + m_assembler.addlRegReg(base, dest); + m_assembler.movbMemReg(dest, dest); + return; + } + + RegisterID scr = claimScratch(); + m_assembler.loadConstant((offset), scr); + m_assembler.addlRegReg(base, scr); + m_assembler.movbMemReg(scr, dest); + releaseScratch(scr); + } + void load8(RegisterID base, int offset, RegisterID dest) { if (!offset) { @@ -749,6 +785,11 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) extuw(dest, dest); } + void load16Signed(RegisterID src, RegisterID dest) + { + m_assembler.movwMemReg(src, dest); + } + void load16(RegisterID r0, RegisterID src, RegisterID dest) { ASSERT(r0 == SH4Registers::r0); @@ -756,6 +797,12 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) extuw(dest, dest); } + void load16Signed(RegisterID r0, RegisterID src, RegisterID dest) + { + ASSERT(r0 == SH4Registers::r0); + m_assembler.movwR0mr(src, dest); + } + void load16(BaseIndex address, RegisterID dest) { RegisterID scr = claimScratch(); @@ -775,6 +822,51 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) releaseScratch(scr); } + void load16Signed(BaseIndex address, RegisterID dest) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + + if (address.offset) + add32(TrustedImm32(address.offset), scr); + if (address.base == SH4Registers::r0) + load16Signed(address.base, scr, dest); + else { + add32(address.base, scr); + load16Signed(scr, dest); + } + + releaseScratch(scr); + } + + void store8(RegisterID src, BaseIndex address) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + + m_assembler.movbRegMem(src, scr); + + releaseScratch(scr); + } + + void store16(RegisterID src, BaseIndex address) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + + m_assembler.movwRegMem(src, scr); + + releaseScratch(scr); + } + void store32(RegisterID src, ImplicitAddress address) { RegisterID scr = claimScratch(); @@ -900,13 +992,59 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) return result; } - // Floating-point operations + // Floating-point operations static bool supportsFloatingPoint() { return true; } static bool supportsFloatingPointTruncate() { return true; } static bool supportsFloatingPointSqrt() { return true; } static bool supportsFloatingPointAbs() { return false; } + void moveDoubleToInts(FPRegisterID src, RegisterID dest1, RegisterID dest2) + { + m_assembler.fldsfpul((FPRegisterID)(src + 1)); + m_assembler.stsfpulReg(dest1); + m_assembler.fldsfpul(src); + m_assembler.stsfpulReg(dest2); + } + + void moveIntsToDouble(RegisterID src1, RegisterID src2, FPRegisterID dest, FPRegisterID scratch) + { + UNUSED_PARAM(scratch); + m_assembler.ldsrmfpul(src1); + m_assembler.fstsfpul((FPRegisterID)(dest + 1)); + m_assembler.ldsrmfpul(src2); + m_assembler.fstsfpul(dest); + } + + void loadFloat(BaseIndex address, FPRegisterID dest) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + if (address.offset) + add32(TrustedImm32(address.offset), scr); + + m_assembler.fmovsReadrm(scr, dest); + releaseScratch(scr); + } + + void loadDouble(BaseIndex address, FPRegisterID dest) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + if (address.offset) + add32(TrustedImm32(address.offset), scr); + + m_assembler.fmovsReadrminc(scr, (FPRegisterID)(dest + 1)); + m_assembler.fmovsReadrm(scr, dest); + releaseScratch(scr); + } + void loadDouble(ImplicitAddress address, FPRegisterID dest) { RegisterID scr = claimScratch(); @@ -935,6 +1073,21 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) releaseScratch(scr); } + void storeFloat(FPRegisterID src, BaseIndex address) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + if (address.offset) + add32(TrustedImm32(address.offset), scr); + + m_assembler.fmovsWriterm(src, scr); + + releaseScratch(scr); + } + void storeDouble(FPRegisterID src, ImplicitAddress address) { RegisterID scr = claimScratch(); @@ -946,11 +1099,44 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) releaseScratch(scr); } + void storeDouble(FPRegisterID src, BaseIndex address) + { + RegisterID scr = claimScratch(); + + move(address.index, scr); + lshift32(TrustedImm32(address.scale), scr); + add32(address.base, scr); + if (address.offset) + add32(TrustedImm32(address.offset), scr); + + m_assembler.fmovsWriterm((FPRegisterID)(src + 1), scr); + m_assembler.addlImm8r(4, scr); + m_assembler.fmovsWriterm(src, scr); + + releaseScratch(scr); + } + + void addDouble(FPRegisterID op1, FPRegisterID op2, FPRegisterID dest) + { + if (op1 == dest) + m_assembler.daddRegReg(op2, dest); + else { + m_assembler.dmovRegReg(op1, dest); + m_assembler.daddRegReg(op2, dest); + } + } + void addDouble(FPRegisterID src, FPRegisterID dest) { m_assembler.daddRegReg(src, dest); } + void addDouble(AbsoluteAddress address, FPRegisterID dest) + { + loadDouble(address.m_ptr, fscratch); + addDouble(fscratch, dest); + } + void addDouble(Address address, FPRegisterID dest) { loadDouble(address, fscratch); @@ -984,6 +1170,18 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) m_assembler.ddivRegReg(src, dest); } + void convertFloatToDouble(FPRegisterID src, FPRegisterID dst) + { + m_assembler.fldsfpul(src); + m_assembler.dcnvsd(dst); + } + + void convertDoubleToFloat(FPRegisterID src, FPRegisterID dst) + { + m_assembler.dcnvds(src); + m_assembler.fstsfpul(dst); + } + void convertInt32ToDouble(RegisterID src, FPRegisterID dest) { m_assembler.ldsrmfpul(src); @@ -1893,7 +2091,7 @@ void or32(TrustedImm32 imm, RegisterID src, RegisterID dest) void urshift32(RegisterID src, TrustedImm32 shiftamount, RegisterID dest) { if (src != dest) - move(src, dest); + move(src, dest); urshift32(shiftamount, dest); } diff --git a/Source/JavaScriptCore/assembler/SH4Assembler.h b/Source/JavaScriptCore/assembler/SH4Assembler.h index 3dbde2fa5..2cd0aa82e 100644 --- a/Source/JavaScriptCore/assembler/SH4Assembler.h +++ b/Source/JavaScriptCore/assembler/SH4Assembler.h @@ -166,6 +166,7 @@ enum { FMOVS_WRITE_RN_DEC_OPCODE = 0xf00b, FMOVS_WRITE_R0RN_OPCODE = 0xf007, FCNVDS_DRM_FPUL_OPCODE = 0xf0bd, + FCNVSD_FPUL_DRN_OPCODE = 0xf0ad, LDS_RM_FPUL_OPCODE = 0x405a, FLDS_FRM_FPUL_OPCODE = 0xf01d, STS_FPUL_RN_OPCODE = 0x005a, @@ -326,8 +327,9 @@ public: padForAlign32 = 0x00090009, }; - enum JumpType { JumpFar, - JumpNear + enum JumpType { + JumpFar, + JumpNear }; SH4Assembler() @@ -491,14 +493,14 @@ public: void sublRegReg(RegisterID src, RegisterID dst) { - uint16_t opc = getOpcodeGroup1(SUB_OPCODE, dst, src); - oneShortOp(opc); + uint16_t opc = getOpcodeGroup1(SUB_OPCODE, dst, src); + oneShortOp(opc); } void subvlRegReg(RegisterID src, RegisterID dst) { - uint16_t opc = getOpcodeGroup1(SUBV_OPCODE, dst, src); - oneShortOp(opc); + uint16_t opc = getOpcodeGroup1(SUBV_OPCODE, dst, src); + oneShortOp(opc); } void xorlRegReg(RegisterID src, RegisterID dst) @@ -803,7 +805,7 @@ public: oneShortOp(opc); } - void floatfpulfrn(RegisterID src) + void floatfpulfrn(FPRegisterID src) { uint16_t opc = getOpcodeGroup2(FLOAT_OPCODE, src); oneShortOp(opc, true, false); @@ -857,13 +859,13 @@ public: oneShortOp(opc, true, false); } - void fldsfpul(RegisterID src) + void fldsfpul(FPRegisterID src) { uint16_t opc = getOpcodeGroup2(FLDS_FRM_FPUL_OPCODE, src); oneShortOp(opc); } - void fstsfpul(RegisterID src) + void fstsfpul(FPRegisterID src) { uint16_t opc = getOpcodeGroup2(FSTS_FPUL_FRN_OPCODE, src); oneShortOp(opc); @@ -889,6 +891,12 @@ public: oneShortOp(opc); } + void dcnvsd(FPRegisterID dst) + { + uint16_t opc = getOpcodeGroup7(FCNVSD_FPUL_DRN_OPCODE, dst >> 1); + oneShortOp(opc); + } + void dcmppeq(FPRegisterID src, FPRegisterID dst) { uint16_t opc = getOpcodeGroup8(FCMPEQ_OPCODE, dst >> 1, src >> 1); @@ -1082,6 +1090,12 @@ public: oneShortOp(getOpcodeGroup4(MOVL_READ_OFFRM_OPCODE, dst, base, offset)); } + void movbRegMem(RegisterID src, RegisterID base) + { + uint16_t opc = getOpcodeGroup1(MOVB_WRITE_RN_OPCODE, base, src); + oneShortOp(opc); + } + void movbMemReg(int offset, RegisterID base, RegisterID dst) { ASSERT(dst == SH4Registers::r0); @@ -1253,7 +1267,7 @@ public: int sizeOfConstantPool() { - return m_buffer.sizeOfConstantPool(); + return m_buffer.sizeOfConstantPool(); } AssemblerLabel align(int alignment) @@ -1305,7 +1319,7 @@ public: *instructionPtr = instruction; printBlockInstr(instructionPtr - 2, from.m_offset, 3); return; - } + } /* MOV #imm, reg => LDR reg braf @reg braf @reg @@ -1592,7 +1606,7 @@ public: size_t codeSize() const { return m_buffer.codeSize(); } #ifdef SH4_ASSEMBLER_TRACING - static void printInstr(uint16_t opc, unsigned int size, bool isdoubleInst = true) + static void printInstr(uint16_t opc, unsigned size, bool isdoubleInst = true) { if (!getenv("JavaScriptCoreDumpJIT")) return; @@ -2073,16 +2087,16 @@ public: WTF::dataLogFV(format, args); } - static void printBlockInstr(uint16_t* first, unsigned int offset, int nbInstr) + static void printBlockInstr(uint16_t* first, unsigned offset, int nbInstr) { printfStdoutInstr(">> repatch instructions after link\n"); for (int i = 0; i <= nbInstr; i++) - printInstr(*(first + i), offset + i); + printInstr(*(first + i), offset + i); printfStdoutInstr(">> end repatch\n"); } #else - static void printInstr(uint16_t opc, unsigned int size, bool isdoubleInst = true) {}; - static void printBlockInstr(uint16_t* first, unsigned int offset, int nbInstr) {}; + static void printInstr(uint16_t opc, unsigned size, bool isdoubleInst = true) { }; + static void printBlockInstr(uint16_t* first, unsigned offset, int nbInstr) { }; #endif static void replaceWithLoad(void* instructionStart) |