| Index: pkg/compiler/lib/src/tree/nodes.dart
|
| diff --git a/pkg/compiler/lib/src/tree/nodes.dart b/pkg/compiler/lib/src/tree/nodes.dart
|
| index a5b20d08b227fb8f435e969db645dd03ab4e31fc..744bdfe62a7ba6005864941db4dbab9f54016db4 100644
|
| --- a/pkg/compiler/lib/src/tree/nodes.dart
|
| +++ b/pkg/compiler/lib/src/tree/nodes.dart
|
| @@ -51,6 +51,10 @@ abstract class Visitor<R> {
|
| R visitForIn(ForIn node) => visitLoop(node);
|
| R visitFunctionDeclaration(FunctionDeclaration node) => visitStatement(node);
|
| R visitFunctionExpression(FunctionExpression node) => visitExpression(node);
|
| + R visitFunctionTypeAnnotation(FunctionTypeAnnotation node) {
|
| + return visitTypeAnnotation(node);
|
| + }
|
| +
|
| R visitGotoStatement(GotoStatement node) => visitStatement(node);
|
| R visitIdentifier(Identifier node) => visitExpression(node);
|
| R visitImport(Import node) => visitLibraryDependency(node);
|
| @@ -82,6 +86,10 @@ abstract class Visitor<R> {
|
|
|
| R visitNewExpression(NewExpression node) => visitExpression(node);
|
| R visitNodeList(NodeList node) => visitNode(node);
|
| + R visitNominalTypeAnnotation(NominalTypeAnnotation node) {
|
| + return visitTypeAnnotation(node);
|
| + }
|
| +
|
| R visitOperator(Operator node) => visitIdentifier(node);
|
| R visitParenthesizedExpression(ParenthesizedExpression node) {
|
| return visitExpression(node);
|
| @@ -179,6 +187,10 @@ abstract class Visitor1<R, A> {
|
| return visitExpression(node, arg);
|
| }
|
|
|
| + R visitFunctionTypeAnnotation(FunctionTypeAnnotation node, A arg) {
|
| + return visitTypeAnnotation(node, arg);
|
| + }
|
| +
|
| R visitGotoStatement(GotoStatement node, A arg) {
|
| return visitStatement(node, arg);
|
| }
|
| @@ -228,6 +240,10 @@ abstract class Visitor1<R, A> {
|
|
|
| R visitNewExpression(NewExpression node, A arg) => visitExpression(node, arg);
|
| R visitNodeList(NodeList node, A arg) => visitNode(node, arg);
|
| + R visitNominalTypeAnnotation(NominalTypeAnnotation node, A arg) {
|
| + visitTypeAnnotation(node, arg);
|
| + }
|
| +
|
| R visitOperator(Operator node, A arg) => visitIdentifier(node, arg);
|
| R visitParenthesizedExpression(ParenthesizedExpression node, A arg) {
|
| return visitExpression(node, arg);
|
| @@ -263,8 +279,8 @@ abstract class Visitor1<R, A> {
|
| R visitLiteralSymbol(LiteralSymbol node, A arg) => visitExpression(node, arg);
|
| R visitThrow(Throw node, A arg) => visitExpression(node, arg);
|
| R visitTryStatement(TryStatement node, A arg) => visitStatement(node, arg);
|
| - R visitTypeAnnotation(TypeAnnotation node, A arg) => visitNode(node, arg);
|
| R visitTypedef(Typedef node, A arg) => visitNode(node, arg);
|
| + R visitTypeAnnotation(TypeAnnotation node, A arg) => visitNode(node, arg);
|
| R visitTypeVariable(TypeVariable node, A arg) => visitNode(node, arg);
|
| R visitVariableDefinitions(VariableDefinitions node, A arg) {
|
| return visitStatement(node, arg);
|
| @@ -363,6 +379,7 @@ abstract class Node extends NullTreeElementMixin implements Spannable {
|
| ForIn asForIn() => null;
|
| FunctionDeclaration asFunctionDeclaration() => null;
|
| FunctionExpression asFunctionExpression() => null;
|
| + FunctionTypeAnnotation asFunctionTypeAnnotation() => null;
|
| Identifier asIdentifier() => null;
|
| If asIf() => null;
|
| Import asImport() => null;
|
| @@ -386,6 +403,7 @@ abstract class Node extends NullTreeElementMixin implements Spannable {
|
| NamedMixinApplication asNamedMixinApplication() => null;
|
| NewExpression asNewExpression() => null;
|
| NodeList asNodeList() => null;
|
| + NominalTypeAnnotation asNominalTypeAnnotation() => null;
|
| Operator asOperator() => null;
|
| ParenthesizedExpression asParenthesizedExpression() => null;
|
| Part asPart() => null;
|
| @@ -404,7 +422,6 @@ abstract class Node extends NullTreeElementMixin implements Spannable {
|
| SwitchStatement asSwitchStatement() => null;
|
| Throw asThrow() => null;
|
| TryStatement asTryStatement() => null;
|
| - TypeAnnotation asTypeAnnotation() => null;
|
| TypeVariable asTypeVariable() => null;
|
| Typedef asTypedef() => null;
|
| VariableDefinitions asVariableDefinitions() => null;
|
| @@ -489,7 +506,7 @@ class ClassNode extends Node {
|
| }
|
|
|
| class MixinApplication extends Node {
|
| - final TypeAnnotation superclass;
|
| + final NominalTypeAnnotation superclass;
|
| final NodeList mixins;
|
|
|
| MixinApplication(this.superclass, this.mixins);
|
| @@ -514,8 +531,6 @@ class MixinApplication extends Node {
|
| Token getEndToken() => mixins.getEndToken();
|
| }
|
|
|
| -// TODO(kasperl): Let this share some structure with the typedef for function
|
| -// type aliases?
|
| class NamedMixinApplication extends Node implements MixinApplication {
|
| final Identifier name;
|
| final NodeList typeParameters;
|
| @@ -530,7 +545,7 @@ class NamedMixinApplication extends Node implements MixinApplication {
|
| NamedMixinApplication(this.name, this.typeParameters, this.modifiers,
|
| this.mixinApplication, this.interfaces, this.classKeyword, this.endToken);
|
|
|
| - TypeAnnotation get superclass => mixinApplication.superclass;
|
| + NominalTypeAnnotation get superclass => mixinApplication.superclass;
|
| NodeList get mixins => mixinApplication.mixins;
|
|
|
| MixinApplication asMixinApplication() => this;
|
| @@ -1723,17 +1738,22 @@ class Rethrow extends Statement {
|
| Token getEndToken() => endToken;
|
| }
|
|
|
| -class TypeAnnotation extends Node {
|
| +abstract class TypeAnnotation extends Node {
|
| +}
|
| +
|
| +class NominalTypeAnnotation extends TypeAnnotation {
|
| final Expression typeName;
|
| final NodeList typeArguments;
|
|
|
| - TypeAnnotation(Expression this.typeName, NodeList this.typeArguments);
|
| + NominalTypeAnnotation(this.typeName, this.typeArguments);
|
|
|
| - TypeAnnotation asTypeAnnotation() => this;
|
| + NominalTypeAnnotation asNominalTypeAnnotation() => this;
|
|
|
| - accept(Visitor visitor) => visitor.visitTypeAnnotation(this);
|
| + accept(Visitor visitor) => visitor.visitNominalTypeAnnotation(this);
|
|
|
| - accept1(Visitor1 visitor, arg) => visitor.visitTypeAnnotation(this, arg);
|
| + accept1(Visitor1 visitor, arg) {
|
| + return visitor.visitNominalTypeAnnotation(this, arg);
|
| + }
|
|
|
| visitChildren(Visitor visitor) {
|
| typeName.accept(visitor);
|
| @@ -1829,7 +1849,13 @@ class VariableDefinitions extends Statement {
|
| return token;
|
| }
|
|
|
| - Token getEndToken() => definitions.getEndToken();
|
| + Token getEndToken() {
|
| + var result = definitions.getEndToken();
|
| + if (result != null) return result;
|
| + assert(definitions.nodes.length == 1);
|
| + assert(definitions.nodes.last == null);
|
| + return type.getEndToken();
|
| + }
|
| }
|
|
|
| abstract class Loop extends Statement {
|
| @@ -2857,16 +2883,30 @@ class Combinator extends Node {
|
| }
|
|
|
| class Typedef extends Node {
|
| + final bool isGeneralizedTypeAlias;
|
| +
|
| + /// Parameters to the template.
|
| + ///
|
| + /// For example, `T` and `S` are template parameters in the following
|
| + /// typedef: `typedef F<S, T> = Function(S, T)`, or, in the inlined syntax,
|
| + /// `typedef F<S, T>(S x, T y)`.
|
| + final NodeList templateParameters;
|
| +
|
| final TypeAnnotation returnType;
|
| final Identifier name;
|
| + /// The generic type parameters to the function type.
|
| + ///
|
| + /// For example `A` and `B` (but not `T`) are type parameters in
|
| + /// `typedef F<T> = Function<A, B>(A, B, T)`;
|
| final NodeList typeParameters;
|
| final NodeList formals;
|
|
|
| final Token typedefKeyword;
|
| final Token endToken;
|
|
|
| - Typedef(this.returnType, this.name, this.typeParameters, this.formals,
|
| - this.typedefKeyword, this.endToken);
|
| + Typedef(this.isGeneralizedTypeAlias, this.templateParameters, this.returnType,
|
| + this.name, this.typeParameters, this.formals, this.typedefKeyword,
|
| + this.endToken);
|
|
|
| Typedef asTypedef() => this;
|
|
|
| @@ -2875,6 +2915,7 @@ class Typedef extends Node {
|
| accept1(Visitor1 visitor, arg) => visitor.visitTypedef(this, arg);
|
|
|
| visitChildren(Visitor visitor) {
|
| + if (templateParameters != null) templateParameters.accept(visitor);
|
| if (returnType != null) returnType.accept(visitor);
|
| name.accept(visitor);
|
| if (typeParameters != null) typeParameters.accept(visitor);
|
| @@ -2882,6 +2923,7 @@ class Typedef extends Node {
|
| }
|
|
|
| visitChildren1(Visitor1 visitor, arg) {
|
| + if (templateParameters != null) templateParameters.accept1(visitor, arg);
|
| if (returnType != null) returnType.accept1(visitor, arg);
|
| name.accept1(visitor, arg);
|
| if (typeParameters != null) typeParameters.accept1(visitor, arg);
|
| @@ -2893,6 +2935,43 @@ class Typedef extends Node {
|
| Token getEndToken() => endToken;
|
| }
|
|
|
| +class FunctionTypeAnnotation extends TypeAnnotation {
|
| + final TypeAnnotation returnType;
|
| + final Token functionToken;
|
| + final NodeList typeParameters;
|
| + final NodeList formals;
|
| +
|
| + FunctionTypeAnnotation(
|
| + this.returnType, this.functionToken, this.typeParameters, this.formals);
|
| +
|
| + FunctionTypeAnnotation asFunctionTypeAnnotation() => this;
|
| +
|
| + accept(Visitor visitor) => visitor.visitFunctionTypeAnnotation(this);
|
| +
|
| + accept1(Visitor1 visitor, arg) {
|
| + return visitor.visitFunctionTypeAnnotation(this, arg);
|
| + }
|
| +
|
| + visitChildren(Visitor visitor) {
|
| + if (returnType != null) returnType.accept(visitor);
|
| + if (typeParameters != null) typeParameters.accept(visitor);
|
| + formals.accept(visitor);
|
| + }
|
| +
|
| + visitChildren1(Visitor1 visitor, arg) {
|
| + if (returnType != null) returnType.accept1(visitor, arg);
|
| + if (typeParameters != null) typeParameters.accept1(visitor, arg);
|
| + formals.accept1(visitor, arg);
|
| + }
|
| +
|
| + Token getBeginToken() {
|
| + if (returnType != null) return returnType.getBeginToken();
|
| + return functionToken;
|
| + }
|
| +
|
| + Token getEndToken() => formals.getEndToken();
|
| +}
|
| +
|
| class TryStatement extends Statement {
|
| final Block tryBlock;
|
| final NodeList catchBlocks;
|
| @@ -3139,6 +3218,8 @@ class ErrorNode extends Node
|
| get type => null;
|
|
|
| // Typedef.
|
| + get isGeneralizedTypeAlias => null;
|
| + get templateParameters => null;
|
| get typeParameters => null;
|
| get formals => null;
|
| get typedefKeyword => null;
|
|
|