| 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 "lib/invocation_mirror.h" | 7 #include "lib/invocation_mirror.h" |
| 8 #include "platform/utils.h" | 8 #include "platform/utils.h" |
| 9 #include "vm/ast_transformer.h" | 9 #include "vm/ast_transformer.h" |
| 10 #include "vm/bootstrap.h" | 10 #include "vm/bootstrap.h" |
| (...skipping 1033 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1044 return error.raw(); | 1044 return error.raw(); |
| 1045 } | 1045 } |
| 1046 UNREACHABLE(); | 1046 UNREACHABLE(); |
| 1047 return Object::null(); | 1047 return Object::null(); |
| 1048 } | 1048 } |
| 1049 | 1049 |
| 1050 | 1050 |
| 1051 RawArray* Parser::EvaluateMetadata() { | 1051 RawArray* Parser::EvaluateMetadata() { |
| 1052 CheckToken(Token::kAT, "Metadata character '@' expected"); | 1052 CheckToken(Token::kAT, "Metadata character '@' expected"); |
| 1053 GrowableObjectArray& meta_values = | 1053 GrowableObjectArray& meta_values = |
| 1054 GrowableObjectArray::Handle(Z, GrowableObjectArray::New()); | 1054 GrowableObjectArray::Handle(Z, GrowableObjectArray::New(Heap::kOld)); |
| 1055 while (CurrentToken() == Token::kAT) { | 1055 while (CurrentToken() == Token::kAT) { |
| 1056 ConsumeToken(); | 1056 ConsumeToken(); |
| 1057 intptr_t expr_pos = TokenPos(); | 1057 intptr_t expr_pos = TokenPos(); |
| 1058 if (!IsIdentifier()) { | 1058 if (!IsIdentifier()) { |
| 1059 ExpectIdentifier("identifier expected"); | 1059 ExpectIdentifier("identifier expected"); |
| 1060 } | 1060 } |
| 1061 // Reject expressions with deferred library prefix eagerly. | 1061 // Reject expressions with deferred library prefix eagerly. |
| 1062 Object& obj = | 1062 Object& obj = |
| 1063 Object::Handle(Z, library_.LookupLocalObject(*CurrentLiteral())); | 1063 Object::Handle(Z, library_.LookupLocalObject(*CurrentLiteral())); |
| 1064 if (!obj.IsNull() && obj.IsLibraryPrefix()) { | 1064 if (!obj.IsNull() && obj.IsLibraryPrefix()) { |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1113 ident->ToCString(), | 1113 ident->ToCString(), |
| 1114 cls.ToCString()); | 1114 cls.ToCString()); |
| 1115 } | 1115 } |
| 1116 expr = GenerateStaticFieldLookup(field, ident_pos); | 1116 expr = GenerateStaticFieldLookup(field, ident_pos); |
| 1117 } | 1117 } |
| 1118 } | 1118 } |
| 1119 if (expr->EvalConstExpr() == NULL) { | 1119 if (expr->EvalConstExpr() == NULL) { |
| 1120 ReportError(expr_pos, "expression must be a compile-time constant"); | 1120 ReportError(expr_pos, "expression must be a compile-time constant"); |
| 1121 } | 1121 } |
| 1122 const Instance& val = EvaluateConstExpr(expr_pos, expr); | 1122 const Instance& val = EvaluateConstExpr(expr_pos, expr); |
| 1123 meta_values.Add(val); | 1123 meta_values.Add(val, Heap::kOld); |
| 1124 } | 1124 } |
| 1125 return Array::MakeArray(meta_values); | 1125 return Array::MakeArray(meta_values); |
| 1126 } | 1126 } |
| 1127 | 1127 |
| 1128 | 1128 |
| 1129 SequenceNode* Parser::ParseStaticInitializer() { | 1129 SequenceNode* Parser::ParseStaticInitializer() { |
| 1130 ExpectIdentifier("field name expected"); | 1130 ExpectIdentifier("field name expected"); |
| 1131 CheckToken(Token::kASSIGN, "field initialier expected"); | 1131 CheckToken(Token::kASSIGN, "field initialier expected"); |
| 1132 ConsumeToken(); | 1132 ConsumeToken(); |
| 1133 OpenFunctionBlock(parsed_function()->function()); | 1133 OpenFunctionBlock(parsed_function()->function()); |
| (...skipping 442 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1576 | 1576 |
| 1577 // Receiver is local 0. | 1577 // Receiver is local 0. |
| 1578 LocalScope* scope = current_block_->scope; | 1578 LocalScope* scope = current_block_->scope; |
| 1579 ArgumentListNode* func_args = new ArgumentListNode(token_pos); | 1579 ArgumentListNode* func_args = new ArgumentListNode(token_pos); |
| 1580 for (intptr_t i = 0; i < desc.Count(); ++i) { | 1580 for (intptr_t i = 0; i < desc.Count(); ++i) { |
| 1581 func_args->Add(new LoadLocalNode(token_pos, scope->VariableAt(i))); | 1581 func_args->Add(new LoadLocalNode(token_pos, scope->VariableAt(i))); |
| 1582 } | 1582 } |
| 1583 | 1583 |
| 1584 if (desc.NamedCount() > 0) { | 1584 if (desc.NamedCount() > 0) { |
| 1585 const Array& arg_names = | 1585 const Array& arg_names = |
| 1586 Array::ZoneHandle(Z, Array::New(desc.NamedCount())); | 1586 Array::ZoneHandle(Z, Array::New(desc.NamedCount(), Heap::kOld)); |
| 1587 for (intptr_t i = 0; i < arg_names.Length(); ++i) { | 1587 for (intptr_t i = 0; i < arg_names.Length(); ++i) { |
| 1588 arg_names.SetAt(i, String::Handle(Z, desc.NameAt(i))); | 1588 arg_names.SetAt(i, String::Handle(Z, desc.NameAt(i))); |
| 1589 } | 1589 } |
| 1590 func_args->set_names(arg_names); | 1590 func_args->set_names(arg_names); |
| 1591 } | 1591 } |
| 1592 | 1592 |
| 1593 const String& func_name = String::ZoneHandle(Z, func.name()); | 1593 const String& func_name = String::ZoneHandle(Z, func.name()); |
| 1594 ArgumentListNode* arguments = BuildNoSuchMethodArguments( | 1594 ArgumentListNode* arguments = BuildNoSuchMethodArguments( |
| 1595 token_pos, func_name, *func_args, NULL, false); | 1595 token_pos, func_name, *func_args, NULL, false); |
| 1596 const intptr_t kNumArguments = 2; // Receiver, InvocationMirror. | 1596 const intptr_t kNumArguments = 2; // Receiver, InvocationMirror. |
| (...skipping 4235 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5832 } | 5832 } |
| 5833 return Api::UnwrapHandle(result); | 5833 return Api::UnwrapHandle(result); |
| 5834 } | 5834 } |
| 5835 | 5835 |
| 5836 | 5836 |
| 5837 void Parser::ParseLibraryName() { | 5837 void Parser::ParseLibraryName() { |
| 5838 ASSERT(CurrentToken() == Token::kLIBRARY); | 5838 ASSERT(CurrentToken() == Token::kLIBRARY); |
| 5839 ConsumeToken(); | 5839 ConsumeToken(); |
| 5840 String& lib_name = *ExpectIdentifier("library name expected"); | 5840 String& lib_name = *ExpectIdentifier("library name expected"); |
| 5841 if (CurrentToken() == Token::kPERIOD) { | 5841 if (CurrentToken() == Token::kPERIOD) { |
| 5842 GrowableHandlePtrArray<const String> pieces(Z, 3); |
| 5843 pieces.Add(lib_name); |
| 5842 while (CurrentToken() == Token::kPERIOD) { | 5844 while (CurrentToken() == Token::kPERIOD) { |
| 5843 ConsumeToken(); | 5845 ConsumeToken(); |
| 5844 lib_name = String::Concat(lib_name, Symbols::Dot()); | 5846 pieces.Add(Symbols::Dot()); |
| 5845 lib_name = String::Concat(lib_name, | 5847 pieces.Add(*ExpectIdentifier("malformed library name")); |
| 5846 *ExpectIdentifier("malformed library name")); | |
| 5847 } | 5848 } |
| 5848 lib_name = Symbols::New(lib_name); | 5849 lib_name = Symbols::FromConcatAll(pieces); |
| 5849 } | 5850 } |
| 5850 library_.SetName(lib_name); | 5851 library_.SetName(lib_name); |
| 5851 ExpectSemicolon(); | 5852 ExpectSemicolon(); |
| 5852 } | 5853 } |
| 5853 | 5854 |
| 5854 | 5855 |
| 5855 void Parser::ParseIdentList(GrowableObjectArray* names) { | 5856 void Parser::ParseIdentList(GrowableObjectArray* names) { |
| 5856 if (!IsIdentifier()) { | 5857 if (!IsIdentifier()) { |
| 5857 ReportError("identifier expected"); | 5858 ReportError("identifier expected"); |
| 5858 } | 5859 } |
| (...skipping 5824 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11683 extractor_name, | 11684 extractor_name, |
| 11684 NULL, // No arguments. | 11685 NULL, // No arguments. |
| 11685 InvocationMirror::kStatic, | 11686 InvocationMirror::kStatic, |
| 11686 is_setter_name | 11687 is_setter_name |
| 11687 ? InvocationMirror::kSetter | 11688 ? InvocationMirror::kSetter |
| 11688 : InvocationMirror::kMethod, | 11689 : InvocationMirror::kMethod, |
| 11689 NULL); // No existing function. | 11690 NULL); // No existing function. |
| 11690 } | 11691 } |
| 11691 | 11692 |
| 11692 // Closurization of instance getter, setter, method or operator. | 11693 // Closurization of instance getter, setter, method or operator. |
| 11694 GrowableHandlePtrArray<const String> pieces(Z, 3); |
| 11695 pieces.Add(Symbols::HashMark()); |
| 11693 if (is_setter_name) { | 11696 if (is_setter_name) { |
| 11694 extractor_name = String::Concat(Symbols::SetterPrefix(), extractor_name); | 11697 pieces.Add(Symbols::SetterPrefix()); |
| 11695 } | 11698 } |
| 11696 extractor_name = Symbols::FromConcat(Symbols::HashMark(), extractor_name); | 11699 pieces.Add(extractor_name); |
| 11700 extractor_name = Symbols::FromConcatAll(pieces); |
| 11697 return new(Z) InstanceGetterNode(property_pos, primary, extractor_name); | 11701 return new(Z) InstanceGetterNode(property_pos, primary, extractor_name); |
| 11698 } | 11702 } |
| 11699 | 11703 |
| 11700 | 11704 |
| 11701 AstNode* Parser::ParsePostfixExpr() { | 11705 AstNode* Parser::ParsePostfixExpr() { |
| 11702 TRACE_PARSER("ParsePostfixExpr"); | 11706 TRACE_PARSER("ParsePostfixExpr"); |
| 11703 String* expr_ident = | 11707 String* expr_ident = |
| 11704 Token::IsIdentifier(CurrentToken()) ? CurrentLiteral() : NULL; | 11708 Token::IsIdentifier(CurrentToken()) ? CurrentLiteral() : NULL; |
| 11705 const intptr_t expr_pos = TokenPos(); | 11709 const intptr_t expr_pos = TokenPos(); |
| 11706 AstNode* expr = ParsePrimary(); | 11710 AstNode* expr = ParsePrimary(); |
| (...skipping 1869 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 13576 | 13580 |
| 13577 String& Parser::Interpolate(const GrowableArray<AstNode*>& values) { | 13581 String& Parser::Interpolate(const GrowableArray<AstNode*>& values) { |
| 13578 const Class& cls = Class::Handle( | 13582 const Class& cls = Class::Handle( |
| 13579 Z, Library::LookupCoreClass(Symbols::StringBase())); | 13583 Z, Library::LookupCoreClass(Symbols::StringBase())); |
| 13580 ASSERT(!cls.IsNull()); | 13584 ASSERT(!cls.IsNull()); |
| 13581 const Function& func = Function::Handle(Z, cls.LookupStaticFunction( | 13585 const Function& func = Function::Handle(Z, cls.LookupStaticFunction( |
| 13582 Library::PrivateCoreLibName(Symbols::Interpolate()))); | 13586 Library::PrivateCoreLibName(Symbols::Interpolate()))); |
| 13583 ASSERT(!func.IsNull()); | 13587 ASSERT(!func.IsNull()); |
| 13584 | 13588 |
| 13585 // Build the array of literal values to interpolate. | 13589 // Build the array of literal values to interpolate. |
| 13586 const Array& value_arr = Array::Handle(Z, Array::New(values.length())); | 13590 const Array& value_arr = Array::Handle(Z, |
| 13591 Array::New(values.length(), Heap::kOld)); |
| 13587 for (int i = 0; i < values.length(); i++) { | 13592 for (int i = 0; i < values.length(); i++) { |
| 13588 ASSERT(values[i]->IsLiteralNode()); | 13593 ASSERT(values[i]->IsLiteralNode()); |
| 13589 value_arr.SetAt(i, values[i]->AsLiteralNode()->literal()); | 13594 value_arr.SetAt(i, values[i]->AsLiteralNode()->literal()); |
| 13590 } | 13595 } |
| 13591 | 13596 |
| 13592 // Build argument array to pass to the interpolation function. | 13597 // Build argument array to pass to the interpolation function. |
| 13593 const Array& interpolate_arg = Array::Handle(Z, Array::New(1)); | 13598 const Array& interpolate_arg = Array::Handle(Z, Array::New(1, Heap::kOld)); |
| 13594 interpolate_arg.SetAt(0, value_arr); | 13599 interpolate_arg.SetAt(0, value_arr); |
| 13595 | 13600 |
| 13596 // Call interpolation function. | 13601 // Call interpolation function. |
| 13597 Object& result = Object::Handle(Z); | 13602 Object& result = Object::Handle(Z); |
| 13598 { | 13603 { |
| 13599 PAUSETIMERSCOPE(T, time_compilation); | 13604 PAUSETIMERSCOPE(T, time_compilation); |
| 13600 result = DartEntry::InvokeFunction(func, interpolate_arg); | 13605 result = DartEntry::InvokeFunction(func, interpolate_arg); |
| 13601 } | 13606 } |
| 13602 if (result.IsUnhandledException()) { | 13607 if (result.IsUnhandledException()) { |
| 13603 ReportError("%s", Error::Cast(result).ToErrorCString()); | 13608 ReportError("%s", Error::Cast(result).ToErrorCString()); |
| (...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 13766 // TODO(hausner): Ideally we should generate the NoSuchMethodError | 13771 // TODO(hausner): Ideally we should generate the NoSuchMethodError |
| 13767 // later, when we know more about how the unresolved name is used. | 13772 // later, when we know more about how the unresolved name is used. |
| 13768 // For example, we don't know yet whether the unresolved name | 13773 // For example, we don't know yet whether the unresolved name |
| 13769 // refers to a getter or a setter. However, it is more awkward | 13774 // refers to a getter or a setter. However, it is more awkward |
| 13770 // to distinuish four NoSuchMethodError cases all over the place | 13775 // to distinuish four NoSuchMethodError cases all over the place |
| 13771 // in the parser. The four cases are: prefixed vs non-prefixed | 13776 // in the parser. The four cases are: prefixed vs non-prefixed |
| 13772 // name, static vs dynamic context in which the unresolved name | 13777 // name, static vs dynamic context in which the unresolved name |
| 13773 // is used. We cheat a little here by looking at the next token | 13778 // is used. We cheat a little here by looking at the next token |
| 13774 // to determine whether we have an unresolved method call or | 13779 // to determine whether we have an unresolved method call or |
| 13775 // field access. | 13780 // field access. |
| 13776 String& qualified_name = String::ZoneHandle(Z, prefix.name()); | 13781 GrowableHandlePtrArray<const String> pieces(Z, 3); |
| 13777 qualified_name = String::Concat(qualified_name, Symbols::Dot()); | 13782 pieces.Add(String::Handle(Z, prefix.name())); |
| 13778 qualified_name = Symbols::FromConcat(qualified_name, ident); | 13783 pieces.Add(Symbols::Dot()); |
| 13784 pieces.Add(ident); |
| 13785 const String& qualified_name = String::ZoneHandle(Z, |
| 13786 Symbols::FromConcatAll(pieces)); |
| 13779 InvocationMirror::Type call_type = | 13787 InvocationMirror::Type call_type = |
| 13780 CurrentToken() == Token::kLPAREN ? | 13788 CurrentToken() == Token::kLPAREN ? |
| 13781 InvocationMirror::kMethod : InvocationMirror::kGetter; | 13789 InvocationMirror::kMethod : InvocationMirror::kGetter; |
| 13782 primary = ThrowNoSuchMethodError(qual_ident_pos, | 13790 primary = ThrowNoSuchMethodError(qual_ident_pos, |
| 13783 current_class(), | 13791 current_class(), |
| 13784 qualified_name, | 13792 qualified_name, |
| 13785 NULL, // No arguments. | 13793 NULL, // No arguments. |
| 13786 InvocationMirror::kTopLevel, | 13794 InvocationMirror::kTopLevel, |
| 13787 call_type, | 13795 call_type, |
| 13788 NULL); // No existing function. | 13796 NULL); // No existing function. |
| (...skipping 512 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 14301 void Parser::SkipQualIdent() { | 14309 void Parser::SkipQualIdent() { |
| 14302 ASSERT(IsIdentifier()); | 14310 ASSERT(IsIdentifier()); |
| 14303 ConsumeToken(); | 14311 ConsumeToken(); |
| 14304 if (CurrentToken() == Token::kPERIOD) { | 14312 if (CurrentToken() == Token::kPERIOD) { |
| 14305 ConsumeToken(); // Consume the kPERIOD token. | 14313 ConsumeToken(); // Consume the kPERIOD token. |
| 14306 ExpectIdentifier("identifier expected after '.'"); | 14314 ExpectIdentifier("identifier expected after '.'"); |
| 14307 } | 14315 } |
| 14308 } | 14316 } |
| 14309 | 14317 |
| 14310 } // namespace dart | 14318 } // namespace dart |
| OLD | NEW |