| 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 part of dart_backend; | 5 part of dart_backend; |
| 6 | 6 |
| 7 // TODO(ahe): This class is simply wrong. This backend should use | 7 // TODO(ahe): This class is simply wrong. This backend should use |
| 8 // elements when it can, not AST nodes. Perhaps a [Map<Element, | 8 // elements when it can, not AST nodes. Perhaps a [Map<Element, |
| 9 // TreeElements>] is what is needed. | 9 // TreeElements>] is what is needed. |
| 10 class ElementAst { | 10 class ElementAst { |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 45 DartImpactTransformer impactTransformer; | 45 DartImpactTransformer impactTransformer; |
| 46 | 46 |
| 47 final Set<ClassElement> usedTypeLiterals = new Set<ClassElement>(); | 47 final Set<ClassElement> usedTypeLiterals = new Set<ClassElement>(); |
| 48 | 48 |
| 49 /// The set of visible platform classes that are implemented by instantiated | 49 /// The set of visible platform classes that are implemented by instantiated |
| 50 /// user classes. | 50 /// user classes. |
| 51 final Set<ClassElement> _userImplementedPlatformClasses = | 51 final Set<ClassElement> _userImplementedPlatformClasses = |
| 52 new Set<ClassElement>(); | 52 new Set<ClassElement>(); |
| 53 | 53 |
| 54 bool enableCodegenWithErrorsIfSupported(Spannable node) { | 54 bool enableCodegenWithErrorsIfSupported(Spannable node) { |
| 55 reporter.reportHintMessage( | 55 reporter.reportHintMessage(node, MessageKind.GENERIC, { |
| 56 node, | 56 'text': "Generation of code with compile time errors is not " |
| 57 MessageKind.GENERIC, | 57 "supported for dart2dart." |
| 58 {'text': "Generation of code with compile time errors is not " | 58 }); |
| 59 "supported for dart2dart."}); | |
| 60 return false; | 59 return false; |
| 61 } | 60 } |
| 62 | 61 |
| 63 /** | 62 /** |
| 64 * Tells whether it is safe to remove type declarations from variables, | 63 * Tells whether it is safe to remove type declarations from variables, |
| 65 * functions parameters. It becomes not safe if: | 64 * functions parameters. It becomes not safe if: |
| 66 * 1) TypeError is used somewhere in the code, | 65 * 1) TypeError is used somewhere in the code, |
| 67 * 2) The code has typedefs in right hand side of IS checks, | 66 * 2) The code has typedefs in right hand side of IS checks, |
| 68 * 3) The code has classes which extend typedefs, have type arguments typedefs | 67 * 3) The code has classes which extend typedefs, have type arguments typedefs |
| 69 * or type variable bounds typedefs. | 68 * or type variable bounds typedefs. |
| 70 * These restrictions can be less strict. | 69 * These restrictions can be less strict. |
| 71 */ | 70 */ |
| 72 bool isSafeToRemoveTypeDeclarations( | 71 bool isSafeToRemoveTypeDeclarations( |
| 73 Map<ClassElement, Iterable<Element>> classMembers) { | 72 Map<ClassElement, Iterable<Element>> classMembers) { |
| 74 ClassElement typeErrorElement = compiler.coreLibrary.find('TypeError'); | 73 ClassElement typeErrorElement = compiler.coreLibrary.find('TypeError'); |
| 75 if (classMembers.containsKey(typeErrorElement) || | 74 if (classMembers.containsKey(typeErrorElement) || |
| 76 compiler.resolverWorld.isChecks.any( | 75 compiler.resolverWorld.isChecks |
| 77 (DartType type) => type.element == typeErrorElement)) { | 76 .any((DartType type) => type.element == typeErrorElement)) { |
| 78 return false; | 77 return false; |
| 79 } | 78 } |
| 80 Set<DartType> processedTypes = new Set<DartType>(); | 79 Set<DartType> processedTypes = new Set<DartType>(); |
| 81 List<DartType> workQueue = new List<DartType>(); | 80 List<DartType> workQueue = new List<DartType>(); |
| 82 workQueue.addAll( | 81 workQueue |
| 83 classMembers.keys.map((classElement) => classElement.thisType)); | 82 .addAll(classMembers.keys.map((classElement) => classElement.thisType)); |
| 84 workQueue.addAll(compiler.resolverWorld.isChecks); | 83 workQueue.addAll(compiler.resolverWorld.isChecks); |
| 85 | 84 |
| 86 while (!workQueue.isEmpty) { | 85 while (!workQueue.isEmpty) { |
| 87 DartType type = workQueue.removeLast(); | 86 DartType type = workQueue.removeLast(); |
| 88 if (processedTypes.contains(type)) continue; | 87 if (processedTypes.contains(type)) continue; |
| 89 processedTypes.add(type); | 88 processedTypes.add(type); |
| 90 if (type is FunctionType) return false; | 89 if (type is FunctionType) return false; |
| 91 if (type is TypedefType) return false; | 90 if (type is TypedefType) return false; |
| 92 if (type is InterfaceType) { | 91 if (type is InterfaceType) { |
| 93 InterfaceType interfaceType = type; | 92 InterfaceType interfaceType = type; |
| (...skipping 15 matching lines...) Expand all Loading... |
| 109 constantCompilerTask = new DartConstantTask(compiler), | 108 constantCompilerTask = new DartConstantTask(compiler), |
| 110 outputter = new DartOutputter( | 109 outputter = new DartOutputter( |
| 111 compiler.reporter, compiler.outputProvider, | 110 compiler.reporter, compiler.outputProvider, |
| 112 forceStripTypes: strips.indexOf('types') != -1, | 111 forceStripTypes: strips.indexOf('types') != -1, |
| 113 multiFile: multiFile, | 112 multiFile: multiFile, |
| 114 enableMinification: compiler.options.enableMinification), | 113 enableMinification: compiler.options.enableMinification), |
| 115 super(compiler) { | 114 super(compiler) { |
| 116 impactTransformer = new DartImpactTransformer(this); | 115 impactTransformer = new DartImpactTransformer(this); |
| 117 } | 116 } |
| 118 | 117 |
| 119 | |
| 120 DiagnosticReporter get reporter => compiler.reporter; | 118 DiagnosticReporter get reporter => compiler.reporter; |
| 121 | 119 |
| 122 Resolution get resolution => compiler.resolution; | 120 Resolution get resolution => compiler.resolution; |
| 123 | 121 |
| 124 bool classNeedsRti(ClassElement cls) => false; | 122 bool classNeedsRti(ClassElement cls) => false; |
| 125 bool methodNeedsRti(FunctionElement function) => false; | 123 bool methodNeedsRti(FunctionElement function) => false; |
| 126 | 124 |
| 127 void enqueueHelpers(ResolutionEnqueuer world, Registry registry) { | 125 void enqueueHelpers(ResolutionEnqueuer world, Registry registry) { |
| 128 // Right now resolver doesn't always resolve interfaces needed | 126 // Right now resolver doesn't always resolve interfaces needed |
| 129 // for literals, so force them. TODO(antonm): fix in the resolver. | 127 // for literals, so force them. TODO(antonm): fix in the resolver. |
| 130 final LITERAL_TYPE_NAMES = const [ | 128 final LITERAL_TYPE_NAMES = const [ |
| 131 'Map', 'List', 'num', 'int', 'double', 'bool' | 129 'Map', |
| 130 'List', |
| 131 'num', |
| 132 'int', |
| 133 'double', |
| 134 'bool' |
| 132 ]; | 135 ]; |
| 133 final coreLibrary = compiler.coreLibrary; | 136 final coreLibrary = compiler.coreLibrary; |
| 134 for (final name in LITERAL_TYPE_NAMES) { | 137 for (final name in LITERAL_TYPE_NAMES) { |
| 135 ClassElement classElement = coreLibrary.findLocal(name); | 138 ClassElement classElement = coreLibrary.findLocal(name); |
| 136 classElement.ensureResolved(resolution); | 139 classElement.ensureResolved(resolution); |
| 137 } | 140 } |
| 138 // Enqueue the methods that the VM might invoke on user objects because | 141 // Enqueue the methods that the VM might invoke on user objects because |
| 139 // we don't trust the resolution to always get these included. | 142 // we don't trust the resolution to always get these included. |
| 140 world.registerDynamicUse(new DynamicUse(Selectors.toString_, null)); | 143 world.registerDynamicUse(new DynamicUse(Selectors.toString_, null)); |
| 141 world.registerDynamicUse( | 144 world.registerDynamicUse(new DynamicUse(Selectors.hashCode_, null)); |
| 142 new DynamicUse(Selectors.hashCode_, null)); | |
| 143 world.registerDynamicUse( | 145 world.registerDynamicUse( |
| 144 new DynamicUse(new Selector.binaryOperator('=='), null)); | 146 new DynamicUse(new Selector.binaryOperator('=='), null)); |
| 145 world.registerDynamicUse( | 147 world.registerDynamicUse(new DynamicUse(Selectors.compareTo, null)); |
| 146 new DynamicUse(Selectors.compareTo, null)); | |
| 147 } | 148 } |
| 148 | 149 |
| 149 WorldImpact codegen(CodegenWorkItem work) { | 150 WorldImpact codegen(CodegenWorkItem work) { |
| 150 return const WorldImpact(); | 151 return const WorldImpact(); |
| 151 } | 152 } |
| 152 | 153 |
| 153 /** | 154 /** |
| 154 * Tells whether we should output given element. Corelib classes like | 155 * Tells whether we should output given element. Corelib classes like |
| 155 * Object should not be in the resulting code. | 156 * Object should not be in the resulting code. |
| 156 */ | 157 */ |
| 157 @override | 158 @override |
| 158 bool shouldOutput(Element element) { | 159 bool shouldOutput(Element element) { |
| 159 return (!element.library.isPlatformLibrary && | 160 return (!element.library.isPlatformLibrary && |
| 160 !element.isSynthesized && | 161 !element.isSynthesized && |
| 161 element is! AbstractFieldElement) | 162 element is! AbstractFieldElement) || |
| 162 || mirrorRenamer.isMirrorHelperLibrary(element.library); | 163 mirrorRenamer.isMirrorHelperLibrary(element.library); |
| 163 } | 164 } |
| 164 | 165 |
| 165 int assembleProgram() { | 166 int assembleProgram() { |
| 166 ElementAst computeElementAst(AstElement element) { | 167 ElementAst computeElementAst(AstElement element) { |
| 167 return new ElementAst(element.resolvedAst.node, | 168 return new ElementAst( |
| 168 element.resolvedAst.elements); | 169 element.resolvedAst.node, element.resolvedAst.elements); |
| 169 } | 170 } |
| 170 | 171 |
| 171 // TODO(johnniwinther): Remove the need for this method. | 172 // TODO(johnniwinther): Remove the need for this method. |
| 172 void postProcessElementAst( | 173 void postProcessElementAst(AstElement element, ElementAst elementAst, |
| 173 AstElement element, ElementAst elementAst, | 174 newTypedefElementCallback, newClassElementCallback) { |
| 174 newTypedefElementCallback, | 175 ReferencedElementCollector collector = new ReferencedElementCollector( |
| 175 newClassElementCallback) { | 176 reporter, |
| 176 ReferencedElementCollector collector = | 177 element, |
| 177 new ReferencedElementCollector(reporter, | 178 elementAst, |
| 178 element, | 179 newTypedefElementCallback, |
| 179 elementAst, | 180 newClassElementCallback); |
| 180 newTypedefElementCallback, | |
| 181 newClassElementCallback); | |
| 182 collector.collect(); | 181 collector.collect(); |
| 183 } | 182 } |
| 184 | 183 |
| 185 int totalSize = outputter.assembleProgram( | 184 int totalSize = outputter.assembleProgram( |
| 186 libraries: compiler.libraryLoader.libraries, | 185 libraries: compiler.libraryLoader.libraries, |
| 187 instantiatedClasses: compiler.resolverWorld.directlyInstantiatedClasses, | 186 instantiatedClasses: compiler.resolverWorld.directlyInstantiatedClasses, |
| 188 resolvedElements: compiler.enqueuer.resolution.processedElements, | 187 resolvedElements: compiler.enqueuer.resolution.processedElements, |
| 189 usedTypeLiterals: usedTypeLiterals, | 188 usedTypeLiterals: usedTypeLiterals, |
| 190 postProcessElementAst: postProcessElementAst, | 189 postProcessElementAst: postProcessElementAst, |
| 191 computeElementAst: computeElementAst, | 190 computeElementAst: computeElementAst, |
| 192 shouldOutput: shouldOutput, | 191 shouldOutput: shouldOutput, |
| 193 isSafeToRemoveTypeDeclarations: isSafeToRemoveTypeDeclarations, | 192 isSafeToRemoveTypeDeclarations: isSafeToRemoveTypeDeclarations, |
| 194 sortElements: Elements.sortedByPosition, | 193 sortElements: Elements.sortedByPosition, |
| 195 mirrorRenamer: mirrorRenamer, | 194 mirrorRenamer: mirrorRenamer, |
| 196 mainFunction: compiler.mainFunction, | 195 mainFunction: compiler.mainFunction, |
| 197 outputUri: compiler.options.outputUri); | 196 outputUri: compiler.options.outputUri); |
| 198 | 197 |
| 199 // Output verbose info about size ratio of resulting bundle to all | 198 // Output verbose info about size ratio of resulting bundle to all |
| 200 // referenced non-platform sources. | 199 // referenced non-platform sources. |
| 201 logResultBundleSizeInfo( | 200 logResultBundleSizeInfo(outputter.libraryInfo.userLibraries, |
| 202 outputter.libraryInfo.userLibraries, | 201 outputter.elementInfo.topLevelElements, totalSize); |
| 203 outputter.elementInfo.topLevelElements, | |
| 204 totalSize); | |
| 205 | 202 |
| 206 return totalSize; | 203 return totalSize; |
| 207 } | 204 } |
| 208 | 205 |
| 209 void logResultBundleSizeInfo(Iterable<LibraryElement> userLibraries, | 206 void logResultBundleSizeInfo(Iterable<LibraryElement> userLibraries, |
| 210 Iterable<Element> topLevelElements, | 207 Iterable<Element> topLevelElements, int totalOutputSize) { |
| 211 int totalOutputSize) { | |
| 212 // Sum total size of scripts in each referenced library. | 208 // Sum total size of scripts in each referenced library. |
| 213 int nonPlatformSize = 0; | 209 int nonPlatformSize = 0; |
| 214 for (LibraryElement lib in userLibraries) { | 210 for (LibraryElement lib in userLibraries) { |
| 215 for (CompilationUnitElement compilationUnit in lib.compilationUnits) { | 211 for (CompilationUnitElement compilationUnit in lib.compilationUnits) { |
| 216 nonPlatformSize += compilationUnit.script.file.length; | 212 nonPlatformSize += compilationUnit.script.file.length; |
| 217 } | 213 } |
| 218 } | 214 } |
| 219 int percentage = totalOutputSize * 100 ~/ nonPlatformSize; | 215 int percentage = totalOutputSize * 100 ~/ nonPlatformSize; |
| 220 log('Total used non-platform files size: ${nonPlatformSize} bytes, ' | 216 log('Total used non-platform files size: ${nonPlatformSize} bytes, ' |
| 221 'Output total size: $totalOutputSize bytes (${percentage}%)'); | 217 'Output total size: $totalOutputSize bytes (${percentage}%)'); |
| (...skipping 10 matching lines...) Expand all Loading... |
| 232 library.forEachLocalMember((Element element) { | 228 library.forEachLocalMember((Element element) { |
| 233 if (element.isClass) { | 229 if (element.isClass) { |
| 234 ClassElement classElement = element; | 230 ClassElement classElement = element; |
| 235 classElement.ensureResolved(resolution); | 231 classElement.ensureResolved(resolution); |
| 236 } | 232 } |
| 237 }); | 233 }); |
| 238 } | 234 } |
| 239 }); | 235 }); |
| 240 if (useMirrorHelperLibrary && | 236 if (useMirrorHelperLibrary && |
| 241 loadedLibraries.containsLibrary(Uris.dart_mirrors)) { | 237 loadedLibraries.containsLibrary(Uris.dart_mirrors)) { |
| 242 return compiler.libraryLoader.loadLibrary( | 238 return compiler.libraryLoader |
| 243 compiler.translateResolvedUri( | 239 .loadLibrary(compiler.translateResolvedUri( |
| 244 loadedLibraries.getLibrary(Uris.dart_mirrors), | 240 loadedLibraries.getLibrary(Uris.dart_mirrors), |
| 245 MirrorRenamerImpl.DART_MIRROR_HELPER, null)). | 241 MirrorRenamerImpl.DART_MIRROR_HELPER, |
| 246 then((LibraryElement library) { | 242 null)) |
| 243 .then((LibraryElement library) { |
| 247 mirrorRenamer = new MirrorRenamerImpl(compiler, this, library); | 244 mirrorRenamer = new MirrorRenamerImpl(compiler, this, library); |
| 248 }); | 245 }); |
| 249 } | 246 } |
| 250 return new Future.value(); | 247 return new Future.value(); |
| 251 } | 248 } |
| 252 | 249 |
| 253 @override | 250 @override |
| 254 void registerStaticUse(Element element, Enqueuer enqueuer) { | 251 void registerStaticUse(Element element, Enqueuer enqueuer) { |
| 255 if (element == compiler.mirrorSystemGetNameFunction) { | 252 if (element == compiler.mirrorSystemGetNameFunction) { |
| 256 FunctionElement getNameFunction = mirrorRenamer.getNameFunction; | 253 FunctionElement getNameFunction = mirrorRenamer.getNameFunction; |
| 257 if (getNameFunction != null) { | 254 if (getNameFunction != null) { |
| 258 enqueuer.addToWorkList(getNameFunction); | 255 enqueuer.addToWorkList(getNameFunction); |
| 259 } | 256 } |
| 260 } | 257 } |
| 261 } | 258 } |
| 262 | 259 |
| 263 @override | 260 @override |
| 264 void registerInstantiatedType(InterfaceType type, | 261 void registerInstantiatedType( |
| 265 Enqueuer enqueuer, | 262 InterfaceType type, Enqueuer enqueuer, Registry registry, |
| 266 Registry registry, | 263 {bool mirrorUsage: false}) { |
| 267 {bool mirrorUsage: false}) { | |
| 268 registerPlatformMembers(type, registerUse: registry.registerDynamicUse); | 264 registerPlatformMembers(type, registerUse: registry.registerDynamicUse); |
| 269 super.registerInstantiatedType( | 265 super.registerInstantiatedType(type, enqueuer, registry, |
| 270 type, enqueuer, registry, mirrorUsage: mirrorUsage); | 266 mirrorUsage: mirrorUsage); |
| 271 } | 267 } |
| 272 | 268 |
| 273 /// Register dynamic access of members of [type] that implement members | 269 /// Register dynamic access of members of [type] that implement members |
| 274 /// of types defined in the platform libraries. | 270 /// of types defined in the platform libraries. |
| 275 void registerPlatformMembers( | 271 void registerPlatformMembers(InterfaceType type, |
| 276 InterfaceType type, | |
| 277 {void registerUse(DynamicUse dynamicUse)}) { | 272 {void registerUse(DynamicUse dynamicUse)}) { |
| 278 | |
| 279 // Without patching, dart2dart has no way of performing sound tree-shaking | 273 // Without patching, dart2dart has no way of performing sound tree-shaking |
| 280 // in face external functions. Therefore we employ another scheme: | 274 // in face external functions. Therefore we employ another scheme: |
| 281 // | 275 // |
| 282 // Based on the assumption that the platform code only relies on the | 276 // Based on the assumption that the platform code only relies on the |
| 283 // interfaces of it's own classes, we can approximate the semantics of | 277 // interfaces of it's own classes, we can approximate the semantics of |
| 284 // external functions by eagerly registering dynamic invocation of instance | 278 // external functions by eagerly registering dynamic invocation of instance |
| 285 // members defined the platform interfaces. | 279 // members defined the platform interfaces. |
| 286 // | 280 // |
| 287 // Since we only need to generate code for non-platform classes we can | 281 // Since we only need to generate code for non-platform classes we can |
| 288 // restrict this registration to platform interfaces implemented by | 282 // restrict this registration to platform interfaces implemented by |
| (...skipping 14 matching lines...) Expand all Loading... |
| 303 // Here `MyRandom` is a subtype if `Random` defined in 'dart:math'. By the | 297 // Here `MyRandom` is a subtype if `Random` defined in 'dart:math'. By the |
| 304 // assumption, all methods defined `Random` are potentially called, and | 298 // assumption, all methods defined `Random` are potentially called, and |
| 305 // therefore, though there are no visible call sites from the user node, | 299 // therefore, though there are no visible call sites from the user node, |
| 306 // dynamic invocation of for instance `nextInt` should be registered. In | 300 // dynamic invocation of for instance `nextInt` should be registered. In |
| 307 // this case, `nextInt` is actually called by the standard implementation of | 301 // this case, `nextInt` is actually called by the standard implementation of |
| 308 // `shuffle`. | 302 // `shuffle`. |
| 309 | 303 |
| 310 ClassElement cls = type.element; | 304 ClassElement cls = type.element; |
| 311 if (!cls.library.isPlatformLibrary) { | 305 if (!cls.library.isPlatformLibrary) { |
| 312 for (Link<DartType> link = cls.allSupertypes; | 306 for (Link<DartType> link = cls.allSupertypes; |
| 313 !link.isEmpty; | 307 !link.isEmpty; |
| 314 link = link.tail) { | 308 link = link.tail) { |
| 315 InterfaceType supertype = link.head; | 309 InterfaceType supertype = link.head; |
| 316 ClassElement superclass = supertype.element; | 310 ClassElement superclass = supertype.element; |
| 317 LibraryElement library = superclass.library; | 311 LibraryElement library = superclass.library; |
| 318 if (library.isPlatformLibrary) { | 312 if (library.isPlatformLibrary) { |
| 319 if (_userImplementedPlatformClasses.add(superclass)) { | 313 if (_userImplementedPlatformClasses.add(superclass)) { |
| 320 // Register selectors for all instance methods since these might | 314 // Register selectors for all instance methods since these might |
| 321 // be called on user classes from within the platform | 315 // be called on user classes from within the platform |
| 322 // implementation. | 316 // implementation. |
| 323 superclass.forEachLocalMember((MemberElement element) { | 317 superclass.forEachLocalMember((MemberElement element) { |
| 324 if (element.isConstructor || element.isStatic) return; | 318 if (element.isConstructor || element.isStatic) return; |
| 325 | 319 |
| 326 FunctionElement function = element.asFunctionElement(); | 320 FunctionElement function = element.asFunctionElement(); |
| 327 element.computeType(resolution); | 321 element.computeType(resolution); |
| 328 Selector selector = new Selector.fromElement(element); | 322 Selector selector = new Selector.fromElement(element); |
| 329 registerUse( | 323 registerUse(new DynamicUse(selector, null)); |
| 330 new DynamicUse(selector, null)); | |
| 331 }); | 324 }); |
| 332 } | 325 } |
| 333 } | 326 } |
| 334 } | 327 } |
| 335 } | 328 } |
| 336 } | 329 } |
| 337 | 330 |
| 338 @override | 331 @override |
| 339 bool enableDeferredLoadingIfSupported(Spannable node, Registry registry) { | 332 bool enableDeferredLoadingIfSupported(Spannable node, Registry registry) { |
| 340 // TODO(sigurdm): Implement deferred loading for dart2dart. | 333 // TODO(sigurdm): Implement deferred loading for dart2dart. |
| (...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 395 | 388 |
| 396 unparseFunctionName(Node name) { | 389 unparseFunctionName(Node name) { |
| 397 if (name != null && renames.containsKey(name)) { | 390 if (name != null && renames.containsKey(name)) { |
| 398 write(renames[name]); | 391 write(renames[name]); |
| 399 } else { | 392 } else { |
| 400 super.unparseFunctionName(name); | 393 super.unparseFunctionName(name); |
| 401 } | 394 } |
| 402 } | 395 } |
| 403 } | 396 } |
| 404 | 397 |
| 405 | |
| 406 /** | 398 /** |
| 407 * Some elements are not recorded by resolver now, | 399 * Some elements are not recorded by resolver now, |
| 408 * for example, typedefs or classes which are only | 400 * for example, typedefs or classes which are only |
| 409 * used in signatures, as/is operators or in super clauses | 401 * used in signatures, as/is operators or in super clauses |
| 410 * (just to name a few). Retraverse AST to pick those up. | 402 * (just to name a few). Retraverse AST to pick those up. |
| 411 */ | 403 */ |
| 412 class ReferencedElementCollector extends Visitor { | 404 class ReferencedElementCollector extends Visitor { |
| 413 final DiagnosticReporter reporter; | 405 final DiagnosticReporter reporter; |
| 414 final Element element; | 406 final Element element; |
| 415 final ElementAst elementAst; | 407 final ElementAst elementAst; |
| 416 final newTypedefElementCallback; | 408 final newTypedefElementCallback; |
| 417 final newClassElementCallback; | 409 final newClassElementCallback; |
| 418 | 410 |
| 419 ReferencedElementCollector(this.reporter, | 411 ReferencedElementCollector(this.reporter, this.element, this.elementAst, |
| 420 this.element, | 412 this.newTypedefElementCallback, this.newClassElementCallback); |
| 421 this.elementAst, | |
| 422 this.newTypedefElementCallback, | |
| 423 this.newClassElementCallback); | |
| 424 | 413 |
| 425 visitNode(Node node) { | 414 visitNode(Node node) { |
| 426 node.visitChildren(this); | 415 node.visitChildren(this); |
| 427 } | 416 } |
| 428 | 417 |
| 429 visitTypeAnnotation(TypeAnnotation typeAnnotation) { | 418 visitTypeAnnotation(TypeAnnotation typeAnnotation) { |
| 430 TreeElements treeElements = elementAst.treeElements; | 419 TreeElements treeElements = elementAst.treeElements; |
| 431 final DartType type = treeElements.getType(typeAnnotation); | 420 final DartType type = treeElements.getType(typeAnnotation); |
| 432 assert(invariant(typeAnnotation, type != null, | 421 assert(invariant(typeAnnotation, type != null, |
| 433 message: "Missing type for type annotation: $treeElements.")); | 422 message: "Missing type for type annotation: $treeElements.")); |
| (...skipping 25 matching lines...) Expand all Loading... |
| 459 | 448 |
| 460 /// [ConstantCompilerTask] for compilation of constants for the Dart backend. | 449 /// [ConstantCompilerTask] for compilation of constants for the Dart backend. |
| 461 /// | 450 /// |
| 462 /// Since this task needs no distinction between frontend and backend constants | 451 /// Since this task needs no distinction between frontend and backend constants |
| 463 /// it also serves as the [BackendConstantEnvironment]. | 452 /// it also serves as the [BackendConstantEnvironment]. |
| 464 class DartConstantTask extends ConstantCompilerTask | 453 class DartConstantTask extends ConstantCompilerTask |
| 465 implements BackendConstantEnvironment { | 454 implements BackendConstantEnvironment { |
| 466 final DartConstantCompiler constantCompiler; | 455 final DartConstantCompiler constantCompiler; |
| 467 | 456 |
| 468 DartConstantTask(Compiler compiler) | 457 DartConstantTask(Compiler compiler) |
| 469 : this.constantCompiler = new DartConstantCompiler(compiler), | 458 : this.constantCompiler = new DartConstantCompiler(compiler), |
| 470 super(compiler); | 459 super(compiler); |
| 471 | 460 |
| 472 String get name => 'ConstantHandler'; | 461 String get name => 'ConstantHandler'; |
| 473 | 462 |
| 474 @override | 463 @override |
| 475 ConstantSystem get constantSystem => constantCompiler.constantSystem; | 464 ConstantSystem get constantSystem => constantCompiler.constantSystem; |
| 476 | 465 |
| 477 @override | 466 @override |
| 478 ConstantValue getConstantValue(ConstantExpression expression) { | 467 ConstantValue getConstantValue(ConstantExpression expression) { |
| 479 return constantCompiler.getConstantValue(expression); | 468 return constantCompiler.getConstantValue(expression); |
| 480 } | 469 } |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 519 }); | 508 }); |
| 520 } | 509 } |
| 521 | 510 |
| 522 void compileVariable(VariableElement element) { | 511 void compileVariable(VariableElement element) { |
| 523 measure(() { | 512 measure(() { |
| 524 constantCompiler.compileVariable(element); | 513 constantCompiler.compileVariable(element); |
| 525 }); | 514 }); |
| 526 } | 515 } |
| 527 | 516 |
| 528 @override | 517 @override |
| 529 ConstantExpression compileNode( | 518 ConstantExpression compileNode(Node node, TreeElements elements, |
| 530 Node node, | |
| 531 TreeElements elements, | |
| 532 {bool enforceConst: true}) { | 519 {bool enforceConst: true}) { |
| 533 return measure(() { | 520 return measure(() { |
| 534 return constantCompiler.compileNodeWithDefinitions(node, elements, | 521 return constantCompiler.compileNodeWithDefinitions(node, elements, |
| 535 isConst: enforceConst); | 522 isConst: enforceConst); |
| 536 }); | 523 }); |
| 537 } | 524 } |
| 538 | 525 |
| 539 @override | 526 @override |
| 540 ConstantExpression compileMetadata( | 527 ConstantExpression compileMetadata( |
| 541 MetadataAnnotation metadata, | 528 MetadataAnnotation metadata, Node node, TreeElements elements) { |
| 542 Node node, | |
| 543 TreeElements elements) { | |
| 544 return measure(() { | 529 return measure(() { |
| 545 return constantCompiler.compileMetadata(metadata, node, elements); | 530 return constantCompiler.compileMetadata(metadata, node, elements); |
| 546 }); | 531 }); |
| 547 } | 532 } |
| 548 | 533 |
| 549 // TODO(johnniwinther): Remove this when values are computed from the | 534 // TODO(johnniwinther): Remove this when values are computed from the |
| 550 // expressions. | 535 // expressions. |
| 551 @override | 536 @override |
| 552 void copyConstantValues(DartConstantTask task) { | 537 void copyConstantValues(DartConstantTask task) { |
| 553 constantCompiler.constantValueMap.addAll( | 538 constantCompiler.constantValueMap |
| 554 task.constantCompiler.constantValueMap); | 539 .addAll(task.constantCompiler.constantValueMap); |
| 555 } | 540 } |
| 556 } | 541 } |
| OLD | NEW |