| 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 20 matching lines...) Expand all Loading... |
| 31 #include "vm/scopes.h" | 31 #include "vm/scopes.h" |
| 32 #include "vm/stack_frame.h" | 32 #include "vm/stack_frame.h" |
| 33 #include "vm/symbols.h" | 33 #include "vm/symbols.h" |
| 34 #include "vm/tags.h" | 34 #include "vm/tags.h" |
| 35 #include "vm/timer.h" | 35 #include "vm/timer.h" |
| 36 #include "vm/zone.h" | 36 #include "vm/zone.h" |
| 37 | 37 |
| 38 namespace dart { | 38 namespace dart { |
| 39 | 39 |
| 40 DEFINE_FLAG(bool, enable_debug_break, false, "Allow use of break \"message\"."); | 40 DEFINE_FLAG(bool, enable_debug_break, false, "Allow use of break \"message\"."); |
| 41 DEFINE_FLAG(bool, enable_mirrors, true, |
| 42 "Disable to make importing dart:mirrors an error."); |
| 41 DEFINE_FLAG(bool, load_deferred_eagerly, false, | 43 DEFINE_FLAG(bool, load_deferred_eagerly, false, |
| 42 "Load deferred libraries eagerly."); | 44 "Load deferred libraries eagerly."); |
| 43 DEFINE_FLAG(bool, trace_parser, false, "Trace parser operations."); | 45 DEFINE_FLAG(bool, trace_parser, false, "Trace parser operations."); |
| 44 DEFINE_FLAG(bool, warn_mixin_typedef, true, "Warning on legacy mixin typedef."); | 46 DEFINE_FLAG(bool, warn_mixin_typedef, true, "Warning on legacy mixin typedef."); |
| 47 |
| 48 DECLARE_FLAG(bool, lazy_dispatchers); |
| 49 DECLARE_FLAG(bool, load_deferred_eagerly); |
| 45 DECLARE_FLAG(bool, throw_on_javascript_int_overflow); | 50 DECLARE_FLAG(bool, throw_on_javascript_int_overflow); |
| 46 DECLARE_FLAG(bool, warn_on_javascript_compatibility); | 51 DECLARE_FLAG(bool, warn_on_javascript_compatibility); |
| 47 DEFINE_FLAG(bool, enable_mirrors, true, | |
| 48 "Disable to make importing dart:mirrors an error."); | |
| 49 DECLARE_FLAG(bool, lazy_dispatchers); | |
| 50 | 52 |
| 51 // Quick access to the current isolate and zone. | 53 // Quick access to the current isolate and zone. |
| 52 #define I (isolate()) | 54 #define I (isolate()) |
| 53 #define Z (zone()) | 55 #define Z (zone()) |
| 54 | 56 |
| 55 | 57 |
| 56 #if defined(DEBUG) | 58 #if defined(DEBUG) |
| 57 class TraceParser : public ValueObject { | 59 class TraceParser : public ValueObject { |
| 58 public: | 60 public: |
| 59 TraceParser(intptr_t token_pos, | 61 TraceParser(intptr_t token_pos, |
| (...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 165 | 167 |
| 166 void ParsedFunction::SetRegExpCompileData( | 168 void ParsedFunction::SetRegExpCompileData( |
| 167 RegExpCompileData* regexp_compile_data) { | 169 RegExpCompileData* regexp_compile_data) { |
| 168 ASSERT(regexp_compile_data_ == NULL); | 170 ASSERT(regexp_compile_data_ == NULL); |
| 169 ASSERT(regexp_compile_data != NULL); | 171 ASSERT(regexp_compile_data != NULL); |
| 170 regexp_compile_data_ = regexp_compile_data; | 172 regexp_compile_data_ = regexp_compile_data; |
| 171 } | 173 } |
| 172 | 174 |
| 173 | 175 |
| 174 void ParsedFunction::AddDeferredPrefix(const LibraryPrefix& prefix) { | 176 void ParsedFunction::AddDeferredPrefix(const LibraryPrefix& prefix) { |
| 177 // 'deferred_prefixes_' are used to invalidate code, but no invalidation is |
| 178 // needed if --load_deferred_eagerly. |
| 179 ASSERT(!FLAG_load_deferred_eagerly); |
| 175 ASSERT(prefix.is_deferred_load()); | 180 ASSERT(prefix.is_deferred_load()); |
| 176 ASSERT(!prefix.is_loaded()); | 181 ASSERT(!prefix.is_loaded()); |
| 177 for (intptr_t i = 0; i < deferred_prefixes_->length(); i++) { | 182 for (intptr_t i = 0; i < deferred_prefixes_->length(); i++) { |
| 178 if ((*deferred_prefixes_)[i]->raw() == prefix.raw()) { | 183 if ((*deferred_prefixes_)[i]->raw() == prefix.raw()) { |
| 179 return; | 184 return; |
| 180 } | 185 } |
| 181 } | 186 } |
| 182 deferred_prefixes_->Add(&LibraryPrefix::ZoneHandle(Z, prefix.raw())); | 187 deferred_prefixes_->Add(&LibraryPrefix::ZoneHandle(Z, prefix.raw())); |
| 183 } | 188 } |
| 184 | 189 |
| (...skipping 9846 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 10031 SequenceNode* sequence = new SequenceNode(sequence_pos, scope); | 10036 SequenceNode* sequence = new SequenceNode(sequence_pos, scope); |
| 10032 if (node != NULL) { | 10037 if (node != NULL) { |
| 10033 sequence->Add(node); | 10038 sequence->Add(node); |
| 10034 } | 10039 } |
| 10035 return sequence; | 10040 return sequence; |
| 10036 } | 10041 } |
| 10037 return node->AsSequenceNode(); | 10042 return node->AsSequenceNode(); |
| 10038 } | 10043 } |
| 10039 | 10044 |
| 10040 | 10045 |
| 10041 AstNode* Parser::ThrowTypeError(intptr_t type_pos, const AbstractType& type) { | 10046 // Call _throwNewIfNotLoaded if prefix is not NULL, otherwise call _throwNew. |
| 10047 AstNode* Parser::ThrowTypeError(intptr_t type_pos, const AbstractType& type, |
| 10048 LibraryPrefix* prefix) { |
| 10042 ArgumentListNode* arguments = new(Z) ArgumentListNode(type_pos); | 10049 ArgumentListNode* arguments = new(Z) ArgumentListNode(type_pos); |
| 10050 |
| 10051 String& method_name = String::Handle(Z); |
| 10052 if (prefix == NULL) { |
| 10053 method_name = Library::PrivateCoreLibName(Symbols::ThrowNew()).raw(); |
| 10054 } else { |
| 10055 arguments->Add(new(Z) LiteralNode(type_pos, *prefix)); |
| 10056 method_name = Library::PrivateCoreLibName( |
| 10057 Symbols::ThrowNewIfNotLoaded()).raw(); |
| 10058 } |
| 10043 // Location argument. | 10059 // Location argument. |
| 10044 arguments->Add(new(Z) LiteralNode( | 10060 arguments->Add(new(Z) LiteralNode( |
| 10045 type_pos, Integer::ZoneHandle(Z, Integer::New(type_pos)))); | 10061 type_pos, Integer::ZoneHandle(Z, Integer::New(type_pos)))); |
| 10046 // Src value argument. | 10062 // Src value argument. |
| 10047 arguments->Add(new(Z) LiteralNode(type_pos, Instance::ZoneHandle(Z))); | 10063 arguments->Add(new(Z) LiteralNode(type_pos, Instance::ZoneHandle(Z))); |
| 10048 // Dst type name argument. | 10064 // Dst type name argument. |
| 10049 arguments->Add(new(Z) LiteralNode(type_pos, Symbols::Malformed())); | 10065 arguments->Add(new(Z) LiteralNode(type_pos, Symbols::Malformed())); |
| 10050 // Dst name argument. | 10066 // Dst name argument. |
| 10051 arguments->Add(new(Z) LiteralNode(type_pos, Symbols::Empty())); | 10067 arguments->Add(new(Z) LiteralNode(type_pos, Symbols::Empty())); |
| 10052 // Malformed type error or malbounded type error. | 10068 // Malformed type error or malbounded type error. |
| 10053 const Error& error = Error::Handle(Z, type.error()); | 10069 const Error& error = Error::Handle(Z, type.error()); |
| 10054 ASSERT(!error.IsNull()); | 10070 ASSERT(!error.IsNull()); |
| 10055 arguments->Add(new(Z) LiteralNode(type_pos, String::ZoneHandle(Z, | 10071 arguments->Add(new(Z) LiteralNode(type_pos, String::ZoneHandle(Z, |
| 10056 Symbols::New(error.ToErrorCString())))); | 10072 Symbols::New(error.ToErrorCString())))); |
| 10057 return MakeStaticCall(Symbols::TypeError(), | 10073 return MakeStaticCall(Symbols::TypeError(), method_name, arguments); |
| 10058 Library::PrivateCoreLibName(Symbols::ThrowNew()), | |
| 10059 arguments); | |
| 10060 } | 10074 } |
| 10061 | 10075 |
| 10062 | 10076 |
| 10077 // Call _throwNewIfNotLoaded if prefix is not NULL, otherwise call _throwNew. |
| 10063 AstNode* Parser::ThrowNoSuchMethodError(intptr_t call_pos, | 10078 AstNode* Parser::ThrowNoSuchMethodError(intptr_t call_pos, |
| 10064 const Class& cls, | 10079 const Class& cls, |
| 10065 const String& function_name, | 10080 const String& function_name, |
| 10066 ArgumentListNode* function_arguments, | 10081 ArgumentListNode* function_arguments, |
| 10067 InvocationMirror::Call im_call, | 10082 InvocationMirror::Call im_call, |
| 10068 InvocationMirror::Type im_type, | 10083 InvocationMirror::Type im_type, |
| 10069 const Function* func) { | 10084 const Function* func, |
| 10085 const LibraryPrefix* prefix) { |
| 10070 ArgumentListNode* arguments = new(Z) ArgumentListNode(call_pos); | 10086 ArgumentListNode* arguments = new(Z) ArgumentListNode(call_pos); |
| 10087 |
| 10088 String& method_name = String::Handle(Z); |
| 10089 if (prefix == NULL) { |
| 10090 method_name = Library::PrivateCoreLibName(Symbols::ThrowNew()).raw(); |
| 10091 } else { |
| 10092 arguments->Add(new(Z) LiteralNode(call_pos, *prefix)); |
| 10093 method_name = Library::PrivateCoreLibName( |
| 10094 Symbols::ThrowNewIfNotLoaded()).raw(); |
| 10095 } |
| 10071 // Object receiver. | 10096 // Object receiver. |
| 10072 // If the function is external and dynamic, pass the actual receiver, | 10097 // If the function is external and dynamic, pass the actual receiver, |
| 10073 // otherwise, pass a class literal of the unresolved method's owner. | 10098 // otherwise, pass a class literal of the unresolved method's owner. |
| 10074 if ((func != NULL) && !func->IsNull() && | 10099 if ((func != NULL) && !func->IsNull() && |
| 10075 func->is_external() && !func->is_static()) { | 10100 func->is_external() && !func->is_static()) { |
| 10076 arguments->Add(LoadReceiver(func->token_pos())); | 10101 arguments->Add(LoadReceiver(func->token_pos())); |
| 10077 } else { | 10102 } else { |
| 10078 Type& type = Type::ZoneHandle(Z, | 10103 Type& type = Type::ZoneHandle(Z, |
| 10079 Type::New(cls, TypeArguments::Handle(Z), call_pos, Heap::kOld)); | 10104 Type::New(cls, TypeArguments::Handle(Z), call_pos, Heap::kOld)); |
| 10080 type ^= ClassFinalizer::FinalizeType( | 10105 type ^= ClassFinalizer::FinalizeType( |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 10133 // descriptive string here and pass it as the only element of the | 10158 // descriptive string here and pass it as the only element of the |
| 10134 // "existingArgumentNames" array of the NoSuchMethodError constructor. | 10159 // "existingArgumentNames" array of the NoSuchMethodError constructor. |
| 10135 // TODO(13471): Separate the implementations of NoSuchMethodError | 10160 // TODO(13471): Separate the implementations of NoSuchMethodError |
| 10136 // between dart2js and VM. Update the constructor to accept a string | 10161 // between dart2js and VM. Update the constructor to accept a string |
| 10137 // describing the formal parameters of an incompatible call target. | 10162 // describing the formal parameters of an incompatible call target. |
| 10138 array = Array::New(1, Heap::kOld); | 10163 array = Array::New(1, Heap::kOld); |
| 10139 array.SetAt(0, String::Handle(Z, function.UserVisibleFormalParameters())); | 10164 array.SetAt(0, String::Handle(Z, function.UserVisibleFormalParameters())); |
| 10140 } | 10165 } |
| 10141 arguments->Add(new(Z) LiteralNode(call_pos, array)); | 10166 arguments->Add(new(Z) LiteralNode(call_pos, array)); |
| 10142 | 10167 |
| 10143 return MakeStaticCall(Symbols::NoSuchMethodError(), | 10168 return MakeStaticCall(Symbols::NoSuchMethodError(), method_name, arguments); |
| 10144 Library::PrivateCoreLibName(Symbols::ThrowNew()), | |
| 10145 arguments); | |
| 10146 } | 10169 } |
| 10147 | 10170 |
| 10148 | 10171 |
| 10149 AstNode* Parser::ParseBinaryExpr(int min_preced) { | 10172 AstNode* Parser::ParseBinaryExpr(int min_preced) { |
| 10150 TRACE_PARSER("ParseBinaryExpr"); | 10173 TRACE_PARSER("ParseBinaryExpr"); |
| 10151 ASSERT(min_preced >= Token::Precedence(Token::kIFNULL)); | 10174 ASSERT(min_preced >= Token::Precedence(Token::kIFNULL)); |
| 10152 AstNode* left_operand = ParseUnaryExpr(); | 10175 AstNode* left_operand = ParseUnaryExpr(); |
| 10153 if (left_operand->IsPrimaryNode() && | 10176 if (left_operand->IsPrimaryNode() && |
| 10154 (left_operand->AsPrimaryNode()->IsSuper())) { | 10177 (left_operand->AsPrimaryNode()->IsSuper())) { |
| 10155 ReportError(left_operand->token_pos(), "illegal use of 'super'"); | 10178 ReportError(left_operand->token_pos(), "illegal use of 'super'"); |
| (...skipping 1653 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11809 if (ident.CharAt(0) == Library::kPrivateIdentifierStart) { | 11832 if (ident.CharAt(0) == Library::kPrivateIdentifierStart) { |
| 11810 // Private names are not exported by libraries. The name mangling | 11833 // Private names are not exported by libraries. The name mangling |
| 11811 // of private names with a library-specific suffix usually ensures | 11834 // of private names with a library-specific suffix usually ensures |
| 11812 // that _x in library A is not found when looked up from library B. | 11835 // that _x in library A is not found when looked up from library B. |
| 11813 // In the pathological case where a library imports itself with | 11836 // In the pathological case where a library imports itself with |
| 11814 // a prefix, the name mangling would not help in hiding the private | 11837 // a prefix, the name mangling would not help in hiding the private |
| 11815 // name, so we need to explicitly reject private names here. | 11838 // name, so we need to explicitly reject private names here. |
| 11816 return NULL; | 11839 return NULL; |
| 11817 } | 11840 } |
| 11818 Object& obj = Object::Handle(Z); | 11841 Object& obj = Object::Handle(Z); |
| 11819 if (prefix.is_loaded()) { | 11842 if (prefix.is_loaded() || FLAG_load_deferred_eagerly) { |
| 11820 obj = prefix.LookupObject(ident); | 11843 obj = prefix.LookupObject(ident); |
| 11821 } else { | 11844 } else { |
| 11822 // Remember that this function depends on an import prefix of an | 11845 // Remember that this function depends on an import prefix of an |
| 11823 // unloaded deferred library. Note that parsed_function() can be | 11846 // unloaded deferred library. Note that parsed_function() can be |
| 11824 // NULL when parsing expressions outside the scope of a function. | 11847 // NULL when parsing expressions outside the scope of a function. |
| 11825 if (parsed_function() != NULL) { | 11848 if (parsed_function() != NULL) { |
| 11826 parsed_function()->AddDeferredPrefix(prefix); | 11849 parsed_function()->AddDeferredPrefix(prefix); |
| 11827 } | 11850 } |
| 11828 } | 11851 } |
| 11829 const bool is_deferred = prefix.is_deferred_load(); | 11852 const bool is_deferred = prefix.is_deferred_load(); |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 11945 current_class(), type, ClassFinalizer::kCanonicalize); | 11968 current_class(), type, ClassFinalizer::kCanonicalize); |
| 11946 // Type may be malbounded, but not malformed. | 11969 // Type may be malbounded, but not malformed. |
| 11947 ASSERT(!type.IsMalformed()); | 11970 ASSERT(!type.IsMalformed()); |
| 11948 resolved = new(Z) TypeNode(primary_pos, type); | 11971 resolved = new(Z) TypeNode(primary_pos, type); |
| 11949 } | 11972 } |
| 11950 } | 11973 } |
| 11951 return resolved; | 11974 return resolved; |
| 11952 } | 11975 } |
| 11953 | 11976 |
| 11954 | 11977 |
| 11955 // Parses type = [ident "."] ident ["<" type { "," type } ">"], then resolve and | |
| 11956 // finalize it according to the given type finalization mode. | |
| 11957 RawAbstractType* Parser::ParseType( | 11978 RawAbstractType* Parser::ParseType( |
| 11958 ClassFinalizer::FinalizationKind finalization, | 11979 ClassFinalizer::FinalizationKind finalization, |
| 11959 bool allow_deferred_type, | 11980 bool allow_deferred_type, |
| 11960 bool consume_unresolved_prefix) { | 11981 bool consume_unresolved_prefix) { |
| 11982 LibraryPrefix& prefix = LibraryPrefix::Handle(Z); |
| 11983 return ParseType(finalization, allow_deferred_type, |
| 11984 consume_unresolved_prefix, &prefix); |
| 11985 } |
| 11986 |
| 11987 // Parses type = [ident "."] ident ["<" type { "," type } ">"], then resolve and |
| 11988 // finalize it according to the given type finalization mode. Returns prefix. |
| 11989 RawAbstractType* Parser::ParseType( |
| 11990 ClassFinalizer::FinalizationKind finalization, |
| 11991 bool allow_deferred_type, |
| 11992 bool consume_unresolved_prefix, |
| 11993 LibraryPrefix* prefix) { |
| 11961 TRACE_PARSER("ParseType"); | 11994 TRACE_PARSER("ParseType"); |
| 11962 CheckToken(Token::kIDENT, "type name expected"); | 11995 CheckToken(Token::kIDENT, "type name expected"); |
| 11963 intptr_t ident_pos = TokenPos(); | 11996 intptr_t ident_pos = TokenPos(); |
| 11964 LibraryPrefix& prefix = LibraryPrefix::Handle(Z); | |
| 11965 String& type_name = String::Handle(Z); | 11997 String& type_name = String::Handle(Z); |
| 11966 | 11998 |
| 11967 if (finalization == ClassFinalizer::kIgnore) { | 11999 if (finalization == ClassFinalizer::kIgnore) { |
| 11968 if (!is_top_level_ && (current_block_ != NULL)) { | 12000 if (!is_top_level_ && (current_block_ != NULL)) { |
| 11969 // Add the library prefix or type class name to the list of referenced | 12001 // Add the library prefix or type class name to the list of referenced |
| 11970 // names of this scope, even if the type is ignored. | 12002 // names of this scope, even if the type is ignored. |
| 11971 current_block_->scope->AddReferencedName(TokenPos(), *CurrentLiteral()); | 12003 current_block_->scope->AddReferencedName(TokenPos(), *CurrentLiteral()); |
| 11972 } | 12004 } |
| 11973 SkipQualIdent(); | 12005 SkipQualIdent(); |
| 11974 } else { | 12006 } else { |
| 11975 prefix = ParsePrefix(); | 12007 *prefix = ParsePrefix(); |
| 11976 type_name = CurrentLiteral()->raw(); | 12008 type_name = CurrentLiteral()->raw(); |
| 11977 ConsumeToken(); | 12009 ConsumeToken(); |
| 11978 | 12010 |
| 11979 // Check whether we have a malformed qualified type name if the caller | 12011 // Check whether we have a malformed qualified type name if the caller |
| 11980 // requests to consume unresolved prefix names: | 12012 // requests to consume unresolved prefix names: |
| 11981 // If we didn't see a valid prefix but the identifier is followed by | 12013 // If we didn't see a valid prefix but the identifier is followed by |
| 11982 // a period and another identifier, consume the qualified identifier | 12014 // a period and another identifier, consume the qualified identifier |
| 11983 // and create a malformed type. | 12015 // and create a malformed type. |
| 11984 if (consume_unresolved_prefix && | 12016 if (consume_unresolved_prefix && |
| 11985 prefix.IsNull() && | 12017 prefix->IsNull() && |
| 11986 (CurrentToken() == Token::kPERIOD) && | 12018 (CurrentToken() == Token::kPERIOD) && |
| 11987 (Token::IsIdentifier(LookaheadToken(1)))) { | 12019 (Token::IsIdentifier(LookaheadToken(1)))) { |
| 11988 if (!is_top_level_ && (current_block_ != NULL)) { | 12020 if (!is_top_level_ && (current_block_ != NULL)) { |
| 11989 // Add the unresolved prefix name to the list of referenced | 12021 // Add the unresolved prefix name to the list of referenced |
| 11990 // names of this scope. | 12022 // names of this scope. |
| 11991 current_block_->scope->AddReferencedName(TokenPos(), type_name); | 12023 current_block_->scope->AddReferencedName(TokenPos(), type_name); |
| 11992 } | 12024 } |
| 11993 ConsumeToken(); // Period token. | 12025 ConsumeToken(); // Period token. |
| 11994 ASSERT(IsIdentifier()); | 12026 ASSERT(IsIdentifier()); |
| 11995 String& qualified_name = String::Handle(Z, type_name.raw()); | 12027 String& qualified_name = String::Handle(Z, type_name.raw()); |
| 11996 qualified_name = String::Concat(qualified_name, Symbols::Dot()); | 12028 qualified_name = String::Concat(qualified_name, Symbols::Dot()); |
| 11997 qualified_name = String::Concat(qualified_name, *CurrentLiteral()); | 12029 qualified_name = String::Concat(qualified_name, *CurrentLiteral()); |
| 11998 ConsumeToken(); | 12030 ConsumeToken(); |
| 11999 // The type is malformed. Skip over its type arguments. | 12031 // The type is malformed. Skip over its type arguments. |
| 12000 ParseTypeArguments(ClassFinalizer::kIgnore); | 12032 ParseTypeArguments(ClassFinalizer::kIgnore); |
| 12001 return ClassFinalizer::NewFinalizedMalformedType( | 12033 return ClassFinalizer::NewFinalizedMalformedType( |
| 12002 Error::Handle(Z), // No previous error. | 12034 Error::Handle(Z), // No previous error. |
| 12003 script_, | 12035 script_, |
| 12004 ident_pos, | 12036 ident_pos, |
| 12005 "qualified name '%s' does not refer to a type", | 12037 "qualified name '%s' does not refer to a type", |
| 12006 qualified_name.ToCString()); | 12038 qualified_name.ToCString()); |
| 12007 } | 12039 } |
| 12008 | 12040 |
| 12009 // If parsing inside a local scope, check whether the type name | 12041 // If parsing inside a local scope, check whether the type name |
| 12010 // is shadowed by a local declaration. | 12042 // is shadowed by a local declaration. |
| 12011 if (!is_top_level_ && | 12043 if (!is_top_level_ && |
| 12012 (prefix.IsNull()) && | 12044 (prefix->IsNull()) && |
| 12013 ResolveIdentInLocalScope(ident_pos, type_name, NULL)) { | 12045 ResolveIdentInLocalScope(ident_pos, type_name, NULL)) { |
| 12014 // The type is malformed. Skip over its type arguments. | 12046 // The type is malformed. Skip over its type arguments. |
| 12015 ParseTypeArguments(ClassFinalizer::kIgnore); | 12047 ParseTypeArguments(ClassFinalizer::kIgnore); |
| 12016 return ClassFinalizer::NewFinalizedMalformedType( | 12048 return ClassFinalizer::NewFinalizedMalformedType( |
| 12017 Error::Handle(Z), // No previous error. | 12049 Error::Handle(Z), // No previous error. |
| 12018 script_, | 12050 script_, |
| 12019 ident_pos, | 12051 ident_pos, |
| 12020 "using '%s' in this context is invalid", | 12052 "using '%s' in this context is invalid", |
| 12021 type_name.ToCString()); | 12053 type_name.ToCString()); |
| 12022 } | 12054 } |
| 12023 if (!prefix.IsNull() && prefix.is_deferred_load()) { | 12055 if (!FLAG_load_deferred_eagerly && |
| 12056 !prefix->IsNull() && prefix->is_deferred_load()) { |
| 12024 // If deferred prefixes are allowed but it is not yet loaded, | 12057 // If deferred prefixes are allowed but it is not yet loaded, |
| 12025 // remember that this function depends on the prefix. | 12058 // remember that this function depends on the prefix. |
| 12026 if (allow_deferred_type && !prefix.is_loaded()) { | 12059 if (allow_deferred_type && !prefix->is_loaded()) { |
| 12027 if (parsed_function() != NULL) { | 12060 if (parsed_function() != NULL) { |
| 12028 parsed_function()->AddDeferredPrefix(prefix); | 12061 parsed_function()->AddDeferredPrefix(*prefix); |
| 12029 } | 12062 } |
| 12030 } | 12063 } |
| 12031 // If the deferred prefixes are not allowed, or if the prefix is not yet | 12064 // If the deferred prefixes are not allowed, or if the prefix is not yet |
| 12032 // loaded when finalization is requested, return a malformed type. | 12065 // loaded when finalization is requested, return a malformed type. |
| 12033 // Otherwise, handle resolution below, as needed. | 12066 // Otherwise, handle resolution below, as needed. |
| 12034 if (!allow_deferred_type || | 12067 if (!allow_deferred_type || |
| 12035 (!prefix.is_loaded() | 12068 (!prefix->is_loaded() |
| 12036 && (finalization > ClassFinalizer::kResolveTypeParameters))) { | 12069 && (finalization > ClassFinalizer::kResolveTypeParameters))) { |
| 12037 ParseTypeArguments(ClassFinalizer::kIgnore); | 12070 ParseTypeArguments(ClassFinalizer::kIgnore); |
| 12038 return ClassFinalizer::NewFinalizedMalformedType( | 12071 return ClassFinalizer::NewFinalizedMalformedType( |
| 12039 Error::Handle(Z), // No previous error. | 12072 Error::Handle(Z), // No previous error. |
| 12040 script_, | 12073 script_, |
| 12041 ident_pos, | 12074 ident_pos, |
| 12042 !prefix.is_loaded() | 12075 !prefix->is_loaded() |
| 12043 ? "deferred type '%s.%s' is not yet loaded" | 12076 ? "deferred type '%s.%s' is not yet loaded" |
| 12044 : "using deferred type '%s.%s' is invalid", | 12077 : "using deferred type '%s.%s' is invalid", |
| 12045 String::Handle(Z, prefix.name()).ToCString(), | 12078 String::Handle(Z, prefix->name()).ToCString(), |
| 12046 type_name.ToCString()); | 12079 type_name.ToCString()); |
| 12047 } | 12080 } |
| 12048 } | 12081 } |
| 12049 } | 12082 } |
| 12050 Object& type_class = Object::Handle(Z); | 12083 Object& type_class = Object::Handle(Z); |
| 12051 // Leave type_class as null if type finalization mode is kIgnore. | 12084 // Leave type_class as null if type finalization mode is kIgnore. |
| 12052 if (finalization != ClassFinalizer::kIgnore) { | 12085 if (finalization != ClassFinalizer::kIgnore) { |
| 12053 type_class = UnresolvedClass::New(prefix, type_name, ident_pos); | 12086 type_class = UnresolvedClass::New(*prefix, type_name, ident_pos); |
| 12054 } | 12087 } |
| 12055 TypeArguments& type_arguments = TypeArguments::Handle( | 12088 TypeArguments& type_arguments = TypeArguments::Handle( |
| 12056 Z, ParseTypeArguments(finalization)); | 12089 Z, ParseTypeArguments(finalization)); |
| 12057 if (finalization == ClassFinalizer::kIgnore) { | 12090 if (finalization == ClassFinalizer::kIgnore) { |
| 12058 return Type::DynamicType(); | 12091 return Type::DynamicType(); |
| 12059 } | 12092 } |
| 12060 AbstractType& type = AbstractType::Handle( | 12093 AbstractType& type = AbstractType::Handle( |
| 12061 Z, Type::New(type_class, type_arguments, ident_pos)); | 12094 Z, Type::New(type_class, type_arguments, ident_pos)); |
| 12062 if (finalization >= ClassFinalizer::kResolveTypeParameters) { | 12095 if (finalization >= ClassFinalizer::kResolveTypeParameters) { |
| 12063 ResolveTypeFromClass(current_class(), finalization, &type); | 12096 ResolveTypeFromClass(current_class(), finalization, &type); |
| (...skipping 528 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 12592 ASSERT((op_kind == Token::kNEW) || (op_kind == Token::kCONST)); | 12625 ASSERT((op_kind == Token::kNEW) || (op_kind == Token::kCONST)); |
| 12593 bool is_const = (op_kind == Token::kCONST); | 12626 bool is_const = (op_kind == Token::kCONST); |
| 12594 if (!IsIdentifier()) { | 12627 if (!IsIdentifier()) { |
| 12595 ReportError("type name expected"); | 12628 ReportError("type name expected"); |
| 12596 } | 12629 } |
| 12597 intptr_t type_pos = TokenPos(); | 12630 intptr_t type_pos = TokenPos(); |
| 12598 // Can't allocate const objects of a deferred type. | 12631 // Can't allocate const objects of a deferred type. |
| 12599 const bool allow_deferred_type = !is_const; | 12632 const bool allow_deferred_type = !is_const; |
| 12600 const bool consume_unresolved_prefix = (LookaheadToken(3) == Token::kLT) || | 12633 const bool consume_unresolved_prefix = (LookaheadToken(3) == Token::kLT) || |
| 12601 (LookaheadToken(3) == Token::kPERIOD); | 12634 (LookaheadToken(3) == Token::kPERIOD); |
| 12635 LibraryPrefix& prefix = LibraryPrefix::ZoneHandle(Z); |
| 12602 AbstractType& type = AbstractType::Handle(Z, | 12636 AbstractType& type = AbstractType::Handle(Z, |
| 12603 ParseType(ClassFinalizer::kCanonicalizeWellFormed, | 12637 ParseType(ClassFinalizer::kCanonicalizeWellFormed, |
| 12604 allow_deferred_type, | 12638 allow_deferred_type, |
| 12605 consume_unresolved_prefix)); | 12639 consume_unresolved_prefix, |
| 12640 &prefix)); |
| 12641 if (FLAG_load_deferred_eagerly && |
| 12642 !prefix.IsNull() && prefix.is_deferred_load() && !prefix.is_loaded()) { |
| 12643 // Add runtime check. |
| 12644 Type& malformed_type = Type::Handle(Z); |
| 12645 malformed_type = ClassFinalizer::NewFinalizedMalformedType( |
| 12646 Error::Handle(Z), // No previous error. |
| 12647 script_, |
| 12648 type_pos, |
| 12649 "deferred type '%s.%s' is not yet loaded", |
| 12650 String::Handle(Z, prefix.name()).ToCString(), |
| 12651 String::Handle(type.Name()).ToCString()); |
| 12652 // Note: Adding a statement to current block is a hack, parsing an |
| 12653 // expression should have no side-effect. |
| 12654 current_block_->statements->Add( |
| 12655 ThrowTypeError(type_pos, malformed_type, &prefix)); |
| 12656 } |
| 12606 // In case the type is malformed, throw a dynamic type error after finishing | 12657 // In case the type is malformed, throw a dynamic type error after finishing |
| 12607 // parsing the instance creation expression. | 12658 // parsing the instance creation expression. |
| 12608 if (!type.IsMalformed() && (type.IsTypeParameter() || type.IsDynamicType())) { | 12659 if (!type.IsMalformed() && (type.IsTypeParameter() || type.IsDynamicType())) { |
| 12609 // Replace the type with a malformed type. | 12660 // Replace the type with a malformed type. |
| 12610 type = ClassFinalizer::NewFinalizedMalformedType( | 12661 type = ClassFinalizer::NewFinalizedMalformedType( |
| 12611 Error::Handle(Z), // No previous error. | 12662 Error::Handle(Z), // No previous error. |
| 12612 script_, | 12663 script_, |
| 12613 type_pos, | 12664 type_pos, |
| 12614 "%s'%s' cannot be instantiated", | 12665 "%s'%s' cannot be instantiated", |
| 12615 type.IsTypeParameter() ? "type parameter " : "", | 12666 type.IsTypeParameter() ? "type parameter " : "", |
| (...skipping 460 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 13076 CurrentToken() == Token::kLPAREN ? | 13127 CurrentToken() == Token::kLPAREN ? |
| 13077 InvocationMirror::kMethod : InvocationMirror::kGetter; | 13128 InvocationMirror::kMethod : InvocationMirror::kGetter; |
| 13078 primary = ThrowNoSuchMethodError(qual_ident_pos, | 13129 primary = ThrowNoSuchMethodError(qual_ident_pos, |
| 13079 current_class(), | 13130 current_class(), |
| 13080 qualified_name, | 13131 qualified_name, |
| 13081 NULL, // No arguments. | 13132 NULL, // No arguments. |
| 13082 InvocationMirror::kTopLevel, | 13133 InvocationMirror::kTopLevel, |
| 13083 call_type, | 13134 call_type, |
| 13084 NULL); // No existing function. | 13135 NULL); // No existing function. |
| 13085 } | 13136 } |
| 13137 } else if (FLAG_load_deferred_eagerly && prefix.is_deferred_load()) { |
| 13138 // primary != NULL. |
| 13139 String& qualified_name = String::ZoneHandle(Z, prefix.name()); |
| 13140 qualified_name = String::Concat(qualified_name, Symbols::Dot()); |
| 13141 qualified_name = String::Concat(qualified_name, ident); |
| 13142 qualified_name = Symbols::New(qualified_name); |
| 13143 InvocationMirror::Type call_type = |
| 13144 CurrentToken() == Token::kLPAREN ? |
| 13145 InvocationMirror::kMethod : InvocationMirror::kGetter; |
| 13146 // Note: Adding a statement to current block is a hack, parsing an |
| 13147 // espression should have no side-effect. |
| 13148 current_block_->statements->Add(ThrowNoSuchMethodError( |
| 13149 qual_ident_pos, |
| 13150 current_class(), |
| 13151 qualified_name, |
| 13152 NULL, // No arguments. |
| 13153 InvocationMirror::kTopLevel, |
| 13154 call_type, |
| 13155 NULL, // No existing function. |
| 13156 &prefix)); |
| 13086 } | 13157 } |
| 13087 } | 13158 } |
| 13088 ASSERT(primary != NULL); | 13159 ASSERT(primary != NULL); |
| 13089 } else if (token == Token::kTHIS) { | 13160 } else if (token == Token::kTHIS) { |
| 13090 LocalVariable* local = LookupLocalScope(Symbols::This()); | 13161 LocalVariable* local = LookupLocalScope(Symbols::This()); |
| 13091 if (local == NULL) { | 13162 if (local == NULL) { |
| 13092 ReportError("receiver 'this' is not in scope"); | 13163 ReportError("receiver 'this' is not in scope"); |
| 13093 } | 13164 } |
| 13094 primary = new(Z) LoadLocalNode(TokenPos(), local); | 13165 primary = new(Z) LoadLocalNode(TokenPos(), local); |
| 13095 ConsumeToken(); | 13166 ConsumeToken(); |
| (...skipping 460 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 13556 void Parser::SkipQualIdent() { | 13627 void Parser::SkipQualIdent() { |
| 13557 ASSERT(IsIdentifier()); | 13628 ASSERT(IsIdentifier()); |
| 13558 ConsumeToken(); | 13629 ConsumeToken(); |
| 13559 if (CurrentToken() == Token::kPERIOD) { | 13630 if (CurrentToken() == Token::kPERIOD) { |
| 13560 ConsumeToken(); // Consume the kPERIOD token. | 13631 ConsumeToken(); // Consume the kPERIOD token. |
| 13561 ExpectIdentifier("identifier expected after '.'"); | 13632 ExpectIdentifier("identifier expected after '.'"); |
| 13562 } | 13633 } |
| 13563 } | 13634 } |
| 13564 | 13635 |
| 13565 } // namespace dart | 13636 } // namespace dart |
| OLD | NEW |