60d03bbcdf4fd278a0b0f0621c8174b7fb261811
[WebKit-https.git] / Source / JavaScriptCore / llint / LLIntSlowPaths.cpp
1 /*
2  * Copyright (C) 2011, 2012, 2013 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 "LLIntSlowPaths.h"
28
29 #if ENABLE(LLINT)
30
31 #include "Arguments.h"
32 #include "ArrayConstructor.h"
33 #include "CallFrame.h"
34 #include "CommonSlowPaths.h"
35 #include "CommonSlowPathsExceptions.h"
36 #include "GetterSetter.h"
37 #include "HostCallReturnValue.h"
38 #include "Interpreter.h"
39 #include "JIT.h"
40 #include "JSActivation.h"
41 #include "JSCJSValue.h"
42 #include "JSGlobalObjectFunctions.h"
43 #include "JSNameScope.h"
44 #include "JSPropertyNameIterator.h"
45 #include "JSString.h"
46 #include "JSWithScope.h"
47 #include "LLIntCommon.h"
48 #include "LLIntExceptions.h"
49 #include "LowLevelInterpreter.h"
50 #include "ObjectConstructor.h"
51 #include "Operations.h"
52 #include "StructureRareDataInlines.h"
53 #include <wtf/StringPrintStream.h>
54
55 namespace JSC { namespace LLInt {
56
57 #define LLINT_BEGIN_NO_SET_PC() \
58     VM& vm = exec->vm();      \
59     NativeCallFrameTracer tracer(&vm, exec)
60
61 #ifndef NDEBUG
62 #define LLINT_SET_PC_FOR_STUBS() do { \
63         exec->codeBlock()->bytecodeOffset(pc); \
64         exec->setCurrentVPC(pc + 1); \
65     } while (false)
66 #else
67 #define LLINT_SET_PC_FOR_STUBS() do { \
68         exec->setCurrentVPC(pc + 1); \
69     } while (false)
70 #endif
71
72 #define LLINT_BEGIN()                           \
73     LLINT_BEGIN_NO_SET_PC();                    \
74     LLINT_SET_PC_FOR_STUBS()
75
76 #define LLINT_OP(index) (exec->uncheckedR(pc[index].u.operand))
77 #define LLINT_OP_C(index) (exec->r(pc[index].u.operand))
78
79 #define LLINT_RETURN_TWO(first, second) do {       \
80         return encodeResult(first, second);        \
81     } while (false)
82
83 #define LLINT_END_IMPL() LLINT_RETURN_TWO(pc, exec)
84
85 #define LLINT_THROW(exceptionToThrow) do {                        \
86         vm.throwException(exec, exceptionToThrow);                \
87         pc = returnToThrow(exec);                                 \
88         LLINT_END_IMPL();                                         \
89     } while (false)
90
91 #define LLINT_CHECK_EXCEPTION() do {                    \
92         if (UNLIKELY(vm.exception())) {                 \
93             pc = returnToThrow(exec);                   \
94             LLINT_END_IMPL();                           \
95         }                                               \
96     } while (false)
97
98 #define LLINT_END() do {                        \
99         LLINT_CHECK_EXCEPTION();                \
100         LLINT_END_IMPL();                       \
101     } while (false)
102
103 #define LLINT_BRANCH(opcode, condition) do {                      \
104         bool __b_condition = (condition);                         \
105         LLINT_CHECK_EXCEPTION();                                  \
106         if (__b_condition)                                        \
107             pc += pc[OPCODE_LENGTH(opcode) - 1].u.operand;        \
108         else                                                      \
109             pc += OPCODE_LENGTH(opcode);                          \
110         LLINT_END_IMPL();                                         \
111     } while (false)
112
113 #define LLINT_RETURN(value) do {                \
114         JSValue __r_returnValue = (value);      \
115         LLINT_CHECK_EXCEPTION();                \
116         LLINT_OP(1) = __r_returnValue;          \
117         LLINT_END_IMPL();                       \
118     } while (false)
119
120 #if ENABLE(VALUE_PROFILER)
121 #define LLINT_RETURN_PROFILED(opcode, value) do {               \
122         JSValue __rp_returnValue = (value);                     \
123         LLINT_CHECK_EXCEPTION();                                \
124         LLINT_OP(1) = __rp_returnValue;                         \
125         LLINT_PROFILE_VALUE(opcode, __rp_returnValue);          \
126         LLINT_END_IMPL();                                       \
127     } while (false)
128
129 #define LLINT_PROFILE_VALUE(opcode, value) do { \
130         pc[OPCODE_LENGTH(opcode) - 1].u.profile->m_buckets[0] = \
131         JSValue::encode(value);                  \
132     } while (false)
133
134 #else // ENABLE(VALUE_PROFILER)
135 #define LLINT_RETURN_PROFILED(opcode, value) LLINT_RETURN(value)
136
137 #define LLINT_PROFILE_VALUE(opcode, value) do { } while (false)
138
139 #endif // ENABLE(VALUE_PROFILER)
140
141 #define LLINT_CALL_END_IMPL(exec, callTarget) LLINT_RETURN_TWO((callTarget), (exec))
142
143 #define LLINT_CALL_THROW(exec, pc, exceptionToThrow) do {               \
144         ExecState* __ct_exec = (exec);                                  \
145         vm.throwException(__ct_exec, exceptionToThrow);                 \
146         LLINT_CALL_END_IMPL(__ct_exec, callToThrow(__ct_exec));         \
147     } while (false)
148
149 #define LLINT_CALL_CHECK_EXCEPTION(exec) do {                           \
150         ExecState* __cce_exec = (exec);                                 \
151         if (UNLIKELY(vm.exception()))                                   \
152             LLINT_CALL_END_IMPL(__cce_exec, callToThrow(__cce_exec));   \
153     } while (false)
154
155 #define LLINT_CALL_RETURN(exec, pc, callTarget) do {                    \
156         ExecState* __cr_exec = (exec);                                  \
157         void* __cr_callTarget = (callTarget);                           \
158         LLINT_CALL_CHECK_EXCEPTION(__cr_exec->callerFrame());           \
159         LLINT_CALL_END_IMPL(__cr_exec, __cr_callTarget);                \
160     } while (false)
161
162 extern "C" SlowPathReturnType llint_trace_operand(ExecState* exec, Instruction* pc, int fromWhere, int operand)
163 {
164     LLINT_BEGIN();
165     dataLogF("%p / %p: executing bc#%zu, op#%u: Trace(%d): %d: %d\n",
166             exec->codeBlock(),
167             exec,
168             static_cast<intptr_t>(pc - exec->codeBlock()->instructions().begin()),
169             exec->vm().interpreter->getOpcodeID(pc[0].u.opcode),
170             fromWhere,
171             operand,
172             pc[operand].u.operand);
173     LLINT_END();
174 }
175
176 extern "C" SlowPathReturnType llint_trace_value(ExecState* exec, Instruction* pc, int fromWhere, int operand)
177 {
178     JSValue value = LLINT_OP_C(operand).jsValue();
179     union {
180         struct {
181             uint32_t tag;
182             uint32_t payload;
183         } bits;
184         EncodedJSValue asValue;
185     } u;
186     u.asValue = JSValue::encode(value);
187     dataLogF(
188         "%p / %p: executing bc#%zu, op#%u: Trace(%d): %d: %d: %08x:%08x: %s\n",
189         exec->codeBlock(),
190         exec,
191         static_cast<intptr_t>(pc - exec->codeBlock()->instructions().begin()),
192         exec->vm().interpreter->getOpcodeID(pc[0].u.opcode),
193         fromWhere,
194         operand,
195         pc[operand].u.operand,
196         u.bits.tag,
197         u.bits.payload,
198         toCString(value).data());
199     LLINT_END_IMPL();
200 }
201
202 LLINT_SLOW_PATH_DECL(trace_prologue)
203 {
204     dataLogF("%p / %p: in prologue.\n", exec->codeBlock(), exec);
205     LLINT_END_IMPL();
206 }
207
208 static void traceFunctionPrologue(ExecState* exec, const char* comment, CodeSpecializationKind kind)
209 {
210     JSFunction* callee = jsCast<JSFunction*>(exec->callee());
211     FunctionExecutable* executable = callee->jsExecutable();
212     CodeBlock* codeBlock = executable->codeBlockFor(kind);
213     dataLogF("%p / %p: in %s of function %p, executable %p; numVars = %u, numParameters = %u, numCalleeRegisters = %u, caller = %p.\n",
214             codeBlock, exec, comment, callee, executable,
215             codeBlock->m_numVars, codeBlock->numParameters(), codeBlock->m_numCalleeRegisters,
216             exec->callerFrame());
217 }
218
219 LLINT_SLOW_PATH_DECL(trace_prologue_function_for_call)
220 {
221     traceFunctionPrologue(exec, "call prologue", CodeForCall);
222     LLINT_END_IMPL();
223 }
224
225 LLINT_SLOW_PATH_DECL(trace_prologue_function_for_construct)
226 {
227     traceFunctionPrologue(exec, "construct prologue", CodeForConstruct);
228     LLINT_END_IMPL();
229 }
230
231 LLINT_SLOW_PATH_DECL(trace_arityCheck_for_call)
232 {
233     traceFunctionPrologue(exec, "call arity check", CodeForCall);
234     LLINT_END_IMPL();
235 }
236
237 LLINT_SLOW_PATH_DECL(trace_arityCheck_for_construct)
238 {
239     traceFunctionPrologue(exec, "construct arity check", CodeForConstruct);
240     LLINT_END_IMPL();
241 }
242
243 LLINT_SLOW_PATH_DECL(trace)
244 {
245     dataLogF("%p / %p: executing bc#%zu, %s, scope %p, pc = %p\n",
246             exec->codeBlock(),
247             exec,
248             static_cast<intptr_t>(pc - exec->codeBlock()->instructions().begin()),
249             opcodeNames[exec->vm().interpreter->getOpcodeID(pc[0].u.opcode)],
250             exec->scope(), pc);
251     if (exec->vm().interpreter->getOpcodeID(pc[0].u.opcode) == op_ret) {
252         dataLogF("Will be returning to %p\n", exec->returnPC().value());
253         dataLogF("The new cfr will be %p\n", exec->callerFrame());
254     }
255     LLINT_END_IMPL();
256 }
257
258 LLINT_SLOW_PATH_DECL(special_trace)
259 {
260     dataLogF("%p / %p: executing special case bc#%zu, op#%u, return PC is %p\n",
261             exec->codeBlock(),
262             exec,
263             static_cast<intptr_t>(pc - exec->codeBlock()->instructions().begin()),
264             exec->vm().interpreter->getOpcodeID(pc[0].u.opcode),
265             exec->returnPC().value());
266     LLINT_END_IMPL();
267 }
268
269 #if ENABLE(JIT)
270 inline bool shouldJIT(ExecState* exec)
271 {
272     // You can modify this to turn off JITting without rebuilding the world.
273     return exec->vm().canUseJIT();
274 }
275
276 // Returns true if we should try to OSR.
277 inline bool jitCompileAndSetHeuristics(CodeBlock* codeBlock, ExecState* exec)
278 {
279     VM& vm = exec->vm();
280     DeferGC deferGC(vm.heap);
281     
282     codeBlock->updateAllValueProfilePredictions();
283     
284     if (!codeBlock->checkIfJITThresholdReached()) {
285         if (Options::verboseOSR())
286             dataLogF("    JIT threshold should be lifted.\n");
287         return false;
288     }
289     
290     switch (codeBlock->jitType()) {
291     case JITCode::BaselineJIT: {
292         if (Options::verboseOSR())
293             dataLogF("    Code was already compiled.\n");
294         codeBlock->jitSoon();
295         return true;
296     }
297     case JITCode::InterpreterThunk: {
298         CompilationResult result = JIT::compile(&vm, codeBlock, JITCompilationCanFail);
299         switch (result) {
300         case CompilationFailed:
301             if (Options::verboseOSR())
302                 dataLogF("    JIT compilation failed.\n");
303             codeBlock->dontJITAnytimeSoon();
304             return false;
305         case CompilationSuccessful:
306             if (Options::verboseOSR())
307                 dataLogF("    JIT compilation successful.\n");
308             codeBlock->install();
309             codeBlock->jitSoon();
310             return true;
311         default:
312             RELEASE_ASSERT_NOT_REACHED();
313             return false;
314         }
315     }
316     default:
317         RELEASE_ASSERT_NOT_REACHED();
318         return false;
319     }
320 }
321
322 enum EntryKind { Prologue, ArityCheck };
323 static SlowPathReturnType entryOSR(ExecState* exec, Instruction*, CodeBlock* codeBlock, const char *name, EntryKind kind)
324 {
325     if (Options::verboseOSR()) {
326         dataLog(
327             *codeBlock, ": Entered ", name, " with executeCounter = ",
328             codeBlock->llintExecuteCounter(), "\n");
329     }
330     
331     if (!shouldJIT(exec)) {
332         codeBlock->dontJITAnytimeSoon();
333         LLINT_RETURN_TWO(0, exec);
334     }
335     if (!jitCompileAndSetHeuristics(codeBlock, exec))
336         LLINT_RETURN_TWO(0, exec);
337     
338     if (kind == Prologue)
339         LLINT_RETURN_TWO(codeBlock->jitCode()->executableAddress(), exec);
340     ASSERT(kind == ArityCheck);
341     LLINT_RETURN_TWO(codeBlock->jitCodeWithArityCheck().executableAddress(), exec);
342 }
343
344 LLINT_SLOW_PATH_DECL(entry_osr)
345 {
346     return entryOSR(exec, pc, exec->codeBlock(), "entry_osr", Prologue);
347 }
348
349 LLINT_SLOW_PATH_DECL(entry_osr_function_for_call)
350 {
351     return entryOSR(exec, pc, jsCast<JSFunction*>(exec->callee())->jsExecutable()->codeBlockForCall(), "entry_osr_function_for_call", Prologue);
352 }
353
354 LLINT_SLOW_PATH_DECL(entry_osr_function_for_construct)
355 {
356     return entryOSR(exec, pc, jsCast<JSFunction*>(exec->callee())->jsExecutable()->codeBlockForConstruct(), "entry_osr_function_for_construct", Prologue);
357 }
358
359 LLINT_SLOW_PATH_DECL(entry_osr_function_for_call_arityCheck)
360 {
361     return entryOSR(exec, pc, jsCast<JSFunction*>(exec->callee())->jsExecutable()->codeBlockForCall(), "entry_osr_function_for_call_arityCheck", ArityCheck);
362 }
363
364 LLINT_SLOW_PATH_DECL(entry_osr_function_for_construct_arityCheck)
365 {
366     return entryOSR(exec, pc, jsCast<JSFunction*>(exec->callee())->jsExecutable()->codeBlockForConstruct(), "entry_osr_function_for_construct_arityCheck", ArityCheck);
367 }
368
369 LLINT_SLOW_PATH_DECL(loop_osr)
370 {
371     CodeBlock* codeBlock = exec->codeBlock();
372
373     if (Options::verboseOSR()) {
374         dataLog(
375             *codeBlock, ": Entered loop_osr with executeCounter = ",
376             codeBlock->llintExecuteCounter(), "\n");
377     }
378     
379     if (!shouldJIT(exec)) {
380         codeBlock->dontJITAnytimeSoon();
381         LLINT_RETURN_TWO(0, exec);
382     }
383     
384     if (!jitCompileAndSetHeuristics(codeBlock, exec))
385         LLINT_RETURN_TWO(0, exec);
386     
387     ASSERT(codeBlock->jitType() == JITCode::BaselineJIT);
388     
389     Vector<BytecodeAndMachineOffset> map;
390     codeBlock->jitCodeMap()->decode(map);
391     BytecodeAndMachineOffset* mapping = binarySearch<BytecodeAndMachineOffset, unsigned>(map, map.size(), pc - codeBlock->instructions().begin(), BytecodeAndMachineOffset::getBytecodeIndex);
392     ASSERT(mapping);
393     ASSERT(mapping->m_bytecodeIndex == static_cast<unsigned>(pc - codeBlock->instructions().begin()));
394     
395     void* jumpTarget = codeBlock->jitCode()->executableAddressAtOffset(mapping->m_machineCodeOffset);
396     ASSERT(jumpTarget);
397     
398     LLINT_RETURN_TWO(jumpTarget, exec);
399 }
400
401 LLINT_SLOW_PATH_DECL(replace)
402 {
403     CodeBlock* codeBlock = exec->codeBlock();
404
405     if (Options::verboseOSR()) {
406         dataLog(
407             *codeBlock, ": Entered replace with executeCounter = ",
408             codeBlock->llintExecuteCounter(), "\n");
409     }
410     
411     if (shouldJIT(exec))
412         jitCompileAndSetHeuristics(codeBlock, exec);
413     else
414         codeBlock->dontJITAnytimeSoon();
415     LLINT_END_IMPL();
416 }
417 #endif // ENABLE(JIT)
418
419 LLINT_SLOW_PATH_DECL(stack_check)
420 {
421     LLINT_BEGIN();
422 #if LLINT_SLOW_PATH_TRACING
423     dataLogF("Checking stack height with exec = %p.\n", exec);
424     dataLogF("CodeBlock = %p.\n", exec->codeBlock());
425     dataLogF("Num callee registers = %u.\n", exec->codeBlock()->m_numCalleeRegisters);
426     dataLogF("Num vars = %u.\n", exec->codeBlock()->m_numVars);
427     dataLogF("Current end is at %p.\n", exec->vm().interpreter->stack().end());
428 #endif
429     ASSERT(!exec->vm().interpreter->stack().containsAddress(&exec->registers()[-exec->codeBlock()->m_numCalleeRegisters]));
430     if (UNLIKELY(!vm.interpreter->stack().grow(&exec->registers()[-exec->codeBlock()->m_numCalleeRegisters]))) {
431         exec = exec->callerFrame();
432         CommonSlowPaths::interpreterThrowInCaller(exec, createStackOverflowError(exec));
433         pc = returnToThrowForThrownException(exec);
434     }
435     LLINT_END_IMPL();
436 }
437
438 LLINT_SLOW_PATH_DECL(slow_path_create_activation)
439 {
440     LLINT_BEGIN();
441 #if LLINT_SLOW_PATH_TRACING
442     dataLogF("Creating an activation, exec = %p!\n", exec);
443 #endif
444     JSActivation* activation = JSActivation::create(vm, exec, exec->codeBlock());
445     exec->setScope(activation);
446     LLINT_RETURN(JSValue(activation));
447 }
448
449 LLINT_SLOW_PATH_DECL(slow_path_new_object)
450 {
451     LLINT_BEGIN();
452     LLINT_RETURN(constructEmptyObject(exec, pc[3].u.objectAllocationProfile->structure()));
453 }
454
455 LLINT_SLOW_PATH_DECL(slow_path_new_array)
456 {
457     LLINT_BEGIN();
458     LLINT_RETURN(constructArrayNegativeIndexed(exec, pc[4].u.arrayAllocationProfile, bitwise_cast<JSValue*>(&LLINT_OP(2)), pc[3].u.operand));
459 }
460
461 LLINT_SLOW_PATH_DECL(slow_path_new_array_with_size)
462 {
463     LLINT_BEGIN();
464     LLINT_RETURN(constructArrayWithSizeQuirk(exec, pc[3].u.arrayAllocationProfile, exec->lexicalGlobalObject(), LLINT_OP_C(2).jsValue()));
465 }
466
467 LLINT_SLOW_PATH_DECL(slow_path_new_array_buffer)
468 {
469     LLINT_BEGIN();
470     LLINT_RETURN(constructArray(exec, pc[4].u.arrayAllocationProfile, exec->codeBlock()->constantBuffer(pc[2].u.operand), pc[3].u.operand));
471 }
472
473 LLINT_SLOW_PATH_DECL(slow_path_new_regexp)
474 {
475     LLINT_BEGIN();
476     RegExp* regExp = exec->codeBlock()->regexp(pc[2].u.operand);
477     if (!regExp->isValid())
478         LLINT_THROW(createSyntaxError(exec, "Invalid flag supplied to RegExp constructor."));
479     LLINT_RETURN(RegExpObject::create(vm, exec->lexicalGlobalObject(), exec->lexicalGlobalObject()->regExpStructure(), regExp));
480 }
481
482 LLINT_SLOW_PATH_DECL(slow_path_check_has_instance)
483 {
484     LLINT_BEGIN();
485     
486     JSValue value = LLINT_OP_C(2).jsValue();
487     JSValue baseVal = LLINT_OP_C(3).jsValue();
488     if (baseVal.isObject()) {
489         JSObject* baseObject = asObject(baseVal);
490         ASSERT(!baseObject->structure()->typeInfo().implementsDefaultHasInstance());
491         if (baseObject->structure()->typeInfo().implementsHasInstance()) {
492             pc += pc[4].u.operand;
493             LLINT_RETURN(jsBoolean(baseObject->methodTable()->customHasInstance(baseObject, exec, value)));
494         }
495     }
496     LLINT_THROW(createInvalidParameterError(exec, "instanceof", baseVal));
497 }
498
499 LLINT_SLOW_PATH_DECL(slow_path_instanceof)
500 {
501     LLINT_BEGIN();
502     JSValue value = LLINT_OP_C(2).jsValue();
503     JSValue proto = LLINT_OP_C(3).jsValue();
504     ASSERT(!value.isObject() || !proto.isObject());
505     LLINT_RETURN(jsBoolean(JSObject::defaultHasInstance(exec, value, proto)));
506 }
507
508 LLINT_SLOW_PATH_DECL(slow_path_get_by_id)
509 {
510     LLINT_BEGIN();
511     CodeBlock* codeBlock = exec->codeBlock();
512     const Identifier& ident = codeBlock->identifier(pc[3].u.operand);
513     JSValue baseValue = LLINT_OP_C(2).jsValue();
514     PropertySlot slot(baseValue);
515
516     JSValue result = baseValue.get(exec, ident, slot);
517     LLINT_CHECK_EXCEPTION();
518     LLINT_OP(1) = result;
519     
520     if (!LLINT_ALWAYS_ACCESS_SLOW
521         && baseValue.isCell()
522         && slot.isCacheable()
523         && slot.slotBase() == baseValue
524         && slot.isCacheableValue()) {
525         
526         JSCell* baseCell = baseValue.asCell();
527         Structure* structure = baseCell->structure();
528         
529         if (!structure->isUncacheableDictionary()
530             && !structure->typeInfo().prohibitsPropertyCaching()) {
531             ConcurrentJITLocker locker(codeBlock->m_lock);
532             
533             pc[4].u.structure.set(
534                 vm, codeBlock->ownerExecutable(), structure);
535             if (isInlineOffset(slot.cachedOffset())) {
536                 pc[0].u.opcode = LLInt::getOpcode(llint_op_get_by_id);
537                 pc[5].u.operand = offsetInInlineStorage(slot.cachedOffset()) * sizeof(JSValue) + JSObject::offsetOfInlineStorage();
538             } else {
539                 pc[0].u.opcode = LLInt::getOpcode(llint_op_get_by_id_out_of_line);
540                 pc[5].u.operand = offsetInButterfly(slot.cachedOffset()) * sizeof(JSValue);
541             }
542         }
543     }
544
545     if (!LLINT_ALWAYS_ACCESS_SLOW
546         && isJSArray(baseValue)
547         && ident == exec->propertyNames().length) {
548         pc[0].u.opcode = LLInt::getOpcode(llint_op_get_array_length);
549 #if ENABLE(VALUE_PROFILER)
550         ArrayProfile* arrayProfile = codeBlock->getOrAddArrayProfile(pc - codeBlock->instructions().begin());
551         arrayProfile->observeStructure(baseValue.asCell()->structure());
552         pc[4].u.arrayProfile = arrayProfile;
553 #endif
554     }
555
556 #if ENABLE(VALUE_PROFILER)    
557     pc[OPCODE_LENGTH(op_get_by_id) - 1].u.profile->m_buckets[0] = JSValue::encode(result);
558 #endif
559     LLINT_END();
560 }
561
562 LLINT_SLOW_PATH_DECL(slow_path_get_arguments_length)
563 {
564     LLINT_BEGIN();
565     CodeBlock* codeBlock = exec->codeBlock();
566     const Identifier& ident = codeBlock->identifier(pc[3].u.operand);
567     JSValue baseValue = LLINT_OP(2).jsValue();
568     PropertySlot slot(baseValue);
569     LLINT_RETURN(baseValue.get(exec, ident, slot));
570 }
571
572 LLINT_SLOW_PATH_DECL(slow_path_put_by_id)
573 {
574     LLINT_BEGIN();
575     CodeBlock* codeBlock = exec->codeBlock();
576     const Identifier& ident = codeBlock->identifier(pc[2].u.operand);
577     
578     JSValue baseValue = LLINT_OP_C(1).jsValue();
579     PutPropertySlot slot(codeBlock->isStrictMode(), codeBlock->putByIdContext());
580     if (pc[8].u.operand)
581         asObject(baseValue)->putDirect(vm, ident, LLINT_OP_C(3).jsValue(), slot);
582     else
583         baseValue.put(exec, ident, LLINT_OP_C(3).jsValue(), slot);
584     LLINT_CHECK_EXCEPTION();
585     
586     if (!LLINT_ALWAYS_ACCESS_SLOW
587         && baseValue.isCell()
588         && slot.isCacheable()) {
589         
590         JSCell* baseCell = baseValue.asCell();
591         Structure* structure = baseCell->structure();
592         
593         if (!structure->isUncacheableDictionary()
594             && !structure->typeInfo().prohibitsPropertyCaching()
595             && baseCell == slot.base()) {
596             
597             if (slot.type() == PutPropertySlot::NewProperty) {
598                 ConcurrentJITLocker locker(codeBlock->m_lock);
599             
600                 if (!structure->isDictionary() && structure->previousID()->outOfLineCapacity() == structure->outOfLineCapacity()) {
601                     ASSERT(structure->previousID()->transitionWatchpointSetHasBeenInvalidated());
602                     
603                     // This is needed because some of the methods we call
604                     // below may GC.
605                     pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id);
606
607                     if (normalizePrototypeChain(exec, baseCell) != InvalidPrototypeChain) {
608                         ASSERT(structure->previousID()->isObject());
609                         pc[4].u.structure.set(
610                             vm, codeBlock->ownerExecutable(), structure->previousID());
611                         if (isInlineOffset(slot.cachedOffset()))
612                             pc[5].u.operand = offsetInInlineStorage(slot.cachedOffset()) * sizeof(JSValue) + JSObject::offsetOfInlineStorage();
613                         else
614                             pc[5].u.operand = offsetInButterfly(slot.cachedOffset()) * sizeof(JSValue);
615                         pc[6].u.structure.set(
616                             vm, codeBlock->ownerExecutable(), structure);
617                         StructureChain* chain = structure->prototypeChain(exec);
618                         ASSERT(chain);
619                         pc[7].u.structureChain.set(
620                             vm, codeBlock->ownerExecutable(), chain);
621                     
622                         if (pc[8].u.operand) {
623                             if (isInlineOffset(slot.cachedOffset()))
624                                 pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id_transition_direct);
625                             else
626                                 pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id_transition_direct_out_of_line);
627                         } else {
628                             if (isInlineOffset(slot.cachedOffset()))
629                                 pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id_transition_normal);
630                             else
631                                 pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id_transition_normal_out_of_line);
632                         }
633                     }
634                 }
635             } else {
636                 pc[4].u.structure.set(
637                     vm, codeBlock->ownerExecutable(), structure);
638                 if (isInlineOffset(slot.cachedOffset())) {
639                     pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id);
640                     pc[5].u.operand = offsetInInlineStorage(slot.cachedOffset()) * sizeof(JSValue) + JSObject::offsetOfInlineStorage();
641                 } else {
642                     pc[0].u.opcode = LLInt::getOpcode(llint_op_put_by_id_out_of_line);
643                     pc[5].u.operand = offsetInButterfly(slot.cachedOffset()) * sizeof(JSValue);
644                 }
645             }
646         }
647     }
648     
649     LLINT_END();
650 }
651
652 LLINT_SLOW_PATH_DECL(slow_path_del_by_id)
653 {
654     LLINT_BEGIN();
655     CodeBlock* codeBlock = exec->codeBlock();
656     JSObject* baseObject = LLINT_OP_C(2).jsValue().toObject(exec);
657     bool couldDelete = baseObject->methodTable()->deleteProperty(baseObject, exec, codeBlock->identifier(pc[3].u.operand));
658     LLINT_CHECK_EXCEPTION();
659     if (!couldDelete && codeBlock->isStrictMode())
660         LLINT_THROW(createTypeError(exec, "Unable to delete property."));
661     LLINT_RETURN(jsBoolean(couldDelete));
662 }
663
664 inline JSValue getByVal(ExecState* exec, JSValue baseValue, JSValue subscript)
665 {
666     if (LIKELY(baseValue.isCell() && subscript.isString())) {
667         if (JSValue result = baseValue.asCell()->fastGetOwnProperty(exec, asString(subscript)->value(exec)))
668             return result;
669     }
670     
671     if (subscript.isUInt32()) {
672         uint32_t i = subscript.asUInt32();
673         if (isJSString(baseValue) && asString(baseValue)->canGetIndex(i))
674             return asString(baseValue)->getIndex(exec, i);
675         
676         return baseValue.get(exec, i);
677     }
678
679     if (isName(subscript))
680         return baseValue.get(exec, jsCast<NameInstance*>(subscript.asCell())->privateName());
681     
682     Identifier property(exec, subscript.toString(exec)->value(exec));
683     return baseValue.get(exec, property);
684 }
685
686 LLINT_SLOW_PATH_DECL(slow_path_get_by_val)
687 {
688     LLINT_BEGIN();
689     LLINT_RETURN_PROFILED(op_get_by_val, getByVal(exec, LLINT_OP_C(2).jsValue(), LLINT_OP_C(3).jsValue()));
690 }
691
692 LLINT_SLOW_PATH_DECL(slow_path_get_argument_by_val)
693 {
694     LLINT_BEGIN();
695     JSValue arguments = LLINT_OP(2).jsValue();
696     if (!arguments) {
697         arguments = Arguments::create(vm, exec);
698         LLINT_CHECK_EXCEPTION();
699         LLINT_OP(2) = arguments;
700         exec->uncheckedR(unmodifiedArgumentsRegister(VirtualRegister(pc[2].u.operand)).offset()) = arguments;
701     }
702     
703     LLINT_RETURN_PROFILED(op_get_argument_by_val, getByVal(exec, arguments, LLINT_OP_C(3).jsValue()));
704 }
705
706 LLINT_SLOW_PATH_DECL(slow_path_get_by_pname)
707 {
708     LLINT_BEGIN();
709     LLINT_RETURN(getByVal(exec, LLINT_OP_C(2).jsValue(), LLINT_OP_C(3).jsValue()));
710 }
711
712 LLINT_SLOW_PATH_DECL(slow_path_put_by_val)
713 {
714     LLINT_BEGIN();
715     
716     JSValue baseValue = LLINT_OP_C(1).jsValue();
717     JSValue subscript = LLINT_OP_C(2).jsValue();
718     JSValue value = LLINT_OP_C(3).jsValue();
719     
720     if (LIKELY(subscript.isUInt32())) {
721         uint32_t i = subscript.asUInt32();
722         if (baseValue.isObject()) {
723             JSObject* object = asObject(baseValue);
724             if (object->canSetIndexQuickly(i))
725                 object->setIndexQuickly(vm, i, value);
726             else
727                 object->methodTable()->putByIndex(object, exec, i, value, exec->codeBlock()->isStrictMode());
728             LLINT_END();
729         }
730         baseValue.putByIndex(exec, i, value, exec->codeBlock()->isStrictMode());
731         LLINT_END();
732     }
733
734     if (isName(subscript)) {
735         PutPropertySlot slot(exec->codeBlock()->isStrictMode());
736         baseValue.put(exec, jsCast<NameInstance*>(subscript.asCell())->privateName(), value, slot);
737         LLINT_END();
738     }
739
740     Identifier property(exec, subscript.toString(exec)->value(exec));
741     LLINT_CHECK_EXCEPTION();
742     PutPropertySlot slot(exec->codeBlock()->isStrictMode());
743     baseValue.put(exec, property, value, slot);
744     LLINT_END();
745 }
746
747 LLINT_SLOW_PATH_DECL(slow_path_del_by_val)
748 {
749     LLINT_BEGIN();
750     JSValue baseValue = LLINT_OP_C(2).jsValue();
751     JSObject* baseObject = baseValue.toObject(exec);
752     
753     JSValue subscript = LLINT_OP_C(3).jsValue();
754     
755     bool couldDelete;
756     
757     uint32_t i;
758     if (subscript.getUInt32(i))
759         couldDelete = baseObject->methodTable()->deletePropertyByIndex(baseObject, exec, i);
760     else if (isName(subscript))
761         couldDelete = baseObject->methodTable()->deleteProperty(baseObject, exec, jsCast<NameInstance*>(subscript.asCell())->privateName());
762     else {
763         LLINT_CHECK_EXCEPTION();
764         Identifier property(exec, subscript.toString(exec)->value(exec));
765         LLINT_CHECK_EXCEPTION();
766         couldDelete = baseObject->methodTable()->deleteProperty(baseObject, exec, property);
767     }
768     
769     if (!couldDelete && exec->codeBlock()->isStrictMode())
770         LLINT_THROW(createTypeError(exec, "Unable to delete property."));
771     
772     LLINT_RETURN(jsBoolean(couldDelete));
773 }
774
775 LLINT_SLOW_PATH_DECL(slow_path_put_by_index)
776 {
777     LLINT_BEGIN();
778     JSValue arrayValue = LLINT_OP_C(1).jsValue();
779     ASSERT(isJSArray(arrayValue));
780     asArray(arrayValue)->putDirectIndex(exec, pc[2].u.operand, LLINT_OP_C(3).jsValue());
781     LLINT_END();
782 }
783
784 LLINT_SLOW_PATH_DECL(slow_path_put_getter_setter)
785 {
786     LLINT_BEGIN();
787     ASSERT(LLINT_OP(1).jsValue().isObject());
788     JSObject* baseObj = asObject(LLINT_OP(1).jsValue());
789     
790     GetterSetter* accessor = GetterSetter::create(exec);
791     LLINT_CHECK_EXCEPTION();
792     
793     JSValue getter = LLINT_OP(3).jsValue();
794     JSValue setter = LLINT_OP(4).jsValue();
795     ASSERT(getter.isObject() || getter.isUndefined());
796     ASSERT(setter.isObject() || setter.isUndefined());
797     ASSERT(getter.isObject() || setter.isObject());
798     
799     if (!getter.isUndefined())
800         accessor->setGetter(vm, asObject(getter));
801     if (!setter.isUndefined())
802         accessor->setSetter(vm, asObject(setter));
803     baseObj->putDirectAccessor(
804         exec,
805         exec->codeBlock()->identifier(pc[2].u.operand),
806         accessor, Accessor);
807     LLINT_END();
808 }
809
810 LLINT_SLOW_PATH_DECL(slow_path_jtrue)
811 {
812     LLINT_BEGIN();
813     LLINT_BRANCH(op_jtrue, LLINT_OP_C(1).jsValue().toBoolean(exec));
814 }
815
816 LLINT_SLOW_PATH_DECL(slow_path_jfalse)
817 {
818     LLINT_BEGIN();
819     LLINT_BRANCH(op_jfalse, !LLINT_OP_C(1).jsValue().toBoolean(exec));
820 }
821
822 LLINT_SLOW_PATH_DECL(slow_path_jless)
823 {
824     LLINT_BEGIN();
825     LLINT_BRANCH(op_jless, jsLess<true>(exec, LLINT_OP_C(1).jsValue(), LLINT_OP_C(2).jsValue()));
826 }
827
828 LLINT_SLOW_PATH_DECL(slow_path_jnless)
829 {
830     LLINT_BEGIN();
831     LLINT_BRANCH(op_jnless, !jsLess<true>(exec, LLINT_OP_C(1).jsValue(), LLINT_OP_C(2).jsValue()));
832 }
833
834 LLINT_SLOW_PATH_DECL(slow_path_jgreater)
835 {
836     LLINT_BEGIN();
837     LLINT_BRANCH(op_jgreater, jsLess<false>(exec, LLINT_OP_C(2).jsValue(), LLINT_OP_C(1).jsValue()));
838 }
839
840 LLINT_SLOW_PATH_DECL(slow_path_jngreater)
841 {
842     LLINT_BEGIN();
843     LLINT_BRANCH(op_jngreater, !jsLess<false>(exec, LLINT_OP_C(2).jsValue(), LLINT_OP_C(1).jsValue()));
844 }
845
846 LLINT_SLOW_PATH_DECL(slow_path_jlesseq)
847 {
848     LLINT_BEGIN();
849     LLINT_BRANCH(op_jlesseq, jsLessEq<true>(exec, LLINT_OP_C(1).jsValue(), LLINT_OP_C(2).jsValue()));
850 }
851
852 LLINT_SLOW_PATH_DECL(slow_path_jnlesseq)
853 {
854     LLINT_BEGIN();
855     LLINT_BRANCH(op_jnlesseq, !jsLessEq<true>(exec, LLINT_OP_C(1).jsValue(), LLINT_OP_C(2).jsValue()));
856 }
857
858 LLINT_SLOW_PATH_DECL(slow_path_jgreatereq)
859 {
860     LLINT_BEGIN();
861     LLINT_BRANCH(op_jgreatereq, jsLessEq<false>(exec, LLINT_OP_C(2).jsValue(), LLINT_OP_C(1).jsValue()));
862 }
863
864 LLINT_SLOW_PATH_DECL(slow_path_jngreatereq)
865 {
866     LLINT_BEGIN();
867     LLINT_BRANCH(op_jngreatereq, !jsLessEq<false>(exec, LLINT_OP_C(2).jsValue(), LLINT_OP_C(1).jsValue()));
868 }
869
870 LLINT_SLOW_PATH_DECL(slow_path_switch_imm)
871 {
872     LLINT_BEGIN();
873     JSValue scrutinee = LLINT_OP_C(3).jsValue();
874     ASSERT(scrutinee.isDouble());
875     double value = scrutinee.asDouble();
876     int32_t intValue = static_cast<int32_t>(value);
877     int defaultOffset = pc[2].u.operand;
878     if (value == intValue) {
879         CodeBlock* codeBlock = exec->codeBlock();
880         pc += codeBlock->switchJumpTable(pc[1].u.operand).offsetForValue(intValue, defaultOffset);
881     } else
882         pc += defaultOffset;
883     LLINT_END();
884 }
885
886 LLINT_SLOW_PATH_DECL(slow_path_switch_char)
887 {
888     LLINT_BEGIN();
889     JSValue scrutinee = LLINT_OP_C(3).jsValue();
890     ASSERT(scrutinee.isString());
891     JSString* string = asString(scrutinee);
892     ASSERT(string->length() == 1);
893     int defaultOffset = pc[2].u.operand;
894     StringImpl* impl = string->value(exec).impl();
895     CodeBlock* codeBlock = exec->codeBlock();
896     pc += codeBlock->switchJumpTable(pc[1].u.operand).offsetForValue((*impl)[0], defaultOffset);
897     LLINT_END();
898 }
899
900 LLINT_SLOW_PATH_DECL(slow_path_switch_string)
901 {
902     LLINT_BEGIN();
903     JSValue scrutinee = LLINT_OP_C(3).jsValue();
904     int defaultOffset = pc[2].u.operand;
905     if (!scrutinee.isString())
906         pc += defaultOffset;
907     else {
908         CodeBlock* codeBlock = exec->codeBlock();
909         pc += codeBlock->stringSwitchJumpTable(pc[1].u.operand).offsetForValue(asString(scrutinee)->value(exec).impl(), defaultOffset);
910     }
911     LLINT_END();
912 }
913
914 LLINT_SLOW_PATH_DECL(slow_path_new_func)
915 {
916     LLINT_BEGIN();
917     CodeBlock* codeBlock = exec->codeBlock();
918     ASSERT(codeBlock->codeType() != FunctionCode
919            || !codeBlock->needsFullScopeChain()
920            || exec->uncheckedR(codeBlock->activationRegister().offset()).jsValue());
921 #if LLINT_SLOW_PATH_TRACING
922     dataLogF("Creating function!\n");
923 #endif
924     LLINT_RETURN(JSFunction::create(exec, codeBlock->functionDecl(pc[2].u.operand), exec->scope()));
925 }
926
927 LLINT_SLOW_PATH_DECL(slow_path_new_func_exp)
928 {
929     LLINT_BEGIN();
930     CodeBlock* codeBlock = exec->codeBlock();
931     FunctionExecutable* function = codeBlock->functionExpr(pc[2].u.operand);
932     JSFunction* func = JSFunction::create(exec, function, exec->scope());
933     
934     LLINT_RETURN(func);
935 }
936
937 static SlowPathReturnType handleHostCall(ExecState* execCallee, Instruction* pc, JSValue callee, CodeSpecializationKind kind)
938 {
939     ExecState* exec = execCallee->callerFrame();
940     VM& vm = exec->vm();
941
942     execCallee->setScope(exec->scope());
943     execCallee->setCodeBlock(0);
944     execCallee->clearReturnPC();
945
946     if (kind == CodeForCall) {
947         CallData callData;
948         CallType callType = getCallData(callee, callData);
949     
950         ASSERT(callType != CallTypeJS);
951     
952         if (callType == CallTypeHost) {
953             NativeCallFrameTracer tracer(&vm, execCallee);
954             execCallee->setCallee(asObject(callee));
955             vm.hostCallReturnValue = JSValue::decode(callData.native.function(execCallee));
956             
957             LLINT_CALL_RETURN(execCallee, pc, LLInt::getCodePtr(getHostCallReturnValue));
958         }
959         
960 #if LLINT_SLOW_PATH_TRACING
961         dataLog("Call callee is not a function: ", callee, "\n");
962 #endif
963
964         ASSERT(callType == CallTypeNone);
965         LLINT_CALL_THROW(exec, pc, createNotAFunctionError(exec, callee));
966     }
967
968     ASSERT(kind == CodeForConstruct);
969     
970     ConstructData constructData;
971     ConstructType constructType = getConstructData(callee, constructData);
972     
973     ASSERT(constructType != ConstructTypeJS);
974     
975     if (constructType == ConstructTypeHost) {
976         NativeCallFrameTracer tracer(&vm, execCallee);
977         execCallee->setCallee(asObject(callee));
978         vm.hostCallReturnValue = JSValue::decode(constructData.native.function(execCallee));
979
980         LLINT_CALL_RETURN(execCallee, pc, LLInt::getCodePtr(getHostCallReturnValue));
981     }
982     
983 #if LLINT_SLOW_PATH_TRACING
984     dataLog("Constructor callee is not a function: ", callee, "\n");
985 #endif
986
987     ASSERT(constructType == ConstructTypeNone);
988     LLINT_CALL_THROW(exec, pc, createNotAConstructorError(exec, callee));
989 }
990
991 inline SlowPathReturnType setUpCall(ExecState* execCallee, Instruction* pc, CodeSpecializationKind kind, JSValue calleeAsValue, LLIntCallLinkInfo* callLinkInfo = 0)
992 {
993 #if LLINT_SLOW_PATH_TRACING
994     dataLogF("Performing call with recorded PC = %p\n", execCallee->callerFrame()->currentVPC());
995 #endif
996
997     JSCell* calleeAsFunctionCell = getJSFunction(calleeAsValue);
998     if (!calleeAsFunctionCell)
999         return handleHostCall(execCallee, pc, calleeAsValue, kind);
1000     
1001     JSFunction* callee = jsCast<JSFunction*>(calleeAsFunctionCell);
1002     JSScope* scope = callee->scopeUnchecked();
1003     VM& vm = *scope->vm();
1004     execCallee->setScope(scope);
1005     ExecutableBase* executable = callee->executable();
1006     
1007     MacroAssemblerCodePtr codePtr;
1008     CodeBlock* codeBlock = 0;
1009     if (executable->isHostFunction())
1010         codePtr = executable->hostCodeEntryFor(kind);
1011     else {
1012         FunctionExecutable* functionExecutable = static_cast<FunctionExecutable*>(executable);
1013         JSObject* error = functionExecutable->prepareForExecution(execCallee, callee->scope(), kind);
1014         if (error)
1015             LLINT_CALL_THROW(execCallee->callerFrame(), pc, error);
1016         codeBlock = functionExecutable->codeBlockFor(kind);
1017         ASSERT(codeBlock);
1018         if (execCallee->argumentCountIncludingThis() < static_cast<size_t>(codeBlock->numParameters()))
1019             codePtr = functionExecutable->jsCodeWithArityCheckEntryFor(kind);
1020         else
1021             codePtr = functionExecutable->jsCodeEntryFor(kind);
1022     }
1023     
1024     if (!LLINT_ALWAYS_ACCESS_SLOW && callLinkInfo) {
1025         ExecState* execCaller = execCallee->callerFrame();
1026         
1027         CodeBlock* callerCodeBlock = execCaller->codeBlock();
1028
1029         ConcurrentJITLocker locker(callerCodeBlock->m_lock);
1030         
1031         if (callLinkInfo->isOnList())
1032             callLinkInfo->remove();
1033         callLinkInfo->callee.set(vm, callerCodeBlock->ownerExecutable(), callee);
1034         callLinkInfo->lastSeenCallee.set(vm, callerCodeBlock->ownerExecutable(), callee);
1035         callLinkInfo->machineCodeTarget = codePtr;
1036         if (codeBlock)
1037             codeBlock->linkIncomingCall(execCaller, callLinkInfo);
1038     }
1039
1040     LLINT_CALL_RETURN(execCallee, pc, codePtr.executableAddress());
1041 }
1042
1043 inline SlowPathReturnType genericCall(ExecState* exec, Instruction* pc, CodeSpecializationKind kind)
1044 {
1045     // This needs to:
1046     // - Set up a call frame.
1047     // - Figure out what to call and compile it if necessary.
1048     // - If possible, link the call's inline cache.
1049     // - Return a tuple of machine code address to call and the new call frame.
1050     
1051     JSValue calleeAsValue = LLINT_OP_C(2).jsValue();
1052     
1053     ExecState* execCallee = exec - pc[4].u.operand;
1054     
1055     execCallee->setArgumentCountIncludingThis(pc[3].u.operand);
1056     execCallee->uncheckedR(JSStack::Callee) = calleeAsValue;
1057     execCallee->setCallerFrame(exec);
1058     
1059     ASSERT(pc[5].u.callLinkInfo);
1060     return setUpCall(execCallee, pc, kind, calleeAsValue, pc[5].u.callLinkInfo);
1061 }
1062
1063 LLINT_SLOW_PATH_DECL(slow_path_call)
1064 {
1065     LLINT_BEGIN_NO_SET_PC();
1066     return genericCall(exec, pc, CodeForCall);
1067 }
1068
1069 LLINT_SLOW_PATH_DECL(slow_path_construct)
1070 {
1071     LLINT_BEGIN_NO_SET_PC();
1072     return genericCall(exec, pc, CodeForConstruct);
1073 }
1074
1075 LLINT_SLOW_PATH_DECL(slow_path_call_varargs)
1076 {
1077     LLINT_BEGIN();
1078     // This needs to:
1079     // - Set up a call frame while respecting the variable arguments.
1080     // - Figure out what to call and compile it if necessary.
1081     // - Return a tuple of machine code address to call and the new call frame.
1082     
1083     JSValue calleeAsValue = LLINT_OP_C(2).jsValue();
1084     
1085     ExecState* execCallee = loadVarargs(
1086         exec, &vm.interpreter->stack(),
1087         LLINT_OP_C(3).jsValue(), LLINT_OP_C(4).jsValue(), pc[5].u.operand);
1088     LLINT_CALL_CHECK_EXCEPTION(exec);
1089     
1090     execCallee->uncheckedR(JSStack::Callee) = calleeAsValue;
1091     execCallee->setCallerFrame(exec);
1092     exec->setCurrentVPC(pc);
1093     
1094     return setUpCall(execCallee, pc, CodeForCall, calleeAsValue);
1095 }
1096
1097 LLINT_SLOW_PATH_DECL(slow_path_call_eval)
1098 {
1099     LLINT_BEGIN_NO_SET_PC();
1100     JSValue calleeAsValue = LLINT_OP(2).jsValue();
1101     
1102     ExecState* execCallee = exec - pc[4].u.operand;
1103     
1104     execCallee->setArgumentCountIncludingThis(pc[3].u.operand);
1105     execCallee->setCallerFrame(exec);
1106     execCallee->uncheckedR(JSStack::Callee) = calleeAsValue;
1107     execCallee->setScope(exec->scope());
1108     execCallee->setReturnPC(LLInt::getCodePtr(llint_generic_return_point));
1109     execCallee->setCodeBlock(0);
1110     exec->setCurrentVPC(pc);
1111     
1112     if (!isHostFunction(calleeAsValue, globalFuncEval))
1113         return setUpCall(execCallee, pc, CodeForCall, calleeAsValue);
1114     
1115     vm.hostCallReturnValue = eval(execCallee);
1116     LLINT_CALL_RETURN(execCallee, pc, LLInt::getCodePtr(getHostCallReturnValue));
1117 }
1118
1119 LLINT_SLOW_PATH_DECL(slow_path_tear_off_activation)
1120 {
1121     LLINT_BEGIN();
1122     ASSERT(exec->codeBlock()->needsFullScopeChain());
1123     jsCast<JSActivation*>(LLINT_OP(1).jsValue())->tearOff(vm);
1124     LLINT_END();
1125 }
1126
1127 LLINT_SLOW_PATH_DECL(slow_path_tear_off_arguments)
1128 {
1129     LLINT_BEGIN();
1130     ASSERT(exec->codeBlock()->usesArguments());
1131     Arguments* arguments = jsCast<Arguments*>(exec->uncheckedR(unmodifiedArgumentsRegister(VirtualRegister(pc[1].u.operand)).offset()).jsValue());
1132     if (JSValue activationValue = LLINT_OP_C(2).jsValue())
1133         arguments->didTearOffActivation(exec, jsCast<JSActivation*>(activationValue));
1134     else
1135         arguments->tearOff(exec);
1136     LLINT_END();
1137 }
1138
1139 LLINT_SLOW_PATH_DECL(slow_path_strcat)
1140 {
1141     LLINT_BEGIN();
1142     LLINT_RETURN(jsStringFromRegisterArray(exec, &LLINT_OP(2), pc[3].u.operand));
1143 }
1144
1145 LLINT_SLOW_PATH_DECL(slow_path_to_primitive)
1146 {
1147     LLINT_BEGIN();
1148     LLINT_RETURN(LLINT_OP_C(2).jsValue().toPrimitive(exec));
1149 }
1150
1151 LLINT_SLOW_PATH_DECL(slow_path_get_pnames)
1152 {
1153     LLINT_BEGIN();
1154     JSValue v = LLINT_OP(2).jsValue();
1155     if (v.isUndefinedOrNull()) {
1156         pc += pc[5].u.operand;
1157         LLINT_END();
1158     }
1159     
1160     JSObject* o = v.toObject(exec);
1161     Structure* structure = o->structure();
1162     JSPropertyNameIterator* jsPropertyNameIterator = structure->enumerationCache();
1163     if (!jsPropertyNameIterator || jsPropertyNameIterator->cachedPrototypeChain() != structure->prototypeChain(exec))
1164         jsPropertyNameIterator = JSPropertyNameIterator::create(exec, o);
1165     
1166     LLINT_OP(1) = JSValue(jsPropertyNameIterator);
1167     LLINT_OP(2) = JSValue(o);
1168     LLINT_OP(3) = Register::withInt(0);
1169     LLINT_OP(4) = Register::withInt(jsPropertyNameIterator->size());
1170     
1171     pc += OPCODE_LENGTH(op_get_pnames);
1172     LLINT_END();
1173 }
1174
1175 LLINT_SLOW_PATH_DECL(slow_path_next_pname)
1176 {
1177     LLINT_BEGIN();
1178     JSObject* base = asObject(LLINT_OP(2).jsValue());
1179     JSString* property = asString(LLINT_OP(1).jsValue());
1180     if (base->hasProperty(exec, Identifier(exec, property->value(exec)))) {
1181         // Go to target.
1182         pc += pc[6].u.operand;
1183     } // Else, don't change the PC, so the interpreter will reloop.
1184     LLINT_END();
1185 }
1186
1187 LLINT_SLOW_PATH_DECL(slow_path_push_with_scope)
1188 {
1189     LLINT_BEGIN();
1190     JSValue v = LLINT_OP_C(1).jsValue();
1191     JSObject* o = v.toObject(exec);
1192     LLINT_CHECK_EXCEPTION();
1193     
1194     exec->setScope(JSWithScope::create(exec, o));
1195     
1196     LLINT_END();
1197 }
1198
1199 LLINT_SLOW_PATH_DECL(slow_path_pop_scope)
1200 {
1201     LLINT_BEGIN();
1202     exec->setScope(exec->scope()->next());
1203     LLINT_END();
1204 }
1205
1206 LLINT_SLOW_PATH_DECL(slow_path_push_name_scope)
1207 {
1208     LLINT_BEGIN();
1209     CodeBlock* codeBlock = exec->codeBlock();
1210     JSNameScope* scope = JSNameScope::create(exec, codeBlock->identifier(pc[1].u.operand), LLINT_OP(2).jsValue(), pc[3].u.operand);
1211     exec->setScope(scope);
1212     LLINT_END();
1213 }
1214
1215 LLINT_SLOW_PATH_DECL(slow_path_throw)
1216 {
1217     LLINT_BEGIN();
1218     LLINT_THROW(LLINT_OP_C(1).jsValue());
1219 }
1220
1221 LLINT_SLOW_PATH_DECL(slow_path_throw_static_error)
1222 {
1223     LLINT_BEGIN();
1224     if (pc[2].u.operand)
1225         LLINT_THROW(createReferenceError(exec, errorDescriptionForValue(exec, LLINT_OP_C(1).jsValue())->value(exec)));
1226     else
1227         LLINT_THROW(createTypeError(exec, errorDescriptionForValue(exec, LLINT_OP_C(1).jsValue())->value(exec)));
1228 }
1229
1230 LLINT_SLOW_PATH_DECL(slow_path_handle_watchdog_timer)
1231 {
1232     LLINT_BEGIN_NO_SET_PC();
1233     if (UNLIKELY(vm.watchdog.didFire(exec)))
1234         LLINT_THROW(createTerminatedExecutionException(&vm));
1235     LLINT_RETURN_TWO(0, exec);
1236 }
1237
1238 LLINT_SLOW_PATH_DECL(slow_path_debug)
1239 {
1240     LLINT_BEGIN();
1241     int debugHookID = pc[1].u.operand;
1242     vm.interpreter->debug(exec, static_cast<DebugHookID>(debugHookID));
1243     
1244     LLINT_END();
1245 }
1246
1247 LLINT_SLOW_PATH_DECL(slow_path_profile_will_call)
1248 {
1249     LLINT_BEGIN();
1250     if (LegacyProfiler* profiler = vm.enabledProfiler())
1251         profiler->willExecute(exec, LLINT_OP(1).jsValue());
1252     LLINT_END();
1253 }
1254
1255 LLINT_SLOW_PATH_DECL(slow_path_profile_did_call)
1256 {
1257     LLINT_BEGIN();
1258     if (LegacyProfiler* profiler = vm.enabledProfiler())
1259         profiler->didExecute(exec, LLINT_OP(1).jsValue());
1260     LLINT_END();
1261 }
1262
1263 LLINT_SLOW_PATH_DECL(throw_from_native_call)
1264 {
1265     LLINT_BEGIN();
1266     ASSERT(vm.exception());
1267     LLINT_END();
1268 }
1269
1270 LLINT_SLOW_PATH_DECL(slow_path_resolve_scope)
1271 {
1272     LLINT_BEGIN();
1273     const Identifier& ident = exec->codeBlock()->identifier(pc[2].u.operand);
1274     LLINT_RETURN(JSScope::resolve(exec, exec->scope(), ident));
1275 }
1276
1277 LLINT_SLOW_PATH_DECL(slow_path_get_from_scope)
1278 {
1279     LLINT_BEGIN();
1280     const Identifier& ident = exec->codeBlock()->identifier(pc[3].u.operand);
1281     JSObject* scope = jsCast<JSObject*>(LLINT_OP(2).jsValue());
1282     ResolveModeAndType modeAndType(pc[4].u.operand);
1283
1284     PropertySlot slot(scope);
1285     if (!scope->getPropertySlot(exec, ident, slot)) {
1286         if (modeAndType.mode() == ThrowIfNotFound)
1287             LLINT_RETURN(exec->vm().throwException(exec, createUndefinedVariableError(exec, ident)));
1288         LLINT_RETURN(jsUndefined());
1289     }
1290
1291     // Covers implicit globals. Since they don't exist until they first execute, we didn't know how to cache them at compile time.
1292     if (slot.isCacheableValue() && slot.slotBase() == scope && scope->structure()->propertyAccessesAreCacheable()) {
1293         if (modeAndType.type() == GlobalProperty || modeAndType.type() == GlobalPropertyWithVarInjectionChecks) {
1294             CodeBlock* codeBlock = exec->codeBlock();
1295             ConcurrentJITLocker locker(codeBlock->m_lock);
1296             pc[5].u.structure.set(exec->vm(), codeBlock->ownerExecutable(), scope->structure());
1297             pc[6].u.operand = slot.cachedOffset();
1298         }
1299     }
1300
1301     LLINT_RETURN(slot.getValue(exec, ident));
1302 }
1303
1304 LLINT_SLOW_PATH_DECL(slow_path_put_to_scope)
1305 {
1306     LLINT_BEGIN();
1307     CodeBlock* codeBlock = exec->codeBlock();
1308     const Identifier& ident = codeBlock->identifier(pc[2].u.operand);
1309     JSObject* scope = jsCast<JSObject*>(LLINT_OP(1).jsValue());
1310     JSValue value = LLINT_OP_C(3).jsValue();
1311     ResolveModeAndType modeAndType = ResolveModeAndType(pc[4].u.operand);
1312
1313     if (modeAndType.mode() == ThrowIfNotFound && !scope->hasProperty(exec, ident))
1314         LLINT_THROW(createUndefinedVariableError(exec, ident));
1315
1316     PutPropertySlot slot(codeBlock->isStrictMode());
1317     scope->methodTable()->put(scope, exec, ident, value, slot);
1318
1319     // Covers implicit globals. Since they don't exist until they first execute, we didn't know how to cache them at compile time.
1320     if (modeAndType.type() == GlobalProperty || modeAndType.type() == GlobalPropertyWithVarInjectionChecks) {
1321         if (slot.isCacheable() && slot.base() == scope && scope->structure()->propertyAccessesAreCacheable()) {
1322             ConcurrentJITLocker locker(codeBlock->m_lock);
1323             pc[5].u.structure.set(exec->vm(), codeBlock->ownerExecutable(), scope->structure());
1324             pc[6].u.operand = slot.cachedOffset();
1325         }
1326     }
1327
1328     LLINT_END();
1329 }
1330
1331 } } // namespace JSC::LLInt
1332
1333 #endif // ENABLE(LLINT)