Diff
Modified: trunk/Source/_javascript_Core/ChangeLog (99894 => 99895)
--- trunk/Source/_javascript_Core/ChangeLog 2011-11-10 21:34:00 UTC (rev 99894)
+++ trunk/Source/_javascript_Core/ChangeLog 2011-11-10 21:41:04 UTC (rev 99895)
@@ -1,5 +1,21 @@
2011-11-10 Gavin Barraclough <[email protected]>
+ Add ARMv7 register info for the DFG JIT
+ https://bugs.webkit.org/show_bug.cgi?id=72050
+
+ Reviewed by Geoff Garen.
+
+ * dfg/DFGFPRInfo.h:
+ (JSC::DFG::FPRInfo::toRegister):
+ (JSC::DFG::FPRInfo::toIndex):
+ (JSC::DFG::FPRInfo::debugName):
+ * dfg/DFGGPRInfo.h:
+ (JSC::DFG::GPRInfo::toRegister):
+ (JSC::DFG::GPRInfo::toIndex):
+ (JSC::DFG::GPRInfo::debugName):
+
+2011-11-10 Gavin Barraclough <[email protected]>
+
#ifdef CPU(X86) specific div/mod code in DFGSpeculativeJIT32_64
https://bugs.webkit.org/show_bug.cgi?id=72047
Modified: trunk/Source/_javascript_Core/dfg/DFGFPRInfo.h (99894 => 99895)
--- trunk/Source/_javascript_Core/dfg/DFGFPRInfo.h 2011-11-10 21:34:00 UTC (rev 99894)
+++ trunk/Source/_javascript_Core/dfg/DFGFPRInfo.h 2011-11-10 21:41:04 UTC (rev 99895)
@@ -36,6 +36,8 @@
typedef MacroAssembler::FPRegisterID FPRReg;
#define InvalidFPRReg ((FPRReg)-1)
+#if CPU(X86) || CPU(X86_64)
+
class FPRInfo {
public:
typedef FPRReg RegisterType;
@@ -48,11 +50,15 @@
static const FPRReg fpRegT3 = X86Registers::xmm3;
static const FPRReg fpRegT4 = X86Registers::xmm4;
static const FPRReg fpRegT5 = X86Registers::xmm5;
- // These constants provide the names for the general purpose argument & return value registers.
+#if CPU(X86_64)
+ // Only X86_64 passes aguments in xmm registers
static const FPRReg argumentFPR0 = X86Registers::xmm0; // fpRegT0
static const FPRReg argumentFPR1 = X86Registers::xmm1; // fpRegT1
static const FPRReg argumentFPR2 = X86Registers::xmm2; // fpRegT2
static const FPRReg argumentFPR3 = X86Registers::xmm3; // fpRegT3
+#endif
+ // On X86 the return will actually be on the x87 stack,
+ // so we'll copy to xmm0 for sanity!
static const FPRReg returnValueFPR = X86Registers::xmm0; // fpRegT0
// FPRReg mapping is direct, the machine regsiter numbers can
@@ -96,6 +102,67 @@
#endif
};
+#endif
+
+#if CPU(ARM_THUMB2)
+
+class FPRInfo {
+public:
+ typedef FPRReg RegisterType;
+ static const unsigned numberOfRegisters = 6;
+
+ // Temporary registers.
+ // d7 is use by the MacroAssembler as fpTempRegister.
+ static const FPRReg fpRegT0 = ARMRegisters::d0;
+ static const FPRReg fpRegT1 = ARMRegisters::d1;
+ static const FPRReg fpRegT2 = ARMRegisters::d2;
+ static const FPRReg fpRegT3 = ARMRegisters::d3;
+ static const FPRReg fpRegT4 = ARMRegisters::d4;
+ static const FPRReg fpRegT5 = ARMRegisters::d5;
+ // ARMv7 doesn't pass arguments in fp registers. The return
+ // value is also actually in integer registers, for now
+ // we'll return in d0 for simplicity.
+ static const FPRReg returnValueFPR = ARMRegisters::d0; // fpRegT0
+
+ // FPRReg mapping is direct, the machine regsiter numbers can
+ // be used directly as indices into the FPR RegisterBank.
+ COMPILE_ASSERT(ARMRegisters::d0 == 0, d0_is_0);
+ COMPILE_ASSERT(ARMRegisters::d1 == 1, d1_is_1);
+ COMPILE_ASSERT(ARMRegisters::d2 == 2, d2_is_2);
+ COMPILE_ASSERT(ARMRegisters::d3 == 3, d3_is_3);
+ COMPILE_ASSERT(ARMRegisters::d4 == 4, d4_is_4);
+ COMPILE_ASSERT(ARMRegisters::d5 == 5, d5_is_5);
+ static FPRReg toRegister(unsigned index)
+ {
+ return (FPRReg)index;
+ }
+ static unsigned toIndex(FPRReg reg)
+ {
+ return (unsigned)reg;
+ }
+
+#ifndef NDEBUG
+ static const char* debugName(FPRReg reg)
+ {
+ ASSERT(reg != InvalidFPRReg);
+ ASSERT(reg < 32);
+ static const char* nameForRegister[32] = {
+ "d0", "d1", "d2", "d3",
+ "d4", "d5", "d6", "d7",
+ "d8", "d9", "d10", "d11",
+ "d12", "d13", "d14", "d15"
+ "d16", "d17", "d18", "d19"
+ "d20", "d21", "d22", "d23"
+ "d24", "d25", "d26", "d27"
+ "d28", "d29", "d30", "d31"
+ };
+ return nameForRegister[reg];
+ }
+#endif
+};
+
+#endif
+
typedef RegisterBank<FPRInfo>::iterator fpr_iterator;
} } // namespace JSC::DFG
Modified: trunk/Source/_javascript_Core/dfg/DFGGPRInfo.h (99894 => 99895)
--- trunk/Source/_javascript_Core/dfg/DFGGPRInfo.h 2011-11-10 21:34:00 UTC (rev 99894)
+++ trunk/Source/_javascript_Core/dfg/DFGGPRInfo.h 2011-11-10 21:41:04 UTC (rev 99895)
@@ -251,22 +251,23 @@
#endif
#if CPU(X86)
+#define NUMBER_OF_ARGUMENT_REGISTERS 0
class GPRInfo {
public:
typedef GPRReg RegisterType;
static const unsigned numberOfRegisters = 5;
- // These registers match the baseline JIT.
- static const GPRReg cachedResultRegister = X86Registers::eax;
- static const GPRReg cachedResultRegister2 = X86Registers::edx;
- static const GPRReg callFrameRegister = X86Registers::edi;
// Temporary registers.
static const GPRReg regT0 = X86Registers::eax;
static const GPRReg regT1 = X86Registers::edx;
static const GPRReg regT2 = X86Registers::ecx;
static const GPRReg regT3 = X86Registers::ebx;
static const GPRReg regT4 = X86Registers::esi;
+ // These registers match the baseline JIT.
+ static const GPRReg cachedResultRegister = regT0;
+ static const GPRReg cachedResultRegister2 = regT1;
+ static const GPRReg callFrameRegister = X86Registers::edi;
// These constants provide the names for the general purpose argument & return value registers.
static const GPRReg argumentGPR0 = X86Registers::ecx; // regT2
static const GPRReg argumentGPR1 = X86Registers::edx; // regT1
@@ -310,6 +311,7 @@
#endif
#if CPU(X86_64)
+#define NUMBER_OF_ARGUMENT_REGISTERS 6
class GPRInfo {
public:
@@ -337,6 +339,8 @@
static const GPRReg argumentGPR1 = X86Registers::esi; // regT5
static const GPRReg argumentGPR2 = X86Registers::edx; // regT1
static const GPRReg argumentGPR3 = X86Registers::ecx; // regT2
+ static const GPRReg argumentGPR4 = X86Registers::r8; // regT6
+ static const GPRReg argumentGPR5 = X86Registers::r9; // regT7
static const GPRReg returnValueGPR = X86Registers::eax; // regT0
static const GPRReg returnValueGPR2 = X86Registers::edx; // regT1
@@ -378,6 +382,78 @@
#endif
+#if CPU(ARM_THUMB2)
+#define NUMBER_OF_ARGUMENT_REGISTERS 4
+
+class GPRInfo {
+public:
+ typedef GPRReg RegisterType;
+ static const unsigned numberOfRegisters = 9;
+
+ // Temporary registers.
+ static const GPRReg regT0 = ARMRegisters::r0;
+ static const GPRReg regT1 = ARMRegisters::r1;
+ static const GPRReg regT2 = ARMRegisters::r2;
+ static const GPRReg regT3 = ARMRegisters::r4;
+ static const GPRReg regT4 = ARMRegisters::r7;
+ static const GPRReg regT5 = ARMRegisters::r8;
+ static const GPRReg regT6 = ARMRegisters::r9;
+ static const GPRReg regT7 = ARMRegisters::r10;
+ static const GPRReg regT8 = ARMRegisters::r11;
+ // These registers match the baseline JIT.
+ static const GPRReg cachedResultRegister = regT0;
+ static const GPRReg cachedResultRegister2 = regT1;
+ static const GPRReg callFrameRegister = ARMRegisters::r5;
+ // These constants provide the names for the general purpose argument & return value registers.
+ static const GPRReg argumentGPR0 = ARMRegisters::r0; // regT0
+ static const GPRReg argumentGPR1 = ARMRegisters::r1; // regT1
+ static const GPRReg argumentGPR2 = ARMRegisters::r2; // regT2
+ // FIXME: r3 is currently used be the MacroAssembler as a temporary - it seems
+ // This could threoretically be a problem if theis is used in code generation
+ // between the arguments being set up, and the call being made. That said,
+ // any change introducing a problem here is likely to be immediately apparent!
+ static const GPRReg argumentGPR3 = ARMRegisters::r3; // FIXME!
+ static const GPRReg returnValueGPR = ARMRegisters::r0; // regT0
+ static const GPRReg returnValueGPR2 = ARMRegisters::r1; // regT1
+
+ static GPRReg toRegister(unsigned index)
+ {
+ ASSERT(index < numberOfRegisters);
+ static const GPRReg registerForIndex[numberOfRegisters] = { regT0, regT1, regT2, regT3, regT4, regT5, regT6, regT7, regT8 };
+ return registerForIndex[index];
+ }
+
+ static unsigned toIndex(GPRReg reg)
+ {
+ ASSERT(reg != InvalidGPRReg);
+ ASSERT(reg < 16);
+ static const unsigned indexForRegister[16] = { 0, 1, 2, InvalidIndex, 3, InvalidIndex, InvalidIndex, 4, 5, 6, 7, 8, InvalidIndex, InvalidIndex, InvalidIndex, InvalidIndex };
+ unsigned result = indexForRegister[reg];
+ ASSERT(result != InvalidIndex);
+ return result;
+ }
+
+#ifndef NDEBUG
+ static const char* debugName(GPRReg reg)
+ {
+ ASSERT(reg != InvalidGPRReg);
+ ASSERT(reg < 16);
+ static const char* nameForRegister[16] = {
+ "r0", "r1", "r2", "r3",
+ "r4", "r5", "r6", "r7",
+ "r8", "r9", "r10", "r11",
+ "r12", "r13", "r14", "r15"
+ };
+ return nameForRegister[reg];
+ }
+#endif
+private:
+
+ static const unsigned InvalidIndex = 0xffffffff;
+};
+
+#endif
+
typedef RegisterBank<GPRInfo>::iterator gpr_iterator;
} } // namespace JSC::DFG