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