Changeset 199792 in webkit


Ignore:
Timestamp:
Apr 20, 2016 3:24:32 PM (8 years ago)
Author:
commit-queue@webkit.org
Message:

[JSC] Add register reuse for ArithAdd of an Int32 and constant in DFG
https://bugs.webkit.org/show_bug.cgi?id=155164

Patch by Benjamin Poulain <bpoulain@apple.com> on 2016-04-20
Reviewed by Mark Lam.

Every "inc" in loop was looking like this:

move rX, rY
inc rY
jo 0x230f4a200580

This patch add register Reuse to that case to remove
the extra "move".

  • dfg/DFGOSRExit.h:

(JSC::DFG::SpeculationRecovery::SpeculationRecovery):
(JSC::DFG::SpeculationRecovery::immediate):

  • dfg/DFGOSRExitCompiler32_64.cpp:

(JSC::DFG::OSRExitCompiler::compileExit):

  • dfg/DFGOSRExitCompiler64.cpp:

(JSC::DFG::OSRExitCompiler::compileExit):

  • dfg/DFGSpeculativeJIT.cpp:

(JSC::DFG::SpeculativeJIT::compileArithAdd):

  • tests/stress/arith-add-with-constant-overflow.js: Added.

(opaqueAdd):

Location:
trunk/Source/JavaScriptCore
Files:
1 added
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/JavaScriptCore/ChangeLog

    r199787 r199792  
     12016-04-20  Benjamin Poulain  <bpoulain@apple.com>
     2
     3        [JSC] Add register reuse for ArithAdd of an Int32 and constant in DFG
     4        https://bugs.webkit.org/show_bug.cgi?id=155164
     5
     6        Reviewed by Mark Lam.
     7
     8        Every "inc" in loop was looking like this:
     9            move rX, rY
     10            inc rY
     11            jo 0x230f4a200580
     12
     13        This patch add register Reuse to that case to remove
     14        the extra "move".
     15
     16        * dfg/DFGOSRExit.h:
     17        (JSC::DFG::SpeculationRecovery::SpeculationRecovery):
     18        (JSC::DFG::SpeculationRecovery::immediate):
     19        * dfg/DFGOSRExitCompiler32_64.cpp:
     20        (JSC::DFG::OSRExitCompiler::compileExit):
     21        * dfg/DFGOSRExitCompiler64.cpp:
     22        (JSC::DFG::OSRExitCompiler::compileExit):
     23        * dfg/DFGSpeculativeJIT.cpp:
     24        (JSC::DFG::SpeculativeJIT::compileArithAdd):
     25        * tests/stress/arith-add-with-constant-overflow.js: Added.
     26        (opaqueAdd):
     27
    1282016-04-20  Saam barati  <sbarati@apple.com>
    229
  • trunk/Source/JavaScriptCore/assembler/MacroAssembler.h

    r197655 r199792  
    16951695    Jump branchAdd32(ResultCondition cond, RegisterID src, Imm32 imm, RegisterID dest)
    16961696    {
    1697         if (src == dest)
    1698             ASSERT(haveScratchRegisterForBlinding());
    1699 
    17001697        if (shouldBlind(imm)) {
    1701             if (src == dest) {
    1702                 move(src, scratchRegisterForBlinding());
    1703                 src = scratchRegisterForBlinding();
     1698            if (src != dest || haveScratchRegisterForBlinding()) {
     1699                if (src == dest) {
     1700                    move(src, scratchRegisterForBlinding());
     1701                    src = scratchRegisterForBlinding();
     1702                }
     1703                loadXorBlindedConstant(xorBlindConstant(imm), dest);
     1704                return branchAdd32(cond, src, dest);
    17041705            }
    1705             loadXorBlindedConstant(xorBlindConstant(imm), dest);
    1706             return branchAdd32(cond, src, dest); 
     1706            // If we don't have a scratch register available for use, we'll just
     1707            // place a random number of nops.
     1708            uint32_t nopCount = random() & 3;
     1709            while (nopCount--)
     1710                nop();
    17071711        }
    17081712        return branchAdd32(cond, src, imm.asTrustedImm32(), dest);           
  • trunk/Source/JavaScriptCore/dfg/DFGOSRExit.h

    r198024 r199792  
    4949// This enum describes the types of additional recovery that
    5050// may need be performed should a speculation check fail.
    51 enum SpeculationRecoveryType {
     51enum SpeculationRecoveryType : uint8_t {
    5252    SpeculativeAdd,
     53    SpeculativeAddImmediate,
    5354    BooleanSpeculationCheck
    5455};
     
    6162public:
    6263    SpeculationRecovery(SpeculationRecoveryType type, GPRReg dest, GPRReg src)
    63         : m_type(type)
     64        : m_src(src)
    6465        , m_dest(dest)
    65         , m_src(src)
     66        , m_type(type)
    6667    {
     68        ASSERT(m_type == SpeculativeAdd || m_type == BooleanSpeculationCheck);
     69    }
     70
     71    SpeculationRecovery(SpeculationRecoveryType type, GPRReg dest, int32_t immediate)
     72        : m_immediate(immediate)
     73        , m_dest(dest)
     74        , m_type(type)
     75    {
     76        ASSERT(m_type == SpeculativeAddImmediate);
    6777    }
    6878
     
    7080    GPRReg dest() { return m_dest; }
    7181    GPRReg src() { return m_src; }
     82    int32_t immediate() { return m_immediate; }
    7283
    7384private:
     85    // different recovery types may required different additional information here.
     86    union {
     87        GPRReg m_src;
     88        int32_t m_immediate;
     89    };
     90    GPRReg m_dest;
     91
    7492    // Indicates the type of additional recovery to be performed.
    7593    SpeculationRecoveryType m_type;
    76     // different recovery types may required different additional information here.
    77     GPRReg m_dest;
    78     GPRReg m_src;
    7994};
    8095
  • trunk/Source/JavaScriptCore/dfg/DFGOSRExitCompiler32_64.cpp

    r198024 r199792  
    5656        case SpeculativeAdd:
    5757            m_jit.sub32(recovery->src(), recovery->dest());
     58            break;
     59
     60        case SpeculativeAddImmediate:
     61            m_jit.sub32(AssemblyHelpers::Imm32(recovery->immediate()), recovery->dest());
    5862            break;
    5963           
  • trunk/Source/JavaScriptCore/dfg/DFGOSRExitCompiler64.cpp

    r198024 r199792  
    6060        case SpeculativeAdd:
    6161            m_jit.sub32(recovery->src(), recovery->dest());
     62            m_jit.or64(GPRInfo::tagTypeNumberRegister, recovery->dest());
     63            break;
     64
     65        case SpeculativeAddImmediate:
     66            m_jit.sub32(AssemblyHelpers::Imm32(recovery->immediate()), recovery->dest());
    6267            m_jit.or64(GPRInfo::tagTypeNumberRegister, recovery->dest());
    6368            break;
  • trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp

    r199748 r199792  
    34973497        if (node->child2()->isInt32Constant()) {
    34983498            SpeculateInt32Operand op1(this, node->child1());
     3499            GPRTemporary result(this, Reuse, op1);
     3500
     3501            GPRReg gpr1 = op1.gpr();
    34993502            int32_t imm2 = node->child2()->asInt32();
     3503            GPRReg gprResult = result.gpr();
    35003504
    35013505            if (!shouldCheckOverflow(node->arithMode())) {
    3502                 GPRTemporary result(this, Reuse, op1);
    3503                 m_jit.add32(Imm32(imm2), op1.gpr(), result.gpr());
    3504                 int32Result(result.gpr(), node);
     3506                m_jit.add32(Imm32(imm2), gpr1, gprResult);
     3507                int32Result(gprResult, node);
    35053508                return;
    35063509            }
    35073510
    3508             GPRTemporary result(this);
    3509             speculationCheck(Overflow, JSValueRegs(), 0, m_jit.branchAdd32(MacroAssembler::Overflow, op1.gpr(), Imm32(imm2), result.gpr()));
    3510 
    3511             int32Result(result.gpr(), node);
     3511            MacroAssembler::Jump check = m_jit.branchAdd32(MacroAssembler::Overflow, gpr1, Imm32(imm2), gprResult);
     3512            if (gpr1 == gprResult) {
     3513                speculationCheck(Overflow, JSValueRegs(), 0, check,
     3514                    SpeculationRecovery(SpeculativeAddImmediate, gpr1, imm2));
     3515            } else
     3516                speculationCheck(Overflow, JSValueRegs(), 0, check);
     3517
     3518            int32Result(gprResult, node);
    35123519            return;
    35133520        }
Note: See TracChangeset for help on using the changeset viewer.