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 206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
217 bool function_in_register = true; | 217 bool function_in_register = true; |
218 | 218 |
219 // Possibly allocate a local context. | 219 // Possibly allocate a local context. |
220 int heap_slots = info->scope()->num_heap_slots() - Context::MIN_CONTEXT_SLOTS; | 220 int heap_slots = info->scope()->num_heap_slots() - Context::MIN_CONTEXT_SLOTS; |
221 if (heap_slots > 0) { | 221 if (heap_slots > 0) { |
222 Comment cmnt(masm_, "[ Allocate context"); | 222 Comment cmnt(masm_, "[ Allocate context"); |
223 // Argument to NewContext is the function, which is still in rdi. | 223 // Argument to NewContext is the function, which is still in rdi. |
224 if (FLAG_harmony_scoping && info->scope()->is_global_scope()) { | 224 if (FLAG_harmony_scoping && info->scope()->is_global_scope()) { |
225 __ Push(rdi); | 225 __ Push(rdi); |
226 __ Push(info->scope()->GetScopeInfo()); | 226 __ Push(info->scope()->GetScopeInfo()); |
227 __ CallRuntime(Runtime::kNewGlobalContext, 2); | 227 __ CallRuntime(Runtime::kHiddenNewGlobalContext, 2); |
228 } else if (heap_slots <= FastNewContextStub::kMaximumSlots) { | 228 } else if (heap_slots <= FastNewContextStub::kMaximumSlots) { |
229 FastNewContextStub stub(heap_slots); | 229 FastNewContextStub stub(heap_slots); |
230 __ CallStub(&stub); | 230 __ CallStub(&stub); |
231 } else { | 231 } else { |
232 __ Push(rdi); | 232 __ Push(rdi); |
233 __ CallRuntime(Runtime::kNewFunctionContext, 1); | 233 __ CallRuntime(Runtime::kHiddenNewFunctionContext, 1); |
234 } | 234 } |
235 function_in_register = false; | 235 function_in_register = false; |
236 // Context is returned in rax. It replaces the context passed to us. | 236 // Context is returned in rax. It replaces the context passed to us. |
237 // It's saved in the stack and kept live in rsi. | 237 // It's saved in the stack and kept live in rsi. |
238 __ movp(rsi, rax); | 238 __ movp(rsi, rax); |
239 __ movp(Operand(rbp, StandardFrameConstants::kContextOffset), rax); | 239 __ movp(Operand(rbp, StandardFrameConstants::kContextOffset), rax); |
240 | 240 |
241 // Copy any necessary parameters into the context. | 241 // Copy any necessary parameters into the context. |
242 int num_parameters = info->scope()->num_parameters(); | 242 int num_parameters = info->scope()->num_parameters(); |
243 for (int i = 0; i < num_parameters; i++) { | 243 for (int i = 0; i < num_parameters; i++) { |
(...skipping 587 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
831 __ Push(Smi::FromInt(attr)); | 831 __ Push(Smi::FromInt(attr)); |
832 // Push initial value, if any. | 832 // Push initial value, if any. |
833 // Note: For variables we must not push an initial value (such as | 833 // Note: For variables we must not push an initial value (such as |
834 // 'undefined') because we may have a (legal) redeclaration and we | 834 // 'undefined') because we may have a (legal) redeclaration and we |
835 // must not destroy the current value. | 835 // must not destroy the current value. |
836 if (hole_init) { | 836 if (hole_init) { |
837 __ PushRoot(Heap::kTheHoleValueRootIndex); | 837 __ PushRoot(Heap::kTheHoleValueRootIndex); |
838 } else { | 838 } else { |
839 __ Push(Smi::FromInt(0)); // Indicates no initial value. | 839 __ Push(Smi::FromInt(0)); // Indicates no initial value. |
840 } | 840 } |
841 __ CallRuntime(Runtime::kDeclareContextSlot, 4); | 841 __ CallRuntime(Runtime::kHiddenDeclareContextSlot, 4); |
842 break; | 842 break; |
843 } | 843 } |
844 } | 844 } |
845 } | 845 } |
846 | 846 |
847 | 847 |
848 void FullCodeGenerator::VisitFunctionDeclaration( | 848 void FullCodeGenerator::VisitFunctionDeclaration( |
849 FunctionDeclaration* declaration) { | 849 FunctionDeclaration* declaration) { |
850 VariableProxy* proxy = declaration->proxy(); | 850 VariableProxy* proxy = declaration->proxy(); |
851 Variable* variable = proxy->var(); | 851 Variable* variable = proxy->var(); |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
885 PrepareForBailoutForId(proxy->id(), NO_REGISTERS); | 885 PrepareForBailoutForId(proxy->id(), NO_REGISTERS); |
886 break; | 886 break; |
887 } | 887 } |
888 | 888 |
889 case Variable::LOOKUP: { | 889 case Variable::LOOKUP: { |
890 Comment cmnt(masm_, "[ FunctionDeclaration"); | 890 Comment cmnt(masm_, "[ FunctionDeclaration"); |
891 __ Push(rsi); | 891 __ Push(rsi); |
892 __ Push(variable->name()); | 892 __ Push(variable->name()); |
893 __ Push(Smi::FromInt(NONE)); | 893 __ Push(Smi::FromInt(NONE)); |
894 VisitForStackValue(declaration->fun()); | 894 VisitForStackValue(declaration->fun()); |
895 __ CallRuntime(Runtime::kDeclareContextSlot, 4); | 895 __ CallRuntime(Runtime::kHiddenDeclareContextSlot, 4); |
896 break; | 896 break; |
897 } | 897 } |
898 } | 898 } |
899 } | 899 } |
900 | 900 |
901 | 901 |
902 void FullCodeGenerator::VisitModuleDeclaration(ModuleDeclaration* declaration) { | 902 void FullCodeGenerator::VisitModuleDeclaration(ModuleDeclaration* declaration) { |
903 Variable* variable = declaration->proxy()->var(); | 903 Variable* variable = declaration->proxy()->var(); |
904 ASSERT(variable->location() == Variable::CONTEXT); | 904 ASSERT(variable->location() == Variable::CONTEXT); |
905 ASSERT(variable->interface()->IsFrozen()); | 905 ASSERT(variable->interface()->IsFrozen()); |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
955 void FullCodeGenerator::VisitExportDeclaration(ExportDeclaration* declaration) { | 955 void FullCodeGenerator::VisitExportDeclaration(ExportDeclaration* declaration) { |
956 // TODO(rossberg) | 956 // TODO(rossberg) |
957 } | 957 } |
958 | 958 |
959 | 959 |
960 void FullCodeGenerator::DeclareGlobals(Handle<FixedArray> pairs) { | 960 void FullCodeGenerator::DeclareGlobals(Handle<FixedArray> pairs) { |
961 // Call the runtime to declare the globals. | 961 // Call the runtime to declare the globals. |
962 __ Push(rsi); // The context is the first argument. | 962 __ Push(rsi); // The context is the first argument. |
963 __ Push(pairs); | 963 __ Push(pairs); |
964 __ Push(Smi::FromInt(DeclareGlobalsFlags())); | 964 __ Push(Smi::FromInt(DeclareGlobalsFlags())); |
965 __ CallRuntime(Runtime::kDeclareGlobals, 3); | 965 __ CallRuntime(Runtime::kHiddenDeclareGlobals, 3); |
966 // Return value is ignored. | 966 // Return value is ignored. |
967 } | 967 } |
968 | 968 |
969 | 969 |
970 void FullCodeGenerator::DeclareModules(Handle<FixedArray> descriptions) { | 970 void FullCodeGenerator::DeclareModules(Handle<FixedArray> descriptions) { |
971 // Call the runtime to declare the modules. | 971 // Call the runtime to declare the modules. |
972 __ Push(descriptions); | 972 __ Push(descriptions); |
973 __ CallRuntime(Runtime::kDeclareModules, 1); | 973 __ CallRuntime(Runtime::kHiddenDeclareModules, 1); |
974 // Return value is ignored. | 974 // Return value is ignored. |
975 } | 975 } |
976 | 976 |
977 | 977 |
978 void FullCodeGenerator::VisitSwitchStatement(SwitchStatement* stmt) { | 978 void FullCodeGenerator::VisitSwitchStatement(SwitchStatement* stmt) { |
979 Comment cmnt(masm_, "[ SwitchStatement"); | 979 Comment cmnt(masm_, "[ SwitchStatement"); |
980 Breakable nested_statement(this, stmt); | 980 Breakable nested_statement(this, stmt); |
981 SetStatementPosition(stmt); | 981 SetStatementPosition(stmt); |
982 | 982 |
983 // Keep the switch value on the stack until a case matches. | 983 // Keep the switch value on the stack until a case matches. |
(...skipping 342 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1326 info->num_literals() == 0) { | 1326 info->num_literals() == 0) { |
1327 FastNewClosureStub stub(info->strict_mode(), info->is_generator()); | 1327 FastNewClosureStub stub(info->strict_mode(), info->is_generator()); |
1328 __ Move(rbx, info); | 1328 __ Move(rbx, info); |
1329 __ CallStub(&stub); | 1329 __ CallStub(&stub); |
1330 } else { | 1330 } else { |
1331 __ Push(rsi); | 1331 __ Push(rsi); |
1332 __ Push(info); | 1332 __ Push(info); |
1333 __ Push(pretenure | 1333 __ Push(pretenure |
1334 ? isolate()->factory()->true_value() | 1334 ? isolate()->factory()->true_value() |
1335 : isolate()->factory()->false_value()); | 1335 : isolate()->factory()->false_value()); |
1336 __ CallRuntime(Runtime::kNewClosure, 3); | 1336 __ CallRuntime(Runtime::kHiddenNewClosure, 3); |
1337 } | 1337 } |
1338 context()->Plug(rax); | 1338 context()->Plug(rax); |
1339 } | 1339 } |
1340 | 1340 |
1341 | 1341 |
1342 void FullCodeGenerator::VisitVariableProxy(VariableProxy* expr) { | 1342 void FullCodeGenerator::VisitVariableProxy(VariableProxy* expr) { |
1343 Comment cmnt(masm_, "[ VariableProxy"); | 1343 Comment cmnt(masm_, "[ VariableProxy"); |
1344 EmitVariableLoad(expr); | 1344 EmitVariableLoad(expr); |
1345 } | 1345 } |
1346 | 1346 |
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1451 Variable* local = var->local_if_not_shadowed(); | 1451 Variable* local = var->local_if_not_shadowed(); |
1452 __ movp(rax, ContextSlotOperandCheckExtensions(local, slow)); | 1452 __ movp(rax, ContextSlotOperandCheckExtensions(local, slow)); |
1453 if (local->mode() == LET || local->mode() == CONST || | 1453 if (local->mode() == LET || local->mode() == CONST || |
1454 local->mode() == CONST_LEGACY) { | 1454 local->mode() == CONST_LEGACY) { |
1455 __ CompareRoot(rax, Heap::kTheHoleValueRootIndex); | 1455 __ CompareRoot(rax, Heap::kTheHoleValueRootIndex); |
1456 __ j(not_equal, done); | 1456 __ j(not_equal, done); |
1457 if (local->mode() == CONST_LEGACY) { | 1457 if (local->mode() == CONST_LEGACY) { |
1458 __ LoadRoot(rax, Heap::kUndefinedValueRootIndex); | 1458 __ LoadRoot(rax, Heap::kUndefinedValueRootIndex); |
1459 } else { // LET || CONST | 1459 } else { // LET || CONST |
1460 __ Push(var->name()); | 1460 __ Push(var->name()); |
1461 __ CallRuntime(Runtime::kThrowReferenceError, 1); | 1461 __ CallRuntime(Runtime::kHiddenThrowReferenceError, 1); |
1462 } | 1462 } |
1463 } | 1463 } |
1464 __ jmp(done); | 1464 __ jmp(done); |
1465 } | 1465 } |
1466 } | 1466 } |
1467 | 1467 |
1468 | 1468 |
1469 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) { | 1469 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) { |
1470 // Record position before possible IC call. | 1470 // Record position before possible IC call. |
1471 SetSourcePosition(proxy->position()); | 1471 SetSourcePosition(proxy->position()); |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1528 if (!skip_init_check) { | 1528 if (!skip_init_check) { |
1529 // Let and const need a read barrier. | 1529 // Let and const need a read barrier. |
1530 Label done; | 1530 Label done; |
1531 GetVar(rax, var); | 1531 GetVar(rax, var); |
1532 __ CompareRoot(rax, Heap::kTheHoleValueRootIndex); | 1532 __ CompareRoot(rax, Heap::kTheHoleValueRootIndex); |
1533 __ j(not_equal, &done, Label::kNear); | 1533 __ j(not_equal, &done, Label::kNear); |
1534 if (var->mode() == LET || var->mode() == CONST) { | 1534 if (var->mode() == LET || var->mode() == CONST) { |
1535 // Throw a reference error when using an uninitialized let/const | 1535 // Throw a reference error when using an uninitialized let/const |
1536 // binding in harmony mode. | 1536 // binding in harmony mode. |
1537 __ Push(var->name()); | 1537 __ Push(var->name()); |
1538 __ CallRuntime(Runtime::kThrowReferenceError, 1); | 1538 __ CallRuntime(Runtime::kHiddenThrowReferenceError, 1); |
1539 } else { | 1539 } else { |
1540 // Uninitalized const bindings outside of harmony mode are unholed. | 1540 // Uninitalized const bindings outside of harmony mode are unholed. |
1541 ASSERT(var->mode() == CONST_LEGACY); | 1541 ASSERT(var->mode() == CONST_LEGACY); |
1542 __ LoadRoot(rax, Heap::kUndefinedValueRootIndex); | 1542 __ LoadRoot(rax, Heap::kUndefinedValueRootIndex); |
1543 } | 1543 } |
1544 __ bind(&done); | 1544 __ bind(&done); |
1545 context()->Plug(rax); | 1545 context()->Plug(rax); |
1546 break; | 1546 break; |
1547 } | 1547 } |
1548 } | 1548 } |
1549 context()->Plug(var); | 1549 context()->Plug(var); |
1550 break; | 1550 break; |
1551 } | 1551 } |
1552 | 1552 |
1553 case Variable::LOOKUP: { | 1553 case Variable::LOOKUP: { |
1554 Comment cmnt(masm_, "[ Lookup slot"); | 1554 Comment cmnt(masm_, "[ Lookup slot"); |
1555 Label done, slow; | 1555 Label done, slow; |
1556 // Generate code for loading from variables potentially shadowed | 1556 // Generate code for loading from variables potentially shadowed |
1557 // by eval-introduced variables. | 1557 // by eval-introduced variables. |
1558 EmitDynamicLookupFastCase(var, NOT_INSIDE_TYPEOF, &slow, &done); | 1558 EmitDynamicLookupFastCase(var, NOT_INSIDE_TYPEOF, &slow, &done); |
1559 __ bind(&slow); | 1559 __ bind(&slow); |
1560 __ Push(rsi); // Context. | 1560 __ Push(rsi); // Context. |
1561 __ Push(var->name()); | 1561 __ Push(var->name()); |
1562 __ CallRuntime(Runtime::kLoadContextSlot, 2); | 1562 __ CallRuntime(Runtime::kHiddenLoadContextSlot, 2); |
1563 __ bind(&done); | 1563 __ bind(&done); |
1564 context()->Plug(rax); | 1564 context()->Plug(rax); |
1565 break; | 1565 break; |
1566 } | 1566 } |
1567 } | 1567 } |
1568 } | 1568 } |
1569 | 1569 |
1570 | 1570 |
1571 void FullCodeGenerator::VisitRegExpLiteral(RegExpLiteral* expr) { | 1571 void FullCodeGenerator::VisitRegExpLiteral(RegExpLiteral* expr) { |
1572 Comment cmnt(masm_, "[ RegExpLiteral"); | 1572 Comment cmnt(masm_, "[ RegExpLiteral"); |
(...skipping 10 matching lines...) Expand all Loading... |
1583 __ movp(rbx, FieldOperand(rcx, literal_offset)); | 1583 __ movp(rbx, FieldOperand(rcx, literal_offset)); |
1584 __ CompareRoot(rbx, Heap::kUndefinedValueRootIndex); | 1584 __ CompareRoot(rbx, Heap::kUndefinedValueRootIndex); |
1585 __ j(not_equal, &materialized, Label::kNear); | 1585 __ j(not_equal, &materialized, Label::kNear); |
1586 | 1586 |
1587 // Create regexp literal using runtime function | 1587 // Create regexp literal using runtime function |
1588 // Result will be in rax. | 1588 // Result will be in rax. |
1589 __ Push(rcx); | 1589 __ Push(rcx); |
1590 __ Push(Smi::FromInt(expr->literal_index())); | 1590 __ Push(Smi::FromInt(expr->literal_index())); |
1591 __ Push(expr->pattern()); | 1591 __ Push(expr->pattern()); |
1592 __ Push(expr->flags()); | 1592 __ Push(expr->flags()); |
1593 __ CallRuntime(Runtime::kMaterializeRegExpLiteral, 4); | 1593 __ CallRuntime(Runtime::kHiddenMaterializeRegExpLiteral, 4); |
1594 __ movp(rbx, rax); | 1594 __ movp(rbx, rax); |
1595 | 1595 |
1596 __ bind(&materialized); | 1596 __ bind(&materialized); |
1597 int size = JSRegExp::kSize + JSRegExp::kInObjectFieldCount * kPointerSize; | 1597 int size = JSRegExp::kSize + JSRegExp::kInObjectFieldCount * kPointerSize; |
1598 Label allocated, runtime_allocate; | 1598 Label allocated, runtime_allocate; |
1599 __ Allocate(size, rax, rcx, rdx, &runtime_allocate, TAG_OBJECT); | 1599 __ Allocate(size, rax, rcx, rdx, &runtime_allocate, TAG_OBJECT); |
1600 __ jmp(&allocated); | 1600 __ jmp(&allocated); |
1601 | 1601 |
1602 __ bind(&runtime_allocate); | 1602 __ bind(&runtime_allocate); |
1603 __ Push(rbx); | 1603 __ Push(rbx); |
1604 __ Push(Smi::FromInt(size)); | 1604 __ Push(Smi::FromInt(size)); |
1605 __ CallRuntime(Runtime::kAllocateInNewSpace, 1); | 1605 __ CallRuntime(Runtime::kHiddenAllocateInNewSpace, 1); |
1606 __ Pop(rbx); | 1606 __ Pop(rbx); |
1607 | 1607 |
1608 __ bind(&allocated); | 1608 __ bind(&allocated); |
1609 // Copy the content into the newly allocated memory. | 1609 // Copy the content into the newly allocated memory. |
1610 // (Unroll copy loop once for better throughput). | 1610 // (Unroll copy loop once for better throughput). |
1611 for (int i = 0; i < size - kPointerSize; i += 2 * kPointerSize) { | 1611 for (int i = 0; i < size - kPointerSize; i += 2 * kPointerSize) { |
1612 __ movp(rdx, FieldOperand(rbx, i)); | 1612 __ movp(rdx, FieldOperand(rbx, i)); |
1613 __ movp(rcx, FieldOperand(rbx, i + kPointerSize)); | 1613 __ movp(rcx, FieldOperand(rbx, i + kPointerSize)); |
1614 __ movp(FieldOperand(rax, i), rdx); | 1614 __ movp(FieldOperand(rax, i), rdx); |
1615 __ movp(FieldOperand(rax, i + kPointerSize), rcx); | 1615 __ movp(FieldOperand(rax, i + kPointerSize), rcx); |
(...skipping 28 matching lines...) Expand all Loading... |
1644 : ObjectLiteral::kNoFlags; | 1644 : ObjectLiteral::kNoFlags; |
1645 int properties_count = constant_properties->length() / 2; | 1645 int properties_count = constant_properties->length() / 2; |
1646 if (expr->may_store_doubles() || expr->depth() > 1 || Serializer::enabled() || | 1646 if (expr->may_store_doubles() || expr->depth() > 1 || Serializer::enabled() || |
1647 flags != ObjectLiteral::kFastElements || | 1647 flags != ObjectLiteral::kFastElements || |
1648 properties_count > FastCloneShallowObjectStub::kMaximumClonedProperties) { | 1648 properties_count > FastCloneShallowObjectStub::kMaximumClonedProperties) { |
1649 __ movp(rdi, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset)); | 1649 __ movp(rdi, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset)); |
1650 __ Push(FieldOperand(rdi, JSFunction::kLiteralsOffset)); | 1650 __ Push(FieldOperand(rdi, JSFunction::kLiteralsOffset)); |
1651 __ Push(Smi::FromInt(expr->literal_index())); | 1651 __ Push(Smi::FromInt(expr->literal_index())); |
1652 __ Push(constant_properties); | 1652 __ Push(constant_properties); |
1653 __ Push(Smi::FromInt(flags)); | 1653 __ Push(Smi::FromInt(flags)); |
1654 __ CallRuntime(Runtime::kCreateObjectLiteral, 4); | 1654 __ CallRuntime(Runtime::kHiddenCreateObjectLiteral, 4); |
1655 } else { | 1655 } else { |
1656 __ movp(rdi, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset)); | 1656 __ movp(rdi, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset)); |
1657 __ movp(rax, FieldOperand(rdi, JSFunction::kLiteralsOffset)); | 1657 __ movp(rax, FieldOperand(rdi, JSFunction::kLiteralsOffset)); |
1658 __ Move(rbx, Smi::FromInt(expr->literal_index())); | 1658 __ Move(rbx, Smi::FromInt(expr->literal_index())); |
1659 __ Move(rcx, constant_properties); | 1659 __ Move(rcx, constant_properties); |
1660 __ Move(rdx, Smi::FromInt(flags)); | 1660 __ Move(rdx, Smi::FromInt(flags)); |
1661 FastCloneShallowObjectStub stub(properties_count); | 1661 FastCloneShallowObjectStub stub(properties_count); |
1662 __ CallStub(&stub); | 1662 __ CallStub(&stub); |
1663 } | 1663 } |
1664 | 1664 |
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1797 allocation_site_mode, | 1797 allocation_site_mode, |
1798 length); | 1798 length); |
1799 __ CallStub(&stub); | 1799 __ CallStub(&stub); |
1800 } else if (expr->depth() > 1 || Serializer::enabled() || | 1800 } else if (expr->depth() > 1 || Serializer::enabled() || |
1801 length > FastCloneShallowArrayStub::kMaximumClonedLength) { | 1801 length > FastCloneShallowArrayStub::kMaximumClonedLength) { |
1802 __ movp(rbx, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset)); | 1802 __ movp(rbx, Operand(rbp, JavaScriptFrameConstants::kFunctionOffset)); |
1803 __ Push(FieldOperand(rbx, JSFunction::kLiteralsOffset)); | 1803 __ Push(FieldOperand(rbx, JSFunction::kLiteralsOffset)); |
1804 __ Push(Smi::FromInt(expr->literal_index())); | 1804 __ Push(Smi::FromInt(expr->literal_index())); |
1805 __ Push(constant_elements); | 1805 __ Push(constant_elements); |
1806 __ Push(Smi::FromInt(flags)); | 1806 __ Push(Smi::FromInt(flags)); |
1807 __ CallRuntime(Runtime::kCreateArrayLiteral, 4); | 1807 __ CallRuntime(Runtime::kHiddenCreateArrayLiteral, 4); |
1808 } else { | 1808 } else { |
1809 ASSERT(IsFastSmiOrObjectElementsKind(constant_elements_kind) || | 1809 ASSERT(IsFastSmiOrObjectElementsKind(constant_elements_kind) || |
1810 FLAG_smi_only_arrays); | 1810 FLAG_smi_only_arrays); |
1811 FastCloneShallowArrayStub::Mode mode = | 1811 FastCloneShallowArrayStub::Mode mode = |
1812 FastCloneShallowArrayStub::CLONE_ANY_ELEMENTS; | 1812 FastCloneShallowArrayStub::CLONE_ANY_ELEMENTS; |
1813 | 1813 |
1814 // If the elements are already FAST_*_ELEMENTS, the boilerplate cannot | 1814 // If the elements are already FAST_*_ELEMENTS, the boilerplate cannot |
1815 // change, so it's possible to specialize the stub in advance. | 1815 // change, so it's possible to specialize the stub in advance. |
1816 if (has_constant_fast_elements) { | 1816 if (has_constant_fast_elements) { |
1817 mode = FastCloneShallowArrayStub::CLONE_ELEMENTS; | 1817 mode = FastCloneShallowArrayStub::CLONE_ELEMENTS; |
(...skipping 191 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2009 __ Move(FieldOperand(rax, JSGeneratorObject::kContinuationOffset), | 2009 __ Move(FieldOperand(rax, JSGeneratorObject::kContinuationOffset), |
2010 Smi::FromInt(continuation.pos())); | 2010 Smi::FromInt(continuation.pos())); |
2011 __ movp(FieldOperand(rax, JSGeneratorObject::kContextOffset), rsi); | 2011 __ movp(FieldOperand(rax, JSGeneratorObject::kContextOffset), rsi); |
2012 __ movp(rcx, rsi); | 2012 __ movp(rcx, rsi); |
2013 __ RecordWriteField(rax, JSGeneratorObject::kContextOffset, rcx, rdx, | 2013 __ RecordWriteField(rax, JSGeneratorObject::kContextOffset, rcx, rdx, |
2014 kDontSaveFPRegs); | 2014 kDontSaveFPRegs); |
2015 __ lea(rbx, Operand(rbp, StandardFrameConstants::kExpressionsOffset)); | 2015 __ lea(rbx, Operand(rbp, StandardFrameConstants::kExpressionsOffset)); |
2016 __ cmpp(rsp, rbx); | 2016 __ cmpp(rsp, rbx); |
2017 __ j(equal, &post_runtime); | 2017 __ j(equal, &post_runtime); |
2018 __ Push(rax); // generator object | 2018 __ Push(rax); // generator object |
2019 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); | 2019 __ CallRuntime(Runtime::kHiddenSuspendJSGeneratorObject, 1); |
2020 __ movp(context_register(), | 2020 __ movp(context_register(), |
2021 Operand(rbp, StandardFrameConstants::kContextOffset)); | 2021 Operand(rbp, StandardFrameConstants::kContextOffset)); |
2022 __ bind(&post_runtime); | 2022 __ bind(&post_runtime); |
2023 | 2023 |
2024 __ Pop(result_register()); | 2024 __ Pop(result_register()); |
2025 EmitReturnSequence(); | 2025 EmitReturnSequence(); |
2026 | 2026 |
2027 __ bind(&resume); | 2027 __ bind(&resume); |
2028 context()->Plug(result_register()); | 2028 context()->Plug(result_register()); |
2029 break; | 2029 break; |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2078 const int generator_object_depth = kPointerSize + handler_size; | 2078 const int generator_object_depth = kPointerSize + handler_size; |
2079 __ movp(rax, Operand(rsp, generator_object_depth)); | 2079 __ movp(rax, Operand(rsp, generator_object_depth)); |
2080 __ Push(rax); // g | 2080 __ Push(rax); // g |
2081 ASSERT(l_continuation.pos() > 0 && Smi::IsValid(l_continuation.pos())); | 2081 ASSERT(l_continuation.pos() > 0 && Smi::IsValid(l_continuation.pos())); |
2082 __ Move(FieldOperand(rax, JSGeneratorObject::kContinuationOffset), | 2082 __ Move(FieldOperand(rax, JSGeneratorObject::kContinuationOffset), |
2083 Smi::FromInt(l_continuation.pos())); | 2083 Smi::FromInt(l_continuation.pos())); |
2084 __ movp(FieldOperand(rax, JSGeneratorObject::kContextOffset), rsi); | 2084 __ movp(FieldOperand(rax, JSGeneratorObject::kContextOffset), rsi); |
2085 __ movp(rcx, rsi); | 2085 __ movp(rcx, rsi); |
2086 __ RecordWriteField(rax, JSGeneratorObject::kContextOffset, rcx, rdx, | 2086 __ RecordWriteField(rax, JSGeneratorObject::kContextOffset, rcx, rdx, |
2087 kDontSaveFPRegs); | 2087 kDontSaveFPRegs); |
2088 __ CallRuntime(Runtime::kSuspendJSGeneratorObject, 1); | 2088 __ CallRuntime(Runtime::kHiddenSuspendJSGeneratorObject, 1); |
2089 __ movp(context_register(), | 2089 __ movp(context_register(), |
2090 Operand(rbp, StandardFrameConstants::kContextOffset)); | 2090 Operand(rbp, StandardFrameConstants::kContextOffset)); |
2091 __ Pop(rax); // result | 2091 __ Pop(rax); // result |
2092 EmitReturnSequence(); | 2092 EmitReturnSequence(); |
2093 __ bind(&l_resume); // received in rax | 2093 __ bind(&l_resume); // received in rax |
2094 __ PopTryHandler(); | 2094 __ PopTryHandler(); |
2095 | 2095 |
2096 // receiver = iter; f = 'next'; arg = received; | 2096 // receiver = iter; f = 'next'; arg = received; |
2097 __ bind(&l_next); | 2097 __ bind(&l_next); |
2098 __ LoadRoot(rcx, Heap::knext_stringRootIndex); // "next" | 2098 __ LoadRoot(rcx, Heap::knext_stringRootIndex); // "next" |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2132 break; | 2132 break; |
2133 } | 2133 } |
2134 } | 2134 } |
2135 } | 2135 } |
2136 | 2136 |
2137 | 2137 |
2138 void FullCodeGenerator::EmitGeneratorResume(Expression *generator, | 2138 void FullCodeGenerator::EmitGeneratorResume(Expression *generator, |
2139 Expression *value, | 2139 Expression *value, |
2140 JSGeneratorObject::ResumeMode resume_mode) { | 2140 JSGeneratorObject::ResumeMode resume_mode) { |
2141 // The value stays in rax, and is ultimately read by the resumed generator, as | 2141 // The value stays in rax, and is ultimately read by the resumed generator, as |
2142 // if the CallRuntime(Runtime::kSuspendJSGeneratorObject) returned it. Or it | 2142 // if CallRuntime(Runtime::kHiddenSuspendJSGeneratorObject) returned it. Or it |
2143 // is read to throw the value when the resumed generator is already closed. | 2143 // is read to throw the value when the resumed generator is already closed. |
2144 // rbx will hold the generator object until the activation has been resumed. | 2144 // rbx will hold the generator object until the activation has been resumed. |
2145 VisitForStackValue(generator); | 2145 VisitForStackValue(generator); |
2146 VisitForAccumulatorValue(value); | 2146 VisitForAccumulatorValue(value); |
2147 __ Pop(rbx); | 2147 __ Pop(rbx); |
2148 | 2148 |
2149 // Check generator state. | 2149 // Check generator state. |
2150 Label wrong_state, closed_state, done; | 2150 Label wrong_state, closed_state, done; |
2151 STATIC_ASSERT(JSGeneratorObject::kGeneratorExecuting < 0); | 2151 STATIC_ASSERT(JSGeneratorObject::kGeneratorExecuting < 0); |
2152 STATIC_ASSERT(JSGeneratorObject::kGeneratorClosed == 0); | 2152 STATIC_ASSERT(JSGeneratorObject::kGeneratorClosed == 0); |
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2213 Label push_operand_holes, call_resume; | 2213 Label push_operand_holes, call_resume; |
2214 __ bind(&push_operand_holes); | 2214 __ bind(&push_operand_holes); |
2215 __ subp(rdx, Immediate(1)); | 2215 __ subp(rdx, Immediate(1)); |
2216 __ j(carry, &call_resume); | 2216 __ j(carry, &call_resume); |
2217 __ Push(rcx); | 2217 __ Push(rcx); |
2218 __ jmp(&push_operand_holes); | 2218 __ jmp(&push_operand_holes); |
2219 __ bind(&call_resume); | 2219 __ bind(&call_resume); |
2220 __ Push(rbx); | 2220 __ Push(rbx); |
2221 __ Push(result_register()); | 2221 __ Push(result_register()); |
2222 __ Push(Smi::FromInt(resume_mode)); | 2222 __ Push(Smi::FromInt(resume_mode)); |
2223 __ CallRuntime(Runtime::kResumeJSGeneratorObject, 3); | 2223 __ CallRuntime(Runtime::kHiddenResumeJSGeneratorObject, 3); |
2224 // Not reached: the runtime call returns elsewhere. | 2224 // Not reached: the runtime call returns elsewhere. |
2225 __ Abort(kGeneratorFailedToResume); | 2225 __ Abort(kGeneratorFailedToResume); |
2226 | 2226 |
2227 // Reach here when generator is closed. | 2227 // Reach here when generator is closed. |
2228 __ bind(&closed_state); | 2228 __ bind(&closed_state); |
2229 if (resume_mode == JSGeneratorObject::NEXT) { | 2229 if (resume_mode == JSGeneratorObject::NEXT) { |
2230 // Return completed iterator result when generator is closed. | 2230 // Return completed iterator result when generator is closed. |
2231 __ PushRoot(Heap::kUndefinedValueRootIndex); | 2231 __ PushRoot(Heap::kUndefinedValueRootIndex); |
2232 // Pop value from top-of-stack slot; box result into result register. | 2232 // Pop value from top-of-stack slot; box result into result register. |
2233 EmitCreateIteratorResult(true); | 2233 EmitCreateIteratorResult(true); |
2234 } else { | 2234 } else { |
2235 // Throw the provided value. | 2235 // Throw the provided value. |
2236 __ Push(rax); | 2236 __ Push(rax); |
2237 __ CallRuntime(Runtime::kThrow, 1); | 2237 __ CallRuntime(Runtime::kHiddenThrow, 1); |
2238 } | 2238 } |
2239 __ jmp(&done); | 2239 __ jmp(&done); |
2240 | 2240 |
2241 // Throw error if we attempt to operate on a running generator. | 2241 // Throw error if we attempt to operate on a running generator. |
2242 __ bind(&wrong_state); | 2242 __ bind(&wrong_state); |
2243 __ Push(rbx); | 2243 __ Push(rbx); |
2244 __ CallRuntime(Runtime::kThrowGeneratorStateError, 1); | 2244 __ CallRuntime(Runtime::kHiddenThrowGeneratorStateError, 1); |
2245 | 2245 |
2246 __ bind(&done); | 2246 __ bind(&done); |
2247 context()->Plug(result_register()); | 2247 context()->Plug(result_register()); |
2248 } | 2248 } |
2249 | 2249 |
2250 | 2250 |
2251 void FullCodeGenerator::EmitCreateIteratorResult(bool done) { | 2251 void FullCodeGenerator::EmitCreateIteratorResult(bool done) { |
2252 Label gc_required; | 2252 Label gc_required; |
2253 Label allocated; | 2253 Label allocated; |
2254 | 2254 |
2255 Handle<Map> map(isolate()->native_context()->generator_result_map()); | 2255 Handle<Map> map(isolate()->native_context()->generator_result_map()); |
2256 | 2256 |
2257 __ Allocate(map->instance_size(), rax, rcx, rdx, &gc_required, TAG_OBJECT); | 2257 __ Allocate(map->instance_size(), rax, rcx, rdx, &gc_required, TAG_OBJECT); |
2258 __ jmp(&allocated); | 2258 __ jmp(&allocated); |
2259 | 2259 |
2260 __ bind(&gc_required); | 2260 __ bind(&gc_required); |
2261 __ Push(Smi::FromInt(map->instance_size())); | 2261 __ Push(Smi::FromInt(map->instance_size())); |
2262 __ CallRuntime(Runtime::kAllocateInNewSpace, 1); | 2262 __ CallRuntime(Runtime::kHiddenAllocateInNewSpace, 1); |
2263 __ movp(context_register(), | 2263 __ movp(context_register(), |
2264 Operand(rbp, StandardFrameConstants::kContextOffset)); | 2264 Operand(rbp, StandardFrameConstants::kContextOffset)); |
2265 | 2265 |
2266 __ bind(&allocated); | 2266 __ bind(&allocated); |
2267 __ Move(rbx, map); | 2267 __ Move(rbx, map); |
2268 __ Pop(rcx); | 2268 __ Pop(rcx); |
2269 __ Move(rdx, isolate()->factory()->ToBoolean(done)); | 2269 __ Move(rdx, isolate()->factory()->ToBoolean(done)); |
2270 ASSERT_EQ(map->instance_size(), 5 * kPointerSize); | 2270 ASSERT_EQ(map->instance_size(), 5 * kPointerSize); |
2271 __ movp(FieldOperand(rax, HeapObject::kMapOffset), rbx); | 2271 __ movp(FieldOperand(rax, HeapObject::kMapOffset), rbx); |
2272 __ Move(FieldOperand(rax, JSObject::kPropertiesOffset), | 2272 __ Move(FieldOperand(rax, JSObject::kPropertiesOffset), |
(...skipping 158 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2431 } | 2431 } |
2432 } | 2432 } |
2433 | 2433 |
2434 | 2434 |
2435 void FullCodeGenerator::EmitCallStoreContextSlot( | 2435 void FullCodeGenerator::EmitCallStoreContextSlot( |
2436 Handle<String> name, StrictMode strict_mode) { | 2436 Handle<String> name, StrictMode strict_mode) { |
2437 __ Push(rax); // Value. | 2437 __ Push(rax); // Value. |
2438 __ Push(rsi); // Context. | 2438 __ Push(rsi); // Context. |
2439 __ Push(name); | 2439 __ Push(name); |
2440 __ Push(Smi::FromInt(strict_mode)); | 2440 __ Push(Smi::FromInt(strict_mode)); |
2441 __ CallRuntime(Runtime::kStoreContextSlot, 4); | 2441 __ CallRuntime(Runtime::kHiddenStoreContextSlot, 4); |
2442 } | 2442 } |
2443 | 2443 |
2444 | 2444 |
2445 void FullCodeGenerator::EmitVariableAssignment(Variable* var, | 2445 void FullCodeGenerator::EmitVariableAssignment(Variable* var, |
2446 Token::Value op) { | 2446 Token::Value op) { |
2447 if (var->IsUnallocated()) { | 2447 if (var->IsUnallocated()) { |
2448 // Global var, const, or let. | 2448 // Global var, const, or let. |
2449 __ Move(rcx, var->name()); | 2449 __ Move(rcx, var->name()); |
2450 __ movp(rdx, GlobalObjectOperand()); | 2450 __ movp(rdx, GlobalObjectOperand()); |
2451 CallStoreIC(); | 2451 CallStoreIC(); |
2452 | 2452 |
2453 } else if (op == Token::INIT_CONST_LEGACY) { | 2453 } else if (op == Token::INIT_CONST_LEGACY) { |
2454 // Const initializers need a write barrier. | 2454 // Const initializers need a write barrier. |
2455 ASSERT(!var->IsParameter()); // No const parameters. | 2455 ASSERT(!var->IsParameter()); // No const parameters. |
2456 if (var->IsLookupSlot()) { | 2456 if (var->IsLookupSlot()) { |
2457 __ Push(rax); | 2457 __ Push(rax); |
2458 __ Push(rsi); | 2458 __ Push(rsi); |
2459 __ Push(var->name()); | 2459 __ Push(var->name()); |
2460 __ CallRuntime(Runtime::kInitializeConstContextSlot, 3); | 2460 __ CallRuntime(Runtime::kHiddenInitializeConstContextSlot, 3); |
2461 } else { | 2461 } else { |
2462 ASSERT(var->IsStackLocal() || var->IsContextSlot()); | 2462 ASSERT(var->IsStackLocal() || var->IsContextSlot()); |
2463 Label skip; | 2463 Label skip; |
2464 MemOperand location = VarOperand(var, rcx); | 2464 MemOperand location = VarOperand(var, rcx); |
2465 __ movp(rdx, location); | 2465 __ movp(rdx, location); |
2466 __ CompareRoot(rdx, Heap::kTheHoleValueRootIndex); | 2466 __ CompareRoot(rdx, Heap::kTheHoleValueRootIndex); |
2467 __ j(not_equal, &skip); | 2467 __ j(not_equal, &skip); |
2468 EmitStoreToStackLocalOrContextSlot(var, location); | 2468 EmitStoreToStackLocalOrContextSlot(var, location); |
2469 __ bind(&skip); | 2469 __ bind(&skip); |
2470 } | 2470 } |
2471 | 2471 |
2472 } else if (var->mode() == LET && op != Token::INIT_LET) { | 2472 } else if (var->mode() == LET && op != Token::INIT_LET) { |
2473 // Non-initializing assignment to let variable needs a write barrier. | 2473 // Non-initializing assignment to let variable needs a write barrier. |
2474 if (var->IsLookupSlot()) { | 2474 if (var->IsLookupSlot()) { |
2475 EmitCallStoreContextSlot(var->name(), strict_mode()); | 2475 EmitCallStoreContextSlot(var->name(), strict_mode()); |
2476 } else { | 2476 } else { |
2477 ASSERT(var->IsStackAllocated() || var->IsContextSlot()); | 2477 ASSERT(var->IsStackAllocated() || var->IsContextSlot()); |
2478 Label assign; | 2478 Label assign; |
2479 MemOperand location = VarOperand(var, rcx); | 2479 MemOperand location = VarOperand(var, rcx); |
2480 __ movp(rdx, location); | 2480 __ movp(rdx, location); |
2481 __ CompareRoot(rdx, Heap::kTheHoleValueRootIndex); | 2481 __ CompareRoot(rdx, Heap::kTheHoleValueRootIndex); |
2482 __ j(not_equal, &assign, Label::kNear); | 2482 __ j(not_equal, &assign, Label::kNear); |
2483 __ Push(var->name()); | 2483 __ Push(var->name()); |
2484 __ CallRuntime(Runtime::kThrowReferenceError, 1); | 2484 __ CallRuntime(Runtime::kHiddenThrowReferenceError, 1); |
2485 __ bind(&assign); | 2485 __ bind(&assign); |
2486 EmitStoreToStackLocalOrContextSlot(var, location); | 2486 EmitStoreToStackLocalOrContextSlot(var, location); |
2487 } | 2487 } |
2488 | 2488 |
2489 } else if (!var->is_const_mode() || op == Token::INIT_CONST) { | 2489 } else if (!var->is_const_mode() || op == Token::INIT_CONST) { |
2490 // Assignment to var or initializing assignment to let/const | 2490 // Assignment to var or initializing assignment to let/const |
2491 // in harmony mode. | 2491 // in harmony mode. |
2492 if (var->IsLookupSlot()) { | 2492 if (var->IsLookupSlot()) { |
2493 EmitCallStoreContextSlot(var->name(), strict_mode()); | 2493 EmitCallStoreContextSlot(var->name(), strict_mode()); |
2494 } else { | 2494 } else { |
(...skipping 206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2701 StackArgumentsAccessor args(rbp, info_->scope()->num_parameters()); | 2701 StackArgumentsAccessor args(rbp, info_->scope()->num_parameters()); |
2702 __ Push(args.GetReceiverOperand()); | 2702 __ Push(args.GetReceiverOperand()); |
2703 | 2703 |
2704 // Push the language mode. | 2704 // Push the language mode. |
2705 __ Push(Smi::FromInt(strict_mode())); | 2705 __ Push(Smi::FromInt(strict_mode())); |
2706 | 2706 |
2707 // Push the start position of the scope the calls resides in. | 2707 // Push the start position of the scope the calls resides in. |
2708 __ Push(Smi::FromInt(scope()->start_position())); | 2708 __ Push(Smi::FromInt(scope()->start_position())); |
2709 | 2709 |
2710 // Do the runtime call. | 2710 // Do the runtime call. |
2711 __ CallRuntime(Runtime::kResolvePossiblyDirectEval, 5); | 2711 __ CallRuntime(Runtime::kHiddenResolvePossiblyDirectEval, 5); |
2712 } | 2712 } |
2713 | 2713 |
2714 | 2714 |
2715 void FullCodeGenerator::VisitCall(Call* expr) { | 2715 void FullCodeGenerator::VisitCall(Call* expr) { |
2716 #ifdef DEBUG | 2716 #ifdef DEBUG |
2717 // We want to verify that RecordJSReturnSite gets called on all paths | 2717 // We want to verify that RecordJSReturnSite gets called on all paths |
2718 // through this function. Avoid early returns. | 2718 // through this function. Avoid early returns. |
2719 expr->return_is_recorded_ = false; | 2719 expr->return_is_recorded_ = false; |
2720 #endif | 2720 #endif |
2721 | 2721 |
2722 Comment cmnt(masm_, "[ Call"); | 2722 Comment cmnt(masm_, "[ Call"); |
2723 Expression* callee = expr->expression(); | 2723 Expression* callee = expr->expression(); |
2724 Call::CallType call_type = expr->GetCallType(isolate()); | 2724 Call::CallType call_type = expr->GetCallType(isolate()); |
2725 | 2725 |
2726 if (call_type == Call::POSSIBLY_EVAL_CALL) { | 2726 if (call_type == Call::POSSIBLY_EVAL_CALL) { |
2727 // In a call to eval, we first call %ResolvePossiblyDirectEval to | 2727 // In a call to eval, we first call RuntimeHidden_ResolvePossiblyDirectEval |
2728 // resolve the function we need to call and the receiver of the call. | 2728 // to resolve the function we need to call and the receiver of the call. |
2729 // Then we call the resolved function using the given arguments. | 2729 // Then we call the resolved function using the given arguments. |
2730 ZoneList<Expression*>* args = expr->arguments(); | 2730 ZoneList<Expression*>* args = expr->arguments(); |
2731 int arg_count = args->length(); | 2731 int arg_count = args->length(); |
2732 { PreservePositionScope pos_scope(masm()->positions_recorder()); | 2732 { PreservePositionScope pos_scope(masm()->positions_recorder()); |
2733 VisitForStackValue(callee); | 2733 VisitForStackValue(callee); |
2734 __ PushRoot(Heap::kUndefinedValueRootIndex); // Reserved receiver slot. | 2734 __ PushRoot(Heap::kUndefinedValueRootIndex); // Reserved receiver slot. |
2735 | 2735 |
2736 // Push the arguments. | 2736 // Push the arguments. |
2737 for (int i = 0; i < arg_count; i++) { | 2737 for (int i = 0; i < arg_count; i++) { |
2738 VisitForStackValue(args->at(i)); | 2738 VisitForStackValue(args->at(i)); |
(...skipping 29 matching lines...) Expand all Loading... |
2768 { PreservePositionScope scope(masm()->positions_recorder()); | 2768 { PreservePositionScope scope(masm()->positions_recorder()); |
2769 // Generate code for loading from variables potentially shadowed by | 2769 // Generate code for loading from variables potentially shadowed by |
2770 // eval-introduced variables. | 2770 // eval-introduced variables. |
2771 EmitDynamicLookupFastCase(proxy->var(), NOT_INSIDE_TYPEOF, &slow, &done); | 2771 EmitDynamicLookupFastCase(proxy->var(), NOT_INSIDE_TYPEOF, &slow, &done); |
2772 } | 2772 } |
2773 __ bind(&slow); | 2773 __ bind(&slow); |
2774 // Call the runtime to find the function to call (returned in rax) and | 2774 // Call the runtime to find the function to call (returned in rax) and |
2775 // the object holding it (returned in rdx). | 2775 // the object holding it (returned in rdx). |
2776 __ Push(context_register()); | 2776 __ Push(context_register()); |
2777 __ Push(proxy->name()); | 2777 __ Push(proxy->name()); |
2778 __ CallRuntime(Runtime::kLoadContextSlot, 2); | 2778 __ CallRuntime(Runtime::kHiddenLoadContextSlot, 2); |
2779 __ Push(rax); // Function. | 2779 __ Push(rax); // Function. |
2780 __ Push(rdx); // Receiver. | 2780 __ Push(rdx); // Receiver. |
2781 | 2781 |
2782 // If fast case code has been generated, emit code to push the function | 2782 // If fast case code has been generated, emit code to push the function |
2783 // and receiver and have the slow path jump around this code. | 2783 // and receiver and have the slow path jump around this code. |
2784 if (done.is_linked()) { | 2784 if (done.is_linked()) { |
2785 Label call; | 2785 Label call; |
2786 __ jmp(&call, Label::kNear); | 2786 __ jmp(&call, Label::kNear); |
2787 __ bind(&done); | 2787 __ bind(&done); |
2788 // Push function. | 2788 // Push function. |
(...skipping 638 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3427 __ bind(&runtime); | 3427 __ bind(&runtime); |
3428 __ PrepareCallCFunction(2); | 3428 __ PrepareCallCFunction(2); |
3429 __ movp(arg_reg_1, object); | 3429 __ movp(arg_reg_1, object); |
3430 __ Move(arg_reg_2, index, Assembler::RelocInfoNone()); | 3430 __ Move(arg_reg_2, index, Assembler::RelocInfoNone()); |
3431 __ CallCFunction(ExternalReference::get_date_field_function(isolate()), 2); | 3431 __ CallCFunction(ExternalReference::get_date_field_function(isolate()), 2); |
3432 __ movp(rsi, Operand(rbp, StandardFrameConstants::kContextOffset)); | 3432 __ movp(rsi, Operand(rbp, StandardFrameConstants::kContextOffset)); |
3433 __ jmp(&done); | 3433 __ jmp(&done); |
3434 } | 3434 } |
3435 | 3435 |
3436 __ bind(¬_date_object); | 3436 __ bind(¬_date_object); |
3437 __ CallRuntime(Runtime::kThrowNotDateError, 0); | 3437 __ CallRuntime(Runtime::kHiddenThrowNotDateError, 0); |
3438 __ bind(&done); | 3438 __ bind(&done); |
3439 context()->Plug(rax); | 3439 context()->Plug(rax); |
3440 } | 3440 } |
3441 | 3441 |
3442 | 3442 |
3443 void FullCodeGenerator::EmitOneByteSeqStringSetChar(CallRuntime* expr) { | 3443 void FullCodeGenerator::EmitOneByteSeqStringSetChar(CallRuntime* expr) { |
3444 ZoneList<Expression*>* args = expr->arguments(); | 3444 ZoneList<Expression*>* args = expr->arguments(); |
3445 ASSERT_EQ(3, args->length()); | 3445 ASSERT_EQ(3, args->length()); |
3446 | 3446 |
3447 Register string = rax; | 3447 Register string = rax; |
(...skipping 777 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4225 } else if (var->IsStackAllocated() || var->IsContextSlot()) { | 4225 } else if (var->IsStackAllocated() || var->IsContextSlot()) { |
4226 // Result of deleting non-global variables is false. 'this' is | 4226 // Result of deleting non-global variables is false. 'this' is |
4227 // not really a variable, though we implement it as one. The | 4227 // not really a variable, though we implement it as one. The |
4228 // subexpression does not have side effects. | 4228 // subexpression does not have side effects. |
4229 context()->Plug(var->is_this()); | 4229 context()->Plug(var->is_this()); |
4230 } else { | 4230 } else { |
4231 // Non-global variable. Call the runtime to try to delete from the | 4231 // Non-global variable. Call the runtime to try to delete from the |
4232 // context where the variable was introduced. | 4232 // context where the variable was introduced. |
4233 __ Push(context_register()); | 4233 __ Push(context_register()); |
4234 __ Push(var->name()); | 4234 __ Push(var->name()); |
4235 __ CallRuntime(Runtime::kDeleteContextSlot, 2); | 4235 __ CallRuntime(Runtime::kHiddenDeleteContextSlot, 2); |
4236 context()->Plug(rax); | 4236 context()->Plug(rax); |
4237 } | 4237 } |
4238 } else { | 4238 } else { |
4239 // Result of deleting non-property, non-variable reference is true. | 4239 // Result of deleting non-property, non-variable reference is true. |
4240 // The subexpression may have side effects. | 4240 // The subexpression may have side effects. |
4241 VisitForEffect(expr->expression()); | 4241 VisitForEffect(expr->expression()); |
4242 context()->Plug(true); | 4242 context()->Plug(true); |
4243 } | 4243 } |
4244 break; | 4244 break; |
4245 } | 4245 } |
(...skipping 266 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4512 Comment cmnt(masm_, "[ Lookup slot"); | 4512 Comment cmnt(masm_, "[ Lookup slot"); |
4513 Label done, slow; | 4513 Label done, slow; |
4514 | 4514 |
4515 // Generate code for loading from variables potentially shadowed | 4515 // Generate code for loading from variables potentially shadowed |
4516 // by eval-introduced variables. | 4516 // by eval-introduced variables. |
4517 EmitDynamicLookupFastCase(proxy->var(), INSIDE_TYPEOF, &slow, &done); | 4517 EmitDynamicLookupFastCase(proxy->var(), INSIDE_TYPEOF, &slow, &done); |
4518 | 4518 |
4519 __ bind(&slow); | 4519 __ bind(&slow); |
4520 __ Push(rsi); | 4520 __ Push(rsi); |
4521 __ Push(proxy->name()); | 4521 __ Push(proxy->name()); |
4522 __ CallRuntime(Runtime::kLoadContextSlotNoReferenceError, 2); | 4522 __ CallRuntime(Runtime::kHiddenLoadContextSlotNoReferenceError, 2); |
4523 PrepareForBailout(expr, TOS_REG); | 4523 PrepareForBailout(expr, TOS_REG); |
4524 __ bind(&done); | 4524 __ bind(&done); |
4525 | 4525 |
4526 context()->Plug(rax); | 4526 context()->Plug(rax); |
4527 } else { | 4527 } else { |
4528 // This expression cannot throw a reference error at the top level. | 4528 // This expression cannot throw a reference error at the top level. |
4529 VisitInDuplicateContext(expr); | 4529 VisitInDuplicateContext(expr); |
4530 } | 4530 } |
4531 } | 4531 } |
4532 | 4532 |
(...skipping 399 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4932 ASSERT_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(), | 4932 ASSERT_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(), |
4933 Assembler::target_address_at(call_target_address, | 4933 Assembler::target_address_at(call_target_address, |
4934 unoptimized_code)); | 4934 unoptimized_code)); |
4935 return OSR_AFTER_STACK_CHECK; | 4935 return OSR_AFTER_STACK_CHECK; |
4936 } | 4936 } |
4937 | 4937 |
4938 | 4938 |
4939 } } // namespace v8::internal | 4939 } } // namespace v8::internal |
4940 | 4940 |
4941 #endif // V8_TARGET_ARCH_X64 | 4941 #endif // V8_TARGET_ARCH_X64 |
OLD | NEW |