| 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 #library('elements'); | 5 #library('elements'); |
| 6 | 6 |
| 7 #import('dart:uri'); | 7 #import('dart:uri'); |
| 8 | 8 |
| 9 #import('../tree/tree.dart'); | 9 #import('../tree/tree.dart'); |
| 10 #import('../scanner/scannerlib.dart'); | 10 #import('../scanner/scannerlib.dart'); |
| (...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 100 static const ElementKind STATEMENT = | 100 static const ElementKind STATEMENT = |
| 101 const ElementKind('statement', ElementCategory.NONE); | 101 const ElementKind('statement', ElementCategory.NONE); |
| 102 static const ElementKind LABEL = | 102 static const ElementKind LABEL = |
| 103 const ElementKind('label', ElementCategory.NONE); | 103 const ElementKind('label', ElementCategory.NONE); |
| 104 static const ElementKind VOID = | 104 static const ElementKind VOID = |
| 105 const ElementKind('void', ElementCategory.NONE); | 105 const ElementKind('void', ElementCategory.NONE); |
| 106 | 106 |
| 107 toString() => id; | 107 toString() => id; |
| 108 } | 108 } |
| 109 | 109 |
| 110 class Element implements Hashable { | 110 class Element implements Hashable, Spannable { |
| 111 final SourceString name; | 111 final SourceString name; |
| 112 final ElementKind kind; | 112 final ElementKind kind; |
| 113 final Element enclosingElement; | 113 final Element enclosingElement; |
| 114 Link<MetadataAnnotation> metadata = const EmptyLink<MetadataAnnotation>(); | 114 Link<MetadataAnnotation> metadata = const EmptyLink<MetadataAnnotation>(); |
| 115 | 115 |
| 116 Element(this.name, this.kind, this.enclosingElement) { | 116 Element(this.name, this.kind, this.enclosingElement) { |
| 117 assert(getLibrary() !== null); | 117 assert(getLibrary() !== null); |
| 118 } | 118 } |
| 119 | 119 |
| 120 Modifiers get modifiers => null; | 120 Modifiers get modifiers => null; |
| (...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 164 bool isSetter() => kind === ElementKind.SETTER; | 164 bool isSetter() => kind === ElementKind.SETTER; |
| 165 bool isAccessor() => isGetter() || isSetter(); | 165 bool isAccessor() => isGetter() || isSetter(); |
| 166 bool isForeign() => kind === ElementKind.FOREIGN; | 166 bool isForeign() => kind === ElementKind.FOREIGN; |
| 167 bool isLibrary() => kind === ElementKind.LIBRARY; | 167 bool isLibrary() => kind === ElementKind.LIBRARY; |
| 168 bool impliesType() => (kind.category & ElementCategory.IMPLIES_TYPE) != 0; | 168 bool impliesType() => (kind.category & ElementCategory.IMPLIES_TYPE) != 0; |
| 169 bool isExtendable() => (kind.category & ElementCategory.IS_EXTENDABLE) != 0; | 169 bool isExtendable() => (kind.category & ElementCategory.IS_EXTENDABLE) != 0; |
| 170 | 170 |
| 171 /** See [ErroneousElement] for documentation. */ | 171 /** See [ErroneousElement] for documentation. */ |
| 172 bool isErroneous() => false; | 172 bool isErroneous() => false; |
| 173 | 173 |
| 174 /** |
| 175 * Is [:true:] if this element has a corresponding patch. |
| 176 * |
| 177 * If [:true:] this element has a non-null [patch] field. |
| 178 * |
| 179 * See [:patch_parser.dart:] for a description of the terminology. |
| 180 */ |
| 181 bool get isPatched => false; |
| 182 |
| 183 /** |
| 184 * Is [:true:] if this element is a patch. |
| 185 * |
| 186 * If [:true:] this element has a non-null [origin] field. |
| 187 * |
| 188 * See [:patch_parser.dart:] for a description of the terminology. |
| 189 */ |
| 190 bool get isPatch => false; |
| 191 |
| 192 |
| 193 /** |
| 194 * Is [:true:] if this element defines the implementation for the entity of |
| 195 * this element. |
| 196 * |
| 197 * See [:patch_parser.dart:] for a description of the terminology. |
| 198 */ |
| 199 bool get isImplementation => implementation === this; |
| 200 |
| 201 /** |
| 202 * Is [:true:] if this element introduces the entity of this element. |
| 203 * |
| 204 * See [:patch_parser.dart:] for a description of the terminology. |
| 205 */ |
| 206 bool get isDeclaration => declaration === this; |
| 207 |
| 208 /** |
| 209 * Returns the element which defines the implementation for the entity of this |
| 210 * element. |
| 211 * |
| 212 * See [:patch_parser.dart:] for a description of the terminology. |
| 213 */ |
| 214 Element get implementation => this; |
| 215 |
| 216 /** |
| 217 * Returns the element which introduces the entity of this element. |
| 218 * |
| 219 * See [:patch_parser.dart:] for a description of the terminology. |
| 220 */ |
| 221 Element get declaration => this; |
| 222 |
| 174 // TODO(johnniwinther): This breaks for libraries (for which enclosing | 223 // TODO(johnniwinther): This breaks for libraries (for which enclosing |
| 175 // elements are null) and is invalid for top level variable declarations for | 224 // elements are null) and is invalid for top level variable declarations for |
| 176 // which the enclosing element is a VariableDeclarations and not a compilation | 225 // which the enclosing element is a VariableDeclarations and not a compilation |
| 177 // unit. | 226 // unit. |
| 178 bool isTopLevel() { | 227 bool isTopLevel() { |
| 179 return enclosingElement !== null && enclosingElement.isCompilationUnit(); | 228 return enclosingElement !== null && enclosingElement.isCompilationUnit(); |
| 180 } | 229 } |
| 181 | 230 |
| 182 bool isAssignable() { | 231 bool isAssignable() { |
| 183 if (modifiers != null && modifiers.isFinalOrConst()) return false; | 232 if (modifiers != null && modifiers.isFinalOrConst()) return false; |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 222 } | 271 } |
| 223 | 272 |
| 224 LibraryElement getLibrary() { | 273 LibraryElement getLibrary() { |
| 225 Element element = this; | 274 Element element = this; |
| 226 while (element.kind !== ElementKind.LIBRARY) { | 275 while (element.kind !== ElementKind.LIBRARY) { |
| 227 element = element.enclosingElement; | 276 element = element.enclosingElement; |
| 228 } | 277 } |
| 229 return element; | 278 return element; |
| 230 } | 279 } |
| 231 | 280 |
| 281 LibraryElement getImplementationLibrary() => getLibrary(); |
| 282 |
| 232 ClassElement getEnclosingClass() { | 283 ClassElement getEnclosingClass() { |
| 233 for (Element e = this; e !== null; e = e.enclosingElement) { | 284 for (Element e = this; e !== null; e = e.enclosingElement) { |
| 234 if (e.isClass()) return e; | 285 if (e.isClass()) return e; |
| 235 } | 286 } |
| 236 return null; | 287 return null; |
| 237 } | 288 } |
| 238 | 289 |
| 239 Element getEnclosingClassOrCompilationUnit() { | 290 Element getEnclosingClassOrCompilationUnit() { |
| 240 for (Element e = this; e !== null; e = e.enclosingElement) { | 291 for (Element e = this; e !== null; e = e.enclosingElement) { |
| 241 if (e.isClass() || e.isCompilationUnit()) return e; | 292 if (e.isClass() || e.isCompilationUnit()) return e; |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 287 | 338 |
| 288 bool _isNative = false; | 339 bool _isNative = false; |
| 289 void setNative() { _isNative = true; } | 340 void setNative() { _isNative = true; } |
| 290 bool isNative() => _isNative; | 341 bool isNative() => _isNative; |
| 291 | 342 |
| 292 FunctionElement asFunctionElement() => null; | 343 FunctionElement asFunctionElement() => null; |
| 293 | 344 |
| 294 Element cloneTo(Element enclosing, DiagnosticListener listener) { | 345 Element cloneTo(Element enclosing, DiagnosticListener listener) { |
| 295 listener.cancel("Unimplemented cloneTo", element: this); | 346 listener.cancel("Unimplemented cloneTo", element: this); |
| 296 } | 347 } |
| 297 | |
| 298 bool get isPatched => false; | |
| 299 } | 348 } |
| 300 | 349 |
| 301 /** | 350 /** |
| 302 * Represents an unresolvable or duplicated element. | 351 * Represents an unresolvable or duplicated element. |
| 303 * | 352 * |
| 304 * An [ErroneousElement] is used instead of [null] to provide additional | 353 * An [ErroneousElement] is used instead of [null] to provide additional |
| 305 * information about the error that caused the element to be unresolvable | 354 * information about the error that caused the element to be unresolvable |
| 306 * or otherwise invalid. | 355 * or otherwise invalid. |
| 307 * | 356 * |
| 308 * Accessing any field or calling any method defined on [ErroneousElement] | 357 * Accessing any field or calling any method defined on [ErroneousElement] |
| (...skipping 29 matching lines...) Expand all Loading... |
| 338 class ErroneousFunctionElement extends ErroneousElement | 387 class ErroneousFunctionElement extends ErroneousElement |
| 339 implements FunctionElement { | 388 implements FunctionElement { |
| 340 ErroneousFunctionElement(Message errorMessage, SourceString targetName, | 389 ErroneousFunctionElement(Message errorMessage, SourceString targetName, |
| 341 Element enclosing) | 390 Element enclosing) |
| 342 : super(errorMessage, targetName, enclosing); | 391 : super(errorMessage, targetName, enclosing); |
| 343 | 392 |
| 344 get type => unsupported(); | 393 get type => unsupported(); |
| 345 get cachedNode => unsupported(); | 394 get cachedNode => unsupported(); |
| 346 get functionSignature => unsupported(); | 395 get functionSignature => unsupported(); |
| 347 get patch => unsupported(); | 396 get patch => unsupported(); |
| 397 get origin => unsupported(); |
| 348 get defaultImplementation => unsupported(); | 398 get defaultImplementation => unsupported(); |
| 349 bool get isPatched => unsupported(); | 399 bool get isPatched => unsupported(); |
| 400 bool get isPatch => unsupported(); |
| 350 setPatch(patch) => unsupported(); | 401 setPatch(patch) => unsupported(); |
| 351 computeSignature(compiler) => unsupported(); | 402 computeSignature(compiler) => unsupported(); |
| 352 requiredParameterCount(compiler) => unsupported(); | 403 requiredParameterCount(compiler) => unsupported(); |
| 353 optionalParameterCount(compiler) => unsupported(); | 404 optionalParameterCount(compiler) => unsupported(); |
| 354 parameterCount(copmiler) => unsupported(); | 405 parameterCount(copmiler) => unsupported(); |
| 355 } | 406 } |
| 356 | 407 |
| 357 class ContainerElement extends Element { | 408 class ContainerElement extends Element { |
| 358 Link<Element> localMembers = const EmptyLink<Element>(); | 409 Link<Element> localMembers = const EmptyLink<Element>(); |
| 359 | 410 |
| (...skipping 613 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 973 int optionalParameterCount(Compiler compiler) { | 1024 int optionalParameterCount(Compiler compiler) { |
| 974 return computeSignature(compiler).optionalParameterCount; | 1025 return computeSignature(compiler).optionalParameterCount; |
| 975 } | 1026 } |
| 976 | 1027 |
| 977 int parameterCount(Compiler compiler) { | 1028 int parameterCount(Compiler compiler) { |
| 978 return computeSignature(compiler).parameterCount; | 1029 return computeSignature(compiler).parameterCount; |
| 979 } | 1030 } |
| 980 | 1031 |
| 981 FunctionType computeType(Compiler compiler) { | 1032 FunctionType computeType(Compiler compiler) { |
| 982 if (type != null) return type; | 1033 if (type != null) return type; |
| 983 type = compiler.computeFunctionType(this, computeSignature(compiler)); | 1034 type = compiler.computeFunctionType(declaration, |
| 1035 computeSignature(compiler)); |
| 984 return type; | 1036 return type; |
| 985 } | 1037 } |
| 986 | 1038 |
| 987 Node parseNode(DiagnosticListener listener) { | 1039 Node parseNode(DiagnosticListener listener) { |
| 988 if (cachedNode !== null) return cachedNode; | 1040 if (cachedNode !== null) return cachedNode; |
| 989 if (patch === null) { | 1041 if (patch === null) { |
| 990 if (modifiers.isExternal()) { | 1042 if (modifiers != null && modifiers.isExternal()) { |
| 991 listener.cancel("Compiling external function with no implementation.", | 1043 listener.cancel("Compiling external function with no implementation.", |
| 992 element: this); | 1044 element: this); |
| 993 } | 1045 } |
| 994 return null; | 1046 return null; |
| 995 } | 1047 } |
| 996 cachedNode = patch.parseNode(listener); | 1048 cachedNode = patch.parseNode(listener); |
| 997 return cachedNode; | 1049 return cachedNode; |
| 998 } | 1050 } |
| 999 | 1051 |
| 1000 Token position() => cachedNode.getBeginToken(); | 1052 Token position() => cachedNode.getBeginToken(); |
| 1001 | 1053 |
| 1002 FunctionElement asFunctionElement() => this; | 1054 FunctionElement asFunctionElement() => this; |
| 1003 | 1055 |
| 1004 FunctionElement cloneTo(Element enclosing, DiagnosticListener listener) { | 1056 String toString() { |
| 1005 FunctionElement result = new FunctionElement.tooMuchOverloading( | 1057 if (isPatch) { |
| 1006 name, cachedNode, kind, modifiers, enclosing, functionSignature); | 1058 return 'patch ${super.toString()}'; |
| 1007 result.defaultImplementation = defaultImplementation; | 1059 } else if (isPatched) { |
| 1008 result.type = type; | 1060 return 'origin ${super.toString()}'; |
| 1009 return result; | 1061 } else { |
| 1062 return super.toString(); |
| 1063 } |
| 1010 } | 1064 } |
| 1011 | 1065 |
| 1012 Scope buildScope() { | 1066 Scope buildScope() { |
| 1013 Scope result = new MethodScope(enclosingElement.buildScope(), this); | 1067 Scope result = |
| 1068 new MethodScope(enclosingElement.buildScope(), this); |
| 1014 if (enclosingElement.isClass()) { | 1069 if (enclosingElement.isClass()) { |
| 1015 ClassScope clsScope = result.parent; | 1070 Scope clsScope = result.parent; |
| 1016 clsScope.inStaticContext = !isInstanceMember() && !isConstructor(); | 1071 clsScope.inStaticContext = !isInstanceMember() && !isConstructor(); |
| 1017 } | 1072 } |
| 1018 return result; | 1073 return result; |
| 1019 } | 1074 } |
| 1020 } | 1075 } |
| 1021 | 1076 |
| 1022 | |
| 1023 class ConstructorBodyElement extends FunctionElement { | 1077 class ConstructorBodyElement extends FunctionElement { |
| 1024 FunctionElement constructor; | 1078 FunctionElement constructor; |
| 1025 | 1079 |
| 1026 ConstructorBodyElement(FunctionElement constructor) | 1080 ConstructorBodyElement(FunctionElement constructor) |
| 1027 : this.constructor = constructor, | 1081 : this.constructor = constructor, |
| 1028 super(constructor.name, | 1082 super(constructor.name, |
| 1029 ElementKind.GENERATIVE_CONSTRUCTOR_BODY, | 1083 ElementKind.GENERATIVE_CONSTRUCTOR_BODY, |
| 1030 null, | 1084 null, |
| 1031 constructor.enclosingElement) { | 1085 constructor.enclosingElement) { |
| 1032 functionSignature = constructor.functionSignature; | 1086 functionSignature = constructor.functionSignature; |
| (...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1148 ClassNode node = parseNode(compiler); | 1202 ClassNode node = parseNode(compiler); |
| 1149 Link<DartType> parameters = | 1203 Link<DartType> parameters = |
| 1150 TypeDeclarationElement.createTypeVariables(this, node.typeParameters); | 1204 TypeDeclarationElement.createTypeVariables(this, node.typeParameters); |
| 1151 type = new InterfaceType(this, parameters); | 1205 type = new InterfaceType(this, parameters); |
| 1152 } | 1206 } |
| 1153 return type; | 1207 return type; |
| 1154 } | 1208 } |
| 1155 | 1209 |
| 1156 bool get isPatched => patch != null; | 1210 bool get isPatched => patch != null; |
| 1157 | 1211 |
| 1212 /** |
| 1213 * Return [:true:] if this element is the [:Object:] class for the [compiler]. |
| 1214 */ |
| 1215 bool isObject(Compiler compiler) => |
| 1216 declaration === compiler.objectClass; |
| 1217 |
| 1158 Link<DartType> get typeVariables => type.arguments; | 1218 Link<DartType> get typeVariables => type.arguments; |
| 1159 | 1219 |
| 1160 ClassElement ensureResolved(Compiler compiler) { | 1220 ClassElement ensureResolved(Compiler compiler) { |
| 1161 if (resolutionState == STATE_NOT_STARTED) { | 1221 if (resolutionState == STATE_NOT_STARTED) { |
| 1162 compiler.resolver.resolveClass(this); | 1222 compiler.resolver.resolveClass(this); |
| 1163 } | 1223 } |
| 1164 return this; | 1224 return this; |
| 1165 } | 1225 } |
| 1166 | 1226 |
| 1167 /** | 1227 /** |
| (...skipping 523 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1691 | 1751 |
| 1692 MetadataAnnotation ensureResolved(Compiler compiler) { | 1752 MetadataAnnotation ensureResolved(Compiler compiler) { |
| 1693 if (resolutionState == STATE_NOT_STARTED) { | 1753 if (resolutionState == STATE_NOT_STARTED) { |
| 1694 compiler.resolver.resolveMetadataAnnotation(this); | 1754 compiler.resolver.resolveMetadataAnnotation(this); |
| 1695 } | 1755 } |
| 1696 return this; | 1756 return this; |
| 1697 } | 1757 } |
| 1698 | 1758 |
| 1699 String toString() => 'MetadataAnnotation($value, $resolutionState)'; | 1759 String toString() => 'MetadataAnnotation($value, $resolutionState)'; |
| 1700 } | 1760 } |
| OLD | NEW |