Unreviewed, rolling out r227592.
[WebKit-https.git] / Source / JavaScriptCore / ftl / FTLLowerDFGToB3.cpp
1 /*
2  * Copyright (C) 2013-2018 Apple Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
17  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
24  */
25
26 #include "config.h"
27 #include "FTLLowerDFGToB3.h"
28
29 #if ENABLE(FTL_JIT)
30
31 #include "AirCode.h"
32 #include "AirGenerationContext.h"
33 #include "AllowMacroScratchRegisterUsage.h"
34 #include "AtomicsObject.h"
35 #include "B3CheckValue.h"
36 #include "B3FenceValue.h"
37 #include "B3PatchpointValue.h"
38 #include "B3SlotBaseValue.h"
39 #include "B3StackmapGenerationParams.h"
40 #include "B3ValueInlines.h"
41 #include "CallFrameShuffler.h"
42 #include "CodeBlockWithJITType.h"
43 #include "DFGAbstractInterpreterInlines.h"
44 #include "DFGCapabilities.h"
45 #include "DFGDominators.h"
46 #include "DFGInPlaceAbstractState.h"
47 #include "DFGOSRAvailabilityAnalysisPhase.h"
48 #include "DFGOSRExitFuzz.h"
49 #include "DirectArguments.h"
50 #include "FTLAbstractHeapRepository.h"
51 #include "FTLAvailableRecovery.h"
52 #include "FTLExceptionTarget.h"
53 #include "FTLForOSREntryJITCode.h"
54 #include "FTLFormattedValue.h"
55 #include "FTLLazySlowPathCall.h"
56 #include "FTLLoweredNodeValue.h"
57 #include "FTLOperations.h"
58 #include "FTLOutput.h"
59 #include "FTLPatchpointExceptionHandle.h"
60 #include "FTLSnippetParams.h"
61 #include "FTLThunks.h"
62 #include "FTLWeightedTarget.h"
63 #include "JITAddGenerator.h"
64 #include "JITBitAndGenerator.h"
65 #include "JITBitOrGenerator.h"
66 #include "JITBitXorGenerator.h"
67 #include "JITDivGenerator.h"
68 #include "JITInlineCacheGenerator.h"
69 #include "JITLeftShiftGenerator.h"
70 #include "JITMathIC.h"
71 #include "JITMulGenerator.h"
72 #include "JITRightShiftGenerator.h"
73 #include "JITSubGenerator.h"
74 #include "JSAsyncFunction.h"
75 #include "JSAsyncGeneratorFunction.h"
76 #include "JSCInlines.h"
77 #include "JSGeneratorFunction.h"
78 #include "JSLexicalEnvironment.h"
79 #include "JSMap.h"
80 #include "OperandsInlines.h"
81 #include "RegExpObject.h"
82 #include "ScopedArguments.h"
83 #include "ScopedArgumentsTable.h"
84 #include "ScratchRegisterAllocator.h"
85 #include "SetupVarargsFrame.h"
86 #include "ShadowChicken.h"
87 #include "StructureStubInfo.h"
88 #include "SuperSampler.h"
89 #include "ThunkGenerators.h"
90 #include "VirtualRegister.h"
91 #include "Watchdog.h"
92 #include <atomic>
93 #include <unordered_set>
94 #include <wtf/Box.h>
95 #include <wtf/Gigacage.h>
96 #include <wtf/RecursableLambda.h>
97
98 #undef RELEASE_ASSERT
99 #define RELEASE_ASSERT(assertion) do { \
100     if (!(assertion)) { \
101         WTFReportAssertionFailure(__FILE__, __LINE__, WTF_PRETTY_FUNCTION, #assertion); \
102         CRASH(); \
103     } \
104 } while (0)
105
106 namespace JSC { namespace FTL {
107
108 using namespace B3;
109 using namespace DFG;
110
111 namespace {
112
113 std::atomic<int> compileCounter;
114
115 #if !ASSERT_DISABLED
116 NO_RETURN_DUE_TO_CRASH static void ftlUnreachable(
117     CodeBlock* codeBlock, BlockIndex blockIndex, unsigned nodeIndex)
118 {
119     dataLog("Crashing in thought-to-be-unreachable FTL-generated code for ", pointerDump(codeBlock), " at basic block #", blockIndex);
120     if (nodeIndex != UINT_MAX)
121         dataLog(", node @", nodeIndex);
122     dataLog(".\n");
123     CRASH();
124 }
125 #endif
126
127 // Using this instead of typeCheck() helps to reduce the load on B3, by creating
128 // significantly less dead code.
129 #define FTL_TYPE_CHECK_WITH_EXIT_KIND(exitKind, lowValue, highValue, typesPassedThrough, failCondition) do { \
130         FormattedValue _ftc_lowValue = (lowValue);                      \
131         Edge _ftc_highValue = (highValue);                              \
132         SpeculatedType _ftc_typesPassedThrough = (typesPassedThrough);  \
133         if (!m_interpreter.needsTypeCheck(_ftc_highValue, _ftc_typesPassedThrough)) \
134             break;                                                      \
135         typeCheck(_ftc_lowValue, _ftc_highValue, _ftc_typesPassedThrough, (failCondition), exitKind); \
136     } while (false)
137
138 #define FTL_TYPE_CHECK(lowValue, highValue, typesPassedThrough, failCondition) \
139     FTL_TYPE_CHECK_WITH_EXIT_KIND(BadType, lowValue, highValue, typesPassedThrough, failCondition)
140
141 class LowerDFGToB3 {
142     WTF_MAKE_NONCOPYABLE(LowerDFGToB3);
143 public:
144     LowerDFGToB3(State& state)
145         : m_graph(state.graph)
146         , m_ftlState(state)
147         , m_out(state)
148         , m_proc(*state.proc)
149         , m_availabilityCalculator(m_graph)
150         , m_state(state.graph)
151         , m_interpreter(state.graph, m_state)
152         , m_indexMaskingMode(Options::enableSpectreMitigations() ?  IndexMaskingEnabled : IndexMaskingDisabled)
153     {
154     }
155     
156     void lower()
157     {
158         State* state = &m_ftlState;
159         
160         CString name;
161         if (verboseCompilationEnabled()) {
162             name = toCString(
163                 "jsBody_", ++compileCounter, "_", codeBlock()->inferredName(),
164                 "_", codeBlock()->hash());
165         } else
166             name = "jsBody";
167
168         {
169             m_proc.setNumEntrypoints(m_graph.m_numberOfEntrypoints);
170             CodeBlock* codeBlock = m_graph.m_codeBlock;
171
172             Ref<B3::Air::PrologueGenerator> catchPrologueGenerator = createSharedTask<B3::Air::PrologueGeneratorFunction>(
173                 [codeBlock] (CCallHelpers& jit, B3::Air::Code& code) {
174                     AllowMacroScratchRegisterUsage allowScratch(jit);
175                     jit.addPtr(CCallHelpers::TrustedImm32(-code.frameSize()), GPRInfo::callFrameRegister, CCallHelpers::stackPointerRegister);
176                     jit.emitSave(code.calleeSaveRegisterAtOffsetList());
177                     jit.emitPutToCallFrameHeader(codeBlock, CallFrameSlot::codeBlock);
178                 });
179
180             for (unsigned catchEntrypointIndex : m_graph.m_entrypointIndexToCatchBytecodeOffset.keys()) {
181                 RELEASE_ASSERT(catchEntrypointIndex != 0);
182                 m_proc.code().setPrologueForEntrypoint(catchEntrypointIndex, catchPrologueGenerator.copyRef());
183             }
184
185             if (m_graph.m_maxLocalsForCatchOSREntry) {
186                 uint32_t numberOfLiveLocals = std::max(*m_graph.m_maxLocalsForCatchOSREntry, 1u); // Make sure we always allocate a non-null catchOSREntryBuffer.
187                 m_ftlState.jitCode->common.catchOSREntryBuffer = m_graph.m_vm.scratchBufferForSize(sizeof(JSValue) * numberOfLiveLocals);
188             }
189         }
190         
191         m_graph.ensureSSADominators();
192
193         if (verboseCompilationEnabled())
194             dataLog("Function ready, beginning lowering.\n");
195
196         m_out.initialize(m_heaps);
197
198         // We use prologue frequency for all of the initialization code.
199         m_out.setFrequency(1);
200         
201         bool hasMultipleEntrypoints = m_graph.m_numberOfEntrypoints > 1;
202     
203         LBasicBlock prologue = m_out.newBlock();
204         LBasicBlock callEntrypointArgumentSpeculations = hasMultipleEntrypoints ? m_out.newBlock() : nullptr;
205         m_handleExceptions = m_out.newBlock();
206
207         for (BlockIndex blockIndex = 0; blockIndex < m_graph.numBlocks(); ++blockIndex) {
208             m_highBlock = m_graph.block(blockIndex);
209             if (!m_highBlock)
210                 continue;
211             m_out.setFrequency(m_highBlock->executionCount);
212             m_blocks.add(m_highBlock, m_out.newBlock());
213         }
214
215         // Back to prologue frequency for any bocks that get sneakily created in the initialization code.
216         m_out.setFrequency(1);
217         
218         m_out.appendTo(prologue, hasMultipleEntrypoints ? callEntrypointArgumentSpeculations : m_handleExceptions);
219         m_out.initializeConstants(m_proc, prologue);
220         createPhiVariables();
221
222         size_t sizeOfCaptured = sizeof(JSValue) * m_graph.m_nextMachineLocal;
223         B3::SlotBaseValue* capturedBase = m_out.lockedStackSlot(sizeOfCaptured);
224         m_captured = m_out.add(capturedBase, m_out.constIntPtr(sizeOfCaptured));
225         state->capturedValue = capturedBase->slot();
226
227         auto preOrder = m_graph.blocksInPreOrder();
228
229         m_callFrame = m_out.framePointer();
230         m_tagTypeNumber = m_out.constInt64(TagTypeNumber);
231         m_tagMask = m_out.constInt64(TagMask);
232
233         // Make sure that B3 knows that we really care about the mask registers. This forces the
234         // constants to be materialized in registers.
235         m_proc.addFastConstant(m_tagTypeNumber->key());
236         m_proc.addFastConstant(m_tagMask->key());
237         
238         // We don't want the CodeBlock to have a weak pointer to itself because
239         // that would cause it to always get collected.
240         m_out.storePtr(m_out.constIntPtr(bitwise_cast<intptr_t>(codeBlock())), addressFor(CallFrameSlot::codeBlock));
241
242         VM* vm = &this->vm();
243
244         // Stack Overflow Check.
245         unsigned exitFrameSize = m_graph.requiredRegisterCountForExit() * sizeof(Register);
246         MacroAssembler::AbsoluteAddress addressOfStackLimit(vm->addressOfSoftStackLimit());
247         PatchpointValue* stackOverflowHandler = m_out.patchpoint(Void);
248         CallSiteIndex callSiteIndex = callSiteIndexForCodeOrigin(m_ftlState, CodeOrigin(0));
249         stackOverflowHandler->appendSomeRegister(m_callFrame);
250         stackOverflowHandler->clobber(RegisterSet::macroScratchRegisters());
251         stackOverflowHandler->numGPScratchRegisters = 1;
252         stackOverflowHandler->setGenerator(
253             [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
254                 AllowMacroScratchRegisterUsage allowScratch(jit);
255                 GPRReg fp = params[0].gpr();
256                 GPRReg scratch = params.gpScratch(0);
257
258                 unsigned ftlFrameSize = params.proc().frameSize();
259                 unsigned maxFrameSize = std::max(exitFrameSize, ftlFrameSize);
260
261                 jit.addPtr(MacroAssembler::TrustedImm32(-maxFrameSize), fp, scratch);
262                 MacroAssembler::JumpList stackOverflow;
263                 if (UNLIKELY(maxFrameSize > Options::reservedZoneSize()))
264                     stackOverflow.append(jit.branchPtr(MacroAssembler::Above, scratch, fp));
265                 stackOverflow.append(jit.branchPtr(MacroAssembler::Above, addressOfStackLimit, scratch));
266
267                 params.addLatePath([=] (CCallHelpers& jit) {
268                     AllowMacroScratchRegisterUsage allowScratch(jit);
269
270                     stackOverflow.link(&jit);
271                     
272                     // FIXME: We would not have to do this if the stack check was part of the Air
273                     // prologue. Then, we would know that there is no way for the callee-saves to
274                     // get clobbered.
275                     // https://bugs.webkit.org/show_bug.cgi?id=172456
276                     jit.emitRestore(params.proc().calleeSaveRegisterAtOffsetList());
277                     
278                     jit.store32(
279                         MacroAssembler::TrustedImm32(callSiteIndex.bits()),
280                         CCallHelpers::tagFor(VirtualRegister(CallFrameSlot::argumentCount)));
281                     jit.copyCalleeSavesToEntryFrameCalleeSavesBuffer(vm->topEntryFrame);
282
283                     jit.move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR0);
284                     jit.move(CCallHelpers::TrustedImmPtr(jit.codeBlock()), GPRInfo::argumentGPR1);
285                     CCallHelpers::Call throwCall = jit.call();
286
287                     jit.move(CCallHelpers::TrustedImmPtr(vm), GPRInfo::argumentGPR0);
288                     jit.move(GPRInfo::callFrameRegister, GPRInfo::argumentGPR1);
289                     CCallHelpers::Call lookupExceptionHandlerCall = jit.call();
290                     jit.jumpToExceptionHandler(*vm);
291
292                     jit.addLinkTask(
293                         [=] (LinkBuffer& linkBuffer) {
294                             linkBuffer.link(throwCall, FunctionPtr(operationThrowStackOverflowError));
295                             linkBuffer.link(lookupExceptionHandlerCall, FunctionPtr(lookupExceptionHandlerFromCallerFrame));
296                     });
297                 });
298             });
299
300         LBasicBlock firstDFGBasicBlock = lowBlock(m_graph.block(0));
301
302         {
303             if (hasMultipleEntrypoints) {
304                 Vector<LBasicBlock> successors(m_graph.m_numberOfEntrypoints);
305                 successors[0] = callEntrypointArgumentSpeculations;
306                 for (unsigned i = 1; i < m_graph.m_numberOfEntrypoints; ++i) {
307                     // Currently, the only other entrypoint is an op_catch entrypoint.
308                     // We do OSR entry at op_catch, and we prove argument formats before
309                     // jumping to FTL code, so we don't need to check argument types here
310                     // for these entrypoints.
311                     successors[i] = firstDFGBasicBlock;
312                 }
313                 
314                 m_out.entrySwitch(successors);
315                 m_out.appendTo(callEntrypointArgumentSpeculations, m_handleExceptions);
316             }
317
318             m_node = nullptr;
319             m_origin = NodeOrigin(CodeOrigin(0), CodeOrigin(0), true);
320
321             // Check Arguments.
322             availabilityMap().clear();
323             availabilityMap().m_locals = Operands<Availability>(codeBlock()->numParameters(), 0);
324             for (unsigned i = codeBlock()->numParameters(); i--;) {
325                 availabilityMap().m_locals.argument(i) =
326                     Availability(FlushedAt(FlushedJSValue, virtualRegisterForArgument(i)));
327             }
328
329             for (unsigned i = codeBlock()->numParameters(); i--;) {
330                 MethodOfGettingAValueProfile profile(&m_graph.m_profiledBlock->valueProfileForArgument(i));
331                 VirtualRegister operand = virtualRegisterForArgument(i);
332                 LValue jsValue = m_out.load64(addressFor(operand));
333                 
334                 switch (m_graph.m_argumentFormats[0][i]) {
335                 case FlushedInt32:
336                     speculate(BadType, jsValueValue(jsValue), profile, isNotInt32(jsValue));
337                     break;
338                 case FlushedBoolean:
339                     speculate(BadType, jsValueValue(jsValue), profile, isNotBoolean(jsValue));
340                     break;
341                 case FlushedCell:
342                     speculate(BadType, jsValueValue(jsValue), profile, isNotCell(jsValue));
343                     break;
344                 case FlushedJSValue:
345                     break;
346                 default:
347                     DFG_CRASH(m_graph, nullptr, "Bad flush format for argument");
348                     break;
349                 }
350             }
351             m_out.jump(firstDFGBasicBlock);
352         }
353
354
355         m_out.appendTo(m_handleExceptions, firstDFGBasicBlock);
356         Box<CCallHelpers::Label> exceptionHandler = state->exceptionHandler;
357         m_out.patchpoint(Void)->setGenerator(
358             [=] (CCallHelpers& jit, const StackmapGenerationParams&) {
359                 CCallHelpers::Jump jump = jit.jump();
360                 jit.addLinkTask(
361                     [=] (LinkBuffer& linkBuffer) {
362                         linkBuffer.link(jump, linkBuffer.locationOf(*exceptionHandler));
363                     });
364             });
365         m_out.unreachable();
366
367         for (DFG::BasicBlock* block : preOrder)
368             compileBlock(block);
369
370         // Make sure everything is decorated. This does a bunch of deferred decorating. This has
371         // to happen last because our abstract heaps are generated lazily. They have to be
372         // generated lazily because we have an infinite number of numbered, indexed, and
373         // absolute heaps. We only become aware of the ones we actually mention while lowering.
374         m_heaps.computeRangesAndDecorateInstructions();
375
376         // We create all Phi's up front, but we may then decide not to compile the basic block
377         // that would have contained one of them. So this creates orphans, which triggers B3
378         // validation failures. Calling this fixes the issue.
379         //
380         // Note that you should avoid the temptation to make this call conditional upon
381         // validation being enabled. B3 makes no guarantees of any kind of correctness when
382         // dealing with IR that would have failed validation. For example, it would be valid to
383         // write a B3 phase that so aggressively assumes the lack of orphans that it would crash
384         // if any orphans were around. We might even have such phases already.
385         m_proc.deleteOrphans();
386
387         // We put the blocks into the B3 procedure in a super weird order. Now we reorder them.
388         m_out.applyBlockOrder();
389     }
390
391 private:
392     
393     void createPhiVariables()
394     {
395         for (BlockIndex blockIndex = m_graph.numBlocks(); blockIndex--;) {
396             DFG::BasicBlock* block = m_graph.block(blockIndex);
397             if (!block)
398                 continue;
399             for (unsigned nodeIndex = block->size(); nodeIndex--;) {
400                 Node* node = block->at(nodeIndex);
401                 if (node->op() != DFG::Phi)
402                     continue;
403                 LType type;
404                 switch (node->flags() & NodeResultMask) {
405                 case NodeResultDouble:
406                     type = Double;
407                     break;
408                 case NodeResultInt32:
409                     type = Int32;
410                     break;
411                 case NodeResultInt52:
412                     type = Int64;
413                     break;
414                 case NodeResultBoolean:
415                     type = Int32;
416                     break;
417                 case NodeResultJS:
418                     type = Int64;
419                     break;
420                 default:
421                     DFG_CRASH(m_graph, node, "Bad Phi node result type");
422                     break;
423                 }
424                 m_phis.add(node, m_proc.add<Value>(B3::Phi, type, Origin(node)));
425             }
426         }
427     }
428     
429     void compileBlock(DFG::BasicBlock* block)
430     {
431         if (!block)
432             return;
433         
434         if (verboseCompilationEnabled())
435             dataLog("Compiling block ", *block, "\n");
436         
437         m_highBlock = block;
438         
439         // Make sure that any blocks created while lowering code in the high block have the frequency of
440         // the high block. This is appropriate because B3 doesn't need precise frequencies. It just needs
441         // something roughly approximate for things like register allocation.
442         m_out.setFrequency(m_highBlock->executionCount);
443         
444         LBasicBlock lowBlock = m_blocks.get(m_highBlock);
445         
446         m_nextHighBlock = 0;
447         for (BlockIndex nextBlockIndex = m_highBlock->index + 1; nextBlockIndex < m_graph.numBlocks(); ++nextBlockIndex) {
448             m_nextHighBlock = m_graph.block(nextBlockIndex);
449             if (m_nextHighBlock)
450                 break;
451         }
452         m_nextLowBlock = m_nextHighBlock ? m_blocks.get(m_nextHighBlock) : 0;
453         
454         // All of this effort to find the next block gives us the ability to keep the
455         // generated IR in roughly program order. This ought not affect the performance
456         // of the generated code (since we expect B3 to reorder things) but it will
457         // make IR dumps easier to read.
458         m_out.appendTo(lowBlock, m_nextLowBlock);
459         
460         if (Options::ftlCrashes())
461             m_out.trap();
462         
463         if (!m_highBlock->cfaHasVisited) {
464             if (verboseCompilationEnabled())
465                 dataLog("Bailing because CFA didn't reach.\n");
466             crash(m_highBlock, nullptr);
467             return;
468         }
469         
470         m_availabilityCalculator.beginBlock(m_highBlock);
471         
472         m_state.reset();
473         m_state.beginBasicBlock(m_highBlock);
474         
475         for (m_nodeIndex = 0; m_nodeIndex < m_highBlock->size(); ++m_nodeIndex) {
476             if (!compileNode(m_nodeIndex))
477                 break;
478         }
479     }
480
481     void safelyInvalidateAfterTermination()
482     {
483         if (verboseCompilationEnabled())
484             dataLog("Bailing.\n");
485         crash();
486
487         // Invalidate dominated blocks. Under normal circumstances we would expect
488         // them to be invalidated already. But you can have the CFA become more
489         // precise over time because the structures of objects change on the main
490         // thread. Failing to do this would result in weird crashes due to a value
491         // being used but not defined. Race conditions FTW!
492         for (BlockIndex blockIndex = m_graph.numBlocks(); blockIndex--;) {
493             DFG::BasicBlock* target = m_graph.block(blockIndex);
494             if (!target)
495                 continue;
496             if (m_graph.m_ssaDominators->dominates(m_highBlock, target)) {
497                 if (verboseCompilationEnabled())
498                     dataLog("Block ", *target, " will bail also.\n");
499                 target->cfaHasVisited = false;
500             }
501         }
502     }
503
504     bool compileNode(unsigned nodeIndex)
505     {
506         if (!m_state.isValid()) {
507             safelyInvalidateAfterTermination();
508             return false;
509         }
510         
511         m_node = m_highBlock->at(nodeIndex);
512         m_origin = m_node->origin;
513         m_out.setOrigin(m_node);
514         
515         if (verboseCompilationEnabled())
516             dataLog("Lowering ", m_node, "\n");
517         
518         m_availableRecoveries.shrink(0);
519         
520         m_interpreter.startExecuting();
521         m_interpreter.executeKnownEdgeTypes(m_node);
522         
523         switch (m_node->op()) {
524         case DFG::Upsilon:
525             compileUpsilon();
526             break;
527         case DFG::Phi:
528             compilePhi();
529             break;
530         case JSConstant:
531             break;
532         case DoubleConstant:
533             compileDoubleConstant();
534             break;
535         case Int52Constant:
536             compileInt52Constant();
537             break;
538         case LazyJSConstant:
539             compileLazyJSConstant();
540             break;
541         case DoubleRep:
542             compileDoubleRep();
543             break;
544         case DoubleAsInt32:
545             compileDoubleAsInt32();
546             break;
547         case DFG::ValueRep:
548             compileValueRep();
549             break;
550         case Int52Rep:
551             compileInt52Rep();
552             break;
553         case ValueToInt32:
554             compileValueToInt32();
555             break;
556         case BooleanToNumber:
557             compileBooleanToNumber();
558             break;
559         case ExtractOSREntryLocal:
560             compileExtractOSREntryLocal();
561             break;
562         case ExtractCatchLocal:
563             compileExtractCatchLocal();
564             break;
565         case GetStack:
566             compileGetStack();
567             break;
568         case PutStack:
569             compilePutStack();
570             break;
571         case DFG::Check:
572             compileNoOp();
573             break;
574         case ToObject:
575         case CallObjectConstructor:
576             compileToObjectOrCallObjectConstructor();
577             break;
578         case ToThis:
579             compileToThis();
580             break;
581         case ValueAdd:
582             compileValueAdd();
583             break;
584         case StrCat:
585             compileStrCat();
586             break;
587         case ArithAdd:
588         case ArithSub:
589             compileArithAddOrSub();
590             break;
591         case ArithClz32:
592             compileArithClz32();
593             break;
594         case ArithMul:
595             compileArithMul();
596             break;
597         case ArithDiv:
598             compileArithDiv();
599             break;
600         case ArithMod:
601             compileArithMod();
602             break;
603         case ArithMin:
604         case ArithMax:
605             compileArithMinOrMax();
606             break;
607         case ArithAbs:
608             compileArithAbs();
609             break;
610         case ArithPow:
611             compileArithPow();
612             break;
613         case ArithRandom:
614             compileArithRandom();
615             break;
616         case ArithRound:
617             compileArithRound();
618             break;
619         case ArithFloor:
620             compileArithFloor();
621             break;
622         case ArithCeil:
623             compileArithCeil();
624             break;
625         case ArithTrunc:
626             compileArithTrunc();
627             break;
628         case ArithSqrt:
629             compileArithSqrt();
630             break;
631         case ArithFRound:
632             compileArithFRound();
633             break;
634         case ArithNegate:
635             compileArithNegate();
636             break;
637         case ArithUnary:
638             compileArithUnary();
639             break;
640         case DFG::BitAnd:
641             compileBitAnd();
642             break;
643         case DFG::BitOr:
644             compileBitOr();
645             break;
646         case DFG::BitXor:
647             compileBitXor();
648             break;
649         case BitRShift:
650             compileBitRShift();
651             break;
652         case BitLShift:
653             compileBitLShift();
654             break;
655         case BitURShift:
656             compileBitURShift();
657             break;
658         case UInt32ToNumber:
659             compileUInt32ToNumber();
660             break;
661         case CheckStructure:
662             compileCheckStructure();
663             break;
664         case CheckStructureOrEmpty:
665             compileCheckStructureOrEmpty();
666             break;
667         case CheckCell:
668             compileCheckCell();
669             break;
670         case CheckNotEmpty:
671             compileCheckNotEmpty();
672             break;
673         case AssertNotEmpty:
674             compileAssertNotEmpty();
675             break;
676         case CheckBadCell:
677             compileCheckBadCell();
678             break;
679         case CheckStringIdent:
680             compileCheckStringIdent();
681             break;
682         case GetExecutable:
683             compileGetExecutable();
684             break;
685         case Arrayify:
686         case ArrayifyToStructure:
687             compileArrayify();
688             break;
689         case PutStructure:
690             compilePutStructure();
691             break;
692         case TryGetById:
693             compileGetById(AccessType::TryGet);
694             break;
695         case GetById:
696         case GetByIdFlush:
697             compileGetById(AccessType::Get);
698             break;
699         case GetByIdWithThis:
700             compileGetByIdWithThis();
701             break;
702         case In:
703             compileIn();
704             break;
705         case HasOwnProperty:
706             compileHasOwnProperty();
707             break;
708         case PutById:
709         case PutByIdDirect:
710         case PutByIdFlush:
711             compilePutById();
712             break;
713         case PutByIdWithThis:
714             compilePutByIdWithThis();
715             break;
716         case PutGetterById:
717         case PutSetterById:
718             compilePutAccessorById();
719             break;
720         case PutGetterSetterById:
721             compilePutGetterSetterById();
722             break;
723         case PutGetterByVal:
724         case PutSetterByVal:
725             compilePutAccessorByVal();
726             break;
727         case DeleteById:
728             compileDeleteById();
729             break;
730         case DeleteByVal:
731             compileDeleteByVal();
732             break;
733         case GetButterfly:
734             compileGetButterfly();
735             break;
736         case ConstantStoragePointer:
737             compileConstantStoragePointer();
738             break;
739         case GetIndexedPropertyStorage:
740             compileGetIndexedPropertyStorage();
741             break;
742         case CheckArray:
743             compileCheckArray();
744             break;
745         case GetArrayLength:
746             compileGetArrayLength();
747             break;
748         case GetVectorLength:
749             compileGetVectorLength();
750             break;
751         case CheckInBounds:
752             compileCheckInBounds();
753             break;
754         case GetByVal:
755             compileGetByVal();
756             break;
757         case GetMyArgumentByVal:
758         case GetMyArgumentByValOutOfBounds:
759             compileGetMyArgumentByVal();
760             break;
761         case GetByValWithThis:
762             compileGetByValWithThis();
763             break;
764         case PutByVal:
765         case PutByValAlias:
766         case PutByValDirect:
767             compilePutByVal();
768             break;
769         case PutByValWithThis:
770             compilePutByValWithThis();
771             break;
772         case AtomicsAdd:
773         case AtomicsAnd:
774         case AtomicsCompareExchange:
775         case AtomicsExchange:
776         case AtomicsLoad:
777         case AtomicsOr:
778         case AtomicsStore:
779         case AtomicsSub:
780         case AtomicsXor:
781             compileAtomicsReadModifyWrite();
782             break;
783         case AtomicsIsLockFree:
784             compileAtomicsIsLockFree();
785             break;
786         case DefineDataProperty:
787             compileDefineDataProperty();
788             break;
789         case DefineAccessorProperty:
790             compileDefineAccessorProperty();
791             break;
792         case ArrayPush:
793             compileArrayPush();
794             break;
795         case ArrayPop:
796             compileArrayPop();
797             break;
798         case ArraySlice:
799             compileArraySlice();
800             break;
801         case ArrayIndexOf:
802             compileArrayIndexOf();
803             break;
804         case CreateActivation:
805             compileCreateActivation();
806             break;
807         case PushWithScope:
808             compilePushWithScope();
809             break;
810         case NewFunction:
811         case NewGeneratorFunction:
812         case NewAsyncGeneratorFunction:
813         case NewAsyncFunction:
814             compileNewFunction();
815             break;
816         case CreateDirectArguments:
817             compileCreateDirectArguments();
818             break;
819         case CreateScopedArguments:
820             compileCreateScopedArguments();
821             break;
822         case CreateClonedArguments:
823             compileCreateClonedArguments();
824             break;
825         case NewObject:
826             compileNewObject();
827             break;
828         case NewStringObject:
829             compileNewStringObject();
830             break;
831         case NewArray:
832             compileNewArray();
833             break;
834         case NewArrayWithSpread:
835             compileNewArrayWithSpread();
836             break;
837         case Spread:
838             compileSpread();
839             break;
840         case NewArrayBuffer:
841             compileNewArrayBuffer();
842             break;
843         case NewArrayWithSize:
844             compileNewArrayWithSize();
845             break;
846         case NewTypedArray:
847             compileNewTypedArray();
848             break;
849         case GetTypedArrayByteOffset:
850             compileGetTypedArrayByteOffset();
851             break;
852         case GetPrototypeOf:
853             compileGetPrototypeOf();
854             break;
855         case AllocatePropertyStorage:
856             compileAllocatePropertyStorage();
857             break;
858         case ReallocatePropertyStorage:
859             compileReallocatePropertyStorage();
860             break;
861         case NukeStructureAndSetButterfly:
862             compileNukeStructureAndSetButterfly();
863             break;
864         case ToNumber:
865             compileToNumber();
866             break;
867         case ToString:
868         case CallStringConstructor:
869             compileToStringOrCallStringConstructor();
870             break;
871         case ToPrimitive:
872             compileToPrimitive();
873             break;
874         case MakeRope:
875             compileMakeRope();
876             break;
877         case StringCharAt:
878             compileStringCharAt();
879             break;
880         case StringCharCodeAt:
881             compileStringCharCodeAt();
882             break;
883         case StringFromCharCode:
884             compileStringFromCharCode();
885             break;
886         case GetByOffset:
887         case GetGetterSetterByOffset:
888             compileGetByOffset();
889             break;
890         case GetGetter:
891             compileGetGetter();
892             break;
893         case GetSetter:
894             compileGetSetter();
895             break;
896         case MultiGetByOffset:
897             compileMultiGetByOffset();
898             break;
899         case PutByOffset:
900             compilePutByOffset();
901             break;
902         case MultiPutByOffset:
903             compileMultiPutByOffset();
904             break;
905         case GetGlobalVar:
906         case GetGlobalLexicalVariable:
907             compileGetGlobalVariable();
908             break;
909         case PutGlobalVariable:
910             compilePutGlobalVariable();
911             break;
912         case NotifyWrite:
913             compileNotifyWrite();
914             break;
915         case GetCallee:
916             compileGetCallee();
917             break;
918         case GetArgumentCountIncludingThis:
919             compileGetArgumentCountIncludingThis();
920             break;
921         case SetArgumentCountIncludingThis:
922             compileSetArgumentCountIncludingThis();
923             break;
924         case GetScope:
925             compileGetScope();
926             break;
927         case SkipScope:
928             compileSkipScope();
929             break;
930         case GetGlobalObject:
931             compileGetGlobalObject();
932             break;
933         case GetGlobalThis:
934             compileGetGlobalThis();
935             break;
936         case GetClosureVar:
937             compileGetClosureVar();
938             break;
939         case PutClosureVar:
940             compilePutClosureVar();
941             break;
942         case GetFromArguments:
943             compileGetFromArguments();
944             break;
945         case PutToArguments:
946             compilePutToArguments();
947             break;
948         case GetArgument:
949             compileGetArgument();
950             break;
951         case CompareEq:
952             compileCompareEq();
953             break;
954         case CompareStrictEq:
955             compileCompareStrictEq();
956             break;
957         case CompareLess:
958             compileCompareLess();
959             break;
960         case CompareLessEq:
961             compileCompareLessEq();
962             break;
963         case CompareGreater:
964             compileCompareGreater();
965             break;
966         case CompareGreaterEq:
967             compileCompareGreaterEq();
968             break;
969         case CompareBelow:
970             compileCompareBelow();
971             break;
972         case CompareBelowEq:
973             compileCompareBelowEq();
974             break;
975         case CompareEqPtr:
976             compileCompareEqPtr();
977             break;
978         case LogicalNot:
979             compileLogicalNot();
980             break;
981         case Call:
982         case TailCallInlinedCaller:
983         case Construct:
984             compileCallOrConstruct();
985             break;
986         case DirectCall:
987         case DirectTailCallInlinedCaller:
988         case DirectConstruct:
989         case DirectTailCall:
990             compileDirectCallOrConstruct();
991             break;
992         case TailCall:
993             compileTailCall();
994             break;
995         case CallVarargs:
996         case CallForwardVarargs:
997         case TailCallVarargs:
998         case TailCallVarargsInlinedCaller:
999         case TailCallForwardVarargs:
1000         case TailCallForwardVarargsInlinedCaller:
1001         case ConstructVarargs:
1002         case ConstructForwardVarargs:
1003             compileCallOrConstructVarargs();
1004             break;
1005         case CallEval:
1006             compileCallEval();
1007             break;
1008         case LoadVarargs:
1009             compileLoadVarargs();
1010             break;
1011         case ForwardVarargs:
1012             compileForwardVarargs();
1013             break;
1014         case DFG::Jump:
1015             compileJump();
1016             break;
1017         case DFG::Branch:
1018             compileBranch();
1019             break;
1020         case DFG::Switch:
1021             compileSwitch();
1022             break;
1023         case DFG::EntrySwitch:
1024             compileEntrySwitch();
1025             break;
1026         case DFG::Return:
1027             compileReturn();
1028             break;
1029         case ForceOSRExit:
1030             compileForceOSRExit();
1031             break;
1032         case CPUIntrinsic:
1033 #if CPU(X86_64)
1034             compileCPUIntrinsic();
1035 #else
1036             RELEASE_ASSERT_NOT_REACHED();
1037 #endif
1038             break;
1039         case Throw:
1040             compileThrow();
1041             break;
1042         case ThrowStaticError:
1043             compileThrowStaticError();
1044             break;
1045         case InvalidationPoint:
1046             compileInvalidationPoint();
1047             break;
1048         case IsEmpty:
1049             compileIsEmpty();
1050             break;
1051         case IsUndefined:
1052             compileIsUndefined();
1053             break;
1054         case IsBoolean:
1055             compileIsBoolean();
1056             break;
1057         case IsNumber:
1058             compileIsNumber();
1059             break;
1060         case IsCellWithType:
1061             compileIsCellWithType();
1062             break;
1063         case MapHash:
1064             compileMapHash();
1065             break;
1066         case NormalizeMapKey:
1067             compileNormalizeMapKey();
1068             break;
1069         case GetMapBucket:
1070             compileGetMapBucket();
1071             break;
1072         case GetMapBucketHead:
1073             compileGetMapBucketHead();
1074             break;
1075         case GetMapBucketNext:
1076             compileGetMapBucketNext();
1077             break;
1078         case LoadKeyFromMapBucket:
1079             compileLoadKeyFromMapBucket();
1080             break;
1081         case LoadValueFromMapBucket:
1082             compileLoadValueFromMapBucket();
1083             break;
1084         case ExtractValueFromWeakMapGet:
1085             compileExtractValueFromWeakMapGet();
1086             break;
1087         case SetAdd:
1088             compileSetAdd();
1089             break;
1090         case MapSet:
1091             compileMapSet();
1092             break;
1093         case WeakMapGet:
1094             compileWeakMapGet();
1095             break;
1096         case IsObject:
1097             compileIsObject();
1098             break;
1099         case IsObjectOrNull:
1100             compileIsObjectOrNull();
1101             break;
1102         case IsFunction:
1103             compileIsFunction();
1104             break;
1105         case IsTypedArrayView:
1106             compileIsTypedArrayView();
1107             break;
1108         case ParseInt:
1109             compileParseInt();
1110             break;
1111         case TypeOf:
1112             compileTypeOf();
1113             break;
1114         case CheckTypeInfoFlags:
1115             compileCheckTypeInfoFlags();
1116             break;
1117         case OverridesHasInstance:
1118             compileOverridesHasInstance();
1119             break;
1120         case InstanceOf:
1121             compileInstanceOf();
1122             break;
1123         case InstanceOfCustom:
1124             compileInstanceOfCustom();
1125             break;
1126         case CountExecution:
1127             compileCountExecution();
1128             break;
1129         case SuperSamplerBegin:
1130             compileSuperSamplerBegin();
1131             break;
1132         case SuperSamplerEnd:
1133             compileSuperSamplerEnd();
1134             break;
1135         case StoreBarrier:
1136         case FencedStoreBarrier:
1137             compileStoreBarrier();
1138             break;
1139         case HasIndexedProperty:
1140             compileHasIndexedProperty();
1141             break;
1142         case HasGenericProperty:
1143             compileHasGenericProperty();
1144             break;
1145         case HasStructureProperty:
1146             compileHasStructureProperty();
1147             break;
1148         case GetDirectPname:
1149             compileGetDirectPname();
1150             break;
1151         case GetEnumerableLength:
1152             compileGetEnumerableLength();
1153             break;
1154         case GetPropertyEnumerator:
1155             compileGetPropertyEnumerator();
1156             break;
1157         case GetEnumeratorStructurePname:
1158             compileGetEnumeratorStructurePname();
1159             break;
1160         case GetEnumeratorGenericPname:
1161             compileGetEnumeratorGenericPname();
1162             break;
1163         case ToIndexString:
1164             compileToIndexString();
1165             break;
1166         case CheckStructureImmediate:
1167             compileCheckStructureImmediate();
1168             break;
1169         case MaterializeNewObject:
1170             compileMaterializeNewObject();
1171             break;
1172         case MaterializeCreateActivation:
1173             compileMaterializeCreateActivation();
1174             break;
1175         case CheckTraps:
1176             if (Options::usePollingTraps())
1177                 compileCheckTraps();
1178             break;
1179         case CreateRest:
1180             compileCreateRest();
1181             break;
1182         case GetRestLength:
1183             compileGetRestLength();
1184             break;
1185         case RegExpExec:
1186             compileRegExpExec();
1187             break;
1188         case RegExpExecNonGlobalOrSticky:
1189             compileRegExpExecNonGlobalOrSticky();
1190             break;
1191         case RegExpTest:
1192             compileRegExpTest();
1193             break;
1194         case RegExpMatchFast:
1195             compileRegExpMatchFast();
1196             break;
1197         case NewRegexp:
1198             compileNewRegexp();
1199             break;
1200         case SetFunctionName:
1201             compileSetFunctionName();
1202             break;
1203         case StringReplace:
1204         case StringReplaceRegExp:
1205             compileStringReplace();
1206             break;
1207         case GetRegExpObjectLastIndex:
1208             compileGetRegExpObjectLastIndex();
1209             break;
1210         case SetRegExpObjectLastIndex:
1211             compileSetRegExpObjectLastIndex();
1212             break;
1213         case LogShadowChickenPrologue:
1214             compileLogShadowChickenPrologue();
1215             break;
1216         case LogShadowChickenTail:
1217             compileLogShadowChickenTail();
1218             break;
1219         case RecordRegExpCachedResult:
1220             compileRecordRegExpCachedResult();
1221             break;
1222         case ResolveScopeForHoistingFuncDeclInEval:
1223             compileResolveScopeForHoistingFuncDeclInEval();
1224             break;
1225         case ResolveScope:
1226             compileResolveScope();
1227             break;
1228         case GetDynamicVar:
1229             compileGetDynamicVar();
1230             break;
1231         case PutDynamicVar:
1232             compilePutDynamicVar();
1233             break;
1234         case Unreachable:
1235             compileUnreachable();
1236             break;
1237         case StringSlice:
1238             compileStringSlice();
1239             break;
1240         case ToLowerCase:
1241             compileToLowerCase();
1242             break;
1243         case NumberToStringWithRadix:
1244             compileNumberToStringWithRadix();
1245             break;
1246         case NumberToStringWithValidRadixConstant:
1247             compileNumberToStringWithValidRadixConstant();
1248             break;
1249         case CheckSubClass:
1250             compileCheckSubClass();
1251             break;
1252         case CallDOM:
1253             compileCallDOM();
1254             break;
1255         case CallDOMGetter:
1256             compileCallDOMGetter();
1257             break;
1258
1259         case PhantomLocal:
1260         case LoopHint:
1261         case MovHint:
1262         case ZombieHint:
1263         case ExitOK:
1264         case PhantomNewObject:
1265         case PhantomNewFunction:
1266         case PhantomNewGeneratorFunction:
1267         case PhantomNewAsyncGeneratorFunction:
1268         case PhantomNewAsyncFunction:
1269         case PhantomCreateActivation:
1270         case PhantomDirectArguments:
1271         case PhantomCreateRest:
1272         case PhantomSpread:
1273         case PhantomNewArrayWithSpread:
1274         case PhantomNewArrayBuffer:
1275         case PhantomClonedArguments:
1276         case PhantomNewRegexp:
1277         case PutHint:
1278         case BottomValue:
1279         case KillStack:
1280         case InitializeEntrypointArguments:
1281             break;
1282         default:
1283             DFG_CRASH(m_graph, m_node, "Unrecognized node in FTL backend");
1284             break;
1285         }
1286         
1287         if (m_node->isTerminal())
1288             return false;
1289         
1290         if (!m_state.isValid()) {
1291             safelyInvalidateAfterTermination();
1292             return false;
1293         }
1294
1295         m_availabilityCalculator.executeNode(m_node);
1296         m_interpreter.executeEffects(nodeIndex);
1297         
1298         return true;
1299     }
1300
1301     void compileUpsilon()
1302     {
1303         LValue upsilonValue = nullptr;
1304         switch (m_node->child1().useKind()) {
1305         case DoubleRepUse:
1306             upsilonValue = lowDouble(m_node->child1());
1307             break;
1308         case Int32Use:
1309         case KnownInt32Use:
1310             upsilonValue = lowInt32(m_node->child1());
1311             break;
1312         case Int52RepUse:
1313             upsilonValue = lowInt52(m_node->child1());
1314             break;
1315         case BooleanUse:
1316         case KnownBooleanUse:
1317             upsilonValue = lowBoolean(m_node->child1());
1318             break;
1319         case CellUse:
1320         case KnownCellUse:
1321             upsilonValue = lowCell(m_node->child1());
1322             break;
1323         case UntypedUse:
1324             upsilonValue = lowJSValue(m_node->child1());
1325             break;
1326         default:
1327             DFG_CRASH(m_graph, m_node, "Bad use kind");
1328             break;
1329         }
1330         ValueFromBlock upsilon = m_out.anchor(upsilonValue);
1331         LValue phiNode = m_phis.get(m_node->phi());
1332         m_out.addIncomingToPhi(phiNode, upsilon);
1333     }
1334     
1335     void compilePhi()
1336     {
1337         LValue phi = m_phis.get(m_node);
1338         m_out.m_block->append(phi);
1339
1340         switch (m_node->flags() & NodeResultMask) {
1341         case NodeResultDouble:
1342             setDouble(phi);
1343             break;
1344         case NodeResultInt32:
1345             setInt32(phi);
1346             break;
1347         case NodeResultInt52:
1348             setInt52(phi);
1349             break;
1350         case NodeResultBoolean:
1351             setBoolean(phi);
1352             break;
1353         case NodeResultJS:
1354             setJSValue(phi);
1355             break;
1356         default:
1357             DFG_CRASH(m_graph, m_node, "Bad use kind");
1358             break;
1359         }
1360     }
1361     
1362     void compileDoubleConstant()
1363     {
1364         setDouble(m_out.constDouble(m_node->asNumber()));
1365     }
1366     
1367     void compileInt52Constant()
1368     {
1369         int64_t value = m_node->asAnyInt();
1370         
1371         setInt52(m_out.constInt64(value << JSValue::int52ShiftAmount));
1372         setStrictInt52(m_out.constInt64(value));
1373     }
1374
1375     void compileLazyJSConstant()
1376     {
1377         PatchpointValue* patchpoint = m_out.patchpoint(Int64);
1378         LazyJSValue value = m_node->lazyJSValue();
1379         patchpoint->setGenerator(
1380             [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
1381                 value.emit(jit, JSValueRegs(params[0].gpr()));
1382             });
1383         patchpoint->effects = Effects::none();
1384         setJSValue(patchpoint);
1385     }
1386
1387     void compileDoubleRep()
1388     {
1389         switch (m_node->child1().useKind()) {
1390         case RealNumberUse: {
1391             LValue value = lowJSValue(m_node->child1(), ManualOperandSpeculation);
1392             
1393             LValue doubleValue = unboxDouble(value);
1394             
1395             LBasicBlock intCase = m_out.newBlock();
1396             LBasicBlock continuation = m_out.newBlock();
1397             
1398             ValueFromBlock fastResult = m_out.anchor(doubleValue);
1399             m_out.branch(
1400                 m_out.doubleEqual(doubleValue, doubleValue),
1401                 usually(continuation), rarely(intCase));
1402             
1403             LBasicBlock lastNext = m_out.appendTo(intCase, continuation);
1404
1405             FTL_TYPE_CHECK(
1406                 jsValueValue(value), m_node->child1(), SpecBytecodeRealNumber,
1407                 isNotInt32(value, provenType(m_node->child1()) & ~SpecDoubleReal));
1408             ValueFromBlock slowResult = m_out.anchor(m_out.intToDouble(unboxInt32(value)));
1409             m_out.jump(continuation);
1410             
1411             m_out.appendTo(continuation, lastNext);
1412             
1413             setDouble(m_out.phi(Double, fastResult, slowResult));
1414             return;
1415         }
1416             
1417         case NotCellUse:
1418         case NumberUse: {
1419             bool shouldConvertNonNumber = m_node->child1().useKind() == NotCellUse;
1420             
1421             LValue value = lowJSValue(m_node->child1(), ManualOperandSpeculation);
1422
1423             LBasicBlock intCase = m_out.newBlock();
1424             LBasicBlock doubleTesting = m_out.newBlock();
1425             LBasicBlock doubleCase = m_out.newBlock();
1426             LBasicBlock nonDoubleCase = m_out.newBlock();
1427             LBasicBlock continuation = m_out.newBlock();
1428             
1429             m_out.branch(
1430                 isNotInt32(value, provenType(m_node->child1())),
1431                 unsure(doubleTesting), unsure(intCase));
1432             
1433             LBasicBlock lastNext = m_out.appendTo(intCase, doubleTesting);
1434             
1435             ValueFromBlock intToDouble = m_out.anchor(
1436                 m_out.intToDouble(unboxInt32(value)));
1437             m_out.jump(continuation);
1438             
1439             m_out.appendTo(doubleTesting, doubleCase);
1440             LValue valueIsNumber = isNumber(value, provenType(m_node->child1()));
1441             m_out.branch(valueIsNumber, usually(doubleCase), rarely(nonDoubleCase));
1442
1443             m_out.appendTo(doubleCase, nonDoubleCase);
1444             ValueFromBlock unboxedDouble = m_out.anchor(unboxDouble(value));
1445             m_out.jump(continuation);
1446
1447             if (shouldConvertNonNumber) {
1448                 LBasicBlock undefinedCase = m_out.newBlock();
1449                 LBasicBlock testNullCase = m_out.newBlock();
1450                 LBasicBlock nullCase = m_out.newBlock();
1451                 LBasicBlock testBooleanTrueCase = m_out.newBlock();
1452                 LBasicBlock convertBooleanTrueCase = m_out.newBlock();
1453                 LBasicBlock convertBooleanFalseCase = m_out.newBlock();
1454
1455                 m_out.appendTo(nonDoubleCase, undefinedCase);
1456                 LValue valueIsUndefined = m_out.equal(value, m_out.constInt64(ValueUndefined));
1457                 m_out.branch(valueIsUndefined, unsure(undefinedCase), unsure(testNullCase));
1458
1459                 m_out.appendTo(undefinedCase, testNullCase);
1460                 ValueFromBlock convertedUndefined = m_out.anchor(m_out.constDouble(PNaN));
1461                 m_out.jump(continuation);
1462
1463                 m_out.appendTo(testNullCase, nullCase);
1464                 LValue valueIsNull = m_out.equal(value, m_out.constInt64(ValueNull));
1465                 m_out.branch(valueIsNull, unsure(nullCase), unsure(testBooleanTrueCase));
1466
1467                 m_out.appendTo(nullCase, testBooleanTrueCase);
1468                 ValueFromBlock convertedNull = m_out.anchor(m_out.constDouble(0));
1469                 m_out.jump(continuation);
1470
1471                 m_out.appendTo(testBooleanTrueCase, convertBooleanTrueCase);
1472                 LValue valueIsBooleanTrue = m_out.equal(value, m_out.constInt64(ValueTrue));
1473                 m_out.branch(valueIsBooleanTrue, unsure(convertBooleanTrueCase), unsure(convertBooleanFalseCase));
1474
1475                 m_out.appendTo(convertBooleanTrueCase, convertBooleanFalseCase);
1476                 ValueFromBlock convertedTrue = m_out.anchor(m_out.constDouble(1));
1477                 m_out.jump(continuation);
1478
1479                 m_out.appendTo(convertBooleanFalseCase, continuation);
1480
1481                 LValue valueIsNotBooleanFalse = m_out.notEqual(value, m_out.constInt64(ValueFalse));
1482                 FTL_TYPE_CHECK(jsValueValue(value), m_node->child1(), ~SpecCellCheck, valueIsNotBooleanFalse);
1483                 ValueFromBlock convertedFalse = m_out.anchor(m_out.constDouble(0));
1484                 m_out.jump(continuation);
1485
1486                 m_out.appendTo(continuation, lastNext);
1487                 setDouble(m_out.phi(Double, intToDouble, unboxedDouble, convertedUndefined, convertedNull, convertedTrue, convertedFalse));
1488                 return;
1489             }
1490             m_out.appendTo(nonDoubleCase, continuation);
1491             FTL_TYPE_CHECK(jsValueValue(value), m_node->child1(), SpecBytecodeNumber, m_out.booleanTrue);
1492             m_out.unreachable();
1493
1494             m_out.appendTo(continuation, lastNext);
1495
1496             setDouble(m_out.phi(Double, intToDouble, unboxedDouble));
1497             return;
1498         }
1499             
1500         case Int52RepUse: {
1501             setDouble(strictInt52ToDouble(lowStrictInt52(m_node->child1())));
1502             return;
1503         }
1504             
1505         default:
1506             DFG_CRASH(m_graph, m_node, "Bad use kind");
1507         }
1508     }
1509
1510     void compileDoubleAsInt32()
1511     {
1512         LValue integerValue = convertDoubleToInt32(lowDouble(m_node->child1()), shouldCheckNegativeZero(m_node->arithMode()));
1513         setInt32(integerValue);
1514     }
1515
1516     void compileValueRep()
1517     {
1518         switch (m_node->child1().useKind()) {
1519         case DoubleRepUse: {
1520             LValue value = lowDouble(m_node->child1());
1521             
1522             if (m_interpreter.needsTypeCheck(m_node->child1(), ~SpecDoubleImpureNaN)) {
1523                 value = m_out.select(
1524                     m_out.doubleEqual(value, value), value, m_out.constDouble(PNaN));
1525             }
1526             
1527             setJSValue(boxDouble(value));
1528             return;
1529         }
1530             
1531         case Int52RepUse: {
1532             setJSValue(strictInt52ToJSValue(lowStrictInt52(m_node->child1())));
1533             return;
1534         }
1535             
1536         default:
1537             DFG_CRASH(m_graph, m_node, "Bad use kind");
1538         }
1539     }
1540     
1541     void compileInt52Rep()
1542     {
1543         switch (m_node->child1().useKind()) {
1544         case Int32Use:
1545             setStrictInt52(m_out.signExt32To64(lowInt32(m_node->child1())));
1546             return;
1547             
1548         case AnyIntUse:
1549             setStrictInt52(
1550                 jsValueToStrictInt52(
1551                     m_node->child1(), lowJSValue(m_node->child1(), ManualOperandSpeculation)));
1552             return;
1553             
1554         case DoubleRepAnyIntUse:
1555             setStrictInt52(
1556                 doubleToStrictInt52(
1557                     m_node->child1(), lowDouble(m_node->child1())));
1558             return;
1559             
1560         default:
1561             RELEASE_ASSERT_NOT_REACHED();
1562         }
1563     }
1564     
1565     void compileValueToInt32()
1566     {
1567         switch (m_node->child1().useKind()) {
1568         case Int52RepUse:
1569             setInt32(m_out.castToInt32(lowStrictInt52(m_node->child1())));
1570             break;
1571             
1572         case DoubleRepUse:
1573             setInt32(doubleToInt32(lowDouble(m_node->child1())));
1574             break;
1575             
1576         case NumberUse:
1577         case NotCellUse: {
1578             LoweredNodeValue value = m_int32Values.get(m_node->child1().node());
1579             if (isValid(value)) {
1580                 setInt32(value.value());
1581                 break;
1582             }
1583             
1584             value = m_jsValueValues.get(m_node->child1().node());
1585             if (isValid(value)) {
1586                 setInt32(numberOrNotCellToInt32(m_node->child1(), value.value()));
1587                 break;
1588             }
1589             
1590             // We'll basically just get here for constants. But it's good to have this
1591             // catch-all since we often add new representations into the mix.
1592             setInt32(
1593                 numberOrNotCellToInt32(
1594                     m_node->child1(),
1595                     lowJSValue(m_node->child1(), ManualOperandSpeculation)));
1596             break;
1597         }
1598             
1599         default:
1600             DFG_CRASH(m_graph, m_node, "Bad use kind");
1601             break;
1602         }
1603     }
1604     
1605     void compileBooleanToNumber()
1606     {
1607         switch (m_node->child1().useKind()) {
1608         case BooleanUse: {
1609             setInt32(m_out.zeroExt(lowBoolean(m_node->child1()), Int32));
1610             return;
1611         }
1612             
1613         case UntypedUse: {
1614             LValue value = lowJSValue(m_node->child1());
1615             
1616             if (!m_interpreter.needsTypeCheck(m_node->child1(), SpecBoolInt32 | SpecBoolean)) {
1617                 setInt32(m_out.bitAnd(m_out.castToInt32(value), m_out.int32One));
1618                 return;
1619             }
1620             
1621             LBasicBlock booleanCase = m_out.newBlock();
1622             LBasicBlock continuation = m_out.newBlock();
1623             
1624             ValueFromBlock notBooleanResult = m_out.anchor(value);
1625             m_out.branch(
1626                 isBoolean(value, provenType(m_node->child1())),
1627                 unsure(booleanCase), unsure(continuation));
1628             
1629             LBasicBlock lastNext = m_out.appendTo(booleanCase, continuation);
1630             ValueFromBlock booleanResult = m_out.anchor(m_out.bitOr(
1631                 m_out.zeroExt(unboxBoolean(value), Int64), m_tagTypeNumber));
1632             m_out.jump(continuation);
1633             
1634             m_out.appendTo(continuation, lastNext);
1635             setJSValue(m_out.phi(Int64, booleanResult, notBooleanResult));
1636             return;
1637         }
1638             
1639         default:
1640             RELEASE_ASSERT_NOT_REACHED();
1641             return;
1642         }
1643     }
1644
1645     void compileExtractOSREntryLocal()
1646     {
1647         EncodedJSValue* buffer = static_cast<EncodedJSValue*>(
1648             m_ftlState.jitCode->ftlForOSREntry()->entryBuffer()->dataBuffer());
1649         setJSValue(m_out.load64(m_out.absolute(buffer + m_node->unlinkedLocal().toLocal())));
1650     }
1651
1652     void compileExtractCatchLocal()
1653     {
1654         EncodedJSValue* buffer = static_cast<EncodedJSValue*>(m_ftlState.jitCode->common.catchOSREntryBuffer->dataBuffer());
1655         setJSValue(m_out.load64(m_out.absolute(buffer + m_node->catchOSREntryIndex())));
1656     }
1657     
1658     void compileGetStack()
1659     {
1660         StackAccessData* data = m_node->stackAccessData();
1661         AbstractValue& value = m_state.variables().operand(data->local);
1662         
1663         DFG_ASSERT(m_graph, m_node, isConcrete(data->format));
1664         DFG_ASSERT(m_graph, m_node, data->format != FlushedDouble); // This just happens to not arise for GetStacks, right now. It would be trivial to support.
1665         
1666         if (isInt32Speculation(value.m_type))
1667             setInt32(m_out.load32(payloadFor(data->machineLocal)));
1668         else
1669             setJSValue(m_out.load64(addressFor(data->machineLocal)));
1670     }
1671     
1672     void compilePutStack()
1673     {
1674         StackAccessData* data = m_node->stackAccessData();
1675         switch (data->format) {
1676         case FlushedJSValue: {
1677             LValue value = lowJSValue(m_node->child1());
1678             m_out.store64(value, addressFor(data->machineLocal));
1679             break;
1680         }
1681             
1682         case FlushedDouble: {
1683             LValue value = lowDouble(m_node->child1());
1684             m_out.storeDouble(value, addressFor(data->machineLocal));
1685             break;
1686         }
1687             
1688         case FlushedInt32: {
1689             LValue value = lowInt32(m_node->child1());
1690             m_out.store32(value, payloadFor(data->machineLocal));
1691             break;
1692         }
1693             
1694         case FlushedInt52: {
1695             LValue value = lowInt52(m_node->child1());
1696             m_out.store64(value, addressFor(data->machineLocal));
1697             break;
1698         }
1699             
1700         case FlushedCell: {
1701             LValue value = lowCell(m_node->child1());
1702             m_out.store64(value, addressFor(data->machineLocal));
1703             break;
1704         }
1705             
1706         case FlushedBoolean: {
1707             speculateBoolean(m_node->child1());
1708             m_out.store64(
1709                 lowJSValue(m_node->child1(), ManualOperandSpeculation),
1710                 addressFor(data->machineLocal));
1711             break;
1712         }
1713             
1714         default:
1715             DFG_CRASH(m_graph, m_node, "Bad flush format");
1716             break;
1717         }
1718     }
1719     
1720     void compileNoOp()
1721     {
1722         DFG_NODE_DO_TO_CHILDREN(m_graph, m_node, speculate);
1723     }
1724
1725     void compileToObjectOrCallObjectConstructor()
1726     {
1727         LValue value = lowJSValue(m_node->child1());
1728
1729         LBasicBlock isCellCase = m_out.newBlock();
1730         LBasicBlock slowCase = m_out.newBlock();
1731         LBasicBlock continuation = m_out.newBlock();
1732
1733         m_out.branch(isCell(value, provenType(m_node->child1())), usually(isCellCase), rarely(slowCase));
1734
1735         LBasicBlock lastNext = m_out.appendTo(isCellCase, slowCase);
1736         ValueFromBlock fastResult = m_out.anchor(value);
1737         m_out.branch(isObject(value), usually(continuation), rarely(slowCase));
1738
1739         m_out.appendTo(slowCase, continuation);
1740
1741         ValueFromBlock slowResult;
1742         if (m_node->op() == ToObject) {
1743             auto* globalObject = m_graph.globalObjectFor(m_node->origin.semantic);
1744             slowResult = m_out.anchor(vmCall(Int64, m_out.operation(operationToObject), m_callFrame, weakPointer(globalObject), value, m_out.constIntPtr(m_graph.identifiers()[m_node->identifierNumber()])));
1745         } else
1746             slowResult = m_out.anchor(vmCall(Int64, m_out.operation(operationCallObjectConstructor), m_callFrame, frozenPointer(m_node->cellOperand()), value));
1747         m_out.jump(continuation);
1748
1749         m_out.appendTo(continuation, lastNext);
1750         setJSValue(m_out.phi(Int64, fastResult, slowResult));
1751     }
1752     
1753     void compileToThis()
1754     {
1755         LValue value = lowJSValue(m_node->child1());
1756         
1757         LBasicBlock isCellCase = m_out.newBlock();
1758         LBasicBlock slowCase = m_out.newBlock();
1759         LBasicBlock continuation = m_out.newBlock();
1760         
1761         m_out.branch(
1762             isCell(value, provenType(m_node->child1())), usually(isCellCase), rarely(slowCase));
1763         
1764         LBasicBlock lastNext = m_out.appendTo(isCellCase, slowCase);
1765         ValueFromBlock fastResult = m_out.anchor(value);
1766         m_out.branch(
1767             m_out.testIsZero32(
1768                 m_out.load8ZeroExt32(value, m_heaps.JSCell_typeInfoFlags),
1769                 m_out.constInt32(OverridesToThis)),
1770             usually(continuation), rarely(slowCase));
1771         
1772         m_out.appendTo(slowCase, continuation);
1773         J_JITOperation_EJ function;
1774         if (m_graph.isStrictModeFor(m_node->origin.semantic))
1775             function = operationToThisStrict;
1776         else
1777             function = operationToThis;
1778         ValueFromBlock slowResult = m_out.anchor(
1779             vmCall(Int64, m_out.operation(function), m_callFrame, value));
1780         m_out.jump(continuation);
1781         
1782         m_out.appendTo(continuation, lastNext);
1783         setJSValue(m_out.phi(Int64, fastResult, slowResult));
1784     }
1785
1786     void compileValueAdd()
1787     {
1788         ArithProfile* arithProfile = m_ftlState.graph.baselineCodeBlockFor(m_node->origin.semantic)->arithProfileForBytecodeOffset(m_node->origin.semantic.bytecodeIndex);
1789         auto repatchingFunction = operationValueAddOptimize;
1790         auto nonRepatchingFunction = operationValueAdd;
1791         compileBinaryMathIC<JITAddGenerator>(arithProfile, repatchingFunction, nonRepatchingFunction);
1792     }
1793
1794     template <typename Generator>
1795     void compileUnaryMathIC(ArithProfile* arithProfile, FunctionPtr repatchingFunction, FunctionPtr nonRepatchingFunction)
1796     {
1797         Node* node = m_node;
1798
1799         LValue operand = lowJSValue(node->child1());
1800
1801         PatchpointValue* patchpoint = m_out.patchpoint(Int64);
1802         patchpoint->appendSomeRegister(operand);
1803         patchpoint->append(m_tagMask, ValueRep::lateReg(GPRInfo::tagMaskRegister));
1804         patchpoint->append(m_tagTypeNumber, ValueRep::lateReg(GPRInfo::tagTypeNumberRegister));
1805         RefPtr<PatchpointExceptionHandle> exceptionHandle = preparePatchpointForExceptions(patchpoint);
1806         patchpoint->numGPScratchRegisters = 1;
1807         patchpoint->clobber(RegisterSet::macroScratchRegisters());
1808         State* state = &m_ftlState;
1809         patchpoint->setGenerator(
1810             [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
1811                 AllowMacroScratchRegisterUsage allowScratch(jit);
1812
1813                 Box<CCallHelpers::JumpList> exceptions =
1814                     exceptionHandle->scheduleExitCreation(params)->jumps(jit);
1815
1816 #if ENABLE(MATH_IC_STATS)
1817                 auto inlineStart = jit.label();
1818 #endif
1819
1820                 Box<MathICGenerationState> mathICGenerationState = Box<MathICGenerationState>::create();
1821                 JITUnaryMathIC<Generator>* mathIC = jit.codeBlock()->addMathIC<Generator>(arithProfile);
1822                 mathIC->m_generator = Generator(JSValueRegs(params[0].gpr()), JSValueRegs(params[1].gpr()), params.gpScratch(0));
1823
1824                 bool shouldEmitProfiling = false;
1825                 bool generatedInline = mathIC->generateInline(jit, *mathICGenerationState, shouldEmitProfiling);
1826
1827                 if (generatedInline) {
1828                     ASSERT(!mathICGenerationState->slowPathJumps.empty());
1829                     auto done = jit.label();
1830                     params.addLatePath([=] (CCallHelpers& jit) {
1831                         AllowMacroScratchRegisterUsage allowScratch(jit);
1832                         mathICGenerationState->slowPathJumps.link(&jit);
1833                         mathICGenerationState->slowPathStart = jit.label();
1834 #if ENABLE(MATH_IC_STATS)
1835                         auto slowPathStart = jit.label();
1836 #endif
1837
1838                         if (mathICGenerationState->shouldSlowPathRepatch) {
1839                             SlowPathCall call = callOperation(*state, params.unavailableRegisters(), jit, node->origin.semantic, exceptions.get(),
1840                                 repatchingFunction, params[0].gpr(), params[1].gpr(), CCallHelpers::TrustedImmPtr(mathIC));
1841                             mathICGenerationState->slowPathCall = call.call();
1842                         } else {
1843                             SlowPathCall call = callOperation(*state, params.unavailableRegisters(), jit, node->origin.semantic,
1844                                 exceptions.get(), nonRepatchingFunction, params[0].gpr(), params[1].gpr());
1845                             mathICGenerationState->slowPathCall = call.call();
1846                         }
1847                         jit.jump().linkTo(done, &jit);
1848
1849                         jit.addLinkTask([=] (LinkBuffer& linkBuffer) {
1850                             mathIC->finalizeInlineCode(*mathICGenerationState, linkBuffer);
1851                         });
1852
1853 #if ENABLE(MATH_IC_STATS)
1854                         auto slowPathEnd = jit.label();
1855                         jit.addLinkTask([=] (LinkBuffer& linkBuffer) {
1856                             size_t size = linkBuffer.locationOf(slowPathEnd).executableAddress<char*>() - linkBuffer.locationOf(slowPathStart).executableAddress<char*>();
1857                             mathIC->m_generatedCodeSize += size;
1858                         });
1859 #endif
1860                     });
1861                 } else {
1862                     callOperation(
1863                         *state, params.unavailableRegisters(), jit, node->origin.semantic, exceptions.get(),
1864                         nonRepatchingFunction, params[0].gpr(), params[1].gpr());
1865                 }
1866
1867 #if ENABLE(MATH_IC_STATS)
1868                 auto inlineEnd = jit.label();
1869                 jit.addLinkTask([=] (LinkBuffer& linkBuffer) {
1870                     size_t size = linkBuffer.locationOf(inlineEnd).executableAddress<char*>() - linkBuffer.locationOf(inlineStart).executableAddress<char*>();
1871                     mathIC->m_generatedCodeSize += size;
1872                 });
1873 #endif
1874             });
1875
1876         setJSValue(patchpoint);
1877     }
1878
1879     template <typename Generator>
1880     void compileBinaryMathIC(ArithProfile* arithProfile, FunctionPtr repatchingFunction, FunctionPtr nonRepatchingFunction)
1881     {
1882         Node* node = m_node;
1883         
1884         LValue left = lowJSValue(node->child1());
1885         LValue right = lowJSValue(node->child2());
1886
1887         SnippetOperand leftOperand(m_state.forNode(node->child1()).resultType());
1888         SnippetOperand rightOperand(m_state.forNode(node->child2()).resultType());
1889             
1890         PatchpointValue* patchpoint = m_out.patchpoint(Int64);
1891         patchpoint->appendSomeRegister(left);
1892         patchpoint->appendSomeRegister(right);
1893         patchpoint->append(m_tagMask, ValueRep::lateReg(GPRInfo::tagMaskRegister));
1894         patchpoint->append(m_tagTypeNumber, ValueRep::lateReg(GPRInfo::tagTypeNumberRegister));
1895         RefPtr<PatchpointExceptionHandle> exceptionHandle =
1896             preparePatchpointForExceptions(patchpoint);
1897         patchpoint->numGPScratchRegisters = 1;
1898         patchpoint->numFPScratchRegisters = 2;
1899         patchpoint->clobber(RegisterSet::macroScratchRegisters());
1900         State* state = &m_ftlState;
1901         patchpoint->setGenerator(
1902             [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
1903                 AllowMacroScratchRegisterUsage allowScratch(jit);
1904
1905
1906                 Box<CCallHelpers::JumpList> exceptions =
1907                     exceptionHandle->scheduleExitCreation(params)->jumps(jit);
1908
1909 #if ENABLE(MATH_IC_STATS)
1910                 auto inlineStart = jit.label();
1911 #endif
1912
1913                 Box<MathICGenerationState> mathICGenerationState = Box<MathICGenerationState>::create();
1914                 JITBinaryMathIC<Generator>* mathIC = jit.codeBlock()->addMathIC<Generator>(arithProfile);
1915                 mathIC->m_generator = Generator(leftOperand, rightOperand, JSValueRegs(params[0].gpr()),
1916                     JSValueRegs(params[1].gpr()), JSValueRegs(params[2].gpr()), params.fpScratch(0),
1917                     params.fpScratch(1), params.gpScratch(0), InvalidFPRReg);
1918
1919                 bool shouldEmitProfiling = false;
1920                 bool generatedInline = mathIC->generateInline(jit, *mathICGenerationState, shouldEmitProfiling);
1921
1922                 if (generatedInline) {
1923                     ASSERT(!mathICGenerationState->slowPathJumps.empty());
1924                     auto done = jit.label();
1925                     params.addLatePath([=] (CCallHelpers& jit) {
1926                         AllowMacroScratchRegisterUsage allowScratch(jit);
1927                         mathICGenerationState->slowPathJumps.link(&jit);
1928                         mathICGenerationState->slowPathStart = jit.label();
1929 #if ENABLE(MATH_IC_STATS)
1930                         auto slowPathStart = jit.label();
1931 #endif
1932
1933                         if (mathICGenerationState->shouldSlowPathRepatch) {
1934                             SlowPathCall call = callOperation(*state, params.unavailableRegisters(), jit, node->origin.semantic, exceptions.get(),
1935                                 repatchingFunction, params[0].gpr(), params[1].gpr(), params[2].gpr(), CCallHelpers::TrustedImmPtr(mathIC));
1936                             mathICGenerationState->slowPathCall = call.call();
1937                         } else {
1938                             SlowPathCall call = callOperation(*state, params.unavailableRegisters(), jit, node->origin.semantic,
1939                                 exceptions.get(), nonRepatchingFunction, params[0].gpr(), params[1].gpr(), params[2].gpr());
1940                             mathICGenerationState->slowPathCall = call.call();
1941                         }
1942                         jit.jump().linkTo(done, &jit);
1943
1944                         jit.addLinkTask([=] (LinkBuffer& linkBuffer) {
1945                             mathIC->finalizeInlineCode(*mathICGenerationState, linkBuffer);
1946                         });
1947
1948 #if ENABLE(MATH_IC_STATS)
1949                         auto slowPathEnd = jit.label();
1950                         jit.addLinkTask([=] (LinkBuffer& linkBuffer) {
1951                             size_t size = linkBuffer.locationOf(slowPathEnd).executableAddress<char*>() - linkBuffer.locationOf(slowPathStart).executableAddress<char*>();
1952                             mathIC->m_generatedCodeSize += size;
1953                         });
1954 #endif
1955                     });
1956                 } else {
1957                     callOperation(
1958                         *state, params.unavailableRegisters(), jit, node->origin.semantic, exceptions.get(),
1959                         nonRepatchingFunction, params[0].gpr(), params[1].gpr(), params[2].gpr());
1960                 }
1961
1962 #if ENABLE(MATH_IC_STATS)
1963                 auto inlineEnd = jit.label();
1964                 jit.addLinkTask([=] (LinkBuffer& linkBuffer) {
1965                     size_t size = linkBuffer.locationOf(inlineEnd).executableAddress<char*>() - linkBuffer.locationOf(inlineStart).executableAddress<char*>();
1966                     mathIC->m_generatedCodeSize += size;
1967                 });
1968 #endif
1969             });
1970
1971         setJSValue(patchpoint);
1972     }
1973     
1974     void compileStrCat()
1975     {
1976         LValue result;
1977         if (m_node->child3()) {
1978             result = vmCall(
1979                 Int64, m_out.operation(operationStrCat3), m_callFrame,
1980                 lowJSValue(m_node->child1(), ManualOperandSpeculation),
1981                 lowJSValue(m_node->child2(), ManualOperandSpeculation),
1982                 lowJSValue(m_node->child3(), ManualOperandSpeculation));
1983         } else {
1984             result = vmCall(
1985                 Int64, m_out.operation(operationStrCat2), m_callFrame,
1986                 lowJSValue(m_node->child1(), ManualOperandSpeculation),
1987                 lowJSValue(m_node->child2(), ManualOperandSpeculation));
1988         }
1989         setJSValue(result);
1990     }
1991     
1992     void compileArithAddOrSub()
1993     {
1994         bool isSub =  m_node->op() == ArithSub;
1995         switch (m_node->binaryUseKind()) {
1996         case Int32Use: {
1997             LValue left = lowInt32(m_node->child1());
1998             LValue right = lowInt32(m_node->child2());
1999
2000             if (!shouldCheckOverflow(m_node->arithMode())) {
2001                 setInt32(isSub ? m_out.sub(left, right) : m_out.add(left, right));
2002                 break;
2003             }
2004
2005             CheckValue* result =
2006                 isSub ? m_out.speculateSub(left, right) : m_out.speculateAdd(left, right);
2007             blessSpeculation(result, Overflow, noValue(), nullptr, m_origin);
2008             setInt32(result);
2009             break;
2010         }
2011             
2012         case Int52RepUse: {
2013             if (!abstractValue(m_node->child1()).couldBeType(SpecInt52Only)
2014                 && !abstractValue(m_node->child2()).couldBeType(SpecInt52Only)) {
2015                 Int52Kind kind;
2016                 LValue left = lowWhicheverInt52(m_node->child1(), kind);
2017                 LValue right = lowInt52(m_node->child2(), kind);
2018                 setInt52(isSub ? m_out.sub(left, right) : m_out.add(left, right), kind);
2019                 break;
2020             }
2021
2022             LValue left = lowInt52(m_node->child1());
2023             LValue right = lowInt52(m_node->child2());
2024             CheckValue* result =
2025                 isSub ? m_out.speculateSub(left, right) : m_out.speculateAdd(left, right);
2026             blessSpeculation(result, Overflow, noValue(), nullptr, m_origin);
2027             setInt52(result);
2028             break;
2029         }
2030             
2031         case DoubleRepUse: {
2032             LValue C1 = lowDouble(m_node->child1());
2033             LValue C2 = lowDouble(m_node->child2());
2034
2035             setDouble(isSub ? m_out.doubleSub(C1, C2) : m_out.doubleAdd(C1, C2));
2036             break;
2037         }
2038
2039         case UntypedUse: {
2040             if (!isSub) {
2041                 DFG_CRASH(m_graph, m_node, "Bad use kind");
2042                 break;
2043             }
2044
2045             ArithProfile* arithProfile = m_ftlState.graph.baselineCodeBlockFor(m_node->origin.semantic)->arithProfileForBytecodeOffset(m_node->origin.semantic.bytecodeIndex);
2046             auto repatchingFunction = operationValueSubOptimize;
2047             auto nonRepatchingFunction = operationValueSub;
2048             compileBinaryMathIC<JITSubGenerator>(arithProfile, repatchingFunction, nonRepatchingFunction);
2049             break;
2050         }
2051
2052         default:
2053             DFG_CRASH(m_graph, m_node, "Bad use kind");
2054             break;
2055         }
2056     }
2057
2058     void compileArithClz32()
2059     {
2060         if (m_node->child1().useKind() == Int32Use || m_node->child1().useKind() == KnownInt32Use) {
2061             LValue operand = lowInt32(m_node->child1());
2062             setInt32(m_out.ctlz32(operand));
2063             return;
2064         }
2065         DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2066         LValue argument = lowJSValue(m_node->child1());
2067         LValue result = vmCall(Int32, m_out.operation(operationArithClz32), m_callFrame, argument);
2068         setInt32(result);
2069     }
2070     
2071     void compileArithMul()
2072     {
2073         switch (m_node->binaryUseKind()) {
2074         case Int32Use: {
2075             LValue left = lowInt32(m_node->child1());
2076             LValue right = lowInt32(m_node->child2());
2077             
2078             LValue result;
2079
2080             if (!shouldCheckOverflow(m_node->arithMode()))
2081                 result = m_out.mul(left, right);
2082             else {
2083                 CheckValue* speculation = m_out.speculateMul(left, right);
2084                 blessSpeculation(speculation, Overflow, noValue(), nullptr, m_origin);
2085                 result = speculation;
2086             }
2087             
2088             if (shouldCheckNegativeZero(m_node->arithMode())) {
2089                 LBasicBlock slowCase = m_out.newBlock();
2090                 LBasicBlock continuation = m_out.newBlock();
2091                 
2092                 m_out.branch(
2093                     m_out.notZero32(result), usually(continuation), rarely(slowCase));
2094                 
2095                 LBasicBlock lastNext = m_out.appendTo(slowCase, continuation);
2096                 speculate(NegativeZero, noValue(), nullptr, m_out.lessThan(left, m_out.int32Zero));
2097                 speculate(NegativeZero, noValue(), nullptr, m_out.lessThan(right, m_out.int32Zero));
2098                 m_out.jump(continuation);
2099                 m_out.appendTo(continuation, lastNext);
2100             }
2101             
2102             setInt32(result);
2103             break;
2104         }
2105             
2106         case Int52RepUse: {
2107             Int52Kind kind;
2108             LValue left = lowWhicheverInt52(m_node->child1(), kind);
2109             LValue right = lowInt52(m_node->child2(), opposite(kind));
2110
2111             CheckValue* result = m_out.speculateMul(left, right);
2112             blessSpeculation(result, Overflow, noValue(), nullptr, m_origin);
2113
2114             if (shouldCheckNegativeZero(m_node->arithMode())) {
2115                 LBasicBlock slowCase = m_out.newBlock();
2116                 LBasicBlock continuation = m_out.newBlock();
2117                 
2118                 m_out.branch(
2119                     m_out.notZero64(result), usually(continuation), rarely(slowCase));
2120                 
2121                 LBasicBlock lastNext = m_out.appendTo(slowCase, continuation);
2122                 speculate(NegativeZero, noValue(), nullptr, m_out.lessThan(left, m_out.int64Zero));
2123                 speculate(NegativeZero, noValue(), nullptr, m_out.lessThan(right, m_out.int64Zero));
2124                 m_out.jump(continuation);
2125                 m_out.appendTo(continuation, lastNext);
2126             }
2127             
2128             setInt52(result);
2129             break;
2130         }
2131             
2132         case DoubleRepUse: {
2133             setDouble(
2134                 m_out.doubleMul(lowDouble(m_node->child1()), lowDouble(m_node->child2())));
2135             break;
2136         }
2137
2138         case UntypedUse: {
2139             ArithProfile* arithProfile = m_ftlState.graph.baselineCodeBlockFor(m_node->origin.semantic)->arithProfileForBytecodeOffset(m_node->origin.semantic.bytecodeIndex);
2140             auto repatchingFunction = operationValueMulOptimize;
2141             auto nonRepatchingFunction = operationValueMul;
2142             compileBinaryMathIC<JITMulGenerator>(arithProfile, repatchingFunction, nonRepatchingFunction);
2143             break;
2144         }
2145
2146         default:
2147             DFG_CRASH(m_graph, m_node, "Bad use kind");
2148             break;
2149         }
2150     }
2151
2152     void compileArithDiv()
2153     {
2154         switch (m_node->binaryUseKind()) {
2155         case Int32Use: {
2156             LValue numerator = lowInt32(m_node->child1());
2157             LValue denominator = lowInt32(m_node->child2());
2158
2159             if (shouldCheckNegativeZero(m_node->arithMode())) {
2160                 LBasicBlock zeroNumerator = m_out.newBlock();
2161                 LBasicBlock numeratorContinuation = m_out.newBlock();
2162
2163                 m_out.branch(
2164                     m_out.isZero32(numerator),
2165                     rarely(zeroNumerator), usually(numeratorContinuation));
2166
2167                 LBasicBlock innerLastNext = m_out.appendTo(zeroNumerator, numeratorContinuation);
2168
2169                 speculate(
2170                     NegativeZero, noValue(), 0, m_out.lessThan(denominator, m_out.int32Zero));
2171
2172                 m_out.jump(numeratorContinuation);
2173
2174                 m_out.appendTo(numeratorContinuation, innerLastNext);
2175             }
2176             
2177             if (shouldCheckOverflow(m_node->arithMode())) {
2178                 LBasicBlock unsafeDenominator = m_out.newBlock();
2179                 LBasicBlock continuation = m_out.newBlock();
2180
2181                 LValue adjustedDenominator = m_out.add(denominator, m_out.int32One);
2182                 m_out.branch(
2183                     m_out.above(adjustedDenominator, m_out.int32One),
2184                     usually(continuation), rarely(unsafeDenominator));
2185
2186                 LBasicBlock lastNext = m_out.appendTo(unsafeDenominator, continuation);
2187                 LValue neg2ToThe31 = m_out.constInt32(-2147483647-1);
2188                 speculate(Overflow, noValue(), nullptr, m_out.isZero32(denominator));
2189                 speculate(Overflow, noValue(), nullptr, m_out.equal(numerator, neg2ToThe31));
2190                 m_out.jump(continuation);
2191
2192                 m_out.appendTo(continuation, lastNext);
2193                 LValue result = m_out.div(numerator, denominator);
2194                 speculate(
2195                     Overflow, noValue(), 0,
2196                     m_out.notEqual(m_out.mul(result, denominator), numerator));
2197                 setInt32(result);
2198             } else
2199                 setInt32(m_out.chillDiv(numerator, denominator));
2200
2201             break;
2202         }
2203             
2204         case DoubleRepUse: {
2205             setDouble(m_out.doubleDiv(
2206                 lowDouble(m_node->child1()), lowDouble(m_node->child2())));
2207             break;
2208         }
2209
2210         case UntypedUse: {
2211             emitBinarySnippet<JITDivGenerator, NeedScratchFPR>(operationValueDiv);
2212             break;
2213         }
2214
2215         default:
2216             DFG_CRASH(m_graph, m_node, "Bad use kind");
2217             break;
2218         }
2219     }
2220     
2221     void compileArithMod()
2222     {
2223         switch (m_node->binaryUseKind()) {
2224         case Int32Use: {
2225             LValue numerator = lowInt32(m_node->child1());
2226             LValue denominator = lowInt32(m_node->child2());
2227
2228             LValue remainder;
2229             if (shouldCheckOverflow(m_node->arithMode())) {
2230                 LBasicBlock unsafeDenominator = m_out.newBlock();
2231                 LBasicBlock continuation = m_out.newBlock();
2232
2233                 LValue adjustedDenominator = m_out.add(denominator, m_out.int32One);
2234                 m_out.branch(
2235                     m_out.above(adjustedDenominator, m_out.int32One),
2236                     usually(continuation), rarely(unsafeDenominator));
2237
2238                 LBasicBlock lastNext = m_out.appendTo(unsafeDenominator, continuation);
2239                 LValue neg2ToThe31 = m_out.constInt32(-2147483647-1);
2240                 speculate(Overflow, noValue(), nullptr, m_out.isZero32(denominator));
2241                 speculate(Overflow, noValue(), nullptr, m_out.equal(numerator, neg2ToThe31));
2242                 m_out.jump(continuation);
2243
2244                 m_out.appendTo(continuation, lastNext);
2245                 LValue result = m_out.mod(numerator, denominator);
2246                 remainder = result;
2247             } else
2248                 remainder = m_out.chillMod(numerator, denominator);
2249
2250             if (shouldCheckNegativeZero(m_node->arithMode())) {
2251                 LBasicBlock negativeNumerator = m_out.newBlock();
2252                 LBasicBlock numeratorContinuation = m_out.newBlock();
2253
2254                 m_out.branch(
2255                     m_out.lessThan(numerator, m_out.int32Zero),
2256                     unsure(negativeNumerator), unsure(numeratorContinuation));
2257
2258                 LBasicBlock innerLastNext = m_out.appendTo(negativeNumerator, numeratorContinuation);
2259
2260                 speculate(NegativeZero, noValue(), 0, m_out.isZero32(remainder));
2261
2262                 m_out.jump(numeratorContinuation);
2263
2264                 m_out.appendTo(numeratorContinuation, innerLastNext);
2265             }
2266
2267             setInt32(remainder);
2268             break;
2269         }
2270             
2271         case DoubleRepUse: {
2272             setDouble(
2273                 m_out.doubleMod(lowDouble(m_node->child1()), lowDouble(m_node->child2())));
2274             break;
2275         }
2276             
2277         default:
2278             DFG_CRASH(m_graph, m_node, "Bad use kind");
2279             break;
2280         }
2281     }
2282
2283     void compileArithMinOrMax()
2284     {
2285         switch (m_node->binaryUseKind()) {
2286         case Int32Use: {
2287             LValue left = lowInt32(m_node->child1());
2288             LValue right = lowInt32(m_node->child2());
2289             
2290             setInt32(
2291                 m_out.select(
2292                     m_node->op() == ArithMin
2293                         ? m_out.lessThan(left, right)
2294                         : m_out.lessThan(right, left),
2295                     left, right));
2296             break;
2297         }
2298             
2299         case DoubleRepUse: {
2300             LValue left = lowDouble(m_node->child1());
2301             LValue right = lowDouble(m_node->child2());
2302             
2303             LBasicBlock notLessThan = m_out.newBlock();
2304             LBasicBlock continuation = m_out.newBlock();
2305             
2306             Vector<ValueFromBlock, 2> results;
2307             
2308             results.append(m_out.anchor(left));
2309             m_out.branch(
2310                 m_node->op() == ArithMin
2311                     ? m_out.doubleLessThan(left, right)
2312                     : m_out.doubleGreaterThan(left, right),
2313                 unsure(continuation), unsure(notLessThan));
2314             
2315             LBasicBlock lastNext = m_out.appendTo(notLessThan, continuation);
2316             results.append(m_out.anchor(m_out.select(
2317                 m_node->op() == ArithMin
2318                     ? m_out.doubleGreaterThanOrEqual(left, right)
2319                     : m_out.doubleLessThanOrEqual(left, right),
2320                 right, m_out.constDouble(PNaN))));
2321             m_out.jump(continuation);
2322             
2323             m_out.appendTo(continuation, lastNext);
2324             setDouble(m_out.phi(Double, results));
2325             break;
2326         }
2327             
2328         default:
2329             DFG_CRASH(m_graph, m_node, "Bad use kind");
2330             break;
2331         }
2332     }
2333     
2334     void compileArithAbs()
2335     {
2336         switch (m_node->child1().useKind()) {
2337         case Int32Use: {
2338             LValue value = lowInt32(m_node->child1());
2339
2340             LValue mask = m_out.aShr(value, m_out.constInt32(31));
2341             LValue result = m_out.bitXor(mask, m_out.add(mask, value));
2342
2343             if (shouldCheckOverflow(m_node->arithMode()))
2344                 speculate(Overflow, noValue(), 0, m_out.lessThan(result, m_out.int32Zero));
2345
2346             setInt32(result);
2347             break;
2348         }
2349             
2350         case DoubleRepUse: {
2351             setDouble(m_out.doubleAbs(lowDouble(m_node->child1())));
2352             break;
2353         }
2354             
2355         default: {
2356             DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2357             LValue argument = lowJSValue(m_node->child1());
2358             LValue result = vmCall(Double, m_out.operation(operationArithAbs), m_callFrame, argument);
2359             setDouble(result);
2360             break;
2361         }
2362         }
2363     }
2364
2365     void compileArithUnary()
2366     {
2367         if (m_node->child1().useKind() == DoubleRepUse) {
2368             setDouble(m_out.doubleUnary(m_node->arithUnaryType(), lowDouble(m_node->child1())));
2369             return;
2370         }
2371         LValue argument = lowJSValue(m_node->child1());
2372         LValue result = vmCall(Double, m_out.operation(DFG::arithUnaryOperation(m_node->arithUnaryType())), m_callFrame, argument);
2373         setDouble(result);
2374     }
2375
2376     void compileArithPow()
2377     {
2378         if (m_node->child2().useKind() == Int32Use)
2379             setDouble(m_out.doublePowi(lowDouble(m_node->child1()), lowInt32(m_node->child2())));
2380         else {
2381             LValue base = lowDouble(m_node->child1());
2382             LValue exponent = lowDouble(m_node->child2());
2383
2384             LBasicBlock integerExponentIsSmallBlock = m_out.newBlock();
2385             LBasicBlock integerExponentPowBlock = m_out.newBlock();
2386             LBasicBlock doubleExponentPowBlockEntry = m_out.newBlock();
2387             LBasicBlock nanExceptionBaseIsOne = m_out.newBlock();
2388             LBasicBlock nanExceptionExponentIsInfinity = m_out.newBlock();
2389             LBasicBlock testExponentIsOneHalf = m_out.newBlock();
2390             LBasicBlock handleBaseZeroExponentIsOneHalf = m_out.newBlock();
2391             LBasicBlock handleInfinityForExponentIsOneHalf = m_out.newBlock();
2392             LBasicBlock exponentIsOneHalfNormal = m_out.newBlock();
2393             LBasicBlock exponentIsOneHalfInfinity = m_out.newBlock();
2394             LBasicBlock testExponentIsNegativeOneHalf = m_out.newBlock();
2395             LBasicBlock testBaseZeroExponentIsNegativeOneHalf = m_out.newBlock();
2396             LBasicBlock handleBaseZeroExponentIsNegativeOneHalf = m_out.newBlock();
2397             LBasicBlock handleInfinityForExponentIsNegativeOneHalf = m_out.newBlock();
2398             LBasicBlock exponentIsNegativeOneHalfNormal = m_out.newBlock();
2399             LBasicBlock exponentIsNegativeOneHalfInfinity = m_out.newBlock();
2400             LBasicBlock powBlock = m_out.newBlock();
2401             LBasicBlock nanExceptionResultIsNaN = m_out.newBlock();
2402             LBasicBlock continuation = m_out.newBlock();
2403
2404             LValue integerExponent = m_out.doubleToInt(exponent);
2405             LValue integerExponentConvertedToDouble = m_out.intToDouble(integerExponent);
2406             LValue exponentIsInteger = m_out.doubleEqual(exponent, integerExponentConvertedToDouble);
2407             m_out.branch(exponentIsInteger, unsure(integerExponentIsSmallBlock), unsure(doubleExponentPowBlockEntry));
2408
2409             LBasicBlock lastNext = m_out.appendTo(integerExponentIsSmallBlock, integerExponentPowBlock);
2410             LValue integerExponentBelowMax = m_out.belowOrEqual(integerExponent, m_out.constInt32(maxExponentForIntegerMathPow));
2411             m_out.branch(integerExponentBelowMax, usually(integerExponentPowBlock), rarely(doubleExponentPowBlockEntry));
2412
2413             m_out.appendTo(integerExponentPowBlock, doubleExponentPowBlockEntry);
2414             ValueFromBlock powDoubleIntResult = m_out.anchor(m_out.doublePowi(base, integerExponent));
2415             m_out.jump(continuation);
2416
2417             // If y is NaN, the result is NaN.
2418             m_out.appendTo(doubleExponentPowBlockEntry, nanExceptionBaseIsOne);
2419             LValue exponentIsNaN;
2420             if (provenType(m_node->child2()) & SpecDoubleNaN)
2421                 exponentIsNaN = m_out.doubleNotEqualOrUnordered(exponent, exponent);
2422             else
2423                 exponentIsNaN = m_out.booleanFalse;
2424             m_out.branch(exponentIsNaN, rarely(nanExceptionResultIsNaN), usually(nanExceptionBaseIsOne));
2425
2426             // If abs(x) is 1 and y is +infinity, the result is NaN.
2427             // If abs(x) is 1 and y is -infinity, the result is NaN.
2428
2429             //     Test if base == 1.
2430             m_out.appendTo(nanExceptionBaseIsOne, nanExceptionExponentIsInfinity);
2431             LValue absoluteBase = m_out.doubleAbs(base);
2432             LValue absoluteBaseIsOne = m_out.doubleEqual(absoluteBase, m_out.constDouble(1));
2433             m_out.branch(absoluteBaseIsOne, rarely(nanExceptionExponentIsInfinity), usually(testExponentIsOneHalf));
2434
2435             //     Test if abs(y) == Infinity.
2436             m_out.appendTo(nanExceptionExponentIsInfinity, testExponentIsOneHalf);
2437             LValue absoluteExponent = m_out.doubleAbs(exponent);
2438             LValue absoluteExponentIsInfinity = m_out.doubleEqual(absoluteExponent, m_out.constDouble(std::numeric_limits<double>::infinity()));
2439             m_out.branch(absoluteExponentIsInfinity, rarely(nanExceptionResultIsNaN), usually(testExponentIsOneHalf));
2440
2441             // If y == 0.5 or y == -0.5, handle it through SQRT.
2442             // We have be carefuly with -0 and -Infinity.
2443
2444             //     Test if y == 0.5
2445             m_out.appendTo(testExponentIsOneHalf, handleBaseZeroExponentIsOneHalf);
2446             LValue exponentIsOneHalf = m_out.doubleEqual(exponent, m_out.constDouble(0.5));
2447             m_out.branch(exponentIsOneHalf, rarely(handleBaseZeroExponentIsOneHalf), usually(testExponentIsNegativeOneHalf));
2448
2449             //     Handle x == -0.
2450             m_out.appendTo(handleBaseZeroExponentIsOneHalf, handleInfinityForExponentIsOneHalf);
2451             LValue baseIsZeroExponentIsOneHalf = m_out.doubleEqual(base, m_out.doubleZero);
2452             ValueFromBlock zeroResultExponentIsOneHalf = m_out.anchor(m_out.doubleZero);
2453             m_out.branch(baseIsZeroExponentIsOneHalf, rarely(continuation), usually(handleInfinityForExponentIsOneHalf));
2454
2455             //     Test if abs(x) == Infinity.
2456             m_out.appendTo(handleInfinityForExponentIsOneHalf, exponentIsOneHalfNormal);
2457             LValue absoluteBaseIsInfinityOneHalf = m_out.doubleEqual(absoluteBase, m_out.constDouble(std::numeric_limits<double>::infinity()));
2458             m_out.branch(absoluteBaseIsInfinityOneHalf, rarely(exponentIsOneHalfInfinity), usually(exponentIsOneHalfNormal));
2459
2460             //     The exponent is 0.5, the base is finite or NaN, we can use SQRT.
2461             m_out.appendTo(exponentIsOneHalfNormal, exponentIsOneHalfInfinity);
2462             ValueFromBlock sqrtResult = m_out.anchor(m_out.doubleSqrt(base));
2463             m_out.jump(continuation);
2464
2465             //     The exponent is 0.5, the base is infinite, the result is always infinite.
2466             m_out.appendTo(exponentIsOneHalfInfinity, testExponentIsNegativeOneHalf);
2467             ValueFromBlock sqrtInfinityResult = m_out.anchor(m_out.constDouble(std::numeric_limits<double>::infinity()));
2468             m_out.jump(continuation);
2469
2470             //     Test if y == -0.5
2471             m_out.appendTo(testExponentIsNegativeOneHalf, testBaseZeroExponentIsNegativeOneHalf);
2472             LValue exponentIsNegativeOneHalf = m_out.doubleEqual(exponent, m_out.constDouble(-0.5));
2473             m_out.branch(exponentIsNegativeOneHalf, rarely(testBaseZeroExponentIsNegativeOneHalf), usually(powBlock));
2474
2475             //     Handle x == -0.
2476             m_out.appendTo(testBaseZeroExponentIsNegativeOneHalf, handleBaseZeroExponentIsNegativeOneHalf);
2477             LValue baseIsZeroExponentIsNegativeOneHalf = m_out.doubleEqual(base, m_out.doubleZero);
2478             m_out.branch(baseIsZeroExponentIsNegativeOneHalf, rarely(handleBaseZeroExponentIsNegativeOneHalf), usually(handleInfinityForExponentIsNegativeOneHalf));
2479
2480             m_out.appendTo(handleBaseZeroExponentIsNegativeOneHalf, handleInfinityForExponentIsNegativeOneHalf);
2481             ValueFromBlock oneOverSqrtZeroResult = m_out.anchor(m_out.constDouble(std::numeric_limits<double>::infinity()));
2482             m_out.jump(continuation);
2483
2484             //     Test if abs(x) == Infinity.
2485             m_out.appendTo(handleInfinityForExponentIsNegativeOneHalf, exponentIsNegativeOneHalfNormal);
2486             LValue absoluteBaseIsInfinityNegativeOneHalf = m_out.doubleEqual(absoluteBase, m_out.constDouble(std::numeric_limits<double>::infinity()));
2487             m_out.branch(absoluteBaseIsInfinityNegativeOneHalf, rarely(exponentIsNegativeOneHalfInfinity), usually(exponentIsNegativeOneHalfNormal));
2488
2489             //     The exponent is -0.5, the base is finite or NaN, we can use 1/SQRT.
2490             m_out.appendTo(exponentIsNegativeOneHalfNormal, exponentIsNegativeOneHalfInfinity);
2491             LValue sqrtBase = m_out.doubleSqrt(base);
2492             ValueFromBlock oneOverSqrtResult = m_out.anchor(m_out.div(m_out.constDouble(1.), sqrtBase));
2493             m_out.jump(continuation);
2494
2495             //     The exponent is -0.5, the base is infinite, the result is always zero.
2496             m_out.appendTo(exponentIsNegativeOneHalfInfinity, powBlock);
2497             ValueFromBlock oneOverSqrtInfinityResult = m_out.anchor(m_out.doubleZero);
2498             m_out.jump(continuation);
2499
2500             m_out.appendTo(powBlock, nanExceptionResultIsNaN);
2501             ValueFromBlock powResult = m_out.anchor(m_out.doublePow(base, exponent));
2502             m_out.jump(continuation);
2503
2504             m_out.appendTo(nanExceptionResultIsNaN, continuation);
2505             ValueFromBlock pureNan = m_out.anchor(m_out.constDouble(PNaN));
2506             m_out.jump(continuation);
2507
2508             m_out.appendTo(continuation, lastNext);
2509             setDouble(m_out.phi(Double, powDoubleIntResult, zeroResultExponentIsOneHalf, sqrtResult, sqrtInfinityResult, oneOverSqrtZeroResult, oneOverSqrtResult, oneOverSqrtInfinityResult, powResult, pureNan));
2510         }
2511     }
2512
2513     void compileArithRandom()
2514     {
2515         JSGlobalObject* globalObject = m_graph.globalObjectFor(m_node->origin.semantic);
2516
2517         // Inlined WeakRandom::advance().
2518         // uint64_t x = m_low;
2519         void* lowAddress = reinterpret_cast<uint8_t*>(globalObject) + JSGlobalObject::weakRandomOffset() + WeakRandom::lowOffset();
2520         LValue low = m_out.load64(m_out.absolute(lowAddress));
2521         // uint64_t y = m_high;
2522         void* highAddress = reinterpret_cast<uint8_t*>(globalObject) + JSGlobalObject::weakRandomOffset() + WeakRandom::highOffset();
2523         LValue high = m_out.load64(m_out.absolute(highAddress));
2524         // m_low = y;
2525         m_out.store64(high, m_out.absolute(lowAddress));
2526
2527         // x ^= x << 23;
2528         LValue phase1 = m_out.bitXor(m_out.shl(low, m_out.constInt64(23)), low);
2529
2530         // x ^= x >> 17;
2531         LValue phase2 = m_out.bitXor(m_out.lShr(phase1, m_out.constInt64(17)), phase1);
2532
2533         // x ^= y ^ (y >> 26);
2534         LValue phase3 = m_out.bitXor(m_out.bitXor(high, m_out.lShr(high, m_out.constInt64(26))), phase2);
2535
2536         // m_high = x;
2537         m_out.store64(phase3, m_out.absolute(highAddress));
2538
2539         // return x + y;
2540         LValue random64 = m_out.add(phase3, high);
2541
2542         // Extract random 53bit. [0, 53] bit is safe integer number ranges in double representation.
2543         LValue random53 = m_out.bitAnd(random64, m_out.constInt64((1ULL << 53) - 1));
2544
2545         LValue double53Integer = m_out.intToDouble(random53);
2546
2547         // Convert `(53bit double integer value) / (1 << 53)` to `(53bit double integer value) * (1.0 / (1 << 53))`.
2548         // In latter case, `1.0 / (1 << 53)` will become a double value represented as (mantissa = 0 & exp = 970, it means 1e-(2**54)).
2549         static const double scale = 1.0 / (1ULL << 53);
2550
2551         // Multiplying 1e-(2**54) with the double integer does not change anything of the mantissa part of the double integer.
2552         // It just reduces the exp part of the given 53bit double integer.
2553         // (Except for 0.0. This is specially handled and in this case, exp just becomes 0.)
2554         // Now we get 53bit precision random double value in [0, 1).
2555         LValue result = m_out.doubleMul(double53Integer, m_out.constDouble(scale));
2556
2557         setDouble(result);
2558     }
2559
2560     void compileArithRound()
2561     {
2562         if (m_node->child1().useKind() == DoubleRepUse) {
2563             LValue result = nullptr;
2564             if (producesInteger(m_node->arithRoundingMode()) && !shouldCheckNegativeZero(m_node->arithRoundingMode())) {
2565                 LValue value = lowDouble(m_node->child1());
2566                 result = m_out.doubleFloor(m_out.doubleAdd(value, m_out.constDouble(0.5)));
2567             } else {
2568                 LBasicBlock realPartIsMoreThanHalf = m_out.newBlock();
2569                 LBasicBlock continuation = m_out.newBlock();
2570
2571                 LValue value = lowDouble(m_node->child1());
2572                 LValue integerValue = m_out.doubleCeil(value);
2573                 ValueFromBlock integerValueResult = m_out.anchor(integerValue);
2574
2575                 LValue realPart = m_out.doubleSub(integerValue, value);
2576
2577                 m_out.branch(m_out.doubleGreaterThanOrUnordered(realPart, m_out.constDouble(0.5)), unsure(realPartIsMoreThanHalf), unsure(continuation));
2578
2579                 LBasicBlock lastNext = m_out.appendTo(realPartIsMoreThanHalf, continuation);
2580                 LValue integerValueRoundedDown = m_out.doubleSub(integerValue, m_out.constDouble(1));
2581                 ValueFromBlock integerValueRoundedDownResult = m_out.anchor(integerValueRoundedDown);
2582                 m_out.jump(continuation);
2583                 m_out.appendTo(continuation, lastNext);
2584
2585                 result = m_out.phi(Double, integerValueResult, integerValueRoundedDownResult);
2586             }
2587
2588             if (producesInteger(m_node->arithRoundingMode())) {
2589                 LValue integerValue = convertDoubleToInt32(result, shouldCheckNegativeZero(m_node->arithRoundingMode()));
2590                 setInt32(integerValue);
2591             } else
2592                 setDouble(result);
2593             return;
2594         }
2595
2596         DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2597         LValue argument = lowJSValue(m_node->child1());
2598         setJSValue(vmCall(Int64, m_out.operation(operationArithRound), m_callFrame, argument));
2599     }
2600
2601     void compileArithFloor()
2602     {
2603         if (m_node->child1().useKind() == DoubleRepUse) {
2604             LValue value = lowDouble(m_node->child1());
2605             LValue integerValue = m_out.doubleFloor(value);
2606             if (producesInteger(m_node->arithRoundingMode()))
2607                 setInt32(convertDoubleToInt32(integerValue, shouldCheckNegativeZero(m_node->arithRoundingMode())));
2608             else
2609                 setDouble(integerValue);
2610             return;
2611         }
2612         DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2613         LValue argument = lowJSValue(m_node->child1());
2614         setJSValue(vmCall(Int64, m_out.operation(operationArithFloor), m_callFrame, argument));
2615     }
2616
2617     void compileArithCeil()
2618     {
2619         if (m_node->child1().useKind() == DoubleRepUse) {
2620             LValue value = lowDouble(m_node->child1());
2621             LValue integerValue = m_out.doubleCeil(value);
2622             if (producesInteger(m_node->arithRoundingMode()))
2623                 setInt32(convertDoubleToInt32(integerValue, shouldCheckNegativeZero(m_node->arithRoundingMode())));
2624             else
2625                 setDouble(integerValue);
2626             return;
2627         }
2628         DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2629         LValue argument = lowJSValue(m_node->child1());
2630         setJSValue(vmCall(Int64, m_out.operation(operationArithCeil), m_callFrame, argument));
2631     }
2632
2633     void compileArithTrunc()
2634     {
2635         if (m_node->child1().useKind() == DoubleRepUse) {
2636             LValue value = lowDouble(m_node->child1());
2637             LValue result = m_out.doubleTrunc(value);
2638             if (producesInteger(m_node->arithRoundingMode()))
2639                 setInt32(convertDoubleToInt32(result, shouldCheckNegativeZero(m_node->arithRoundingMode())));
2640             else
2641                 setDouble(result);
2642             return;
2643         }
2644         DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2645         LValue argument = lowJSValue(m_node->child1());
2646         setJSValue(vmCall(Int64, m_out.operation(operationArithTrunc), m_callFrame, argument));
2647     }
2648
2649     void compileArithSqrt()
2650     {
2651         if (m_node->child1().useKind() == DoubleRepUse) {
2652             setDouble(m_out.doubleSqrt(lowDouble(m_node->child1())));
2653             return;
2654         }
2655         LValue argument = lowJSValue(m_node->child1());
2656         LValue result = vmCall(Double, m_out.operation(operationArithSqrt), m_callFrame, argument);
2657         setDouble(result);
2658     }
2659
2660     void compileArithFRound()
2661     {
2662         if (m_node->child1().useKind() == DoubleRepUse) {
2663             setDouble(m_out.fround(lowDouble(m_node->child1())));
2664             return;
2665         }
2666         LValue argument = lowJSValue(m_node->child1());
2667         LValue result = vmCall(Double, m_out.operation(operationArithFRound), m_callFrame, argument);
2668         setDouble(result);
2669     }
2670     
2671     void compileArithNegate()
2672     {
2673         switch (m_node->child1().useKind()) {
2674         case Int32Use: {
2675             LValue value = lowInt32(m_node->child1());
2676             
2677             LValue result;
2678             if (!shouldCheckOverflow(m_node->arithMode()))
2679                 result = m_out.neg(value);
2680             else if (!shouldCheckNegativeZero(m_node->arithMode())) {
2681                 CheckValue* check = m_out.speculateSub(m_out.int32Zero, value);
2682                 blessSpeculation(check, Overflow, noValue(), nullptr, m_origin);
2683                 result = check;
2684             } else {
2685                 speculate(Overflow, noValue(), 0, m_out.testIsZero32(value, m_out.constInt32(0x7fffffff)));
2686                 result = m_out.neg(value);
2687             }
2688
2689             setInt32(result);
2690             break;
2691         }
2692             
2693         case Int52RepUse: {
2694             if (!abstractValue(m_node->child1()).couldBeType(SpecInt52Only)) {
2695                 Int52Kind kind;
2696                 LValue value = lowWhicheverInt52(m_node->child1(), kind);
2697                 LValue result = m_out.neg(value);
2698                 if (shouldCheckNegativeZero(m_node->arithMode()))
2699                     speculate(NegativeZero, noValue(), 0, m_out.isZero64(result));
2700                 setInt52(result, kind);
2701                 break;
2702             }
2703             
2704             LValue value = lowInt52(m_node->child1());
2705             CheckValue* result = m_out.speculateSub(m_out.int64Zero, value);
2706             blessSpeculation(result, Int52Overflow, noValue(), nullptr, m_origin);
2707             if (shouldCheckNegativeZero(m_node->arithMode()))
2708                 speculate(NegativeZero, noValue(), 0, m_out.isZero64(result));
2709             setInt52(result);
2710             break;
2711         }
2712             
2713         case DoubleRepUse: {
2714             setDouble(m_out.doubleNeg(lowDouble(m_node->child1())));
2715             break;
2716         }
2717             
2718         default:
2719             DFG_ASSERT(m_graph, m_node, m_node->child1().useKind() == UntypedUse);
2720             ArithProfile* arithProfile = m_ftlState.graph.baselineCodeBlockFor(m_node->origin.semantic)->arithProfileForBytecodeOffset(m_node->origin.semantic.bytecodeIndex);
2721             auto repatchingFunction = operationArithNegateOptimize;
2722             auto nonRepatchingFunction = operationArithNegate;
2723             compileUnaryMathIC<JITNegGenerator>(arithProfile, repatchingFunction, nonRepatchingFunction);
2724             break;
2725         }
2726     }
2727     
2728     void compileBitAnd()
2729     {
2730         if (m_node->isBinaryUseKind(UntypedUse)) {
2731             emitBinaryBitOpSnippet<JITBitAndGenerator>(operationValueBitAnd);
2732             return;
2733         }
2734         setInt32(m_out.bitAnd(lowInt32(m_node->child1()), lowInt32(m_node->child2())));
2735     }
2736     
2737     void compileBitOr()
2738     {
2739         if (m_node->isBinaryUseKind(UntypedUse)) {
2740             emitBinaryBitOpSnippet<JITBitOrGenerator>(operationValueBitOr);
2741             return;
2742         }
2743         setInt32(m_out.bitOr(lowInt32(m_node->child1()), lowInt32(m_node->child2())));
2744     }
2745     
2746     void compileBitXor()
2747     {
2748         if (m_node->isBinaryUseKind(UntypedUse)) {
2749             emitBinaryBitOpSnippet<JITBitXorGenerator>(operationValueBitXor);
2750             return;
2751         }
2752         setInt32(m_out.bitXor(lowInt32(m_node->child1()), lowInt32(m_node->child2())));
2753     }
2754     
2755     void compileBitRShift()
2756     {
2757         if (m_node->isBinaryUseKind(UntypedUse)) {
2758             emitRightShiftSnippet(JITRightShiftGenerator::SignedShift);
2759             return;
2760         }
2761         setInt32(m_out.aShr(
2762             lowInt32(m_node->child1()),
2763             m_out.bitAnd(lowInt32(m_node->child2()), m_out.constInt32(31))));
2764     }
2765     
2766     void compileBitLShift()
2767     {
2768         if (m_node->isBinaryUseKind(UntypedUse)) {
2769             emitBinaryBitOpSnippet<JITLeftShiftGenerator>(operationValueBitLShift);
2770             return;
2771         }
2772         setInt32(m_out.shl(
2773             lowInt32(m_node->child1()),
2774             m_out.bitAnd(lowInt32(m_node->child2()), m_out.constInt32(31))));
2775     }
2776     
2777     void compileBitURShift()
2778     {
2779         if (m_node->isBinaryUseKind(UntypedUse)) {
2780             emitRightShiftSnippet(JITRightShiftGenerator::UnsignedShift);
2781             return;
2782         }
2783         setInt32(m_out.lShr(
2784             lowInt32(m_node->child1()),
2785             m_out.bitAnd(lowInt32(m_node->child2()), m_out.constInt32(31))));
2786     }
2787     
2788     void compileUInt32ToNumber()
2789     {
2790         LValue value = lowInt32(m_node->child1());
2791
2792         if (doesOverflow(m_node->arithMode())) {
2793             setStrictInt52(m_out.zeroExtPtr(value));
2794             return;
2795         }
2796
2797         speculate(Overflow, noValue(), 0, m_out.lessThan(value, m_out.int32Zero));
2798         setInt32(value);
2799     }
2800     
2801     void compileCheckStructure()
2802     {
2803         ExitKind exitKind;
2804         if (m_node->child1()->hasConstant())
2805             exitKind = BadConstantCache;
2806         else
2807             exitKind = BadCache;
2808
2809         switch (m_node->child1().useKind()) {
2810         case CellUse:
2811         case KnownCellUse: {
2812             LValue cell = lowCell(m_node->child1());
2813             
2814             checkStructure(
2815                 m_out.load32(cell, m_heaps.JSCell_structureID), jsValueValue(cell),
2816                 exitKind, m_node->structureSet(),
2817                 [&] (RegisteredStructure structure) {
2818                     return weakStructureID(structure);
2819                 });
2820             return;
2821         }
2822
2823         case CellOrOtherUse: {
2824             LValue value = lowJSValue(m_node->child1(), ManualOperandSpeculation);
2825
2826             LBasicBlock cellCase = m_out.newBlock();
2827             LBasicBlock notCellCase = m_out.newBlock();
2828             LBasicBlock continuation = m_out.newBlock();
2829
2830             m_out.branch(
2831                 isCell(value, provenType(m_node->child1())), unsure(cellCase), unsure(notCellCase));
2832
2833             LBasicBlock lastNext = m_out.appendTo(cellCase, notCellCase);
2834             checkStructure(
2835                 m_out.load32(value, m_heaps.JSCell_structureID), jsValueValue(value),
2836                 exitKind, m_node->structureSet(),
2837                 [&] (RegisteredStructure structure) {
2838                     return weakStructureID(structure);
2839                 });
2840             m_out.jump(continuation);
2841
2842             m_out.appendTo(notCellCase, continuation);
2843             FTL_TYPE_CHECK(jsValueValue(value), m_node->child1(), SpecCell | SpecOther, isNotOther(value));
2844             m_out.jump(continuation);
2845
2846             m_out.appendTo(continuation, lastNext);
2847             return;
2848         }
2849
2850         default:
2851             DFG_CRASH(m_graph, m_node, "Bad use kind");
2852             return;
2853         }
2854     }
2855
2856     void compileCheckStructureOrEmpty()
2857     {
2858         ExitKind exitKind;
2859         if (m_node->child1()->hasConstant())
2860             exitKind = BadConstantCache;
2861         else
2862             exitKind = BadCache;
2863
2864         LValue cell = lowCell(m_node->child1());
2865         bool maySeeEmptyValue = m_interpreter.forNode(m_node->child1()).m_type & SpecEmpty;
2866         LBasicBlock notEmpty;
2867         LBasicBlock continuation;
2868         LBasicBlock lastNext;
2869         if (maySeeEmptyValue) {
2870             notEmpty = m_out.newBlock();
2871             continuation = m_out.newBlock();
2872             m_out.branch(m_out.isZero64(cell), unsure(continuation), unsure(notEmpty));
2873             lastNext = m_out.appendTo(notEmpty, continuation);
2874         }
2875
2876         checkStructure(
2877             m_out.load32(cell, m_heaps.JSCell_structureID), jsValueValue(cell),
2878             exitKind, m_node->structureSet(),
2879             [&] (RegisteredStructure structure) {
2880                 return weakStructureID(structure);
2881             });
2882
2883         if (maySeeEmptyValue) {
2884             m_out.jump(continuation);
2885             m_out.appendTo(continuation, lastNext);
2886         }
2887     }
2888     
2889     void compileCheckCell()
2890     {
2891         LValue cell = lowCell(m_node->child1());
2892         
2893         speculate(
2894             BadCell, jsValueValue(cell), m_node->child1().node(),
2895             m_out.notEqual(cell, weakPointer(m_node->cellOperand()->cell())));
2896     }
2897     
2898     void compileCheckBadCell()
2899     {
2900         terminate(BadCell);
2901     }
2902
2903     void compileCheckNotEmpty()
2904     {
2905         speculate(TDZFailure, noValue(), nullptr, m_out.isZero64(lowJSValue(m_node->child1())));
2906     }
2907
2908     void compileAssertNotEmpty()
2909     {
2910         if (!validationEnabled())
2911             return;
2912
2913         B3::PatchpointValue* patchpoint = m_out.patchpoint(Void);
2914         patchpoint->appendSomeRegister(lowJSValue(m_node->child1()));
2915         patchpoint->setGenerator(
2916             [=] (CCallHelpers& jit, const StackmapGenerationParams& params) {
2917                 AllowMacroScratchRegisterUsage allowScratch(jit);
2918                 GPRReg input =  params[0].gpr();
2919                 CCallHelpers::Jump done = jit.branchTest64(CCallHelpers::NonZero, input);
2920                 jit.breakpoint();
2921                 done.link(&jit);
2922             });
2923     }
2924
2925     void compileCheckStringIdent()
2926     {
2927         UniquedStringImpl* uid = m_node->uidOperand();
2928         LValue stringImpl = lowStringIdent(m_node->child1());
2929         speculate(BadIdent, noValue(), nullptr, m_out.notEqual(stringImpl, m_out.constIntPtr(uid)));
2930     }
2931
2932     void compileGetExecutable()
2933     {
2934         LValue cell = lowCell(m_node->child1());
2935         speculateFunction(m_node->child1(), cell);
2936         setJSValue(m_out.loadPtr(cell, m_heaps.JSFunction_executable));
2937     }
2938     
2939     void compileArrayify()
2940     {
2941         LValue cell = lowCell(m_node->child1());
2942         LValue property = !!m_node->child2() ? lowInt32(m_node->child2()) : 0;
2943         
2944         LBasicBlock unexpectedStructure = m_out.newBlock();
2945         LBasicBlock continuation = m_out.newBlock();
2946         
2947         auto isUnexpectedArray = [&] (LValue cell) {
2948             if (m_node->op() == Arrayify)
2949                 return m_out.logicalNot(isArrayTypeForArrayify(cell, m_node->arrayMode()));
2950
2951             ASSERT(m_node->op() == ArrayifyToStructure);
2952             return m_out.notEqual(m_out.load32(cell, m_heaps.JSCell_structureID), weakStructureID(m_node->structure()));
2953         };
2954
2955         m_out.branch(isUnexpectedArray(cell), rarely(unexpectedStructure), usually(continuation));
2956
2957         LBasicBlock lastNext = m_out.appendTo(unexpectedStructure, continuation);
2958         
2959         if (property) {
2960             switch (m_node->arrayMode().type()) {
2961             case Array::Int32:
2962             case Array::Double:
2963             case Array::Contiguous:
2964                 speculate(
2965                     Uncountable, noValue(), 0,
2966                     m_out.aboveOrEqual(property, m_out.constInt32(MIN_SPARSE_ARRAY_INDEX)));
2967                 break;
2968             default:
2969                 break;
2970             }
2971         }
2972         
2973         switch (m_node->arrayMode().type()) {
2974         case Array::Int32:
2975             vmCall(Void, m_out.operation(operationEnsureInt32), m_callFrame, cell);
2976             break;
2977         case Array::Double:
2978             vmCall(Void, m_out.operation(operationEnsureDouble), m_callFrame, cell);
2979             break;
2980         case Array::Contiguous:
2981             vmCall(Void, m_out.operation(operationEnsureContiguous), m_callFrame, cell);
2982             break;
2983         case Array::ArrayStorage:
2984         case Array::SlowPutArrayStorage:
2985             vmCall(Void, m_out.operation(operationEnsureArrayStorage), m_callFrame, cell);
2986             break;
2987         default:
2988             DFG_CRASH(m_graph, m_node, "Bad array type");
2989             break;
2990         }
2991         
2992         speculate(BadIndexingType, jsValueValue(cell), 0, isUnexpectedArray(cell));
2993         m_out.jump(continuation);
2994         
2995         m_out.appendTo(continuation, lastNext);
2996     }
2997     
2998     void compilePutStructure()
2999     {
3000         m_ftlState.jitCode->common.notifyCompilingStructureTransition(m_graph.m_plan, codeBlock(), m_node);
3001         
3002         RegisteredStructure oldStructure = m_node->transition()->previous;
3003         RegisteredStructure newStructure = m_node->transition()->next;
3004         ASSERT_UNUSED(oldStructure, oldStructure->indexingType() == newStructure->indexingType());
3005         ASSERT(oldStructure->typeInfo().inlineTypeFlags() == newStructure->typeInfo().inlineTypeFlags());
3006         ASSERT(oldStructure->typeInfo().type() == newStructure->typeInfo().type());
3007
3008         LValue cell = lowCell(m_node->child1()); 
3009         m_out.store32(
3010             weakStructureID(newStructure),
3011             cell, m_heaps.JSCell_structureID);
3012     }
3013     
3014     void compileGetById(AccessType type)
3015     {
3016         ASSERT(type == AccessType::Get || type == AccessType::TryGet);
3017         switch (m_node->child1().useKind()) {
3018         case CellUse: {
3019             setJSValue(getById(lowCell(m_node->child1()), type));
3020             return;
3021         }
3022             
3023         case UntypedUse: {
3024             // This is pretty weird, since we duplicate the slow path both here and in the
3025             // code generated by the IC. We should investigate making this less bad.
3026             // https://bugs.webkit.org/show_bug.cgi?id=127830
3027             LValue value = lowJSValue(m_node->child1());
3028             
3029             LBasicBlock cellCase = m_out.newBlock();
3030             LBasicBlock notCellCase = m_out.newBlock();
3031             LBasicBlock continuation = m_out.newBlock();
3032             
3033             m_out.branch(
3034                 isCell(value, provenType(m_node->child1())), unsure(cellCase), unsure(notCellCase));
3035             
3036             LBasicBlock lastNext = m_out.appendTo(cellCase, notCellCase);
3037             ValueFromBlock cellResult = m_out.anchor(getById(value, type));
3038             m_out.jump(continuation);
3039
3040             J_JITOperation_EJI getByIdFunction;
3041             if (type == AccessType::Get)
3042                 getByIdFunction = operationGetByIdGeneric;
3043             else
3044                 getByIdFunction = operationTryGetByIdGeneric;
3045
3046             m_out.appendTo(notCellCase, continuation);
3047             ValueFromBlock notCellResult = m_out.anchor(vmCall(
3048                 Int64, m_out.operation(getByIdFunction),
3049                 m_callFrame, value,
3050                 m_out.constIntPtr(m_graph.identifiers()[m_node->identifierNumber()])));
3051             m_out.jump(continuation);
3052             
3053             m_out.appendTo(continuation, lastNext);
3054             setJSValue(m_out.phi(Int64, cellResult, notCellResult));
3055             return;
3056         }
3057             
3058         default:
3059             DFG_CRASH(m_graph, m_node, "Bad use kind");
3060             return;
3061         }
3062     }
3063
3064     void compileGetByIdWithThis()
3065     {
3066         if (m_node->child1().useKind() == CellUse && m_node->child2().useKind() == CellUse)
3067             setJSValue(getByIdWithThis(lowCell(m_node->child1()), lowCell(m_node->child2())));
3068         else {
3069             LValue base = lowJSValue(m_node->child1());
3070             LValue thisValue = lowJSValue(m_node->child2());
3071             
3072             LBasicBlock baseCellCase = m_out.newBlock();
3073             LBasicBlock notCellCase = m_out.newBlock();
3074             LBasicBlock thisValueCellCase = m_out.newBlock();
3075             LBasicBlock continuation = m_out.newBlock();
3076             
3077             m_out.branch(
3078                 isCell(base, provenType(m_node->child1())), unsure(baseCellCase), unsure(notCellCase));
3079             
3080             LBasicBlock lastNext = m_out.appendTo(baseCellCase, thisValueCellCase);
3081             
3082             m_out.branch(
3083                 isCell(thisValue, provenType(m_node->child2())), unsure(thisValueCellCase), unsure(notCellCase));
3084             
3085             m_out.appendTo(thisValueCellCase, notCellCase);
3086             ValueFromBlock cellResult = m_out.anchor(getByIdWithThis(base, thisValue));
3087             m_out.jump(continuation);
3088
3089             m_out.appendTo(notCellCase, continuation);
3090             ValueFromBlock notCellResult = m_out.anchor(vmCall(
3091                 Int64, m_out.operation(operationGetByIdWithThis),
3092                 m_callFrame, base, thisValue,
3093                 m_out.constIntPtr(m_graph.identifiers()[m_node->identifierNumber()])));
3094             m_out.jump(continuation);
3095             
3096             m_out.appendTo(continuation, lastNext);
3097             setJSValue(m_out.phi(Int64, cellResult, notCellResult));
3098         }
3099         
3100     }
3101
3102     void compileGetByValWithThis()
3103     {
3104         LValue base = lowJSValue(m_node->child1());
3105         LValue thisValue = lowJSValue(m_node->child2());
3106         LValue subscript = lowJSValue(m_node->child3());
3107
3108         LValue result = vmCall(Int64, m_out.operation(operationGetByValWithThis), m_callFrame, base, thisValue, subscript);
3109         setJSValue(result);
3110     }
3111
3112     void compilePutByIdWithThis()
3113     {
3114         LValue base = lowJSValue(m_node->child1());
3115         LValue thisValue = lowJSValue(m_node->child2());
3116         LValue value = lowJSValue(m_node->child3());
3117
3118         vmCall(Void, m_out.operation(m_graph.isStrictModeFor(m_node->origin.semantic) ? operationPutByIdWithThisStrict : operationPutByIdWithThis),
3119             m_callFrame, base, thisValue, value, m_out.constIntPtr(m_graph.identifiers()[m_node->identifierNumber()]));
3120     }
3121
3122     void compilePutByValWithThis()
3123     {
3124         LValue base = lowJSValue(m_graph.varArgChild(m_node, 0));
3125         LValue thisValue = lowJSValue(m_graph.varArgChild(m_node, 1));
3126         LValue property = lowJSValue(m_graph.varArgChild(m_node, 2));
3127         LValue value = lowJSValue(m_graph.varArgChild(m_node, 3));
3128
3129         vmCall(Void, m_out.operation(m_graph.isStrictModeFor(m_node->origin.semantic) ? operationPutByValWithThisStrict : operationPutByValWithThis),
3130             m_callFrame, base, thisValue, property, value);
3131     }
3132     
3133     void compileAtomicsReadModifyWrite()
3134     {
3135         TypedArrayType type = m_node->arrayMode().typedArrayType();
3136         unsigned numExtraArgs = numExtraAtomicsArgs(m_node->op());
3137         Edge baseEdge = m_graph.child(m_node, 0);
3138         Edge indexEdge = m_graph.child(m_node, 1);
3139         Edge argEdges[maxNumExtraAtomicsArgs];
3140         for (unsigned i = numExtraArgs; i--;)
3141             argEdges[i] = m_graph.child(m_node, 2 + i);
3142         Edge storageEdge = m_graph.child(m_node, 2 + numExtraArgs);
3143         
3144         auto operation = [&] () -> LValue {
3145             switch (m_node->op()) {
3146             case AtomicsAdd:
3147                 return m_out.operation(operationAtomicsAdd);
3148             case AtomicsAnd: