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

Unified Diff: runtime/vm/parser.cc

Issue 11232071: Ambiguous references do not necessarily cause compilation errors (issue 5736). (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 8 years, 2 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 side-by-side diff with in-line comments
Download patch
Index: runtime/vm/parser.cc
===================================================================
--- runtime/vm/parser.cc (revision 13985)
+++ runtime/vm/parser.cc (working copy)
@@ -2515,8 +2515,10 @@
if (type.IsTypeParameter() || type.IsDynamicType()) {
// Replace the type with a malformed type and compile a throw when called.
redirection_type = ClassFinalizer::NewFinalizedMalformedType(
+ Error::Handle(), // No previous error.
current_class(),
type_pos,
+ ClassFinalizer::kTryResolve, // No compile-time error.
"factory '%s' may not redirect to %s'%s'",
method->name->ToCString(),
type.IsTypeParameter() ? "type parameter " : "",
@@ -6446,6 +6448,19 @@
}
+RawError* Parser::FormatErrorMsg(const Script& script,
+ intptr_t token_pos,
+ const char* message_header,
+ const char* format, ...) {
+ va_list args;
+ va_start(args, format);
+ const Error& error = Error::Handle(
+ FormatError(script, token_pos, message_header, format, args));
+ va_end(args);
+ return error.raw();
+}
+
+
RawString* Parser::FormatMessage(const Script& script,
intptr_t token_pos,
const char* message_header,
@@ -7637,37 +7652,67 @@
if (ParsingStaticMember()) {
ASSERT(scope_class.raw() == current_class().raw());
*type = ClassFinalizer::NewFinalizedMalformedType(
+ Error::Handle(), // No previous error.
scope_class,
type->token_pos(),
+ finalization,
"type parameter '%s' cannot be referenced "
"from static member",
String::Handle(type_parameter.name()).ToCString());
return;
}
- // TODO(regis): Should this be a malformed type as well?
- // A type parameter cannot be parameterized, so report an error if
- // type arguments have previously been parsed.
+ // A type parameter cannot be parameterized, so make the type
+ // malformed if type arguments have previously been parsed.
hausner 2012/10/23 22:02:24 indentation
regis 2012/10/23 22:30:25 Strange. I do not see this bad indentation in the
if (!AbstractTypeArguments::Handle(type->arguments()).IsNull()) {
- ErrorMsg(type_parameter.token_pos(),
- "type parameter '%s' cannot be parameterized",
- String::Handle(type_parameter.name()).ToCString());
+ *type = ClassFinalizer::NewFinalizedMalformedType(
+ Error::Handle(), // No previous error.
+ scope_class,
+ type_parameter.token_pos(),
+ finalization,
+ "type parameter '%s' cannot be parameterized",
+ String::Handle(type_parameter.name()).ToCString());
+ return;
}
*type = type_parameter.raw();
return;
}
}
// Resolve classname in the scope of the current library.
+ Error& error = Error::Handle();
resolved_type_class =
ResolveClassInCurrentLibraryScope(unresolved_class.token_pos(),
- unresolved_class_name);
+ unresolved_class_name,
+ &error);
+ if (!error.IsNull()) {
+ *type = ClassFinalizer::NewFinalizedMalformedType(
+ error,
+ scope_class,
+ unresolved_class.token_pos(),
+ finalization,
+ "cannot resolve class '%s'",
+ unresolved_class_name.ToCString());
+ return;
+ }
} else {
LibraryPrefix& lib_prefix =
LibraryPrefix::Handle(unresolved_class.library_prefix());
// Resolve class name in the scope of the library prefix.
+ Error& error = Error::Handle();
resolved_type_class =
ResolveClassInPrefixScope(unresolved_class.token_pos(),
- lib_prefix,
- unresolved_class_name);
+ lib_prefix,
+ unresolved_class_name,
+ &error);
+ if (!error.IsNull()) {
+ *type = ClassFinalizer::NewFinalizedMalformedType(
+ error,
+ scope_class,
+ unresolved_class.token_pos(),
+ finalization,
+ "cannot resolve class '%s'",
+ unresolved_class_name.ToCString());
+ return;
+ }
}
// At this point, we can only have a parameterized_type.
Type& parameterized_type = Type::Handle();
@@ -8135,7 +8180,8 @@
// of the current library, but is defined in more than one imported
// library, i.e. if the name cannot be resolved unambiguously.
RawObject* Parser::ResolveNameInCurrentLibraryScope(intptr_t ident_pos,
- const String& name) {
+ const String& name,
+ Error* error) {
TRACE_PARSER("ResolveNameInCurrentLibraryScope");
Object& obj = Object::Handle(LookupNameInLibrary(library_, name));
if (obj.IsNull()) {
@@ -8152,20 +8198,30 @@
const Library& lib = Library::Handle(import.library());
if (!first_lib_url.IsNull()) {
// Found duplicate definition.
+ Error& ambiguous_ref_error = Error::Handle();
if (first_lib_url.raw() == lib.url()) {
- ErrorMsg(ident_pos,
- "ambiguous reference: "
- "'%s' as library '%s' is imported multiple times",
- name.ToCString(),
- first_lib_url.ToCString());
+ ambiguous_ref_error = FormatErrorMsg(
+ script_, ident_pos, "Error",
+ "ambiguous reference: "
+ "'%s' as library '%s' is imported multiple times",
+ name.ToCString(),
+ first_lib_url.ToCString());
} else {
- ErrorMsg(ident_pos,
- "ambiguous reference: "
- "'%s' is defined in library '%s' and also in '%s'",
- name.ToCString(),
- first_lib_url.ToCString(),
- String::Handle(lib.url()).ToCString());
+ ambiguous_ref_error = FormatErrorMsg(
+ script_, ident_pos, "Error",
+ "ambiguous reference: "
+ "'%s' is defined in library '%s' and also in '%s'",
+ name.ToCString(),
+ first_lib_url.ToCString(),
+ String::Handle(lib.url()).ToCString());
}
+ if (error == NULL) {
+ // Report a compile time error since the caller is not interested
+ // in the error.
+ ErrorMsg(ambiguous_ref_error);
+ }
+ *error = ambiguous_ref_error.raw();
+ return Object::null();
} else {
first_lib_url = lib.url();
obj = imported_obj.raw();
@@ -8178,9 +8234,10 @@
RawClass* Parser::ResolveClassInCurrentLibraryScope(intptr_t ident_pos,
- const String& name) {
+ const String& name,
+ Error* error) {
const Object& obj =
- Object::Handle(ResolveNameInCurrentLibraryScope(ident_pos, name));
+ Object::Handle(ResolveNameInCurrentLibraryScope(ident_pos, name, error));
if (obj.IsClass()) {
return Class::Cast(obj).raw();
}
@@ -8198,7 +8255,7 @@
const String& ident) {
TRACE_PARSER("ResolveIdentInCurrentLibraryScope");
const Object& obj =
- Object::Handle(ResolveNameInCurrentLibraryScope(ident_pos, ident));
+ Object::Handle(ResolveNameInCurrentLibraryScope(ident_pos, ident, NULL));
if (obj.IsClass()) {
const Class& cls = Class::Cast(obj);
return new PrimaryNode(ident_pos, Class::ZoneHandle(cls.raw()));
@@ -8229,7 +8286,8 @@
RawObject* Parser::ResolveNameInPrefixScope(intptr_t ident_pos,
const LibraryPrefix& prefix,
- const String& name) {
+ const String& name,
+ Error* error) {
TRACE_PARSER("ResolveNameInPrefixScope");
Namespace& import = Namespace::Handle();
String& first_lib_url = String::Handle();
@@ -8246,19 +8304,29 @@
first_lib_url = lib.url();
} else {
// Found duplicate definition.
+ Error& ambiguous_ref_error = Error::Handle();
if (first_lib_url.raw() == lib.url()) {
- ErrorMsg(ident_pos,
- "ambiguous reference: '%s.%s' is imported multiple times",
- String::Handle(prefix.name()).ToCString(),
- name.ToCString());
+ ambiguous_ref_error = FormatErrorMsg(
+ script_, ident_pos, "Error",
+ "ambiguous reference: '%s.%s' is imported multiple times",
+ String::Handle(prefix.name()).ToCString(),
+ name.ToCString());
} else {
- ErrorMsg(ident_pos,
- "ambiguous reference: '%s.%s' is defined in '%s' and '%s'",
- String::Handle(prefix.name()).ToCString(),
- name.ToCString(),
- first_lib_url.ToCString(),
- String::Handle(lib.url()).ToCString());
+ ambiguous_ref_error = FormatErrorMsg(
+ script_, ident_pos, "Error",
+ "ambiguous reference: '%s.%s' is defined in '%s' and '%s'",
+ String::Handle(prefix.name()).ToCString(),
+ name.ToCString(),
+ first_lib_url.ToCString(),
+ String::Handle(lib.url()).ToCString());
}
+ if (error == NULL) {
+ // Report a compile time error since the caller is not interested
+ // in the error.
+ ErrorMsg(ambiguous_ref_error);
+ }
+ *error = ambiguous_ref_error.raw();
+ return Object::null();
}
}
}
@@ -8268,9 +8336,10 @@
RawClass* Parser::ResolveClassInPrefixScope(intptr_t ident_pos,
const LibraryPrefix& prefix,
- const String& name) {
+ const String& name,
+ Error* error) {
const Object& obj =
- Object::Handle(ResolveNameInPrefixScope(ident_pos, prefix, name));
+ Object::Handle(ResolveNameInPrefixScope(ident_pos, prefix, name, error));
if (obj.IsClass()) {
return Class::Cast(obj).raw();
}
@@ -8287,7 +8356,7 @@
const String& ident) {
TRACE_PARSER("ResolveIdentInPrefixScope");
Object& obj =
- Object::Handle(ResolveNameInPrefixScope(ident_pos, prefix, ident));
+ Object::Handle(ResolveNameInPrefixScope(ident_pos, prefix, ident, NULL));
if (obj.IsNull()) {
// Unresolved prefixed primary identifier.
ErrorMsg(ident_pos, "identifier '%s.%s' cannot be resolved",
@@ -8886,10 +8955,13 @@
// In case the type is malformed, throw a dynamic type error after finishing
// parsing the instance creation expression.
if (type.IsTypeParameter() || type.IsDynamicType()) {
+ ASSERT(!type.IsMalformed());
// Replace the type with a malformed type.
type = ClassFinalizer::NewFinalizedMalformedType(
+ Error::Handle(), // No previous error.
current_class(),
type_pos,
+ ClassFinalizer::kTryResolve, // No compile-time error.
"%s'%s' cannot be instantiated",
type.IsTypeParameter() ? "type parameter " : "",
type.IsTypeParameter() ?
@@ -8953,8 +9025,10 @@
// Replace the type with a malformed type and compile a throw or report
// a compile-time error if the constructor is const.
type = ClassFinalizer::NewFinalizedMalformedType(
+ Error::Handle(), // No previous error.
current_class(),
call_pos,
+ ClassFinalizer::kTryResolve, // No compile-time error.
"interface '%s' has no constructor named '%s'",
type_class_name.ToCString(),
external_constructor_name.ToCString());
@@ -9021,8 +9095,10 @@
// Replace the type with a malformed type and compile a throw or report a
// compile-time error if the constructor is const.
type = ClassFinalizer::NewFinalizedMalformedType(
+ Error::Handle(), // No previous error.
current_class(),
call_pos,
+ ClassFinalizer::kTryResolve, // No compile-time error.
"class '%s' has no constructor or factory named '%s'",
String::Handle(constructor_class.Name()).ToCString(),
external_constructor_name.ToCString());

Powered by Google App Engine
This is Rietveld 408576698