OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/compiler/ast-graph-builder.h" | 5 #include "src/compiler/ast-graph-builder.h" |
6 | 6 |
7 #include "src/ast/compile-time-value.h" | 7 #include "src/ast/compile-time-value.h" |
8 #include "src/ast/scopes.h" | 8 #include "src/ast/scopes.h" |
9 #include "src/compilation-info.h" | 9 #include "src/compilation-info.h" |
10 #include "src/compiler.h" | 10 #include "src/compiler.h" |
(...skipping 1596 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1607 | 1607 |
1608 // Load the "prototype" from the constructor. | 1608 // Load the "prototype" from the constructor. |
1609 PrepareEagerCheckpoint(expr->CreateLiteralId()); | 1609 PrepareEagerCheckpoint(expr->CreateLiteralId()); |
1610 Handle<Name> name = isolate()->factory()->prototype_string(); | 1610 Handle<Name> name = isolate()->factory()->prototype_string(); |
1611 VectorSlotPair pair = CreateVectorSlotPair(expr->PrototypeSlot()); | 1611 VectorSlotPair pair = CreateVectorSlotPair(expr->PrototypeSlot()); |
1612 Node* prototype = BuildNamedLoad(literal, name, pair); | 1612 Node* prototype = BuildNamedLoad(literal, name, pair); |
1613 PrepareFrameState(prototype, expr->PrototypeId(), | 1613 PrepareFrameState(prototype, expr->PrototypeId(), |
1614 OutputFrameStateCombine::Push()); | 1614 OutputFrameStateCombine::Push()); |
1615 environment()->Push(prototype); | 1615 environment()->Push(prototype); |
1616 | 1616 |
| 1617 Node* needs_name; |
| 1618 bool check_name = !expr->has_name_static_property() && |
| 1619 !expr->constructor()->raw_name()->IsEmpty(); |
| 1620 if (check_name) { |
| 1621 needs_name = jsgraph()->TrueConstant(); |
| 1622 } |
| 1623 |
1617 // Create nodes to store method values into the literal. | 1624 // Create nodes to store method values into the literal. |
1618 for (int i = 0; i < expr->properties()->length(); i++) { | 1625 for (int i = 0; i < expr->properties()->length(); i++) { |
1619 ClassLiteral::Property* property = expr->properties()->at(i); | 1626 ClassLiteral::Property* property = expr->properties()->at(i); |
1620 environment()->Push(environment()->Peek(property->is_static() ? 1 : 0)); | 1627 environment()->Push(environment()->Peek(property->is_static() ? 1 : 0)); |
1621 | 1628 |
1622 VisitForValue(property->key()); | 1629 VisitForValue(property->key()); |
1623 Node* name = BuildToName(environment()->Pop(), expr->GetIdForProperty(i)); | 1630 Node* name = BuildToName(environment()->Pop(), expr->GetIdForProperty(i)); |
1624 environment()->Push(name); | 1631 environment()->Push(name); |
1625 | 1632 |
1626 // The static prototype property is read only. We handle the non computed | |
1627 // property name case in the parser. Since this is the only case where we | |
1628 // need to check for an own read only property we special case this so we do | |
1629 // not need to do this for every property. | |
1630 if (property->is_static() && property->is_computed_name()) { | 1633 if (property->is_static() && property->is_computed_name()) { |
| 1634 // Check for a static property called "name". The non computed property |
| 1635 // name is handled in the parser. |
| 1636 if (check_name) { |
| 1637 IfBuilder needs_name_is_false(this); |
| 1638 Node* needs_name_is_false_cond = |
| 1639 NewNode(javascript()->StrictEqual(CompareOperationHint::kAny), |
| 1640 needs_name, jsgraph()->FalseConstant()); |
| 1641 needs_name_is_false.If(needs_name_is_false_cond, BranchHint::kFalse); |
| 1642 needs_name_is_false.Then(); |
| 1643 needs_name_is_false.Else(); |
| 1644 { |
| 1645 IfBuilder has_name(this); |
| 1646 Node* name_string = |
| 1647 jsgraph()->Constant(isolate()->factory()->name_string()); |
| 1648 Node* has_name_cond = |
| 1649 NewNode(javascript()->StrictEqual(CompareOperationHint::kAny), |
| 1650 name, name_string); |
| 1651 has_name.If(has_name_cond, BranchHint::kFalse); |
| 1652 has_name.Then(); |
| 1653 needs_name = jsgraph()->FalseConstant(); |
| 1654 has_name.Else(); |
| 1655 has_name.End(); |
| 1656 } |
| 1657 needs_name_is_false.End(); |
| 1658 } |
| 1659 |
| 1660 // The static prototype property is read only. We handle the non computed |
| 1661 // property name case in the parser. Since this is the only case where we |
| 1662 // need to check for an own read only property we special case this so we |
| 1663 // do |
| 1664 // not need to do this for every property. |
1631 Node* check = BuildThrowIfStaticPrototype(environment()->Pop(), | 1665 Node* check = BuildThrowIfStaticPrototype(environment()->Pop(), |
1632 expr->GetIdForProperty(i)); | 1666 expr->GetIdForProperty(i)); |
1633 environment()->Push(check); | 1667 environment()->Push(check); |
1634 } | 1668 } |
1635 | 1669 |
1636 VisitForValue(property->value()); | 1670 VisitForValue(property->value()); |
1637 Node* value = environment()->Pop(); | 1671 Node* value = environment()->Pop(); |
1638 Node* key = environment()->Pop(); | 1672 Node* key = environment()->Pop(); |
1639 Node* receiver = environment()->Pop(); | 1673 Node* receiver = environment()->Pop(); |
1640 | 1674 |
(...skipping 24 matching lines...) Expand all Loading... |
1665 NewNode(op, receiver, key, value, attr); | 1699 NewNode(op, receiver, key, value, attr); |
1666 break; | 1700 break; |
1667 } | 1701 } |
1668 case ClassLiteral::Property::FIELD: { | 1702 case ClassLiteral::Property::FIELD: { |
1669 UNREACHABLE(); | 1703 UNREACHABLE(); |
1670 break; | 1704 break; |
1671 } | 1705 } |
1672 } | 1706 } |
1673 } | 1707 } |
1674 | 1708 |
| 1709 prototype = environment()->Pop(); |
| 1710 |
| 1711 // Install a "name" property if missing. |
| 1712 if (check_name) { |
| 1713 IfBuilder install_name(this); |
| 1714 Node* install_name_cond = |
| 1715 NewNode(javascript()->StrictEqual(CompareOperationHint::kAny), |
| 1716 needs_name, jsgraph()->TrueConstant()); |
| 1717 install_name.If(install_name_cond, BranchHint::kTrue); |
| 1718 install_name.Then(); |
| 1719 { |
| 1720 literal = environment()->Pop(); |
| 1721 const Operator* op = |
| 1722 javascript()->CallRuntime(Runtime::kInstallClassNameAccessor); |
| 1723 literal = NewNode(op, literal); |
| 1724 PrepareFrameState(literal, BailoutId::None()); |
| 1725 environment()->Push(literal); |
| 1726 } |
| 1727 install_name.Else(); |
| 1728 install_name.End(); |
| 1729 } |
| 1730 |
1675 // Set the constructor to have fast properties. | 1731 // Set the constructor to have fast properties. |
1676 prototype = environment()->Pop(); | |
1677 literal = environment()->Pop(); | 1732 literal = environment()->Pop(); |
1678 const Operator* op = javascript()->CallRuntime(Runtime::kToFastProperties); | 1733 const Operator* op = javascript()->CallRuntime(Runtime::kToFastProperties); |
1679 literal = NewNode(op, literal); | 1734 literal = NewNode(op, literal); |
1680 | 1735 |
1681 // Assign to class variable. | 1736 // Assign to class variable. |
1682 if (expr->class_variable_proxy() != nullptr) { | 1737 if (expr->class_variable_proxy() != nullptr) { |
1683 Variable* var = expr->class_variable_proxy()->var(); | 1738 Variable* var = expr->class_variable_proxy()->var(); |
1684 VectorSlotPair feedback = CreateVectorSlotPair( | 1739 VectorSlotPair feedback = CreateVectorSlotPair( |
1685 expr->NeedsProxySlot() ? expr->ProxySlot() | 1740 expr->NeedsProxySlot() ? expr->ProxySlot() |
1686 : FeedbackVectorSlot::Invalid()); | 1741 : FeedbackVectorSlot::Invalid()); |
(...skipping 2668 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4355 // Phi does not exist yet, introduce one. | 4410 // Phi does not exist yet, introduce one. |
4356 value = NewPhi(inputs, value, control); | 4411 value = NewPhi(inputs, value, control); |
4357 value->ReplaceInput(inputs - 1, other); | 4412 value->ReplaceInput(inputs - 1, other); |
4358 } | 4413 } |
4359 return value; | 4414 return value; |
4360 } | 4415 } |
4361 | 4416 |
4362 } // namespace compiler | 4417 } // namespace compiler |
4363 } // namespace internal | 4418 } // namespace internal |
4364 } // namespace v8 | 4419 } // namespace v8 |
OLD | NEW |