Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(286)

Side by Side Diff: runtime/vm/parser.cc

Issue 226953002: Implement deferred constant support (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 6 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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 1989 matching lines...) Expand 10 before | Expand all | Expand 10 after
2000 } 2000 }
2001 super_op = new StaticCallNode(operator_pos, super_operator, op_arguments); 2001 super_op = new StaticCallNode(operator_pos, super_operator, op_arguments);
2002 if (negate_result) { 2002 if (negate_result) {
2003 super_op = new UnaryOpNode(operator_pos, Token::kNOT, super_op); 2003 super_op = new UnaryOpNode(operator_pos, Token::kNOT, super_op);
2004 } 2004 }
2005 } 2005 }
2006 return super_op; 2006 return super_op;
2007 } 2007 }
2008 2008
2009 2009
2010 AstNode* Parser::CreateImplicitClosureNode(const Function& func, 2010 ClosureNode* Parser::CreateImplicitClosureNode(const Function& func,
2011 intptr_t token_pos, 2011 intptr_t token_pos,
2012 AstNode* receiver) { 2012 AstNode* receiver) {
2013 Function& implicit_closure_function = 2013 Function& implicit_closure_function =
2014 Function::ZoneHandle(func.ImplicitClosureFunction()); 2014 Function::ZoneHandle(func.ImplicitClosureFunction());
2015 if (receiver != NULL) { 2015 if (receiver != NULL) {
2016 // If we create an implicit instance closure from inside a closure of a 2016 // If we create an implicit instance closure from inside a closure of a
2017 // parameterized class, make sure that the receiver is captured as 2017 // parameterized class, make sure that the receiver is captured as
2018 // instantiator. 2018 // instantiator.
2019 if (current_block_->scope->function_level() > 0) { 2019 if (current_block_->scope->function_level() > 0) {
2020 const Class& signature_class = Class::Handle( 2020 const Class& signature_class = Class::Handle(
2021 implicit_closure_function.signature_class()); 2021 implicit_closure_function.signature_class());
2022 if (signature_class.NumTypeParameters() > 0) { 2022 if (signature_class.NumTypeParameters() > 0) {
(...skipping 6010 matching lines...) Expand 10 before | Expand all | Expand 10 after
8033 ErrorMsg("expression expected after throw"); 8033 ErrorMsg("expression expected after throw");
8034 } 8034 }
8035 AstNode* expr = ParseExpr(require_compiletime_const, consume_cascades); 8035 AstNode* expr = ParseExpr(require_compiletime_const, consume_cascades);
8036 return new ThrowNode(expr_pos, expr, NULL); 8036 return new ThrowNode(expr_pos, expr, NULL);
8037 } 8037 }
8038 AstNode* expr = ParseConditionalExpr(); 8038 AstNode* expr = ParseConditionalExpr();
8039 if (!Token::IsAssignmentOperator(CurrentToken())) { 8039 if (!Token::IsAssignmentOperator(CurrentToken())) {
8040 if ((CurrentToken() == Token::kCASCADE) && consume_cascades) { 8040 if ((CurrentToken() == Token::kCASCADE) && consume_cascades) {
8041 return ParseCascades(expr); 8041 return ParseCascades(expr);
8042 } 8042 }
8043 expr = LiteralIfStaticConst(expr);
8044 if (require_compiletime_const) { 8043 if (require_compiletime_const) {
8045 expr = FoldConstExpr(expr_pos, expr); 8044 expr = FoldConstExpr(expr_pos, expr);
8045 } else {
8046 expr = LiteralIfStaticConst(expr);
8046 } 8047 }
8047 return expr; 8048 return expr;
8048 } 8049 }
8049 // Assignment expressions. 8050 // Assignment expressions.
8050 if (!IsLegalAssignableSyntax(expr, TokenPos())) { 8051 if (!IsLegalAssignableSyntax(expr, TokenPos())) {
8051 ErrorMsg(expr_pos, "expression is not assignable"); 8052 ErrorMsg(expr_pos, "expression is not assignable");
8052 } 8053 }
8053 const Token::Kind assignment_op = CurrentToken(); 8054 const Token::Kind assignment_op = CurrentToken();
8054 const intptr_t assignment_pos = TokenPos(); 8055 const intptr_t assignment_pos = TokenPos();
8055 ConsumeToken(); 8056 ConsumeToken();
(...skipping 329 matching lines...) Expand 10 before | Expand all | Expand 10 after
8385 // for a field (which may be defined in a subclass.) 8386 // for a field (which may be defined in a subclass.)
8386 // In metadata, an unresolved identifier cannot be a compile-time constant. 8387 // In metadata, an unresolved identifier cannot be a compile-time constant.
8387 String& name = String::CheckedZoneHandle(primary->primary().raw()); 8388 String& name = String::CheckedZoneHandle(primary->primary().raw());
8388 if (parsing_metadata_) { 8389 if (parsing_metadata_) {
8389 ErrorMsg(primary->token_pos(), 8390 ErrorMsg(primary->token_pos(),
8390 "unresolved identifier '%s' is not a compile-time constant", 8391 "unresolved identifier '%s' is not a compile-time constant",
8391 name.ToCString()); 8392 name.ToCString());
8392 } 8393 }
8393 if (current_function().is_static() || 8394 if (current_function().is_static() ||
8394 current_function().IsInFactoryScope()) { 8395 current_function().IsInFactoryScope()) {
8395 return new StaticGetterNode(primary->token_pos(), 8396 StaticGetterNode* getter =
8396 NULL, // No receiver. 8397 new StaticGetterNode(primary->token_pos(),
8397 false, // Not a super getter. 8398 NULL, // No receiver.
8398 Class::ZoneHandle(current_class().raw()), 8399 false, // Not a super getter.
8399 name); 8400 Class::ZoneHandle(current_class().raw()),
8401 name);
8402 getter->set_is_deferred(primary->is_deferred_reference());
8403 return getter;
8400 } else { 8404 } else {
8401 AstNode* receiver = LoadReceiver(primary->token_pos()); 8405 AstNode* receiver = LoadReceiver(primary->token_pos());
8402 return CallGetter(node->token_pos(), receiver, name); 8406 return CallGetter(node->token_pos(), receiver, name);
8403 } 8407 }
8404 } 8408 }
8405 return primary; 8409 return primary;
8406 } 8410 }
8407 8411
8408 8412
8409 AstNode* Parser::LoadClosure(PrimaryNode* primary) { 8413 AstNode* Parser::LoadClosure(PrimaryNode* primary) {
8410 ASSERT(primary->primary().IsFunction()); 8414 ASSERT(primary->primary().IsFunction());
8411 AstNode* closure = NULL;
8412 const Function& func = 8415 const Function& func =
8413 Function::CheckedZoneHandle(primary->primary().raw()); 8416 Function::CheckedZoneHandle(primary->primary().raw());
8414 const String& funcname = String::ZoneHandle(func.name()); 8417 const String& funcname = String::ZoneHandle(func.name());
8415 if (func.is_static()) { 8418 if (func.is_static()) {
8416 // Static function access. 8419 // Static function access.
8417 closure = CreateImplicitClosureNode(func, primary->token_pos(), NULL); 8420 ClosureNode* closure =
8421 CreateImplicitClosureNode(func, primary->token_pos(), NULL);
8422 closure->set_is_deferred(primary->is_deferred_reference());
8423 return closure;
8418 } else { 8424 } else {
8419 // Instance function access. 8425 // Instance function access.
8420 if (parsing_metadata_) { 8426 if (parsing_metadata_) {
8421 ErrorMsg(primary->token_pos(), 8427 ErrorMsg(primary->token_pos(),
8422 "cannot access instance method '%s' from metadata", 8428 "cannot access instance method '%s' from metadata",
8423 funcname.ToCString()); 8429 funcname.ToCString());
8424 } 8430 }
8425 if (current_function().is_static() || 8431 if (current_function().is_static() ||
8426 current_function().IsInFactoryScope()) { 8432 current_function().IsInFactoryScope()) {
8427 ErrorMsg(primary->token_pos(), 8433 ErrorMsg(primary->token_pos(),
8428 "cannot access instance method '%s' from static method", 8434 "cannot access instance method '%s' from static method",
8429 funcname.ToCString()); 8435 funcname.ToCString());
8430 } 8436 }
8431 AstNode* receiver = LoadReceiver(primary->token_pos()); 8437 AstNode* receiver = LoadReceiver(primary->token_pos());
8432 closure = CallGetter(primary->token_pos(), receiver, funcname); 8438 return CallGetter(primary->token_pos(), receiver, funcname);
8433 } 8439 }
8434 return closure; 8440 UNREACHABLE();
8441 return NULL;
8435 } 8442 }
8436 8443
8437 8444
8438 AstNode* Parser::ParseSelectors(AstNode* primary, bool is_cascade) { 8445 AstNode* Parser::ParseSelectors(AstNode* primary, bool is_cascade) {
8439 AstNode* left = primary; 8446 AstNode* left = primary;
8440 while (true) { 8447 while (true) {
8441 AstNode* selector = NULL; 8448 AstNode* selector = NULL;
8442 if (CurrentToken() == Token::kPERIOD) { 8449 if (CurrentToken() == Token::kPERIOD) {
8443 ConsumeToken(); 8450 ConsumeToken();
8444 if (left->IsPrimaryNode()) { 8451 if (left->IsPrimaryNode()) {
(...skipping 808 matching lines...) Expand 10 before | Expand all | Expand 10 after
9253 if (prefix.is_loaded()) { 9260 if (prefix.is_loaded()) {
9254 obj = prefix.LookupObject(ident); 9261 obj = prefix.LookupObject(ident);
9255 } else { 9262 } else {
9256 // Remember that this function depends on an import prefix of an 9263 // Remember that this function depends on an import prefix of an
9257 // unloaded deferred library. Note that parsed_function() can be 9264 // unloaded deferred library. Note that parsed_function() can be
9258 // NULL when parsing expressions outside the scope of a function. 9265 // NULL when parsing expressions outside the scope of a function.
9259 if (parsed_function() != NULL) { 9266 if (parsed_function() != NULL) {
9260 parsed_function()->AddDeferredPrefix(prefix); 9267 parsed_function()->AddDeferredPrefix(prefix);
9261 } 9268 }
9262 } 9269 }
9270 const bool is_deferred = prefix.is_deferred_load();
9263 if (obj.IsNull()) { 9271 if (obj.IsNull()) {
9264 // Unresolved prefixed primary identifier. 9272 // Unresolved prefixed primary identifier.
9265 return NULL; 9273 return NULL;
9266 } else if (obj.IsClass()) { 9274 } else if (obj.IsClass()) {
9267 const Class& cls = Class::Cast(obj); 9275 const Class& cls = Class::Cast(obj);
9268 return new PrimaryNode(ident_pos, Class::ZoneHandle(cls.raw())); 9276 PrimaryNode* primary =
9277 new PrimaryNode(ident_pos, Class::ZoneHandle(cls.raw()));
9278 primary->set_is_deferred(is_deferred);
9279 return primary;
9269 } else if (obj.IsField()) { 9280 } else if (obj.IsField()) {
9270 const Field& field = Field::Cast(obj); 9281 const Field& field = Field::Cast(obj);
9271 ASSERT(field.is_static()); 9282 ASSERT(field.is_static());
9272 return GenerateStaticFieldLookup(field, ident_pos); 9283 AstNode* get_field = GenerateStaticFieldLookup(field, ident_pos);
9284 ASSERT(get_field != NULL);
9285 ASSERT(get_field->IsLoadStaticFieldNode() ||
9286 get_field->IsStaticGetterNode());
9287 if (get_field->IsLoadStaticFieldNode()) {
9288 get_field->AsLoadStaticFieldNode()->set_is_deferred(is_deferred);
9289 } else if (get_field->IsStaticGetterNode()) {
9290 get_field->AsStaticGetterNode()->set_is_deferred(is_deferred);
9291 }
9292 return get_field;
9273 } else if (obj.IsFunction()) { 9293 } else if (obj.IsFunction()) {
9274 const Function& func = Function::Cast(obj); 9294 const Function& func = Function::Cast(obj);
9275 ASSERT(func.is_static()); 9295 ASSERT(func.is_static());
9276 if (func.IsGetterFunction() || func.IsSetterFunction()) { 9296 if (func.IsGetterFunction() || func.IsSetterFunction()) {
9277 return new StaticGetterNode(ident_pos, 9297 StaticGetterNode* getter =
9278 /* receiver */ NULL, 9298 new StaticGetterNode(ident_pos,
9279 /* is_super_getter */ false, 9299 /* receiver */ NULL,
9280 Class::ZoneHandle(func.Owner()), 9300 /* is_super_getter */ false,
9281 ident); 9301 Class::ZoneHandle(func.Owner()),
9282 9302 ident);
9303 getter->set_is_deferred(is_deferred);
9304 return getter;
9283 } else { 9305 } else {
9284 return new PrimaryNode(ident_pos, Function::ZoneHandle(func.raw())); 9306 PrimaryNode* primary =
9307 new PrimaryNode(ident_pos, Function::ZoneHandle(func.raw()));
9308 primary->set_is_deferred(is_deferred);
9309 return primary;
9285 } 9310 }
9286 } 9311 }
9287 // All possible object types are handled above. 9312 // All possible object types are handled above.
9288 UNREACHABLE(); 9313 UNREACHABLE();
9289 return NULL; 9314 return NULL;
9290 } 9315 }
9291 9316
9292 9317
9293 // Resolve identifier. Issue an error message if 9318 // Resolve identifier. Issue an error message if
9294 // the ident refers to a method and allow_closure_names is false. 9319 // the ident refers to a method and allow_closure_names is false.
(...skipping 1585 matching lines...) Expand 10 before | Expand all | Expand 10 after
10880 void Parser::SkipQualIdent() { 10905 void Parser::SkipQualIdent() {
10881 ASSERT(IsIdentifier()); 10906 ASSERT(IsIdentifier());
10882 ConsumeToken(); 10907 ConsumeToken();
10883 if (CurrentToken() == Token::kPERIOD) { 10908 if (CurrentToken() == Token::kPERIOD) {
10884 ConsumeToken(); // Consume the kPERIOD token. 10909 ConsumeToken(); // Consume the kPERIOD token.
10885 ExpectIdentifier("identifier expected after '.'"); 10910 ExpectIdentifier("identifier expected after '.'");
10886 } 10911 }
10887 } 10912 }
10888 10913
10889 } // namespace dart 10914 } // namespace dart
OLDNEW
« runtime/vm/ast.h ('K') | « runtime/vm/parser.h ('k') | tests/language/language.status » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698