Changeset 91280 in webkit


Ignore:
Timestamp:
Jul 19, 2011 11:55:16 AM (13 years ago)
Author:
commit-queue@webkit.org
Message:

DFG JIT sometimes emits spill code even when the respective values
are never needed.
https://bugs.webkit.org/show_bug.cgi?id=64774

Patch by Filip Pizlo <fpizlo@apple.com> on 2011-07-19
Reviewed by Gavin Barraclough.

The main high-level change is that it is now easier to call use() on a
virtual register. JSValueOperand and its other-typed relatives now have
a handy use() method, and jsValueResult() and friends now make it easier to
pass UseChildrenCalledExplicitly.

The rest of this patch hoists the call to use() as high as possible for
all of those cases where either flushRegisters() or silentSpillAllRegisters()
may be called.

  • dfg/DFGJITCodeGenerator.cpp:

(JSC::DFG::JITCodeGenerator::cachedGetById):
(JSC::DFG::JITCodeGenerator::cachedGetMethod):
(JSC::DFG::JITCodeGenerator::nonSpeculativePeepholeBranch):
(JSC::DFG::JITCodeGenerator::nonSpeculativeNonPeepholeCompare):
(JSC::DFG::JITCodeGenerator::nonSpeculativeCompare):
(JSC::DFG::JITCodeGenerator::nonSpeculativePeepholeStrictEq):
(JSC::DFG::JITCodeGenerator::nonSpeculativeNonPeepholeStrictEq):
(JSC::DFG::JITCodeGenerator::nonSpeculativeStrictEq):
(JSC::DFG::JITCodeGenerator::emitBranch):

  • dfg/DFGJITCodeGenerator.h:

(JSC::DFG::JITCodeGenerator::use):
(JSC::DFG::JITCodeGenerator::integerResult):
(JSC::DFG::JITCodeGenerator::jsValueResult):
(JSC::DFG::IntegerOperand::use):
(JSC::DFG::DoubleOperand::use):
(JSC::DFG::JSValueOperand::use):

  • dfg/DFGNonSpeculativeJIT.cpp:

(JSC::DFG::NonSpeculativeJIT::valueToNumber):
(JSC::DFG::NonSpeculativeJIT::valueToInt32):
(JSC::DFG::NonSpeculativeJIT::knownConstantArithOp):
(JSC::DFG::NonSpeculativeJIT::basicArithOp):
(JSC::DFG::NonSpeculativeJIT::compile):

  • dfg/DFGSpeculativeJIT.cpp:

(JSC::DFG::SpeculativeJIT::compile):

  • dfg/DFGSpeculativeJIT.h:

(JSC::DFG::SpeculateStrictInt32Operand::use):
(JSC::DFG::SpeculateCellOperand::use):

Location:
trunk/Source/JavaScriptCore
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/ChangeLog

    r91275 r91280  
     12011-07-19  Filip Pizlo  <fpizlo@apple.com>
     2
     3        DFG JIT sometimes emits spill code even when the respective values
     4        are never needed.
     5        https://bugs.webkit.org/show_bug.cgi?id=64774
     6
     7        Reviewed by Gavin Barraclough.
     8       
     9        The main high-level change is that it is now easier to call use() on a
     10        virtual register.  JSValueOperand and its other-typed relatives now have
     11        a handy use() method, and jsValueResult() and friends now make it easier to
     12        pass UseChildrenCalledExplicitly.
     13       
     14        The rest of this patch hoists the call to use() as high as possible for
     15        all of those cases where either flushRegisters() or silentSpillAllRegisters()
     16        may be called.
     17
     18        * dfg/DFGJITCodeGenerator.cpp:
     19        (JSC::DFG::JITCodeGenerator::cachedGetById):
     20        (JSC::DFG::JITCodeGenerator::cachedGetMethod):
     21        (JSC::DFG::JITCodeGenerator::nonSpeculativePeepholeBranch):
     22        (JSC::DFG::JITCodeGenerator::nonSpeculativeNonPeepholeCompare):
     23        (JSC::DFG::JITCodeGenerator::nonSpeculativeCompare):
     24        (JSC::DFG::JITCodeGenerator::nonSpeculativePeepholeStrictEq):
     25        (JSC::DFG::JITCodeGenerator::nonSpeculativeNonPeepholeStrictEq):
     26        (JSC::DFG::JITCodeGenerator::nonSpeculativeStrictEq):
     27        (JSC::DFG::JITCodeGenerator::emitBranch):
     28        * dfg/DFGJITCodeGenerator.h:
     29        (JSC::DFG::JITCodeGenerator::use):
     30        (JSC::DFG::JITCodeGenerator::integerResult):
     31        (JSC::DFG::JITCodeGenerator::jsValueResult):
     32        (JSC::DFG::IntegerOperand::use):
     33        (JSC::DFG::DoubleOperand::use):
     34        (JSC::DFG::JSValueOperand::use):
     35        * dfg/DFGNonSpeculativeJIT.cpp:
     36        (JSC::DFG::NonSpeculativeJIT::valueToNumber):
     37        (JSC::DFG::NonSpeculativeJIT::valueToInt32):
     38        (JSC::DFG::NonSpeculativeJIT::knownConstantArithOp):
     39        (JSC::DFG::NonSpeculativeJIT::basicArithOp):
     40        (JSC::DFG::NonSpeculativeJIT::compile):
     41        * dfg/DFGSpeculativeJIT.cpp:
     42        (JSC::DFG::SpeculativeJIT::compile):
     43        * dfg/DFGSpeculativeJIT.h:
     44        (JSC::DFG::SpeculateStrictInt32Operand::use):
     45        (JSC::DFG::SpeculateCellOperand::use):
     46
    1472011-07-19  Xan Lopez  <xlopez@igalia.com>
    248
  • trunk/Source/JavaScriptCore/dfg/DFGJITCodeGenerator.cpp

    r91226 r91280  
    392392}
    393393
    394 JITCompiler::Call JITCodeGenerator::cachedGetById(GPRReg baseGPR, GPRReg resultGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget, NodeType nodeType)
    395 {
    396     GPRReg scratchGPR;
    397    
    398     if (resultGPR == baseGPR)
    399         scratchGPR = tryAllocate();
    400     else
    401         scratchGPR = resultGPR;
    402    
     394JITCompiler::Call JITCodeGenerator::cachedGetById(GPRReg baseGPR, GPRReg resultGPR, GPRReg scratchGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget, NodeType nodeType)
     395{
    403396    JITCompiler::DataLabelPtr structureToCompare;
    404397    JITCompiler::Jump structureCheck = m_jit.branchPtrWithPatch(JITCompiler::NotEqual, JITCompiler::Address(baseGPR, JSCell::structureOffset()), structureToCompare, JITCompiler::TrustedImmPtr(reinterpret_cast<void*>(-1)));
     
    512505}
    513506
    514 void JITCodeGenerator::cachedGetMethod(GPRReg baseGPR, GPRReg resultGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget)
     507void JITCodeGenerator::cachedGetMethod(GPRReg baseGPR, GPRReg resultGPR, GPRReg scratchGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget)
    515508{
    516509    JITCompiler::Call slowCall;
     
    528521    wrongProtoStructure.link(&m_jit);
    529522   
    530     slowCall = cachedGetById(baseGPR, resultGPR, identifierNumber, slowPathTarget, GetMethod);
     523    slowCall = cachedGetById(baseGPR, resultGPR, scratchGPR, identifierNumber, slowPathTarget, GetMethod);
    531524   
    532525    done.link(&m_jit);
     
    654647   
    655648    if (isKnownNotInteger(node.child1()) || isKnownNotInteger(node.child2())) {
    656         flushRegisters();
    657 
    658649        GPRResult result(this);
    659650        GPRReg resultGPR = result.gpr();
    660651   
     652        arg1.use();
     653        arg2.use();
     654   
     655        flushRegisters();
     656
    661657        callOperation(helperFunction, resultGPR, arg1GPR, arg2GPR);
    662658        addBranch(m_jit.branchTest8(callResultCondition, resultGPR), taken);
     
    664660        GPRTemporary result(this, arg2);
    665661        GPRReg resultGPR = result.gpr();
     662   
     663        arg1.use();
     664        arg2.use();
    666665   
    667666        if (!isKnownInteger(node.child1()))
     
    702701   
    703702    if (isKnownNotInteger(node.child1()) || isKnownNotInteger(node.child2())) {
    704         flushRegisters();
    705        
    706703        GPRResult result(this);
    707704        GPRReg resultGPR = result.gpr();
    708705   
     706        arg1.use();
     707        arg2.use();
     708   
     709        flushRegisters();
     710       
    709711        callOperation(helperFunction, resultGPR, arg1GPR, arg2GPR);
    710712       
    711713        m_jit.or32(TrustedImm32(ValueFalse), resultGPR);
    712         jsValueResult(resultGPR, m_compileIndex);
     714        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    713715    } else {
    714716        GPRTemporary result(this, arg2);
    715717        GPRReg resultGPR = result.gpr();
     718
     719        arg1.use();
     720        arg2.use();
    716721   
    717722        if (!isKnownInteger(node.child1()))
     
    741746        m_jit.or32(TrustedImm32(ValueFalse), resultGPR);
    742747       
    743         jsValueResult(resultGPR, m_compileIndex);
     748        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    744749    }
    745750}
     
    753758        nonSpeculativePeepholeBranch(node, branchNodeIndex, cond, helperFunction);
    754759   
    755         use(node.child1());
    756         use(node.child2());
    757760        m_compileIndex = branchNodeIndex;
    758761       
     
    788791    GPRReg resultGPR = result.gpr();
    789792   
     793    arg1.use();
     794    arg2.use();
     795   
    790796    if (isKnownCell(node.child1()) && isKnownCell(node.child2())) {
    791797        // see if we get lucky: if the arguments are cells and they reference the same
     
    840846    GPRReg resultGPR = result.gpr();
    841847   
     848    arg1.use();
     849    arg2.use();
     850   
    842851    if (isKnownCell(node.child1()) && isKnownCell(node.child2())) {
    843852        // see if we get lucky: if the arguments are cells and they reference the same
     
    899908    }
    900909   
    901     jsValueResult(resultGPR, m_compileIndex);
     910    jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    902911}
    903912
     
    913922        nonSpeculativePeepholeStrictEq(node, branchNodeIndex, invert);
    914923   
    915         use(node.child1());
    916         use(node.child2());
    917924        m_compileIndex = branchNodeIndex;
    918925       
     
    932939    GPRTemporary result(this);
    933940    GPRReg resultGPR = result.gpr();
     941   
     942    value.use();
    934943   
    935944    BlockIndex taken = m_jit.graph().blockIndexForBytecodeOffset(node.takenBytecodeOffset());
     
    952961        addBranch(m_jit.jump(), notTaken);
    953962   
    954     noResult(m_compileIndex);
     963    noResult(m_compileIndex, UseChildrenCalledExplicitly);
    955964}
    956965
  • trunk/Source/JavaScriptCore/dfg/DFGJITCodeGenerator.h

    r91226 r91280  
    158158    }
    159159
     160    // Called on an operand once it has been consumed by a parent node.
     161    void use(NodeIndex nodeIndex)
     162    {
     163        VirtualRegister virtualRegister = m_jit.graph()[nodeIndex].virtualRegister();
     164        GenerationInfo& info = m_generationInfo[virtualRegister];
     165
     166        // use() returns true when the value becomes dead, and any
     167        // associated resources may be freed.
     168        if (!info.use())
     169            return;
     170
     171        // Release the associated machine registers.
     172        DataFormat registerFormat = info.registerFormat();
     173        if (registerFormat == DataFormatDouble)
     174            m_fprs.release(info.fpr());
     175        else if (registerFormat != DataFormatNone)
     176            m_gprs.release(info.gpr());
     177    }
     178
    160179    static void writeBarrier(MacroAssembler&, GPRReg ownerGPR, GPRReg scratchGPR);
    161180
     
    356375    {
    357376        return unboxDouble(gpr, fprAllocate());
    358     }
    359 
    360     // Called on an operand once it has been consumed by a parent node.
    361     void use(NodeIndex nodeIndex)
    362     {
    363         VirtualRegister virtualRegister = m_jit.graph()[nodeIndex].virtualRegister();
    364         GenerationInfo& info = m_generationInfo[virtualRegister];
    365 
    366         // use() returns true when the value becomes dead, and any
    367         // associated resources may be freed.
    368         if (!info.use())
    369             return;
    370 
    371         // Release the associated machine registers.
    372         DataFormat registerFormat = info.registerFormat();
    373         if (registerFormat == DataFormatDouble)
    374             m_fprs.release(info.fpr());
    375         else if (registerFormat != DataFormatNone)
    376             m_gprs.release(info.gpr());
    377377    }
    378378
     
    560560    }
    561561
    562     JITCompiler::Call cachedGetById(GPRReg baseGPR, GPRReg resultGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget = JITCompiler::Jump(), NodeType = GetById);
     562    JITCompiler::Call cachedGetById(GPRReg baseGPR, GPRReg resultGPR, GPRReg scratchGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget = JITCompiler::Jump(), NodeType = GetById);
    563563    void cachedPutById(GPRReg baseGPR, GPRReg valueGPR, GPRReg scratchGPR, unsigned identifierNumber, PutKind, JITCompiler::Jump slowPathTarget = JITCompiler::Jump());
    564     void cachedGetMethod(GPRReg baseGPR, GPRReg resultGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget = JITCompiler::Jump());
     564    void cachedGetMethod(GPRReg baseGPR, GPRReg resultGPR, GPRReg scratchGPR, unsigned identifierNumber, JITCompiler::Jump slowPathTarget = JITCompiler::Jump());
    565565   
    566566    void nonSpeculativeNonPeepholeCompareNull(NodeIndex operand, bool invert = false);
     
    613613        }
    614614    }
     615    void integerResult(GPRReg reg, NodeIndex nodeIndex, UseChildrenMode mode)
     616    {
     617        integerResult(reg, nodeIndex, DataFormatInteger, mode);
     618    }
    615619    void noResult(NodeIndex nodeIndex, UseChildrenMode mode = CallUseChildren)
    616620    {
     
    644648        GenerationInfo& info = m_generationInfo[virtualRegister];
    645649        info.initJSValue(nodeIndex, node.refCount(), reg, format);
     650    }
     651    void jsValueResult(GPRReg reg, NodeIndex nodeIndex, UseChildrenMode mode)
     652    {
     653        jsValueResult(reg, nodeIndex, DataFormatJS, mode);
    646654    }
    647655    void doubleResult(FPRReg reg, NodeIndex nodeIndex, UseChildrenMode mode = CallUseChildren)
     
    9961004        return m_gprOrInvalid;
    9971005    }
     1006   
     1007    void use()
     1008    {
     1009        m_jit->use(m_index);
     1010    }
    9981011
    9991012private:
     
    10331046        return m_fprOrInvalid;
    10341047    }
     1048   
     1049    void use()
     1050    {
     1051        m_jit->use(m_index);
     1052    }
    10351053
    10361054private:
     
    10681086            m_gprOrInvalid = m_jit->fillJSValue(index());
    10691087        return m_gprOrInvalid;
     1088    }
     1089   
     1090    void use()
     1091    {
     1092        m_jit->use(m_index);
    10701093    }
    10711094
  • trunk/Source/JavaScriptCore/dfg/DFGNonSpeculativeJIT.cpp

    r91226 r91280  
    6060{
    6161    GPRReg jsValueGpr = operand.gpr();
     62    operand.use();
    6263
    6364    JITCompiler::Jump isInteger = m_jit.branchPtr(MacroAssembler::AboveOrEqual, jsValueGpr, GPRInfo::tagTypeNumberRegister);
     
    8889{
    8990    GPRReg jsValueGpr = operand.gpr();
     91    operand.use();
    9092
    9193    JITCompiler::Jump isInteger = m_jit.branchPtr(MacroAssembler::AboveOrEqual, jsValueGpr, GPRInfo::tagTypeNumberRegister);
     
    127129    GPRTemporary result(this, regArg);
    128130    GPRReg resultGPR = result.gpr();
     131   
     132    regArg.use();
     133    use(immChild);
    129134
    130135    JITCompiler::Jump notInt;
     
    221226    done.link(&m_jit);
    222227       
    223     jsValueResult(resultGPR, m_compileIndex);
     228    jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    224229}
    225230
     
    235240
    236241    GPRReg resultGPR = result.gpr();
     242   
     243    arg1.use();
     244    arg2.use();
    237245   
    238246    JITCompiler::JumpList slowPath;
     
    300308    done.link(&m_jit);
    301309       
    302     jsValueResult(resultGPR, m_compileIndex);
     310    jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    303311}
    304312
     
    448456            DoubleOperand op1(this, node.child1());
    449457            GPRTemporary result(this);
     458            op1.use();
    450459            numberToInt32(op1.fpr(), result.gpr());
    451             integerResult(result.gpr(), m_compileIndex);
     460            integerResult(result.gpr(), m_compileIndex, UseChildrenCalledExplicitly);
    452461            break;
    453462        }
     
    456465        GPRTemporary result(this, op1);
    457466        valueToInt32(op1, result.gpr());
    458         integerResult(result.gpr(), m_compileIndex);
     467        integerResult(result.gpr(), m_compileIndex, UseChildrenCalledExplicitly);
    459468        break;
    460469    }
     
    475484        GPRTemporary result(this);
    476485        valueToNumber(op1, result.gpr());
    477         jsValueResult(result.gpr(), m_compileIndex);
     486        jsValueResult(result.gpr(), m_compileIndex, UseChildrenCalledExplicitly);
    478487        break;
    479488    }
     
    538547        FPRReg op1FPR = op1Double.fpr();
    539548        FPRReg op2FPR = op2Double.fpr();
     549       
     550        op1.use();
     551        op2.use();
    540552   
    541553        JITCompiler::Jump firstOpNotInt;
     
    624636        done.link(&m_jit);
    625637   
    626         jsValueResult(X86Registers::edx, m_compileIndex);
     638        jsValueResult(X86Registers::edx, m_compileIndex, UseChildrenCalledExplicitly);
    627639        break;
    628640    }
     
    631643        JSValueOperand arg1(this, node.child1());
    632644        GPRTemporary result(this);
    633 
     645       
    634646        GPRReg arg1GPR = arg1.gpr();
    635647        GPRReg resultGPR = result.gpr();
    636648       
     649        arg1.use();
     650
    637651        m_jit.move(arg1GPR, resultGPR);
    638652        m_jit.xorPtr(TrustedImm32(static_cast<int32_t>(ValueFalse)), resultGPR);
     
    649663
    650664        m_jit.xorPtr(TrustedImm32(static_cast<int32_t>(ValueTrue)), resultGPR);
    651         jsValueResult(resultGPR, m_compileIndex);
     665        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    652666        break;
    653667    }
     
    704718        GPRReg storageGPR = storage.gpr();
    705719        GPRReg cleanIndexGPR = cleanIndex.gpr();
     720       
     721        base.use();
     722        property.use();
    706723
    707724        JITCompiler::Jump baseNotCell = m_jit.branchTestPtr(MacroAssembler::NonZero, baseGPR, GPRInfo::tagMaskRegister);
     
    740757        done.link(&m_jit);
    741758
    742         jsValueResult(storageGPR, m_compileIndex);
     759        jsValueResult(storageGPR, m_compileIndex, UseChildrenCalledExplicitly);
    743760        break;
    744761    }
     
    752769        GPRReg arg2GPR = arg2.gpr();
    753770        GPRReg arg3GPR = arg3.gpr();
     771       
     772        arg1.use();
     773        arg2.use();
     774        arg3.use();
    754775        flushRegisters();
    755776
    756         GPRResult result(this);
    757777        callOperation(m_jit.codeBlock()->isStrictMode() ? operationPutByValStrict : operationPutByValNonStrict, arg1GPR, arg2GPR, arg3GPR);
    758778
    759         noResult(m_compileIndex);
     779        noResult(m_compileIndex, UseChildrenCalledExplicitly);
    760780        break;
    761781    }
     
    766786        GPRTemporary result(this, base);
    767787        GPRReg resultGPR = result.gpr();
     788        GPRReg scratchGPR;
     789       
     790        if (resultGPR == baseGPR)
     791            scratchGPR = tryAllocate();
     792        else
     793            scratchGPR = resultGPR;
     794       
     795        base.use();
    768796
    769797        JITCompiler::Jump notCell = m_jit.branchTestPtr(MacroAssembler::NonZero, baseGPR, GPRInfo::tagMaskRegister);
    770798
    771         cachedGetById(baseGPR, resultGPR, node.identifierNumber(), notCell);
    772 
    773         jsValueResult(resultGPR, m_compileIndex);
     799        cachedGetById(baseGPR, resultGPR, scratchGPR, node.identifierNumber(), notCell);
     800
     801        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    774802        break;
    775803    }
     
    780808        GPRTemporary result(this, base);
    781809        GPRReg resultGPR = result.gpr();
     810        GPRReg scratchGPR;
     811        if (resultGPR == baseGPR)
     812            scratchGPR = tryAllocate();
     813        else
     814            scratchGPR = resultGPR;
     815       
     816        base.use();
    782817
    783818        JITCompiler::Jump notCell = m_jit.branchTestPtr(MacroAssembler::NonZero, baseGPR, GPRInfo::tagMaskRegister);
    784819
    785         cachedGetMethod(baseGPR, resultGPR, node.identifierNumber(), notCell);
    786 
    787         jsValueResult(resultGPR, m_compileIndex);
     820        cachedGetMethod(baseGPR, resultGPR, scratchGPR, node.identifierNumber(), notCell);
     821
     822        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    788823        break;
    789824    }
     
    795830        GPRReg valueGPR = value.gpr();
    796831        GPRReg baseGPR = base.gpr();
     832        GPRReg scratchGPR = scratch.gpr();
     833       
     834        base.use();
     835        value.use();
    797836       
    798837        JITCompiler::Jump notCell = m_jit.branchTestPtr(MacroAssembler::NonZero, baseGPR, GPRInfo::tagMaskRegister);
    799838
    800         cachedPutById(baseGPR, valueGPR, scratch.gpr(), node.identifierNumber(), NotDirect, notCell);
    801 
    802         noResult(m_compileIndex);
     839        cachedPutById(baseGPR, valueGPR, scratchGPR, node.identifierNumber(), NotDirect, notCell);
     840
     841        noResult(m_compileIndex, UseChildrenCalledExplicitly);
    803842        break;
    804843    }
     
    811850        GPRReg baseGPR = base.gpr();
    812851       
     852        base.use();
     853        value.use();
     854       
    813855        JITCompiler::Jump notCell = m_jit.branchTestPtr(MacroAssembler::NonZero, baseGPR, GPRInfo::tagMaskRegister);
    814856
    815857        cachedPutById(baseGPR, valueGPR, scratch.gpr(), node.identifierNumber(), Direct, notCell);
    816858
    817         noResult(m_compileIndex);
     859        noResult(m_compileIndex, UseChildrenCalledExplicitly);
    818860        break;
    819861    }
     
    925967        GPRReg prototypeReg = prototype.gpr();
    926968        GPRReg scratchReg = scratch.gpr();
     969       
     970        value.use();
     971        base.use();
     972        prototype.use();
    927973
    928974        // Check that operands are cells (base is checked by CheckHasInstance, so we can just assert).
     
    9741020        wasNotInstance.link(&m_jit);
    9751021        wasNotDefaultHasInstance.link(&m_jit);
    976         jsValueResult(scratchReg, m_compileIndex);
     1022        jsValueResult(scratchReg, m_compileIndex, UseChildrenCalledExplicitly);
    9771023        break;
    9781024    }
  • trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp

    r91226 r91280  
    850850        if (baseNode.op != GetLocal || m_jit.graph().getPrediction(baseNode.local()) != PredictArray)
    851851            speculationCheck(m_jit.branchPtr(MacroAssembler::NotEqual, MacroAssembler::Address(baseReg), MacroAssembler::TrustedImmPtr(m_jit.globalData()->jsArrayVPtr)));
     852
     853        base.use();
     854        property.use();
     855        value.use();
     856       
    852857        MacroAssembler::Jump withinArrayBounds = m_jit.branch32(MacroAssembler::Below, propertyReg, MacroAssembler::Address(baseReg, JSArray::vectorLengthOffset()));
    853858
     
    884889        wasBeyondArrayBounds.link(&m_jit);
    885890
    886         noResult(m_compileIndex);
     891        noResult(m_compileIndex, UseChildrenCalledExplicitly);
    887892        break;
    888893    }
     
    962967        SpeculateCellOperand base(this, node.child1());
    963968        GPRTemporary result(this, base);
    964 
     969       
     970        GPRReg baseGPR = base.gpr();
    965971        GPRReg resultGPR = result.gpr();
    966 
    967         cachedGetById(base.gpr(), resultGPR, node.identifierNumber());
    968 
    969         jsValueResult(resultGPR, m_compileIndex);
     972        GPRReg scratchGPR;
     973       
     974        if (resultGPR == baseGPR)
     975            scratchGPR = tryAllocate();
     976        else
     977            scratchGPR = resultGPR;
     978       
     979        base.use();
     980
     981        cachedGetById(baseGPR, resultGPR, scratchGPR, node.identifierNumber());
     982
     983        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    970984        break;
    971985    }
     
    975989        GPRTemporary result(this, base);
    976990
     991        GPRReg baseGPR = base.gpr();
    977992        GPRReg resultGPR = result.gpr();
    978 
    979         cachedGetMethod(base.gpr(), resultGPR, node.identifierNumber());
    980 
    981         jsValueResult(resultGPR, m_compileIndex);
     993        GPRReg scratchGPR;
     994       
     995        if (resultGPR == baseGPR)
     996            scratchGPR = tryAllocate();
     997        else
     998            scratchGPR = resultGPR;
     999       
     1000        base.use();
     1001
     1002        cachedGetMethod(baseGPR, resultGPR, scratchGPR, node.identifierNumber());
     1003
     1004        jsValueResult(resultGPR, m_compileIndex, UseChildrenCalledExplicitly);
    9821005        break;
    9831006    }
     
    9871010        JSValueOperand value(this, node.child2());
    9881011        GPRTemporary scratch(this);
    989 
    990         cachedPutById(base.gpr(), value.gpr(), scratch.gpr(), node.identifierNumber(), NotDirect);
    991        
    992         noResult(m_compileIndex);
     1012       
     1013        GPRReg baseGPR = base.gpr();
     1014        GPRReg valueGPR = value.gpr();
     1015        GPRReg scratchGPR = scratch.gpr();
     1016       
     1017        base.use();
     1018        value.use();
     1019
     1020        cachedPutById(baseGPR, valueGPR, scratchGPR, node.identifierNumber(), NotDirect);
     1021       
     1022        noResult(m_compileIndex, UseChildrenCalledExplicitly);
    9931023        break;
    9941024    }
     
    9981028        JSValueOperand value(this, node.child2());
    9991029        GPRTemporary scratch(this);
    1000 
    1001         cachedPutById(base.gpr(), value.gpr(), scratch.gpr(), node.identifierNumber(), Direct);
    1002 
    1003         noResult(m_compileIndex);
     1030       
     1031        GPRReg baseGPR = base.gpr();
     1032        GPRReg valueGPR = value.gpr();
     1033        GPRReg scratchGPR = scratch.gpr();
     1034       
     1035        base.use();
     1036        value.use();
     1037
     1038        cachedPutById(baseGPR, valueGPR, scratchGPR, node.identifierNumber(), Direct);
     1039
     1040        noResult(m_compileIndex, UseChildrenCalledExplicitly);
    10041041        break;
    10051042    }
  • trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.h

    r91156 r91280  
    294294        return m_gprOrInvalid;
    295295    }
     296   
     297    void use()
     298    {
     299        m_jit->use(m_index);
     300    }
    296301
    297302private:
     
    365370            m_gprOrInvalid = m_jit->fillSpeculateCell(index());
    366371        return m_gprOrInvalid;
     372    }
     373   
     374    void use()
     375    {
     376        m_jit->use(m_index);
    367377    }
    368378
Note: See TracChangeset for help on using the changeset viewer.