Chromium Code Reviews| 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/bootstrap.h" | 9 #include "vm/bootstrap.h" |
| 10 #include "vm/class_finalizer.h" | 10 #include "vm/class_finalizer.h" |
| (...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 237 | 237 |
| 238 // For parsing a compilation unit. | 238 // For parsing a compilation unit. |
| 239 Parser::Parser(const Script& script, const Library& library, intptr_t token_pos) | 239 Parser::Parser(const Script& script, const Library& library, intptr_t token_pos) |
| 240 : isolate_(Isolate::Current()), | 240 : isolate_(Isolate::Current()), |
| 241 script_(Script::Handle(isolate_, script.raw())), | 241 script_(Script::Handle(isolate_, script.raw())), |
| 242 tokens_iterator_(TokenStream::Handle(isolate_, script.tokens()), | 242 tokens_iterator_(TokenStream::Handle(isolate_, script.tokens()), |
| 243 token_pos), | 243 token_pos), |
| 244 token_kind_(Token::kILLEGAL), | 244 token_kind_(Token::kILLEGAL), |
| 245 current_block_(NULL), | 245 current_block_(NULL), |
| 246 is_top_level_(false), | 246 is_top_level_(false), |
| 247 parsing_metadata_(false), | |
| 247 current_member_(NULL), | 248 current_member_(NULL), |
| 248 allow_function_literals_(true), | 249 allow_function_literals_(true), |
| 249 parsed_function_(NULL), | 250 parsed_function_(NULL), |
| 250 innermost_function_(Function::Handle(isolate_)), | 251 innermost_function_(Function::Handle(isolate_)), |
| 251 literal_token_(LiteralToken::Handle(isolate_)), | 252 literal_token_(LiteralToken::Handle(isolate_)), |
| 252 current_class_(Class::Handle(isolate_)), | 253 current_class_(Class::Handle(isolate_)), |
| 253 library_(Library::Handle(isolate_, library.raw())), | 254 library_(Library::Handle(isolate_, library.raw())), |
| 254 try_blocks_list_(NULL), | 255 try_blocks_list_(NULL), |
| 255 last_used_try_index_(0), | 256 last_used_try_index_(0), |
| 256 unregister_pending_function_(false) { | 257 unregister_pending_function_(false) { |
| 257 ASSERT(tokens_iterator_.IsValid()); | 258 ASSERT(tokens_iterator_.IsValid()); |
| 258 ASSERT(!library.IsNull()); | 259 ASSERT(!library.IsNull()); |
| 259 } | 260 } |
| 260 | 261 |
| 261 | 262 |
| 262 // For parsing a function. | 263 // For parsing a function. |
| 263 Parser::Parser(const Script& script, | 264 Parser::Parser(const Script& script, |
| 264 ParsedFunction* parsed_function, | 265 ParsedFunction* parsed_function, |
| 265 intptr_t token_position) | 266 intptr_t token_position) |
| 266 : isolate_(Isolate::Current()), | 267 : isolate_(Isolate::Current()), |
| 267 script_(Script::Handle(isolate_, script.raw())), | 268 script_(Script::Handle(isolate_, script.raw())), |
| 268 tokens_iterator_(TokenStream::Handle(isolate_, script.tokens()), | 269 tokens_iterator_(TokenStream::Handle(isolate_, script.tokens()), |
| 269 token_position), | 270 token_position), |
| 270 token_kind_(Token::kILLEGAL), | 271 token_kind_(Token::kILLEGAL), |
| 271 current_block_(NULL), | 272 current_block_(NULL), |
| 272 is_top_level_(false), | 273 is_top_level_(false), |
| 274 parsing_metadata_(false), | |
| 273 current_member_(NULL), | 275 current_member_(NULL), |
| 274 allow_function_literals_(true), | 276 allow_function_literals_(true), |
| 275 parsed_function_(parsed_function), | 277 parsed_function_(parsed_function), |
| 276 innermost_function_(Function::Handle(isolate_, | 278 innermost_function_(Function::Handle(isolate_, |
| 277 parsed_function->function().raw())), | 279 parsed_function->function().raw())), |
| 278 literal_token_(LiteralToken::Handle(isolate_)), | 280 literal_token_(LiteralToken::Handle(isolate_)), |
| 279 current_class_(Class::Handle(isolate_, | 281 current_class_(Class::Handle(isolate_, |
| 280 parsed_function->function().Owner())), | 282 parsed_function->function().Owner())), |
| 281 library_(Library::Handle(Class::Handle( | 283 library_(Library::Handle(Class::Handle( |
| 282 isolate_, | 284 isolate_, |
| (...skipping 569 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 852 Isolate* isolate = Isolate::Current(); | 854 Isolate* isolate = Isolate::Current(); |
| 853 StackZone zone(isolate); | 855 StackZone zone(isolate); |
| 854 LongJump* base = isolate->long_jump_base(); | 856 LongJump* base = isolate->long_jump_base(); |
| 855 LongJump jump; | 857 LongJump jump; |
| 856 isolate->set_long_jump_base(&jump); | 858 isolate->set_long_jump_base(&jump); |
| 857 if (setjmp(*jump.Set()) == 0) { | 859 if (setjmp(*jump.Set()) == 0) { |
| 858 const Script& script = Script::Handle(cls.script()); | 860 const Script& script = Script::Handle(cls.script()); |
| 859 const Library& lib = Library::Handle(cls.library()); | 861 const Library& lib = Library::Handle(cls.library()); |
| 860 Parser parser(script, lib, token_pos); | 862 Parser parser(script, lib, token_pos); |
| 861 parser.set_current_class(cls); | 863 parser.set_current_class(cls); |
| 864 parser.set_parsing_metadata(true); | |
| 862 return parser.EvaluateMetadata(); | 865 return parser.EvaluateMetadata(); |
| 863 } else { | 866 } else { |
| 864 Error& error = Error::Handle(); | 867 Error& error = Error::Handle(); |
| 865 error = isolate->object_store()->sticky_error(); | 868 error = isolate->object_store()->sticky_error(); |
| 866 isolate->object_store()->clear_sticky_error(); | 869 isolate->object_store()->clear_sticky_error(); |
| 867 isolate->set_long_jump_base(base); | 870 isolate->set_long_jump_base(base); |
| 868 return error.raw(); | 871 return error.raw(); |
| 869 } | 872 } |
| 870 UNREACHABLE(); | 873 UNREACHABLE(); |
| 871 return Object::null(); | 874 return Object::null(); |
| (...skipping 7368 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 8240 PrimaryNode* primary = node->AsPrimaryNode(); | 8243 PrimaryNode* primary = node->AsPrimaryNode(); |
| 8241 if (primary->primary().IsString()) { | 8244 if (primary->primary().IsString()) { |
| 8242 if (primary->IsSuper()) { | 8245 if (primary->IsSuper()) { |
| 8243 return primary; | 8246 return primary; |
| 8244 } | 8247 } |
| 8245 // In a static method, evaluation of an unresolved identifier causes a | 8248 // In a static method, evaluation of an unresolved identifier causes a |
| 8246 // NoSuchMethodError to be thrown. | 8249 // NoSuchMethodError to be thrown. |
| 8247 // In an instance method, we convert this into a getter call | 8250 // In an instance method, we convert this into a getter call |
| 8248 // for a field (which may be defined in a subclass.) | 8251 // for a field (which may be defined in a subclass.) |
| 8249 String& name = String::CheckedZoneHandle(primary->primary().raw()); | 8252 String& name = String::CheckedZoneHandle(primary->primary().raw()); |
| 8250 if (current_function().is_static() || | 8253 if (parsing_metadata_ || |
|
hausner
2013/11/19 00:07:24
Please add to the comment above why we distinguish
rmacnak
2013/11/19 01:01:24
Rewrote as a more intention-revealing error path a
| |
| 8254 current_function().is_static() || | |
| 8251 current_function().IsInFactoryScope()) { | 8255 current_function().IsInFactoryScope()) { |
| 8252 return new StaticGetterNode(primary->token_pos(), | 8256 return new StaticGetterNode(primary->token_pos(), |
| 8253 NULL, // No receiver. | 8257 NULL, // No receiver. |
| 8254 false, // Not a super getter. | 8258 false, // Not a super getter. |
| 8255 Class::ZoneHandle(current_class().raw()), | 8259 Class::ZoneHandle(current_class().raw()), |
| 8256 name); | 8260 name); |
| 8257 } else { | 8261 } else { |
| 8258 AstNode* receiver = LoadReceiver(primary->token_pos()); | 8262 AstNode* receiver = LoadReceiver(primary->token_pos()); |
| 8259 return CallGetter(node->token_pos(), receiver, name); | 8263 return CallGetter(node->token_pos(), receiver, name); |
| 8260 } | 8264 } |
| 8261 } | 8265 } |
| 8262 return primary; | 8266 return primary; |
| 8263 } | 8267 } |
| 8264 | 8268 |
| 8265 | 8269 |
| 8266 AstNode* Parser::LoadClosure(PrimaryNode* primary) { | 8270 AstNode* Parser::LoadClosure(PrimaryNode* primary) { |
| 8267 ASSERT(primary->primary().IsFunction()); | 8271 ASSERT(primary->primary().IsFunction()); |
| 8268 AstNode* closure = NULL; | 8272 AstNode* closure = NULL; |
| 8269 const Function& func = | 8273 const Function& func = |
| 8270 Function::CheckedZoneHandle(primary->primary().raw()); | 8274 Function::CheckedZoneHandle(primary->primary().raw()); |
| 8271 const String& funcname = String::ZoneHandle(func.name()); | 8275 const String& funcname = String::ZoneHandle(func.name()); |
| 8272 if (func.is_static()) { | 8276 if (func.is_static()) { |
| 8273 // Static function access. | 8277 // Static function access. |
| 8274 closure = CreateImplicitClosureNode(func, primary->token_pos(), NULL); | 8278 closure = CreateImplicitClosureNode(func, primary->token_pos(), NULL); |
| 8275 } else { | 8279 } else { |
| 8276 // Instance function access. | 8280 // Instance function access. |
| 8281 if (parsing_metadata_) { | |
| 8282 ErrorMsg(primary->token_pos(), | |
| 8283 "cannot access instance method '%s' from metadata", | |
| 8284 funcname.ToCString()); | |
| 8285 } | |
| 8277 if (current_function().is_static() || | 8286 if (current_function().is_static() || |
| 8278 current_function().IsInFactoryScope()) { | 8287 current_function().IsInFactoryScope()) { |
| 8279 ErrorMsg(primary->token_pos(), | 8288 ErrorMsg(primary->token_pos(), |
| 8280 "cannot access instance method '%s' from static method", | 8289 "cannot access instance method '%s' from static method", |
| 8281 funcname.ToCString()); | 8290 funcname.ToCString()); |
| 8282 } | 8291 } |
| 8283 AstNode* receiver = LoadReceiver(primary->token_pos()); | 8292 AstNode* receiver = LoadReceiver(primary->token_pos()); |
| 8284 closure = CallGetter(primary->token_pos(), receiver, funcname); | 8293 closure = CallGetter(primary->token_pos(), receiver, funcname); |
| 8285 } | 8294 } |
| 8286 return closure; | 8295 return closure; |
| (...skipping 362 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 8649 // A found name is treated as accessed and possibly marked as captured. | 8658 // A found name is treated as accessed and possibly marked as captured. |
| 8650 const bool kTestOnly = false; | 8659 const bool kTestOnly = false; |
| 8651 return current_block_->scope->LookupVariable(ident, kTestOnly); | 8660 return current_block_->scope->LookupVariable(ident, kTestOnly); |
| 8652 } | 8661 } |
| 8653 | 8662 |
| 8654 | 8663 |
| 8655 void Parser::CheckInstanceFieldAccess(intptr_t field_pos, | 8664 void Parser::CheckInstanceFieldAccess(intptr_t field_pos, |
| 8656 const String& field_name) { | 8665 const String& field_name) { |
| 8657 // Fields are not accessible from a static function, except from a | 8666 // Fields are not accessible from a static function, except from a |
| 8658 // constructor, which is considered as non-static by the compiler. | 8667 // constructor, which is considered as non-static by the compiler. |
| 8668 if (parsing_metadata_) { | |
| 8669 ErrorMsg(field_pos, | |
| 8670 "cannot access instance field '%s' from metadata", | |
| 8671 field_name.ToCString()); | |
| 8672 } | |
| 8659 if (current_function().is_static()) { | 8673 if (current_function().is_static()) { |
| 8660 ErrorMsg(field_pos, | 8674 ErrorMsg(field_pos, |
| 8661 "cannot access instance field '%s' from a static function", | 8675 "cannot access instance field '%s' from a static function", |
| 8662 field_name.ToCString()); | 8676 field_name.ToCString()); |
| 8663 } | 8677 } |
| 8664 } | 8678 } |
| 8665 | 8679 |
| 8666 | 8680 |
| 8667 bool Parser::ParsingStaticMember() const { | 8681 bool Parser::ParsingStaticMember() const { |
| 8668 if (is_top_level_) { | 8682 if (is_top_level_) { |
| (...skipping 2030 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 10699 void Parser::SkipQualIdent() { | 10713 void Parser::SkipQualIdent() { |
| 10700 ASSERT(IsIdentifier()); | 10714 ASSERT(IsIdentifier()); |
| 10701 ConsumeToken(); | 10715 ConsumeToken(); |
| 10702 if (CurrentToken() == Token::kPERIOD) { | 10716 if (CurrentToken() == Token::kPERIOD) { |
| 10703 ConsumeToken(); // Consume the kPERIOD token. | 10717 ConsumeToken(); // Consume the kPERIOD token. |
| 10704 ExpectIdentifier("identifier expected after '.'"); | 10718 ExpectIdentifier("identifier expected after '.'"); |
| 10705 } | 10719 } |
| 10706 } | 10720 } |
| 10707 | 10721 |
| 10708 } // namespace dart | 10722 } // namespace dart |
| OLD | NEW |