Changeset 231195 in webkit
- Timestamp:
- May 1, 2018 8:42:11 AM (6 years ago)
- Location:
- trunk
- Files:
-
- 1 added
- 17 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/JSTests/ChangeLog
r231193 r231195 1 2018-05-01 Dominik Infuehr <dinfuehr@igalia.com> 2 3 Add SetCallee as DFG-Operation 4 https://bugs.webkit.org/show_bug.cgi?id=184582 5 6 Reviewed by Filip Pizlo. 7 8 Added test that runs into infinite loop without updating the callee and 9 therefore emitting SetCallee in DFG for recursive tail calls. 10 11 * stress/closure-recursive-tail-call-infinite-loop.js: Added. 12 (Foo): 13 (second): 14 (first): 15 (return.closure): 16 (createClosure): 17 1 18 2018-04-30 Saam Barati <sbarati@apple.com> 2 19 -
trunk/Source/JavaScriptCore/ChangeLog
r231194 r231195 1 2018-05-01 Dominik Infuehr <dinfuehr@igalia.com> 2 3 Add SetCallee as DFG-Operation 4 https://bugs.webkit.org/show_bug.cgi?id=184582 5 6 Reviewed by Filip Pizlo. 7 8 For recursive tail calls not only the argument count can change but also the 9 callee. Add SetCallee to DFG that sets the callee slot in the current call frame. 10 Also update the callee when optimizing a recursive tail call. 11 Enable recursive tail call optimization also for closures. 12 13 * dfg/DFGAbstractInterpreterInlines.h: 14 (JSC::DFG::AbstractInterpreter<AbstractStateType>::executeEffects): 15 * dfg/DFGByteCodeParser.cpp: 16 (JSC::DFG::ByteCodeParser::handleRecursiveTailCall): 17 (JSC::DFG::ByteCodeParser::handleCallVariant): 18 * dfg/DFGClobberize.h: 19 (JSC::DFG::clobberize): 20 * dfg/DFGDoesGC.cpp: 21 (JSC::DFG::doesGC): 22 * dfg/DFGFixupPhase.cpp: 23 (JSC::DFG::FixupPhase::fixupNode): 24 * dfg/DFGMayExit.cpp: 25 * dfg/DFGNodeType.h: 26 * dfg/DFGPredictionPropagationPhase.cpp: 27 * dfg/DFGSafeToExecute.h: 28 (JSC::DFG::safeToExecute): 29 * dfg/DFGSpeculativeJIT.cpp: 30 (JSC::DFG::SpeculativeJIT::compileSetCallee): 31 * dfg/DFGSpeculativeJIT.h: 32 * dfg/DFGSpeculativeJIT32_64.cpp: 33 (JSC::DFG::SpeculativeJIT::compile): 34 * dfg/DFGSpeculativeJIT64.cpp: 35 (JSC::DFG::SpeculativeJIT::compile): 36 * ftl/FTLCapabilities.cpp: 37 (JSC::FTL::canCompile): 38 * ftl/FTLLowerDFGToB3.cpp: 39 (JSC::FTL::DFG::LowerDFGToB3::compileNode): 40 (JSC::FTL::DFG::LowerDFGToB3::compileSetCallee): 41 1 42 2018-05-01 Oleksandr Skachkov <gskachkov@gmail.com> 2 43 -
trunk/Source/JavaScriptCore/dfg/DFGAbstractInterpreterInlines.h
r231145 r231195 2449 2449 break; 2450 2450 2451 case SetCallee: 2451 2452 case SetArgumentCountIncludingThis: 2452 2453 break; -
trunk/Source/JavaScriptCore/dfg/DFGByteCodeParser.cpp
r230929 r231195 157 157 Node* getArgumentCount(); 158 158 template<typename ChecksFunctor> 159 bool handleRecursiveTailCall( CallVariant, int registerOffset, int argumentCountIncludingThis, const ChecksFunctor& emitFunctionCheckIfNeeded);159 bool handleRecursiveTailCall(Node* callTargetNode, CallVariant, int registerOffset, int argumentCountIncludingThis, const ChecksFunctor& emitFunctionCheckIfNeeded); 160 160 unsigned inliningCost(CallVariant, int argumentCountIncludingThis, InlineCallFrame::Kind); // Return UINT_MAX if it's not an inlining candidate. By convention, intrinsics have a cost of 1. 161 161 // Handle inlining. Return true if it succeeded, false if we need to plant a call. … … 1357 1357 1358 1358 template<typename ChecksFunctor> 1359 bool ByteCodeParser::handleRecursiveTailCall( CallVariant callVariant, int registerOffset, int argumentCountIncludingThis, const ChecksFunctor& emitFunctionCheckIfNeeded)1359 bool ByteCodeParser::handleRecursiveTailCall(Node* callTargetNode, CallVariant callVariant, int registerOffset, int argumentCountIncludingThis, const ChecksFunctor& emitFunctionCheckIfNeeded) 1360 1360 { 1361 1361 if (UNLIKELY(!Options::optimizeRecursiveTailCalls())) 1362 return false;1363 1364 // Currently we cannot do this optimisation for closures. The problem is that "emitFunctionChecks" which we use later is too coarse, only checking the executable1365 // and not the value of captured variables.1366 if (callVariant.isClosureCall())1367 1362 return false; 1368 1363 … … 1386 1381 } 1387 1382 1383 // If an InlineCallFrame is not a closure, it was optimized using a constant callee. 1384 // Check if this is the same callee that we try to inline here. 1385 if (stackEntry->m_inlineCallFrame && !stackEntry->m_inlineCallFrame->isClosureCall) { 1386 if (stackEntry->m_inlineCallFrame->calleeConstant() != callVariant.function()) 1387 continue; 1388 } 1389 1388 1390 // We must add some check that the profiling information was correct and the target of this call is what we thought. 1389 1391 emitFunctionCheckIfNeeded(); 1390 1392 // We flush everything, as if we were in the backedge of a loop (see treatment of op_jmp in parseBlock). 1391 1393 flushForTerminal(); 1394 1395 // We must set the callee to the right value 1396 if (stackEntry->m_inlineCallFrame) { 1397 if (stackEntry->m_inlineCallFrame->isClosureCall) 1398 setDirect(stackEntry->remapOperand(VirtualRegister(CallFrameSlot::callee)), callTargetNode, NormalSet); 1399 } else 1400 addToGraph(SetCallee, callTargetNode); 1392 1401 1393 1402 // We must set the arguments to the right values … … 1684 1693 }; 1685 1694 1686 if (kind == InlineCallFrame::TailCall && ByteCodeParser::handleRecursiveTailCall(call ee, registerOffset, argumentCountIncludingThis, insertChecksWithAccounting)) {1695 if (kind == InlineCallFrame::TailCall && ByteCodeParser::handleRecursiveTailCall(callTargetNode, callee, registerOffset, argumentCountIncludingThis, insertChecksWithAccounting)) { 1687 1696 RELEASE_ASSERT(didInsertChecks); 1688 1697 return CallOptimizationResult::OptimizedToJump; -
trunk/Source/JavaScriptCore/dfg/DFGClobberize.h
r231145 r231195 696 696 def(HeapLocation(StackLoc, AbstractHeap(Stack, CallFrameSlot::callee)), LazyNode(node)); 697 697 return; 698 699 case SetCallee: 700 write(AbstractHeap(Stack, CallFrameSlot::callee)); 701 return; 698 702 699 703 case GetArgumentCountIncludingThis: { -
trunk/Source/JavaScriptCore/dfg/DFGDoesGC.cpp
r230376 r231195 52 52 case IdentityWithProfile: 53 53 case GetCallee: 54 case SetCallee: 54 55 case GetArgumentCountIncludingThis: 55 56 case SetArgumentCountIncludingThis: -
trunk/Source/JavaScriptCore/dfg/DFGFixupPhase.cpp
r230516 r231195 2133 2133 break; 2134 2134 } 2135 break; 2136 2137 case SetCallee: 2138 fixEdge<CellUse>(node->child1()); 2135 2139 break; 2136 2140 -
trunk/Source/JavaScriptCore/dfg/DFGMayExit.cpp
r229514 r231195 75 75 case GetStack: 76 76 case GetCallee: 77 case SetCallee: 77 78 case GetArgumentCountIncludingThis: 78 79 case SetArgumentCountIncludingThis: -
trunk/Source/JavaScriptCore/dfg/DFGNodeType.h
r230964 r231195 55 55 macro(CreateThis, NodeResultJS) /* Note this is not MustGenerate since we're returning it anyway. */ \ 56 56 macro(GetCallee, NodeResultJS) \ 57 macro(SetCallee, NodeMustGenerate) \ 57 58 macro(GetArgumentCountIncludingThis, NodeResultInt32) \ 58 59 macro(SetArgumentCountIncludingThis, NodeMustGenerate) \ -
trunk/Source/JavaScriptCore/dfg/DFGPredictionPropagationPhase.cpp
r230516 r231195 777 777 } 778 778 779 case SetCallee: 779 780 case SetArgumentCountIncludingThis: 780 781 break; -
trunk/Source/JavaScriptCore/dfg/DFGSafeToExecute.h
r230516 r231195 173 173 case CreateThis: 174 174 case GetCallee: 175 case SetCallee: 175 176 case GetArgumentCountIncludingThis: 176 177 case SetArgumentCountIncludingThis: -
trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.cpp
r231129 r231195 11867 11867 } 11868 11868 11869 void SpeculativeJIT::compileSetCallee(Node* node) 11870 { 11871 SpeculateCellOperand callee(this, node->child1()); 11872 m_jit.storeCell(callee.gpr(), JITCompiler::payloadFor(CallFrameSlot::callee)); 11873 noResult(node); 11874 } 11875 11869 11876 void SpeculativeJIT::compileGetArgumentCountIncludingThis(Node* node) 11870 11877 { -
trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT.h
r230748 r231195 1460 1460 void compileGetSetter(Node*); 1461 1461 void compileGetCallee(Node*); 1462 void compileSetCallee(Node*); 1462 1463 void compileGetArgumentCountIncludingThis(Node*); 1463 1464 void compileSetArgumentCountIncludingThis(Node*); -
trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT32_64.cpp
r230626 r231195 3254 3254 case GetCallee: { 3255 3255 compileGetCallee(node); 3256 break; 3257 } 3258 3259 case SetCallee: { 3260 compileSetCallee(node); 3256 3261 break; 3257 3262 } -
trunk/Source/JavaScriptCore/dfg/DFGSpeculativeJIT64.cpp
r230748 r231195 3475 3475 case GetCallee: { 3476 3476 compileGetCallee(node); 3477 break; 3478 } 3479 3480 case SetCallee: { 3481 compileSetCallee(node); 3477 3482 break; 3478 3483 } -
trunk/Source/JavaScriptCore/ftl/FTLCapabilities.cpp
r230516 r231195 183 183 case GetScope: 184 184 case GetCallee: 185 case SetCallee: 185 186 case GetArgumentCountIncludingThis: 186 187 case SetArgumentCountIncludingThis: -
trunk/Source/JavaScriptCore/ftl/FTLLowerDFGToB3.cpp
r231129 r231195 925 925 compileGetCallee(); 926 926 break; 927 case SetCallee: 928 compileSetCallee(); 929 break; 927 930 case GetArgumentCountIncludingThis: 928 931 compileGetArgumentCountIncludingThis(); … … 6626 6629 { 6627 6630 setJSValue(m_out.loadPtr(addressFor(CallFrameSlot::callee))); 6631 } 6632 6633 void compileSetCallee() 6634 { 6635 auto callee = lowCell(m_node->child1()); 6636 m_out.storePtr(callee, payloadFor(CallFrameSlot::callee)); 6628 6637 } 6629 6638
Note: See TracChangeset
for help on using the changeset viewer.