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

Unified Diff: lib/compiler/implementation/resolver.dart

Issue 10832029: Substitution implemented for the class hierarchy. (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 8 years, 5 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: lib/compiler/implementation/resolver.dart
diff --git a/lib/compiler/implementation/resolver.dart b/lib/compiler/implementation/resolver.dart
index 94808dc9e4b4d63e5c9a268f40e52da970dde9cf..771c5dc12db4721d708bbf8cec6c9cdc9d12e5e9 100644
--- a/lib/compiler/implementation/resolver.dart
+++ b/lib/compiler/implementation/resolver.dart
@@ -569,7 +569,8 @@ class CommonResolverVisitor<R> extends AbstractVisitor<R> {
CommonResolverVisitor(Compiler this.compiler);
R visitNode(Node node) {
- cancel(node, 'internal error');
+ cancel(node,
+ 'internal error: Unhandled node: ${node.getObjectDescription()}');
}
R visitEmptyStatement(Node node) => null;
@@ -1654,22 +1655,14 @@ class ClassResolverVisitor extends CommonResolverVisitor<Type> {
Type visitClassNode(ClassNode node) {
compiler.ensure(classElement !== null);
compiler.ensure(!classElement.isResolved);
- final Link<Node> parameters =
+
+ classElement.ensureParametersAndType(compiler);
+ context = new TypeVariablesScope(context, classElement);
+
+ // Resolve the bounds of type variables.
+ Link<Node> parameters =
node.typeParameters !== null ? node.typeParameters.nodes
: const EmptyLink<TypeVariable>();
- // Create types and elements for type variable.
- for (Link<Node> link = parameters; !link.isEmpty(); link = link.tail) {
- TypeVariable typeNode = link.head;
- SourceString variableName = typeNode.name.source;
- TypeVariableType variableType = new TypeVariableType(variableName);
- TypeVariableElement variableElement =
- new TypeVariableElement(variableName, classElement, node,
- variableType);
- variableType.element = variableElement;
- classElement.typeParameters[variableName] = variableElement;
- context = new TypeVariablesScope(context, classElement);
- }
- // Resolve the bounds of type variables.
for (Link<Node> link = parameters; !link.isEmpty(); link = link.tail) {
TypeVariable typeNode = link.head;
SourceString variableName = typeNode.name.source;
@@ -1687,6 +1680,7 @@ class ClassResolverVisitor extends CommonResolverVisitor<Type> {
}
}
}
+
// Find super type.
Type supertype = visit(node.superclass);
if (supertype !== null && supertype.element.isExtendable()) {
@@ -1730,7 +1724,30 @@ class ClassResolverVisitor extends CommonResolverVisitor<Type> {
}
Type visitTypeAnnotation(TypeAnnotation node) {
- return visit(node.typeName);
+ Type type = visit(node.typeName);
+ if (type is! InterfaceType) {
+ // TODO(johnniwinther): Handle function types.
+ return type;
+ }
+ if (node.typeArguments === null) {
+ if (type.arguments.isEmpty()) {
+ return type;
+ }
+ // Return the 'raw' version, for example List for List<E>.
+ return new InterfaceType(type.element);
+ }
+ var typeArguments = new LinkBuilder<Type>();
+ var link = node.typeArguments.nodes;
+ while (!link.isEmpty()) {
+ typeArguments.addLast(visit(link.head));
+ link = link.tail;
+ }
+ // TODO(johnniwinther): Check argument count and bounds.
+ return new InterfaceType(type.element, typeArguments.toLink());
+ }
+
+ Type visitTypeVariable(TypeVariable node) {
+ return visit(node.name);
}
Type visitIdentifier(Identifier node) {
@@ -1751,7 +1768,7 @@ class ClassResolverVisitor extends CommonResolverVisitor<Type> {
} else if (element.isTypedef()) {
compiler.unimplemented('visitIdentifier for typedefs', node: node);
} else {
- // TODO(ngeoffray): Use type variables.
+ // Type variables are handled in [visitTypeAnnotation].
return element.computeType(compiler);
}
}
@@ -1799,11 +1816,10 @@ class ClassResolverVisitor extends CommonResolverVisitor<Type> {
}
void calculateAllSupertypes(ClassElement cls, Set<ClassElement> seen) {
- // TODO(karlklose): substitute type variables.
// TODO(karlklose): check if type arguments match, if a classelement occurs
// more than once in the supertypes.
if (cls.allSupertypes !== null) return;
- final Type supertype = cls.supertype;
+ final InterfaceType supertype = cls.supertype;
if (seen.contains(cls)) {
error(cls.parseNode(compiler),
MessageKind.CYCLIC_CLASS_HIERARCHY,
@@ -1811,9 +1827,24 @@ class ClassResolverVisitor extends CommonResolverVisitor<Type> {
cls.allSupertypes = const EmptyLink<Type>();
} else if (supertype != null) {
seen.add(cls);
+ ClassElement supertypeElement = supertype.element;
Link<Type> superSupertypes =
- getOrCalculateAllSupertypes(supertype.element, seen);
- Link<Type> supertypes = new Link<Type>(supertype, superSupertypes);
+ getOrCalculateAllSupertypes(supertypeElement, seen);
+ var superTypesBuilder = new LinkBuilder<Type>();
+ superTypesBuilder.addLast(supertype);
+
+ // Substitute type variables in supertypes.
+ var superTypeParameters = <Type>[];
+ var typeVariableElements = supertypeElement.typeParameters.getValues();
+ for (TypeVariableElement typeVariableElement in typeVariableElements) {
+ superTypeParameters.add(typeVariableElement.type);
+ }
+ for (Type superSupertype in superSupertypes) {
+ superTypesBuilder.addLast(superSupertype.subst(
+ supertype.arguments, superTypeParameters));
+ }
+
+ Link<Type> supertypes = superTypesBuilder.toLink();
for (Link<Type> interfaces = cls.interfaces;
!interfaces.isEmpty();
interfaces = interfaces.tail) {

Powered by Google App Engine
This is Rietveld 408576698