[JAEGER] Added JSOP_ARGINC,ARGDEC,INCARG,DECARG.

This commit is contained in:
David Anderson
2010-06-10 17:29:57 -07:00
parent 1241be309e
commit 36f9e6e948
8 changed files with 95 additions and 13 deletions

View File

@@ -252,10 +252,10 @@ OPDEF(JSOP_DEFSHARP, 93, "defsharp", NULL, 5, 0, 0, 0, JOF_UINT16
OPDEF(JSOP_USESHARP, 94, "usesharp", NULL, 5, 0, 1, 0, JOF_UINT16PAIR|JOF_SHARPSLOT)
/* Fast inc/dec ops for args and locals. */
OPDEF(JSOP_INCARG, 95, "incarg", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_INC)
OPDEF(JSOP_DECARG, 96, "decarg", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_DEC)
OPDEF(JSOP_ARGINC, 97, "arginc", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_INC|JOF_POST)
OPDEF(JSOP_ARGDEC, 98, "argdec", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_DEC|JOF_POST)
OPDEF(JSOP_INCARG, 95, "incarg", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_INC|JOF_TMPSLOT2)
OPDEF(JSOP_DECARG, 96, "decarg", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_DEC|JOF_TMPSLOT2)
OPDEF(JSOP_ARGINC, 97, "arginc", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_INC|JOF_POST|JOF_TMPSLOT2)
OPDEF(JSOP_ARGDEC, 98, "argdec", NULL, 3, 0, 1, 15, JOF_QARG |JOF_NAME|JOF_DEC|JOF_POST|JOF_TMPSLOT2)
OPDEF(JSOP_INCLOCAL, 99, "inclocal", NULL, 3, 0, 1, 15, JOF_LOCAL|JOF_NAME|JOF_INC)
OPDEF(JSOP_DECLOCAL, 100,"declocal", NULL, 3, 0, 1, 15, JOF_LOCAL|JOF_NAME|JOF_DEC)

View File

@@ -885,6 +885,23 @@ mjit::Compiler::generateMethod()
}
END_CASE(JSOP_INITELEM)
BEGIN_CASE(JSOP_INCARG)
BEGIN_CASE(JSOP_DECARG)
BEGIN_CASE(JSOP_ARGINC)
BEGIN_CASE(JSOP_ARGDEC)
{
jsbytecode *next = &PC[JSOP_ARGINC_LENGTH];
bool popped = false;
if (JSOp(*next) == JSOP_POP && !analysis[next].nincoming)
popped = true;
jsop_arginc(op, GET_SLOTNO(PC), popped);
PC += JSOP_ARGINC_LENGTH;
if (popped)
PC += JSOP_POP_LENGTH;
break;
}
END_CASE(JSOP_ARGDEC)
BEGIN_CASE(JSOP_FORNAME)
prepareStubCall();
masm.move(ImmPtr(script->getAtom(fullAtomIndex(PC))), Registers::ArgReg1);

View File

