| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 1621 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1632 __ push(eax); // Save result on the stack | 1632 __ push(eax); // Save result on the stack |
| 1633 result_saved = true; | 1633 result_saved = true; |
| 1634 } | 1634 } |
| 1635 switch (property->kind()) { | 1635 switch (property->kind()) { |
| 1636 case ObjectLiteral::Property::CONSTANT: | 1636 case ObjectLiteral::Property::CONSTANT: |
| 1637 UNREACHABLE(); | 1637 UNREACHABLE(); |
| 1638 case ObjectLiteral::Property::MATERIALIZED_LITERAL: | 1638 case ObjectLiteral::Property::MATERIALIZED_LITERAL: |
| 1639 ASSERT(!CompileTimeValue::IsCompileTimeValue(value)); | 1639 ASSERT(!CompileTimeValue::IsCompileTimeValue(value)); |
| 1640 // Fall through. | 1640 // Fall through. |
| 1641 case ObjectLiteral::Property::COMPUTED: | 1641 case ObjectLiteral::Property::COMPUTED: |
| 1642 if (key->handle()->IsInternalizedString()) { | 1642 if (key->value()->IsInternalizedString()) { |
| 1643 if (property->emit_store()) { | 1643 if (property->emit_store()) { |
| 1644 VisitForAccumulatorValue(value); | 1644 VisitForAccumulatorValue(value); |
| 1645 __ mov(ecx, Immediate(key->handle())); | 1645 __ mov(ecx, Immediate(key->value())); |
| 1646 __ mov(edx, Operand(esp, 0)); | 1646 __ mov(edx, Operand(esp, 0)); |
| 1647 Handle<Code> ic = is_classic_mode() | 1647 Handle<Code> ic = is_classic_mode() |
| 1648 ? isolate()->builtins()->StoreIC_Initialize() | 1648 ? isolate()->builtins()->StoreIC_Initialize() |
| 1649 : isolate()->builtins()->StoreIC_Initialize_Strict(); | 1649 : isolate()->builtins()->StoreIC_Initialize_Strict(); |
| 1650 CallIC(ic, RelocInfo::CODE_TARGET, key->LiteralFeedbackId()); | 1650 CallIC(ic, RelocInfo::CODE_TARGET, key->LiteralFeedbackId()); |
| 1651 PrepareForBailoutForId(key->id(), NO_REGISTERS); | 1651 PrepareForBailoutForId(key->id(), NO_REGISTERS); |
| 1652 } else { | 1652 } else { |
| 1653 VisitForEffect(value); | 1653 VisitForEffect(value); |
| 1654 } | 1654 } |
| 1655 break; | 1655 break; |
| (...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1775 } | 1775 } |
| 1776 | 1776 |
| 1777 bool result_saved = false; // Is the result saved to the stack? | 1777 bool result_saved = false; // Is the result saved to the stack? |
| 1778 | 1778 |
| 1779 // Emit code to evaluate all the non-constant subexpressions and to store | 1779 // Emit code to evaluate all the non-constant subexpressions and to store |
| 1780 // them into the newly cloned array. | 1780 // them into the newly cloned array. |
| 1781 for (int i = 0; i < length; i++) { | 1781 for (int i = 0; i < length; i++) { |
| 1782 Expression* subexpr = subexprs->at(i); | 1782 Expression* subexpr = subexprs->at(i); |
| 1783 // If the subexpression is a literal or a simple materialized literal it | 1783 // If the subexpression is a literal or a simple materialized literal it |
| 1784 // is already set in the cloned array. | 1784 // is already set in the cloned array. |
| 1785 if (subexpr->AsLiteral() != NULL || | 1785 if (CompileTimeValue::IsCompileTimeValue(subexpr)) continue; |
| 1786 CompileTimeValue::IsCompileTimeValue(subexpr)) { | |
| 1787 continue; | |
| 1788 } | |
| 1789 | 1786 |
| 1790 if (!result_saved) { | 1787 if (!result_saved) { |
| 1791 __ push(eax); // array literal. | 1788 __ push(eax); // array literal. |
| 1792 __ push(Immediate(Smi::FromInt(expr->literal_index()))); | 1789 __ push(Immediate(Smi::FromInt(expr->literal_index()))); |
| 1793 result_saved = true; | 1790 result_saved = true; |
| 1794 } | 1791 } |
| 1795 VisitForAccumulatorValue(subexpr); | 1792 VisitForAccumulatorValue(subexpr); |
| 1796 | 1793 |
| 1797 if (IsFastObjectElementsKind(constant_elements_kind)) { | 1794 if (IsFastObjectElementsKind(constant_elements_kind)) { |
| 1798 // Fast-case array literal with ElementsKind of FAST_*_ELEMENTS, they | 1795 // Fast-case array literal with ElementsKind of FAST_*_ELEMENTS, they |
| (...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1946 // this. It stays on the stack while we update the iterator. | 1943 // this. It stays on the stack while we update the iterator. |
| 1947 VisitForStackValue(expr->expression()); | 1944 VisitForStackValue(expr->expression()); |
| 1948 | 1945 |
| 1949 switch (expr->yield_kind()) { | 1946 switch (expr->yield_kind()) { |
| 1950 case Yield::SUSPEND: | 1947 case Yield::SUSPEND: |
| 1951 // Pop value from top-of-stack slot; box result into result register. | 1948 // Pop value from top-of-stack slot; box result into result register. |
| 1952 EmitCreateIteratorResult(false); | 1949 EmitCreateIteratorResult(false); |
| 1953 __ push(result_register()); | 1950 __ push(result_register()); |
| 1954 // Fall through. | 1951 // Fall through. |
| 1955 case Yield::INITIAL: { | 1952 case Yield::INITIAL: { |
| 1956 VisitForStackValue(expr->generator_object()); | 1953 Label suspend, continuation, post_runtime, resume; |
| 1954 |
| 1955 __ jmp(&suspend); |
| 1956 |
| 1957 __ bind(&continuation); |
| 1958 __ jmp(&resume); |
| 1959 |
| 1960 __ bind(&suspend); |
| 1961 VisitForAccumulatorValue(expr->generator_object()); |
| 1962 ASSERT(continuation.pos() > 0 && Smi::IsValid(continuation.pos())); |
| 1963 __ mov(FieldOperand(eax, JSGeneratorObject::kContinuationOffset), |
| 1964 Immediate(Smi::FromInt(continuation.pos()))); |
| 1965 __ mov(FieldOperand(eax, JSGeneratorObject::kContextOffset), esi); |
| 1966 __ mov(ecx, esi); |
| 1967 __ RecordWriteField(eax, JSGeneratorObject::kContextOffset, ecx, edx, |
| 1968 kDontSaveFPRegs); |
| 1969 __ lea(ebx, Operand(ebp, StandardFrameConstants::kExpressionsOffset)); |
| 1970 __ cmp(esp, ebx); |
| 1971 __ j(equal, &post_runtime); |
| 1972 __ push(eax); // generator object |
| 1957 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); | 1973 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); |
| 1958 __ mov(context_register(), | 1974 __ mov(context_register(), |
| 1959 Operand(ebp, StandardFrameConstants::kContextOffset)); | 1975 Operand(ebp, StandardFrameConstants::kContextOffset)); |
| 1960 | 1976 __ bind(&post_runtime); |
| 1961 Label resume; | |
| 1962 __ CompareRoot(result_register(), Heap::kTheHoleValueRootIndex); | |
| 1963 __ j(not_equal, &resume); | |
| 1964 __ pop(result_register()); | 1977 __ pop(result_register()); |
| 1965 EmitReturnSequence(); | 1978 EmitReturnSequence(); |
| 1966 | 1979 |
| 1967 __ bind(&resume); | 1980 __ bind(&resume); |
| 1968 context()->Plug(result_register()); | 1981 context()->Plug(result_register()); |
| 1969 break; | 1982 break; |
| 1970 } | 1983 } |
| 1971 | 1984 |
| 1972 case Yield::FINAL: { | 1985 case Yield::FINAL: { |
| 1973 VisitForAccumulatorValue(expr->generator_object()); | 1986 VisitForAccumulatorValue(expr->generator_object()); |
| 1974 __ mov(FieldOperand(result_register(), | 1987 __ mov(FieldOperand(result_register(), |
| 1975 JSGeneratorObject::kContinuationOffset), | 1988 JSGeneratorObject::kContinuationOffset), |
| 1976 Immediate(Smi::FromInt(JSGeneratorObject::kGeneratorClosed))); | 1989 Immediate(Smi::FromInt(JSGeneratorObject::kGeneratorClosed))); |
| 1977 // Pop value from top-of-stack slot, box result into result register. | 1990 // Pop value from top-of-stack slot, box result into result register. |
| 1978 EmitCreateIteratorResult(true); | 1991 EmitCreateIteratorResult(true); |
| 1979 EmitUnwindBeforeReturn(); | 1992 EmitUnwindBeforeReturn(); |
| 1980 EmitReturnSequence(); | 1993 EmitReturnSequence(); |
| 1981 break; | 1994 break; |
| 1982 } | 1995 } |
| 1983 | 1996 |
| 1984 case Yield::DELEGATING: { | 1997 case Yield::DELEGATING: { |
| 1985 VisitForStackValue(expr->generator_object()); | 1998 VisitForStackValue(expr->generator_object()); |
| 1986 | 1999 |
| 1987 // Initial stack layout is as follows: | 2000 // Initial stack layout is as follows: |
| 1988 // [sp + 1 * kPointerSize] iter | 2001 // [sp + 1 * kPointerSize] iter |
| 1989 // [sp + 0 * kPointerSize] g | 2002 // [sp + 0 * kPointerSize] g |
| 1990 | 2003 |
| 1991 Label l_catch, l_try, l_resume, l_next, l_call, l_loop; | 2004 Label l_catch, l_try, l_suspend, l_continuation, l_resume; |
| 2005 Label l_next, l_call, l_loop; |
| 1992 // Initial send value is undefined. | 2006 // Initial send value is undefined. |
| 1993 __ mov(eax, isolate()->factory()->undefined_value()); | 2007 __ mov(eax, isolate()->factory()->undefined_value()); |
| 1994 __ jmp(&l_next); | 2008 __ jmp(&l_next); |
| 1995 | 2009 |
| 1996 // catch (e) { receiver = iter; f = 'throw'; arg = e; goto l_call; } | 2010 // catch (e) { receiver = iter; f = 'throw'; arg = e; goto l_call; } |
| 1997 __ bind(&l_catch); | 2011 __ bind(&l_catch); |
| 1998 handler_table()->set(expr->index(), Smi::FromInt(l_catch.pos())); | 2012 handler_table()->set(expr->index(), Smi::FromInt(l_catch.pos())); |
| 1999 __ mov(ecx, isolate()->factory()->throw_string()); // "throw" | 2013 __ mov(ecx, isolate()->factory()->throw_string()); // "throw" |
| 2000 __ push(ecx); // "throw" | 2014 __ push(ecx); // "throw" |
| 2001 __ push(Operand(esp, 2 * kPointerSize)); // iter | 2015 __ push(Operand(esp, 2 * kPointerSize)); // iter |
| 2002 __ push(eax); // exception | 2016 __ push(eax); // exception |
| 2003 __ jmp(&l_call); | 2017 __ jmp(&l_call); |
| 2004 | 2018 |
| 2005 // try { received = %yield result } | 2019 // try { received = %yield result } |
| 2006 // Shuffle the received result above a try handler and yield it without | 2020 // Shuffle the received result above a try handler and yield it without |
| 2007 // re-boxing. | 2021 // re-boxing. |
| 2008 __ bind(&l_try); | 2022 __ bind(&l_try); |
| 2009 __ pop(eax); // result | 2023 __ pop(eax); // result |
| 2010 __ PushTryHandler(StackHandler::CATCH, expr->index()); | 2024 __ PushTryHandler(StackHandler::CATCH, expr->index()); |
| 2011 const int handler_size = StackHandlerConstants::kSize; | 2025 const int handler_size = StackHandlerConstants::kSize; |
| 2012 __ push(eax); // result | 2026 __ push(eax); // result |
| 2013 __ push(Operand(esp, (0 + 1) * kPointerSize + handler_size)); // g | 2027 __ jmp(&l_suspend); |
| 2028 __ bind(&l_continuation); |
| 2029 __ jmp(&l_resume); |
| 2030 __ bind(&l_suspend); |
| 2031 const int generator_object_depth = kPointerSize + handler_size; |
| 2032 __ mov(eax, Operand(esp, generator_object_depth)); |
| 2033 __ push(eax); // g |
| 2034 ASSERT(l_continuation.pos() > 0 && Smi::IsValid(l_continuation.pos())); |
| 2035 __ mov(FieldOperand(eax, JSGeneratorObject::kContinuationOffset), |
| 2036 Immediate(Smi::FromInt(l_continuation.pos()))); |
| 2037 __ mov(FieldOperand(eax, JSGeneratorObject::kContextOffset), esi); |
| 2038 __ mov(ecx, esi); |
| 2039 __ RecordWriteField(eax, JSGeneratorObject::kContextOffset, ecx, edx, |
| 2040 kDontSaveFPRegs); |
| 2014 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); | 2041 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); |
| 2015 __ mov(context_register(), | 2042 __ mov(context_register(), |
| 2016 Operand(ebp, StandardFrameConstants::kContextOffset)); | 2043 Operand(ebp, StandardFrameConstants::kContextOffset)); |
| 2017 __ CompareRoot(eax, Heap::kTheHoleValueRootIndex); | |
| 2018 __ j(not_equal, &l_resume); | |
| 2019 __ pop(eax); // result | 2044 __ pop(eax); // result |
| 2020 EmitReturnSequence(); | 2045 EmitReturnSequence(); |
| 2021 __ bind(&l_resume); // received in eax | 2046 __ bind(&l_resume); // received in eax |
| 2022 __ PopTryHandler(); | 2047 __ PopTryHandler(); |
| 2023 | 2048 |
| 2024 // receiver = iter; f = iter.next; arg = received; | 2049 // receiver = iter; f = iter.next; arg = received; |
| 2025 __ bind(&l_next); | 2050 __ bind(&l_next); |
| 2026 __ mov(ecx, isolate()->factory()->next_string()); // "next" | 2051 __ mov(ecx, isolate()->factory()->next_string()); // "next" |
| 2027 __ push(ecx); | 2052 __ push(ecx); |
| 2028 __ push(Operand(esp, 2 * kPointerSize)); // iter | 2053 __ push(Operand(esp, 2 * kPointerSize)); // iter |
| (...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2084 // Push receiver. | 2109 // Push receiver. |
| 2085 __ push(FieldOperand(ebx, JSGeneratorObject::kReceiverOffset)); | 2110 __ push(FieldOperand(ebx, JSGeneratorObject::kReceiverOffset)); |
| 2086 | 2111 |
| 2087 // Push holes for arguments to generator function. | 2112 // Push holes for arguments to generator function. |
| 2088 __ mov(edx, FieldOperand(edi, JSFunction::kSharedFunctionInfoOffset)); | 2113 __ mov(edx, FieldOperand(edi, JSFunction::kSharedFunctionInfoOffset)); |
| 2089 __ mov(edx, | 2114 __ mov(edx, |
| 2090 FieldOperand(edx, SharedFunctionInfo::kFormalParameterCountOffset)); | 2115 FieldOperand(edx, SharedFunctionInfo::kFormalParameterCountOffset)); |
| 2091 __ mov(ecx, isolate()->factory()->the_hole_value()); | 2116 __ mov(ecx, isolate()->factory()->the_hole_value()); |
| 2092 Label push_argument_holes, push_frame; | 2117 Label push_argument_holes, push_frame; |
| 2093 __ bind(&push_argument_holes); | 2118 __ bind(&push_argument_holes); |
| 2094 __ sub(edx, Immediate(1)); | 2119 __ sub(edx, Immediate(Smi::FromInt(1))); |
| 2095 __ j(carry, &push_frame); | 2120 __ j(carry, &push_frame); |
| 2096 __ push(ecx); | 2121 __ push(ecx); |
| 2097 __ jmp(&push_argument_holes); | 2122 __ jmp(&push_argument_holes); |
| 2098 | 2123 |
| 2099 // Enter a new JavaScript frame, and initialize its slots as they were when | 2124 // Enter a new JavaScript frame, and initialize its slots as they were when |
| 2100 // the generator was suspended. | 2125 // the generator was suspended. |
| 2101 Label resume_frame; | 2126 Label resume_frame; |
| 2102 __ bind(&push_frame); | 2127 __ bind(&push_frame); |
| 2103 __ call(&resume_frame); | 2128 __ call(&resume_frame); |
| 2104 __ jmp(&done); | 2129 __ jmp(&done); |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2186 // Only the value field needs a write barrier, as the other values are in the | 2211 // Only the value field needs a write barrier, as the other values are in the |
| 2187 // root set. | 2212 // root set. |
| 2188 __ RecordWriteField(eax, JSGeneratorObject::kResultValuePropertyOffset, | 2213 __ RecordWriteField(eax, JSGeneratorObject::kResultValuePropertyOffset, |
| 2189 ecx, edx, kDontSaveFPRegs); | 2214 ecx, edx, kDontSaveFPRegs); |
| 2190 } | 2215 } |
| 2191 | 2216 |
| 2192 | 2217 |
| 2193 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) { | 2218 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) { |
| 2194 SetSourcePosition(prop->position()); | 2219 SetSourcePosition(prop->position()); |
| 2195 Literal* key = prop->key()->AsLiteral(); | 2220 Literal* key = prop->key()->AsLiteral(); |
| 2196 ASSERT(!key->handle()->IsSmi()); | 2221 ASSERT(!key->value()->IsSmi()); |
| 2197 __ mov(ecx, Immediate(key->handle())); | 2222 __ mov(ecx, Immediate(key->value())); |
| 2198 Handle<Code> ic = isolate()->builtins()->LoadIC_Initialize(); | 2223 Handle<Code> ic = isolate()->builtins()->LoadIC_Initialize(); |
| 2199 CallIC(ic, RelocInfo::CODE_TARGET, prop->PropertyFeedbackId()); | 2224 CallIC(ic, RelocInfo::CODE_TARGET, prop->PropertyFeedbackId()); |
| 2200 } | 2225 } |
| 2201 | 2226 |
| 2202 | 2227 |
| 2203 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) { | 2228 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) { |
| 2204 SetSourcePosition(prop->position()); | 2229 SetSourcePosition(prop->position()); |
| 2205 Handle<Code> ic = isolate()->builtins()->KeyedLoadIC_Initialize(); | 2230 Handle<Code> ic = isolate()->builtins()->KeyedLoadIC_Initialize(); |
| 2206 CallIC(ic, RelocInfo::CODE_TARGET, prop->PropertyFeedbackId()); | 2231 CallIC(ic, RelocInfo::CODE_TARGET, prop->PropertyFeedbackId()); |
| 2207 } | 2232 } |
| (...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2341 Variable* var = expr->AsVariableProxy()->var(); | 2366 Variable* var = expr->AsVariableProxy()->var(); |
| 2342 EffectContext context(this); | 2367 EffectContext context(this); |
| 2343 EmitVariableAssignment(var, Token::ASSIGN); | 2368 EmitVariableAssignment(var, Token::ASSIGN); |
| 2344 break; | 2369 break; |
| 2345 } | 2370 } |
| 2346 case NAMED_PROPERTY: { | 2371 case NAMED_PROPERTY: { |
| 2347 __ push(eax); // Preserve value. | 2372 __ push(eax); // Preserve value. |
| 2348 VisitForAccumulatorValue(prop->obj()); | 2373 VisitForAccumulatorValue(prop->obj()); |
| 2349 __ mov(edx, eax); | 2374 __ mov(edx, eax); |
| 2350 __ pop(eax); // Restore value. | 2375 __ pop(eax); // Restore value. |
| 2351 __ mov(ecx, prop->key()->AsLiteral()->handle()); | 2376 __ mov(ecx, prop->key()->AsLiteral()->value()); |
| 2352 Handle<Code> ic = is_classic_mode() | 2377 Handle<Code> ic = is_classic_mode() |
| 2353 ? isolate()->builtins()->StoreIC_Initialize() | 2378 ? isolate()->builtins()->StoreIC_Initialize() |
| 2354 : isolate()->builtins()->StoreIC_Initialize_Strict(); | 2379 : isolate()->builtins()->StoreIC_Initialize_Strict(); |
| 2355 CallIC(ic); | 2380 CallIC(ic); |
| 2356 break; | 2381 break; |
| 2357 } | 2382 } |
| 2358 case KEYED_PROPERTY: { | 2383 case KEYED_PROPERTY: { |
| 2359 __ push(eax); // Preserve value. | 2384 __ push(eax); // Preserve value. |
| 2360 VisitForStackValue(prop->obj()); | 2385 VisitForStackValue(prop->obj()); |
| 2361 VisitForAccumulatorValue(prop->key()); | 2386 VisitForAccumulatorValue(prop->key()); |
| (...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2468 // Assignment to a property, using a named store IC. | 2493 // Assignment to a property, using a named store IC. |
| 2469 // eax : value | 2494 // eax : value |
| 2470 // esp[0] : receiver | 2495 // esp[0] : receiver |
| 2471 | 2496 |
| 2472 Property* prop = expr->target()->AsProperty(); | 2497 Property* prop = expr->target()->AsProperty(); |
| 2473 ASSERT(prop != NULL); | 2498 ASSERT(prop != NULL); |
| 2474 ASSERT(prop->key()->AsLiteral() != NULL); | 2499 ASSERT(prop->key()->AsLiteral() != NULL); |
| 2475 | 2500 |
| 2476 // Record source code position before IC call. | 2501 // Record source code position before IC call. |
| 2477 SetSourcePosition(expr->position()); | 2502 SetSourcePosition(expr->position()); |
| 2478 __ mov(ecx, prop->key()->AsLiteral()->handle()); | 2503 __ mov(ecx, prop->key()->AsLiteral()->value()); |
| 2479 __ pop(edx); | 2504 __ pop(edx); |
| 2480 Handle<Code> ic = is_classic_mode() | 2505 Handle<Code> ic = is_classic_mode() |
| 2481 ? isolate()->builtins()->StoreIC_Initialize() | 2506 ? isolate()->builtins()->StoreIC_Initialize() |
| 2482 : isolate()->builtins()->StoreIC_Initialize_Strict(); | 2507 : isolate()->builtins()->StoreIC_Initialize_Strict(); |
| 2483 CallIC(ic, RelocInfo::CODE_TARGET, expr->AssignmentFeedbackId()); | 2508 CallIC(ic, RelocInfo::CODE_TARGET, expr->AssignmentFeedbackId()); |
| 2484 | 2509 |
| 2485 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); | 2510 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); |
| 2486 context()->Plug(eax); | 2511 context()->Plug(eax); |
| 2487 } | 2512 } |
| 2488 | 2513 |
| (...skipping 244 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2733 // LoadContextSlot. That object could be the hole if the receiver is | 2758 // LoadContextSlot. That object could be the hole if the receiver is |
| 2734 // implicitly the global object. | 2759 // implicitly the global object. |
| 2735 EmitCallWithStub(expr, RECEIVER_MIGHT_BE_IMPLICIT); | 2760 EmitCallWithStub(expr, RECEIVER_MIGHT_BE_IMPLICIT); |
| 2736 | 2761 |
| 2737 } else if (property != NULL) { | 2762 } else if (property != NULL) { |
| 2738 { PreservePositionScope scope(masm()->positions_recorder()); | 2763 { PreservePositionScope scope(masm()->positions_recorder()); |
| 2739 VisitForStackValue(property->obj()); | 2764 VisitForStackValue(property->obj()); |
| 2740 } | 2765 } |
| 2741 if (property->key()->IsPropertyName()) { | 2766 if (property->key()->IsPropertyName()) { |
| 2742 EmitCallWithIC(expr, | 2767 EmitCallWithIC(expr, |
| 2743 property->key()->AsLiteral()->handle(), | 2768 property->key()->AsLiteral()->value(), |
| 2744 RelocInfo::CODE_TARGET); | 2769 RelocInfo::CODE_TARGET); |
| 2745 } else { | 2770 } else { |
| 2746 EmitKeyedCallWithIC(expr, property->key()); | 2771 EmitKeyedCallWithIC(expr, property->key()); |
| 2747 } | 2772 } |
| 2748 | 2773 |
| 2749 } else { | 2774 } else { |
| 2750 // Call to an arbitrary expression not handled specially above. | 2775 // Call to an arbitrary expression not handled specially above. |
| 2751 { PreservePositionScope scope(masm()->positions_recorder()); | 2776 { PreservePositionScope scope(masm()->positions_recorder()); |
| 2752 VisitForStackValue(callee); | 2777 VisitForStackValue(callee); |
| 2753 } | 2778 } |
| (...skipping 597 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3351 | 3376 |
| 3352 __ bind(&done); | 3377 __ bind(&done); |
| 3353 context()->Plug(eax); | 3378 context()->Plug(eax); |
| 3354 } | 3379 } |
| 3355 | 3380 |
| 3356 | 3381 |
| 3357 void FullCodeGenerator::EmitDateField(CallRuntime* expr) { | 3382 void FullCodeGenerator::EmitDateField(CallRuntime* expr) { |
| 3358 ZoneList<Expression*>* args = expr->arguments(); | 3383 ZoneList<Expression*>* args = expr->arguments(); |
| 3359 ASSERT(args->length() == 2); | 3384 ASSERT(args->length() == 2); |
| 3360 ASSERT_NE(NULL, args->at(1)->AsLiteral()); | 3385 ASSERT_NE(NULL, args->at(1)->AsLiteral()); |
| 3361 Smi* index = Smi::cast(*(args->at(1)->AsLiteral()->handle())); | 3386 Smi* index = Smi::cast(*(args->at(1)->AsLiteral()->value())); |
| 3362 | 3387 |
| 3363 VisitForAccumulatorValue(args->at(0)); // Load the object. | 3388 VisitForAccumulatorValue(args->at(0)); // Load the object. |
| 3364 | 3389 |
| 3365 Label runtime, done, not_date_object; | 3390 Label runtime, done, not_date_object; |
| 3366 Register object = eax; | 3391 Register object = eax; |
| 3367 Register result = eax; | 3392 Register result = eax; |
| 3368 Register scratch = ecx; | 3393 Register scratch = ecx; |
| 3369 | 3394 |
| 3370 __ JumpIfSmi(object, ¬_date_object); | 3395 __ JumpIfSmi(object, ¬_date_object); |
| 3371 __ CmpObjectType(object, JS_DATE_TYPE, scratch); | 3396 __ CmpObjectType(object, JS_DATE_TYPE, scratch); |
| (...skipping 408 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3780 __ CallStub(&stub); | 3805 __ CallStub(&stub); |
| 3781 context()->Plug(eax); | 3806 context()->Plug(eax); |
| 3782 } | 3807 } |
| 3783 | 3808 |
| 3784 | 3809 |
| 3785 void FullCodeGenerator::EmitGetFromCache(CallRuntime* expr) { | 3810 void FullCodeGenerator::EmitGetFromCache(CallRuntime* expr) { |
| 3786 ZoneList<Expression*>* args = expr->arguments(); | 3811 ZoneList<Expression*>* args = expr->arguments(); |
| 3787 ASSERT_EQ(2, args->length()); | 3812 ASSERT_EQ(2, args->length()); |
| 3788 | 3813 |
| 3789 ASSERT_NE(NULL, args->at(0)->AsLiteral()); | 3814 ASSERT_NE(NULL, args->at(0)->AsLiteral()); |
| 3790 int cache_id = Smi::cast(*(args->at(0)->AsLiteral()->handle()))->value(); | 3815 int cache_id = Smi::cast(*(args->at(0)->AsLiteral()->value()))->value(); |
| 3791 | 3816 |
| 3792 Handle<FixedArray> jsfunction_result_caches( | 3817 Handle<FixedArray> jsfunction_result_caches( |
| 3793 isolate()->native_context()->jsfunction_result_caches()); | 3818 isolate()->native_context()->jsfunction_result_caches()); |
| 3794 if (jsfunction_result_caches->length() <= cache_id) { | 3819 if (jsfunction_result_caches->length() <= cache_id) { |
| 3795 __ Abort("Attempt to use undefined cache."); | 3820 __ Abort("Attempt to use undefined cache."); |
| 3796 __ mov(eax, isolate()->factory()->undefined_value()); | 3821 __ mov(eax, isolate()->factory()->undefined_value()); |
| 3797 context()->Plug(eax); | 3822 context()->Plug(eax); |
| 3798 return; | 3823 return; |
| 3799 } | 3824 } |
| 3800 | 3825 |
| (...skipping 691 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4492 } | 4517 } |
| 4493 } else { | 4518 } else { |
| 4494 // Perform the assignment as if via '='. | 4519 // Perform the assignment as if via '='. |
| 4495 EmitVariableAssignment(expr->expression()->AsVariableProxy()->var(), | 4520 EmitVariableAssignment(expr->expression()->AsVariableProxy()->var(), |
| 4496 Token::ASSIGN); | 4521 Token::ASSIGN); |
| 4497 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); | 4522 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); |
| 4498 context()->Plug(eax); | 4523 context()->Plug(eax); |
| 4499 } | 4524 } |
| 4500 break; | 4525 break; |
| 4501 case NAMED_PROPERTY: { | 4526 case NAMED_PROPERTY: { |
| 4502 __ mov(ecx, prop->key()->AsLiteral()->handle()); | 4527 __ mov(ecx, prop->key()->AsLiteral()->value()); |
| 4503 __ pop(edx); | 4528 __ pop(edx); |
| 4504 Handle<Code> ic = is_classic_mode() | 4529 Handle<Code> ic = is_classic_mode() |
| 4505 ? isolate()->builtins()->StoreIC_Initialize() | 4530 ? isolate()->builtins()->StoreIC_Initialize() |
| 4506 : isolate()->builtins()->StoreIC_Initialize_Strict(); | 4531 : isolate()->builtins()->StoreIC_Initialize_Strict(); |
| 4507 CallIC(ic, RelocInfo::CODE_TARGET, expr->CountStoreFeedbackId()); | 4532 CallIC(ic, RelocInfo::CODE_TARGET, expr->CountStoreFeedbackId()); |
| 4508 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); | 4533 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); |
| 4509 if (expr->is_postfix()) { | 4534 if (expr->is_postfix()) { |
| 4510 if (!context()->IsEffect()) { | 4535 if (!context()->IsEffect()) { |
| 4511 context()->PlugTOS(); | 4536 context()->PlugTOS(); |
| 4512 } | 4537 } |
| (...skipping 380 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4893 *stack_depth = 0; | 4918 *stack_depth = 0; |
| 4894 *context_length = 0; | 4919 *context_length = 0; |
| 4895 return previous_; | 4920 return previous_; |
| 4896 } | 4921 } |
| 4897 | 4922 |
| 4898 #undef __ | 4923 #undef __ |
| 4899 | 4924 |
| 4900 } } // namespace v8::internal | 4925 } } // namespace v8::internal |
| 4901 | 4926 |
| 4902 #endif // V8_TARGET_ARCH_IA32 | 4927 #endif // V8_TARGET_ARCH_IA32 |
| OLD | NEW |