[JAEGER] Fixed JSOP_SETNAME not ordering the stack correctly.

This commit is contained in:
David Anderson 2010-06-02 15:25:53 -07:00
parent 37e94e6030
commit 03ba62a0cc
4 changed files with 55 additions and 1 deletions

View File

@ -478,7 +478,13 @@ mjit::Compiler::generateMethod()
prepareStubCall();
masm.move(Imm32(fullAtomIndex(PC)), Registers::ArgReg1);
stubCall(stubs::SetName, Uses(2), Defs(1));
frame.pop();
if (JSOp(PC[JSOP_SETNAME_LENGTH]) == JSOP_POP &&
!analysis[&PC[JSOP_SETNAME_LENGTH]].nincoming) {
frame.popn(2);
PC += JSOP_SETNAME_LENGTH + JSOP_POP_LENGTH;
break;
}
frame.popAfterSet();
END_CASE(JSOP_SETNAME)
BEGIN_CASE(JSOP_DEFFUN)

View File

@ -372,3 +372,35 @@ FrameState::ownRegForData(FrameEntry *fe)
return reg;
}
void
FrameState::popAfterSet()
{
FrameEntry *top = peek(-1);
FrameEntry *down = peek(-2);
if (down->type.inRegister())
forgetReg(down->type.reg());
if (down->data.inRegister())
forgetReg(down->data.reg());
if (top->isConstant()) {
down->setConstant(Jsvalify(top->getValue()));
} else {
down->type.unsync();
if (top->isTypeKnown()) {
down->setTypeTag(top->getTypeTag());
} else {
down->type.inherit(top->type);
if (top->type.inRegister())
moveOwnership(top->type.reg(), down);
}
down->data.unsync();
down->data.inherit(top->data);
if (top->data.inRegister())
moveOwnership(top->data.reg(), down);
}
/* It is now okay to just decrement sp. */
sp--;
}

View File

@ -298,6 +298,12 @@ class FrameState
*/
inline Jump testInt32(Assembler::Condition cond, FrameEntry *fe);
/*
* Special helper for pop-after-set opcodes, which swap the top two stack
* elements, then pop.
*/
void popAfterSet();
/*
* Returns the current stack depth of the frame.
*/
@ -321,6 +327,11 @@ class FrameState
inline void syncType(const FrameEntry *fe, Assembler &masm) const;
inline void syncData(const FrameEntry *fe, Assembler &masm) const;
void
moveOwnership(RegisterID reg, FrameEntry *newFe) {
regstate[reg].fe = newFe;
}
RegisterID evictSomething() {
return evictSomething(Registers::AvailRegs);
}

View File

@ -112,6 +112,11 @@ struct RematInfo {
sync_ = UNSYNCED;
}
void inherit(const RematInfo &other) {
reg_ = other.reg_;
location_ = other.location_;
}
private:
/* Set if location is PhysLoc_Register. */
RegisterID reg_;