@@ -151,6 +151,7 @@ class Compiler
void jsop_objtostr();
void jsop_not();
void jsop_typeof();
void jsop_arginc(JSOp op, uint32 slot, bool popped);
#define STUB_CALL_TYPE(type) \
Call stubCall(type stub, Uses uses, Defs defs) { \

View File

@@ -378,6 +378,14 @@ FrameState::syncData(const FrameEntry *fe, Address to, Assembler &masm) const
}
}
inline void
FrameState::forgetType(FrameEntry *fe)
{
JS_ASSERT(fe->isTypeKnown() && !fe->type.synced());
syncType(fe, addressOf(fe), masm);
fe->type.setMemory();
}
inline void
FrameState::learnType(FrameEntry *fe, JSValueMask32 tag)
{

View File

@@ -326,6 +326,11 @@ class FrameState
*/
inline void learnType(FrameEntry *fe, JSValueMask32 tag);
/*
* Forget a type, syncing in the process.
*/
inline void forgetType(FrameEntry *fe);
/*
* Helper function. Tests if a slot's type is an integer. Condition should
* be Equal or NotEqual.

View File

@@ -146,29 +146,29 @@ StubCompiler::finalize(uint8 *ncode)
}
JSC::MacroAssembler::Call
StubCompiler::vpInc(JSOp op, bool pushed)
StubCompiler::vpInc(JSOp op, uint32 depth)
{
uint32 slots = frame.stackDepth() + script->nfixed;
if (pushed) {
JS_ASSERT(frame.stackDepth());
slots--;
}
uint32 slots = depth + script->nfixed;
VoidVpStub stub = NULL;
switch (op) {
case JSOP_GLOBALINC:
case JSOP_ARGINC:
stub = stubs::VpInc;
break;
case JSOP_GLOBALDEC:
case JSOP_ARGDEC:
stub = stubs::VpDec;
break;
case JSOP_INCGLOBAL:
case JSOP_INCARG:
stub = stubs::IncVp;
break;
case JSOP_DECGLOBAL:
case JSOP_DECARG:
stub = stubs::DecVp;
break;

View File

@@ -108,7 +108,7 @@ class StubCompiler
return masm.buffer();
}
Call vpInc(JSOp op, bool pushed);
Call vpInc(JSOp op, uint32 depth);
#define STUB_CALL_TYPE(type) \
Call call(type stub) { \
@@ -125,6 +125,7 @@ class StubCompiler
void linkExit(Jump j);
void leave();
void leaveWithDepth(uint32 depth);
/*
* Rejoins slow-path code back to the fast-path. The invalidation param

View File

@@ -326,6 +326,7 @@ mjit::Compiler::jsop_globalinc(JSOp op, uint32 index)
RegisterID data;
RegisterID reg = frame.allocReg();
Address addr = masm.objSlotRef(globalObj, reg, slot);
uint32 depth = frame.stackDepth();
if (post && !popped) {
frame.push(addr);
@@ -349,7 +350,7 @@ mjit::Compiler::jsop_globalinc(JSOp op, uint32 index)
stubcc.leave();
stubcc.masm.lea(addr, Registers::ArgReg1);
stubcc.vpInc(op, post && !popped);
stubcc.vpInc(op, depth);
masm.storeData32(data, addr);
@@ -695,3 +696,52 @@ mjit::Compiler::jsop_typeof()
frame.pushTypedPayload(JSVAL_MASK32_STRING, Registers::ReturnReg);
}
void
mjit::Compiler::jsop_arginc(JSOp op, uint32 slot, bool popped)
{
int amt = (js_CodeSpec[op].format & JOF_INC) ? 1 : -1;
bool post = !!(js_CodeSpec[op].format & JOF_POST);
uint32 depth = frame.stackDepth();
jsop_getarg(slot);
if (post && !popped)
frame.dup();
FrameEntry *fe = frame.peek(-1);
Jump notInt = frame.testInt32(Assembler::NotEqual, fe);
stubcc.linkExit(notInt);
RegisterID reg = frame.ownRegForData(fe);
frame.pop();
Jump ovf;
if (amt > 0)
ovf = masm.branchAdd32(Assembler::Overflow, Imm32(1), reg);
else
ovf = masm.branchSub32(Assembler::Overflow, Imm32(1), reg);
stubcc.linkExit(ovf);
Address argv(Assembler::FpReg, offsetof(JSStackFrame, argv));
stubcc.leave();
stubcc.masm.loadPtr(argv, Registers::ArgReg1);
stubcc.masm.addPtr(Imm32(sizeof(Value) * slot), Registers::ArgReg1, Registers::ArgReg1);
stubcc.vpInc(op, depth);
frame.pushTypedPayload(JSVAL_MASK32_INT32, reg);
fe = frame.peek(-1);
reg = frame.allocReg();
masm.loadPtr(argv, reg);
Address address = Address(reg, slot * sizeof(Value));
frame.storeTo(fe, address, popped);
frame.freeReg(reg);
if (post || popped)
frame.pop();
else
frame.forgetType(fe);
stubcc.rejoin(1);
}