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 class TypeCheckerTask extends CompilerTask { | 5 class TypeCheckerTask extends CompilerTask { |
6 TypeCheckerTask(Compiler compiler) : super(compiler); | 6 TypeCheckerTask(Compiler compiler) : super(compiler); |
7 String get name() => "Type checker"; | 7 String get name() => "Type checker"; |
8 | 8 |
9 static final bool LOG_FAILURES = false; | 9 static final bool LOG_FAILURES = false; |
10 | 10 |
(...skipping 15 matching lines...) Expand all Loading... | |
26 | 26 |
27 interface Type { | 27 interface Type { |
28 SourceString get name(); | 28 SourceString get name(); |
29 Element get element(); | 29 Element get element(); |
30 } | 30 } |
31 | 31 |
32 class TypeVariableType implements Type { | 32 class TypeVariableType implements Type { |
33 final SourceString name; | 33 final SourceString name; |
34 Element element; | 34 Element element; |
35 TypeVariableType(this.name, [this.element]); | 35 TypeVariableType(this.name, [this.element]); |
36 | |
37 toString() => name.toString(); | |
36 } | 38 } |
37 | 39 |
38 /** | 40 /** |
39 * A statement type tracks whether a statement returns or may return. | 41 * A statement type tracks whether a statement returns or may return. |
40 */ | 42 */ |
41 class StatementType implements Type { | 43 class StatementType implements Type { |
42 final String stringName; | 44 final String stringName; |
43 Element get element() => null; | 45 Element get element() => null; |
44 | 46 |
45 SourceString get name() => new SourceString(stringName); | 47 SourceString get name() => new SourceString(stringName); |
46 | 48 |
47 const StatementType(this.stringName); | 49 const StatementType(this.stringName); |
48 | 50 |
49 static final RETURNING = const StatementType('<returning>'); | 51 static final RETURNING = const StatementType('<returning>'); |
50 static final NOT_RETURNING = const StatementType('<not returning>'); | 52 static final NOT_RETURNING = const StatementType('<not returning>'); |
51 static final MAYBE_RETURNING = const StatementType('<maybe returning>'); | 53 static final MAYBE_RETURNING = const StatementType('<maybe returning>'); |
52 | 54 |
53 /** Combine the information about two control-flow edges that are joined. */ | 55 /** Combine the information about two control-flow edges that are joined. */ |
54 StatementType join(StatementType other) { | 56 StatementType join(StatementType other) { |
55 return (this === other) ? this : MAYBE_RETURNING; | 57 return (this === other) ? this : MAYBE_RETURNING; |
56 } | 58 } |
57 | 59 |
58 String toString() => stringName; | 60 String toString() => stringName; |
59 } | 61 } |
60 | 62 |
61 class SimpleType implements Type { | 63 class InterfaceType implements Type { |
62 final SourceString name; | 64 final SourceString name; |
ahe
2012/04/12 15:05:23
This field seems redundant.
| |
63 final Element element; | 65 final ClassElement element; |
66 final Link<Type> arguments; | |
64 | 67 |
65 const SimpleType(SourceString this.name, Element this.element); | 68 const InterfaceType(this.name, this.element, this.arguments); |
66 | 69 |
70 toString() { | |
71 StringBuffer sb = new StringBuffer(); | |
72 sb.add(name.slowToString()); | |
73 if (!arguments.isEmpty()) { | |
74 sb.add('<'); | |
75 arguments.printOn(sb); | |
ahe
2012/04/12 15:05:23
Add argument: ', '
| |
76 sb.add('>'); | |
77 } | |
78 return sb.toString(); | |
79 } | |
80 } | |
81 | |
82 // TODO(karlklose): merge into InterfaceType as a named constructor. | |
83 class SimpleType extends InterfaceType { | |
84 const SimpleType(SourceString name, Element element) | |
85 : super(name, element, const EmptyLink<Type>()); | |
67 String toString() => name.slowToString(); | 86 String toString() => name.slowToString(); |
68 } | 87 } |
69 | 88 |
70 class FunctionType implements Type { | 89 class FunctionType implements Type { |
71 final Element element; | 90 final Element element; |
72 final Type returnType; | 91 final Type returnType; |
73 final Link<Type> parameterTypes; | 92 final Link<Type> parameterTypes; |
74 | 93 |
75 const FunctionType(Type this.returnType, Link<Type> this.parameterTypes, | 94 const FunctionType(Type this.returnType, Link<Type> this.parameterTypes, |
76 Element this.element); | 95 Element this.element); |
(...skipping 17 matching lines...) Expand all Loading... | |
94 static final DYNAMIC = const SourceString('Dynamic'); | 113 static final DYNAMIC = const SourceString('Dynamic'); |
95 static final STRING = const SourceString('String'); | 114 static final STRING = const SourceString('String'); |
96 static final BOOL = const SourceString('bool'); | 115 static final BOOL = const SourceString('bool'); |
97 static final OBJECT = const SourceString('Object'); | 116 static final OBJECT = const SourceString('Object'); |
98 static final LIST = const SourceString('List'); | 117 static final LIST = const SourceString('List'); |
99 | 118 |
100 final SimpleType voidType; | 119 final SimpleType voidType; |
101 final SimpleType dynamicType; | 120 final SimpleType dynamicType; |
102 | 121 |
103 Types() : this.with(new LibraryElement(new Script(null, null))); | 122 Types() : this.with(new LibraryElement(new Script(null, null))); |
123 | |
104 Types.with(LibraryElement library) | 124 Types.with(LibraryElement library) |
105 : voidType = new SimpleType(VOID, new ClassElement(VOID, library)), | 125 : voidType = new SimpleType(VOID, new ClassElement(VOID, library)), |
106 dynamicType = new SimpleType(DYNAMIC, new ClassElement(DYNAMIC, library)); | 126 dynamicType = new SimpleType(VOID, new ClassElement(DYNAMIC, library)); |
ahe
2012/04/12 15:05:23
VOID?
| |
107 | 127 |
108 Type lookup(SourceString s) { | 128 Type lookup(SourceString s) { |
109 if (VOID == s) { | 129 if (VOID == s) { |
110 return voidType; | 130 return voidType; |
111 } else if (DYNAMIC == s || s.stringValue === 'var') { | 131 } else if (DYNAMIC == s || s.stringValue === 'var') { |
112 return dynamicType; | 132 return dynamicType; |
113 } | 133 } |
114 return null; | 134 return null; |
115 } | 135 } |
116 | 136 |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
165 Element element = compiler.coreLibrary.find(name); | 185 Element element = compiler.coreLibrary.find(name); |
166 if (element !== null && element.kind === ElementKind.CLASS) { | 186 if (element !== null && element.kind === ElementKind.CLASS) { |
167 return element.computeType(compiler); | 187 return element.computeType(compiler); |
168 } | 188 } |
169 return null; | 189 return null; |
170 } | 190 } |
171 | 191 |
172 class TypeCheckerVisitor implements Visitor<Type> { | 192 class TypeCheckerVisitor implements Visitor<Type> { |
173 final Compiler compiler; | 193 final Compiler compiler; |
174 final TreeElements elements; | 194 final TreeElements elements; |
175 Node lastSeenNode; | |
176 final Types types; | 195 final Types types; |
177 | 196 |
197 Node lastSeenNode; | |
178 Type expectedReturnType; | 198 Type expectedReturnType; |
179 ClassElement currentClass; | 199 ClassElement currentClass; |
180 | 200 |
181 Type intType; | 201 Type intType; |
182 Type doubleType; | 202 Type doubleType; |
183 Type boolType; | 203 Type boolType; |
184 Type stringType; | 204 Type stringType; |
185 Type objectType; | 205 Type objectType; |
186 Type listType; | 206 Type listType; |
187 | 207 |
188 TypeCheckerVisitor(Compiler this.compiler, TreeElements this.elements, | 208 TypeCheckerVisitor(this.compiler, this.elements, this.types) { |
189 Types this.types) { | |
190 intType = lookupType(Types.INT, compiler, types); | 209 intType = lookupType(Types.INT, compiler, types); |
191 doubleType = lookupType(Types.DOUBLE, compiler, types); | 210 doubleType = lookupType(Types.DOUBLE, compiler, types); |
192 boolType = lookupType(Types.BOOL, compiler, types); | 211 boolType = lookupType(Types.BOOL, compiler, types); |
193 stringType = lookupType(Types.STRING, compiler, types); | 212 stringType = lookupType(Types.STRING, compiler, types); |
194 objectType = lookupType(Types.OBJECT, compiler, types); | 213 objectType = lookupType(Types.OBJECT, compiler, types); |
195 listType = lookupType(Types.LIST, compiler, types); | 214 listType = lookupType(Types.LIST, compiler, types); |
196 } | 215 } |
197 | 216 |
198 Type fail(node, [reason]) { | 217 Type fail(node, [reason]) { |
199 String message = 'cannot type-check'; | 218 String message = 'cannot type-check'; |
(...skipping 507 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
707 } | 726 } |
708 | 727 |
709 visitCatchBlock(CatchBlock node) { | 728 visitCatchBlock(CatchBlock node) { |
710 fail(node); | 729 fail(node); |
711 } | 730 } |
712 | 731 |
713 visitTypedef(Typedef node) { | 732 visitTypedef(Typedef node) { |
714 fail(node); | 733 fail(node); |
715 } | 734 } |
716 } | 735 } |
OLD | NEW |