OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/parser.h" | 5 #include "vm/parser.h" |
6 | 6 |
7 #include "vm/bigint_operations.h" | 7 #include "vm/bigint_operations.h" |
8 #include "vm/class_finalizer.h" | 8 #include "vm/class_finalizer.h" |
9 #include "vm/compiler.h" | 9 #include "vm/compiler.h" |
10 #include "vm/compiler_stats.h" | 10 #include "vm/compiler_stats.h" |
(...skipping 1460 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1471 ResolveDynamicFunction(super_class, field_name)); | 1471 ResolveDynamicFunction(super_class, field_name)); |
1472 if (super_function.IsNull()) { | 1472 if (super_function.IsNull()) { |
1473 ErrorMsg(field_pos, "field or getter '%s' not found in superclass", | 1473 ErrorMsg(field_pos, "field or getter '%s' not found in superclass", |
1474 field_name.ToCString()); | 1474 field_name.ToCString()); |
1475 } | 1475 } |
1476 return CreateImplicitClosureNode(super_function, | 1476 return CreateImplicitClosureNode(super_function, |
1477 field_pos, | 1477 field_pos, |
1478 implicit_argument); | 1478 implicit_argument); |
1479 } | 1479 } |
1480 // All dynamic getters take one argument and no named arguments. | 1480 // All dynamic getters take one argument and no named arguments. |
1481 ASSERT(super_getter.AreValidArgumentCounts(1, 0)); | 1481 ASSERT(super_getter.AreValidArgumentCounts(1, 0, NULL, 0)); |
1482 ArgumentListNode* getter_arguments = new ArgumentListNode(field_pos); | 1482 ArgumentListNode* getter_arguments = new ArgumentListNode(field_pos); |
1483 getter_arguments->Add(implicit_argument); | 1483 getter_arguments->Add(implicit_argument); |
1484 AstNode* super_field = | 1484 AstNode* super_field = |
1485 new StaticCallNode(field_pos, super_getter, getter_arguments); | 1485 new StaticCallNode(field_pos, super_getter, getter_arguments); |
1486 | 1486 |
1487 if (Token::IsAssignmentOperator(CurrentToken())) { | 1487 if (Token::IsAssignmentOperator(CurrentToken())) { |
1488 const String& setter_name = | 1488 const String& setter_name = |
1489 String::ZoneHandle(Field::SetterName(field_name)); | 1489 String::ZoneHandle(Field::SetterName(field_name)); |
1490 const Function& super_setter = Function::ZoneHandle( | 1490 const Function& super_setter = Function::ZoneHandle( |
1491 ResolveDynamicFunction(super_class, setter_name)); | 1491 ResolveDynamicFunction(super_class, setter_name)); |
1492 if (super_setter.IsNull()) { | 1492 if (super_setter.IsNull()) { |
1493 ErrorMsg(field_pos, | 1493 ErrorMsg(field_pos, |
1494 "field '%s' not assignable in superclass", | 1494 "field '%s' not assignable in superclass", |
1495 field_name.ToCString()); | 1495 field_name.ToCString()); |
1496 } | 1496 } |
1497 // All dynamic setters take two arguments and no named arguments. | 1497 // All dynamic setters take two arguments and no named arguments. |
1498 ASSERT(super_setter.AreValidArgumentCounts(2, 0)); | 1498 ASSERT(super_setter.AreValidArgumentCounts(2, 0, NULL, 0)); |
1499 | 1499 |
1500 Token::Kind assignment_op = CurrentToken(); | 1500 Token::Kind assignment_op = CurrentToken(); |
1501 ConsumeToken(); | 1501 ConsumeToken(); |
1502 AstNode* value = ParseExpr(kAllowConst); | 1502 AstNode* value = ParseExpr(kAllowConst); |
1503 value = ExpandAssignableOp(field_pos, assignment_op, super_field, value); | 1503 value = ExpandAssignableOp(field_pos, assignment_op, super_field, value); |
1504 | 1504 |
1505 ArgumentListNode* setter_arguments = new ArgumentListNode(field_pos); | 1505 ArgumentListNode* setter_arguments = new ArgumentListNode(field_pos); |
1506 setter_arguments->Add(implicit_argument); | 1506 setter_arguments->Add(implicit_argument); |
1507 setter_arguments->Add(value); | 1507 setter_arguments->Add(value); |
1508 super_field = new StaticCallNode(field_pos, super_setter, setter_arguments); | 1508 super_field = new StaticCallNode(field_pos, super_setter, setter_arguments); |
(...skipping 19 matching lines...) Expand all Loading... |
1528 // Implicit 'this' parameter is the first argument. | 1528 // Implicit 'this' parameter is the first argument. |
1529 AstNode* implicit_argument = new LoadLocalNode(supercall_pos, *receiver); | 1529 AstNode* implicit_argument = new LoadLocalNode(supercall_pos, *receiver); |
1530 arguments->Add(implicit_argument); | 1530 arguments->Add(implicit_argument); |
1531 // Implicit construction phase parameter is second argument. | 1531 // Implicit construction phase parameter is second argument. |
1532 AstNode* phase_parameter = | 1532 AstNode* phase_parameter = |
1533 new LiteralNode(supercall_pos, | 1533 new LiteralNode(supercall_pos, |
1534 Smi::ZoneHandle(Smi::New(Function::kCtorPhaseAll))); | 1534 Smi::ZoneHandle(Smi::New(Function::kCtorPhaseAll))); |
1535 arguments->Add(phase_parameter); | 1535 arguments->Add(phase_parameter); |
1536 const Function& super_ctor = Function::ZoneHandle( | 1536 const Function& super_ctor = Function::ZoneHandle( |
1537 super_class.LookupConstructor(ctor_name)); | 1537 super_class.LookupConstructor(ctor_name)); |
1538 if (super_ctor.IsNull() || | 1538 if (super_ctor.IsNull()) { |
1539 !super_ctor.AreValidArguments(arguments->length(), | 1539 ErrorMsg(supercall_pos, |
1540 arguments->names())) { | 1540 "unresolved implicit call to super constructor '%s()'", |
| 1541 String::Handle(super_class.Name()).ToCString()); |
| 1542 } |
| 1543 const intptr_t kMessageBufferSize = 256; |
| 1544 char message_buffer[kMessageBufferSize]; |
| 1545 if (!super_ctor.AreValidArguments(arguments->length(), |
| 1546 arguments->names(), |
| 1547 message_buffer, |
| 1548 kMessageBufferSize)) { |
1541 ErrorMsg(supercall_pos, | 1549 ErrorMsg(supercall_pos, |
1542 "unresolved implicit call to super constructor '%s()'", | 1550 "invalid arguments passed to super constructor '%s()': %s", |
1543 String::Handle(super_class.Name()).ToCString()); | 1551 String::Handle(super_class.Name()).ToCString(), |
| 1552 message_buffer); |
1544 } | 1553 } |
1545 CheckFunctionIsCallable(supercall_pos, super_ctor); | 1554 CheckFunctionIsCallable(supercall_pos, super_ctor); |
1546 current_block_->statements->Add( | 1555 current_block_->statements->Add( |
1547 new StaticCallNode(supercall_pos, super_ctor, arguments)); | 1556 new StaticCallNode(supercall_pos, super_ctor, arguments)); |
1548 } | 1557 } |
1549 | 1558 |
1550 | 1559 |
1551 AstNode* Parser::ParseSuperInitializer(const Class& cls, | 1560 AstNode* Parser::ParseSuperInitializer(const Class& cls, |
1552 LocalVariable* receiver) { | 1561 LocalVariable* receiver) { |
1553 TRACE_PARSER("ParseSuperInitializer"); | 1562 TRACE_PARSER("ParseSuperInitializer"); |
(...skipping 27 matching lines...) Expand all Loading... |
1581 Smi::ZoneHandle(Smi::New(Function::kCtorPhaseAll))); | 1590 Smi::ZoneHandle(Smi::New(Function::kCtorPhaseAll))); |
1582 arguments->Add(phase_parameter); | 1591 arguments->Add(phase_parameter); |
1583 // 'this' parameter must not be accessible to the other super call arguments. | 1592 // 'this' parameter must not be accessible to the other super call arguments. |
1584 receiver->set_invisible(true); | 1593 receiver->set_invisible(true); |
1585 ParseActualParameters(arguments, kAllowConst); | 1594 ParseActualParameters(arguments, kAllowConst); |
1586 receiver->set_invisible(false); | 1595 receiver->set_invisible(false); |
1587 | 1596 |
1588 // Resolve the constructor. | 1597 // Resolve the constructor. |
1589 const Function& super_ctor = Function::ZoneHandle( | 1598 const Function& super_ctor = Function::ZoneHandle( |
1590 super_class.LookupConstructor(ctor_name)); | 1599 super_class.LookupConstructor(ctor_name)); |
1591 if (super_ctor.IsNull() || | 1600 if (super_ctor.IsNull()) { |
1592 !super_ctor.AreValidArguments(arguments->length(), | |
1593 arguments->names())) { | |
1594 ErrorMsg(supercall_pos, | 1601 ErrorMsg(supercall_pos, |
1595 "super class constructor '%s' not found", | 1602 "super class constructor '%s' not found", |
1596 ctor_name.ToCString()); | 1603 ctor_name.ToCString()); |
1597 } | 1604 } |
| 1605 const intptr_t kMessageBufferSize = 256; |
| 1606 char message_buffer[kMessageBufferSize]; |
| 1607 if (!super_ctor.AreValidArguments(arguments->length(), |
| 1608 arguments->names(), |
| 1609 message_buffer, |
| 1610 kMessageBufferSize)) { |
| 1611 ErrorMsg(supercall_pos, |
| 1612 "invalid arguments passed to super class constructor '%s': %s", |
| 1613 ctor_name.ToCString(), |
| 1614 message_buffer); |
| 1615 } |
1598 CheckFunctionIsCallable(supercall_pos, super_ctor); | 1616 CheckFunctionIsCallable(supercall_pos, super_ctor); |
1599 return new StaticCallNode(supercall_pos, super_ctor, arguments); | 1617 return new StaticCallNode(supercall_pos, super_ctor, arguments); |
1600 } | 1618 } |
1601 | 1619 |
1602 | 1620 |
1603 AstNode* Parser::ParseInitializer(const Class& cls, LocalVariable* receiver) { | 1621 AstNode* Parser::ParseInitializer(const Class& cls, LocalVariable* receiver) { |
1604 TRACE_PARSER("ParseInitializer"); | 1622 TRACE_PARSER("ParseInitializer"); |
1605 const intptr_t field_pos = TokenPos(); | 1623 const intptr_t field_pos = TokenPos(); |
1606 if (CurrentToken() == Token::kTHIS) { | 1624 if (CurrentToken() == Token::kTHIS) { |
1607 ConsumeToken(); | 1625 ConsumeToken(); |
(...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1755 // Construction phase parameter is second argument. | 1773 // Construction phase parameter is second argument. |
1756 LocalVariable* phase_param = LookupPhaseParameter(); | 1774 LocalVariable* phase_param = LookupPhaseParameter(); |
1757 ASSERT(phase_param != NULL); | 1775 ASSERT(phase_param != NULL); |
1758 AstNode* phase_argument = new LoadLocalNode(call_pos, *phase_param); | 1776 AstNode* phase_argument = new LoadLocalNode(call_pos, *phase_param); |
1759 arguments->Add(phase_argument); | 1777 arguments->Add(phase_argument); |
1760 ParseActualParameters(arguments, kAllowConst); | 1778 ParseActualParameters(arguments, kAllowConst); |
1761 | 1779 |
1762 // Resolve the constructor. | 1780 // Resolve the constructor. |
1763 const Function& redirect_ctor = Function::ZoneHandle( | 1781 const Function& redirect_ctor = Function::ZoneHandle( |
1764 cls.LookupConstructor(ctor_name)); | 1782 cls.LookupConstructor(ctor_name)); |
1765 if (redirect_ctor.IsNull() || | 1783 if (redirect_ctor.IsNull()) { |
1766 !redirect_ctor.AreValidArguments(arguments->length(), | 1784 ErrorMsg(call_pos, "constructor '%s' not found", ctor_name.ToCString()); |
1767 arguments->names())) { | 1785 } |
1768 ErrorMsg(call_pos, "constructor '%s' not found", | 1786 const intptr_t kMessageBufferSize = 256; |
1769 ctor_name.ToCString()); | 1787 char message_buffer[kMessageBufferSize]; |
| 1788 if (!redirect_ctor.AreValidArguments(arguments->length(), |
| 1789 arguments->names(), |
| 1790 message_buffer, |
| 1791 kMessageBufferSize)) { |
| 1792 ErrorMsg(call_pos, |
| 1793 "invalid arguments passed to constructor '%s': %s", |
| 1794 ctor_name.ToCString(), |
| 1795 message_buffer); |
1770 } | 1796 } |
1771 CheckFunctionIsCallable(call_pos, redirect_ctor); | 1797 CheckFunctionIsCallable(call_pos, redirect_ctor); |
1772 current_block_->statements->Add( | 1798 current_block_->statements->Add( |
1773 new StaticCallNode(call_pos, redirect_ctor, arguments)); | 1799 new StaticCallNode(call_pos, redirect_ctor, arguments)); |
1774 } | 1800 } |
1775 | 1801 |
1776 | 1802 |
1777 SequenceNode* Parser::MakeImplicitConstructor(const Function& func) { | 1803 SequenceNode* Parser::MakeImplicitConstructor(const Function& func) { |
1778 ASSERT(func.IsConstructor()); | 1804 ASSERT(func.IsConstructor()); |
1779 const intptr_t ctor_pos = TokenPos(); | 1805 const intptr_t ctor_pos = TokenPos(); |
(...skipping 240 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2020 if (arg->IsLoadLocalNode()) { | 2046 if (arg->IsLoadLocalNode()) { |
2021 const LocalVariable& temp = arg->AsLoadLocalNode()->local(); | 2047 const LocalVariable& temp = arg->AsLoadLocalNode()->local(); |
2022 super_call_args->Add(new LoadLocalNode(TokenPos(), temp)); | 2048 super_call_args->Add(new LoadLocalNode(TokenPos(), temp)); |
2023 } else if (arg->IsStoreLocalNode()) { | 2049 } else if (arg->IsStoreLocalNode()) { |
2024 const LocalVariable& temp = arg->AsStoreLocalNode()->local(); | 2050 const LocalVariable& temp = arg->AsStoreLocalNode()->local(); |
2025 super_call_args->Add(new LoadLocalNode(TokenPos(), temp)); | 2051 super_call_args->Add(new LoadLocalNode(TokenPos(), temp)); |
2026 } | 2052 } |
2027 } | 2053 } |
2028 } | 2054 } |
2029 ASSERT(super_ctor.AreValidArguments(super_call_args->length(), | 2055 ASSERT(super_ctor.AreValidArguments(super_call_args->length(), |
2030 super_call_args->names())); | 2056 super_call_args->names(), |
| 2057 NULL, |
| 2058 0)); |
2031 current_block_->statements->Add( | 2059 current_block_->statements->Add( |
2032 new StaticCallNode(TokenPos(), super_ctor, super_call_args)); | 2060 new StaticCallNode(TokenPos(), super_ctor, super_call_args)); |
2033 } | 2061 } |
2034 | 2062 |
2035 if (CurrentToken() == Token::kLBRACE) { | 2063 if (CurrentToken() == Token::kLBRACE) { |
2036 ConsumeToken(); | 2064 ConsumeToken(); |
2037 ParseStatementSequence(); | 2065 ParseStatementSequence(); |
2038 ExpectToken(Token::kRBRACE); | 2066 ExpectToken(Token::kRBRACE); |
2039 } else if (CurrentToken() == Token::kARROW) { | 2067 } else if (CurrentToken() == Token::kARROW) { |
2040 ErrorMsg("constructors may not return a value"); | 2068 ErrorMsg("constructors may not return a value"); |
(...skipping 5863 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7904 const String& external_constructor_name = | 7932 const String& external_constructor_name = |
7905 (named_constructor ? constructor_name : type_class_name); | 7933 (named_constructor ? constructor_name : type_class_name); |
7906 Function& constructor = Function::ZoneHandle( | 7934 Function& constructor = Function::ZoneHandle( |
7907 type_class.LookupConstructor(constructor_name)); | 7935 type_class.LookupConstructor(constructor_name)); |
7908 if (constructor.IsNull()) { | 7936 if (constructor.IsNull()) { |
7909 ErrorMsg(type_pos, | 7937 ErrorMsg(type_pos, |
7910 "interface '%s' has no constructor named '%s'", | 7938 "interface '%s' has no constructor named '%s'", |
7911 type_class_name.ToCString(), | 7939 type_class_name.ToCString(), |
7912 external_constructor_name.ToCString()); | 7940 external_constructor_name.ToCString()); |
7913 } | 7941 } |
7914 if (!constructor.AreValidArguments(arguments_length, arguments->names())) { | 7942 const intptr_t kMessageBufferSize = 256; |
| 7943 char message_buffer[kMessageBufferSize]; |
| 7944 if (!constructor.AreValidArguments(arguments_length, |
| 7945 arguments->names(), |
| 7946 message_buffer, |
| 7947 kMessageBufferSize)) { |
7915 ErrorMsg(call_pos, | 7948 ErrorMsg(call_pos, |
7916 "invalid arguments passed to constructor '%s' " | 7949 "invalid arguments passed to constructor '%s' " |
7917 "for interface '%s'", | 7950 "for interface '%s': %s", |
7918 external_constructor_name.ToCString(), | 7951 external_constructor_name.ToCString(), |
7919 type_class_name.ToCString()); | 7952 type_class_name.ToCString(), |
| 7953 message_buffer); |
7920 } | 7954 } |
7921 if (!type_class.HasFactoryClass()) { | 7955 if (!type_class.HasFactoryClass()) { |
7922 ErrorMsg(type_pos, | 7956 ErrorMsg(type_pos, |
7923 "cannot allocate interface '%s' without factory class", | 7957 "cannot allocate interface '%s' without factory class", |
7924 type_class_name.ToCString()); | 7958 type_class_name.ToCString()); |
7925 } | 7959 } |
7926 if (!type_class.HasResolvedFactoryClass()) { | 7960 if (!type_class.HasResolvedFactoryClass()) { |
7927 // This error can occur only with bootstrap classes. | 7961 // This error can occur only with bootstrap classes. |
7928 const UnresolvedClass& unresolved = | 7962 const UnresolvedClass& unresolved = |
7929 UnresolvedClass::Handle(type_class.UnresolvedFactoryClass()); | 7963 UnresolvedClass::Handle(type_class.UnresolvedFactoryClass()); |
(...skipping 29 matching lines...) Expand all Loading... |
7959 arguments_length -= 1; | 7993 arguments_length -= 1; |
7960 } | 7994 } |
7961 if (constructor.IsNull()) { | 7995 if (constructor.IsNull()) { |
7962 const String& external_constructor_name = | 7996 const String& external_constructor_name = |
7963 (named_constructor ? constructor_name : constructor_class_name); | 7997 (named_constructor ? constructor_name : constructor_class_name); |
7964 ErrorMsg(type_pos, | 7998 ErrorMsg(type_pos, |
7965 "class '%s' has no constructor or factory named '%s'", | 7999 "class '%s' has no constructor or factory named '%s'", |
7966 String::Handle(constructor_class.Name()).ToCString(), | 8000 String::Handle(constructor_class.Name()).ToCString(), |
7967 external_constructor_name.ToCString()); | 8001 external_constructor_name.ToCString()); |
7968 } | 8002 } |
7969 if (!constructor.AreValidArguments(arguments_length, arguments->names())) { | 8003 const intptr_t kMessageBufferSize = 256; |
| 8004 char message_buffer[kMessageBufferSize]; |
| 8005 if (!constructor.AreValidArguments(arguments_length, |
| 8006 arguments->names(), |
| 8007 message_buffer, |
| 8008 kMessageBufferSize)) { |
7970 const String& external_constructor_name = | 8009 const String& external_constructor_name = |
7971 (named_constructor ? constructor_name : constructor_class_name); | 8010 (named_constructor ? constructor_name : constructor_class_name); |
7972 ErrorMsg(call_pos, | 8011 ErrorMsg(call_pos, |
7973 "invalid arguments passed to constructor '%s' for class '%s'", | 8012 "invalid arguments passed to constructor '%s' for class '%s': %s", |
7974 external_constructor_name.ToCString(), | 8013 external_constructor_name.ToCString(), |
7975 String::Handle(constructor_class.Name()).ToCString()); | 8014 String::Handle(constructor_class.Name()).ToCString(), |
| 8015 message_buffer); |
7976 } | 8016 } |
7977 | 8017 |
7978 // Now that the constructor to be called is identified, finalize the type | 8018 // Now that the constructor to be called is identified, finalize the type |
7979 // argument vector to be passed. | 8019 // argument vector to be passed. |
7980 // The type argument vector of the parsed type was finalized in ParseType. | 8020 // The type argument vector of the parsed type was finalized in ParseType. |
7981 // If the constructor class was changed from the interface class to the | 8021 // If the constructor class was changed from the interface class to the |
7982 // factory class, we need to finalize the type argument vector again, because | 8022 // factory class, we need to finalize the type argument vector again, because |
7983 // it may be longer due to the factory class extending a class, or/and because | 8023 // it may be longer due to the factory class extending a class, or/and because |
7984 // the bounds on the factory class may be tighter than on the interface. | 8024 // the bounds on the factory class may be tighter than on the interface. |
7985 if (constructor_class.raw() != type_class.raw()) { | 8025 if (constructor_class.raw() != type_class.raw()) { |
(...skipping 638 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
8624 void Parser::SkipQualIdent() { | 8664 void Parser::SkipQualIdent() { |
8625 ASSERT(IsIdentifier()); | 8665 ASSERT(IsIdentifier()); |
8626 ConsumeToken(); | 8666 ConsumeToken(); |
8627 if (CurrentToken() == Token::kPERIOD) { | 8667 if (CurrentToken() == Token::kPERIOD) { |
8628 ConsumeToken(); // Consume the kPERIOD token. | 8668 ConsumeToken(); // Consume the kPERIOD token. |
8629 ExpectIdentifier("identifier expected after '.'"); | 8669 ExpectIdentifier("identifier expected after '.'"); |
8630 } | 8670 } |
8631 } | 8671 } |
8632 | 8672 |
8633 } // namespace dart | 8673 } // namespace dart |
OLD | NEW |