| OLD | NEW |
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, 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 // Tests that the closed world computed from [WorldImpact]s derived from kernel | 5 // Tests that the closed world computed from [WorldImpact]s derived from kernel |
| 6 // is equivalent to the original computed from resolution. | 6 // is equivalent to the original computed from resolution. |
| 7 library dart2js.kernel.closed_world_test; | 7 library dart2js.kernel.closed_world_test; |
| 8 | 8 |
| 9 import 'package:async_helper/async_helper.dart'; | 9 import 'package:async_helper/async_helper.dart'; |
| 10 import 'package:compiler/src/closure.dart'; |
| 10 import 'package:compiler/src/commandline_options.dart'; | 11 import 'package:compiler/src/commandline_options.dart'; |
| 11 import 'package:compiler/src/common.dart'; | 12 import 'package:compiler/src/common.dart'; |
| 12 import 'package:compiler/src/common_elements.dart'; | 13 import 'package:compiler/src/common_elements.dart'; |
| 13 import 'package:compiler/src/common/backend_api.dart'; | 14 import 'package:compiler/src/common/backend_api.dart'; |
| 14 import 'package:compiler/src/common/resolution.dart'; | 15 import 'package:compiler/src/common/resolution.dart'; |
| 16 import 'package:compiler/src/common/work.dart'; |
| 15 import 'package:compiler/src/compiler.dart'; | 17 import 'package:compiler/src/compiler.dart'; |
| 16 import 'package:compiler/src/deferred_load.dart'; | 18 import 'package:compiler/src/deferred_load.dart'; |
| 17 import 'package:compiler/src/elements/resolution_types.dart'; | 19 import 'package:compiler/src/elements/resolution_types.dart'; |
| 18 import 'package:compiler/src/elements/elements.dart'; | 20 import 'package:compiler/src/elements/elements.dart'; |
| 21 import 'package:compiler/src/elements/entities.dart'; |
| 22 import 'package:compiler/src/elements/types.dart'; |
| 19 import 'package:compiler/src/enqueue.dart'; | 23 import 'package:compiler/src/enqueue.dart'; |
| 20 import 'package:compiler/src/js_backend/backend.dart'; | 24 import 'package:compiler/src/js_backend/backend.dart'; |
| 21 import 'package:compiler/src/js_backend/backend_helpers.dart'; | 25 import 'package:compiler/src/js_backend/backend_helpers.dart'; |
| 22 import 'package:compiler/src/js_backend/backend_impact.dart'; | 26 import 'package:compiler/src/js_backend/backend_impact.dart'; |
| 23 import 'package:compiler/src/js_backend/backend_usage.dart'; | 27 import 'package:compiler/src/js_backend/backend_usage.dart'; |
| 24 import 'package:compiler/src/js_backend/custom_elements_analysis.dart'; | 28 import 'package:compiler/src/js_backend/custom_elements_analysis.dart'; |
| 25 import 'package:compiler/src/js_backend/native_data.dart'; | 29 import 'package:compiler/src/js_backend/native_data.dart'; |
| 30 import 'package:compiler/src/js_backend/impact_transformer.dart'; |
| 26 import 'package:compiler/src/js_backend/interceptor_data.dart'; | 31 import 'package:compiler/src/js_backend/interceptor_data.dart'; |
| 27 import 'package:compiler/src/js_backend/lookup_map_analysis.dart'; | 32 import 'package:compiler/src/js_backend/lookup_map_analysis.dart'; |
| 28 import 'package:compiler/src/js_backend/mirrors_analysis.dart'; | 33 import 'package:compiler/src/js_backend/mirrors_analysis.dart'; |
| 29 import 'package:compiler/src/js_backend/mirrors_data.dart'; | 34 import 'package:compiler/src/js_backend/mirrors_data.dart'; |
| 30 import 'package:compiler/src/js_backend/no_such_method_registry.dart'; | 35 import 'package:compiler/src/js_backend/no_such_method_registry.dart'; |
| 31 import 'package:compiler/src/js_backend/resolution_listener.dart'; | 36 import 'package:compiler/src/js_backend/resolution_listener.dart'; |
| 32 import 'package:compiler/src/js_backend/type_variable_handler.dart'; | 37 import 'package:compiler/src/js_backend/type_variable_handler.dart'; |
| 33 import 'package:compiler/src/native/enqueue.dart'; | 38 import 'package:compiler/src/native/enqueue.dart'; |
| 34 import 'package:compiler/src/kernel/world_builder.dart'; | 39 import 'package:compiler/src/kernel/world_builder.dart'; |
| 35 import 'package:compiler/src/options.dart'; | 40 import 'package:compiler/src/options.dart'; |
| 36 import 'package:compiler/src/ssa/kernel_impact.dart'; | 41 import 'package:compiler/src/ssa/kernel_impact.dart'; |
| 37 import 'package:compiler/src/serialization/equivalence.dart'; | 42 import 'package:compiler/src/serialization/equivalence.dart'; |
| 38 import 'package:compiler/src/universe/world_builder.dart'; | 43 import 'package:compiler/src/universe/world_builder.dart'; |
| 39 import 'package:compiler/src/universe/world_impact.dart'; | 44 import 'package:compiler/src/universe/world_impact.dart'; |
| 40 import 'package:compiler/src/world.dart'; | 45 import 'package:compiler/src/world.dart'; |
| 46 import 'package:kernel/ast.dart' as ir; |
| 41 import 'impact_test.dart'; | 47 import 'impact_test.dart'; |
| 42 import '../memory_compiler.dart'; | 48 import '../memory_compiler.dart'; |
| 43 import '../serialization/helper.dart'; | 49 import '../serialization/helper.dart'; |
| 44 import '../serialization/model_test_helper.dart'; | 50 import '../serialization/model_test_helper.dart'; |
| 45 | 51 |
| 46 const SOURCE = const { | 52 const SOURCE = const { |
| 47 'main.dart': ''' | 53 'main.dart': ''' |
| 48 abstract class A { | 54 abstract class A { |
| 49 // redirecting factory in abstract class to other class | 55 // redirecting factory in abstract class to other class |
| 50 factory A.a() = D.a; | 56 factory A.a() = D.a; |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 101 // Create a new resolution enqueuer and feed it with the [WorldImpact]s | 107 // Create a new resolution enqueuer and feed it with the [WorldImpact]s |
| 102 // computed from kernel through the [build] in `kernel_impact.dart`. | 108 // computed from kernel through the [build] in `kernel_impact.dart`. |
| 103 ResolutionEnqueuer enqueuer = new ResolutionEnqueuer( | 109 ResolutionEnqueuer enqueuer = new ResolutionEnqueuer( |
| 104 compiler.enqueuer, | 110 compiler.enqueuer, |
| 105 compiler.options, | 111 compiler.options, |
| 106 compiler.reporter, | 112 compiler.reporter, |
| 107 const TreeShakingEnqueuerStrategy(), | 113 const TreeShakingEnqueuerStrategy(), |
| 108 createResolutionEnqueuerListener(compiler), | 114 createResolutionEnqueuerListener(compiler), |
| 109 new ElementResolutionWorldBuilder( | 115 new ElementResolutionWorldBuilder( |
| 110 backend, compiler.resolution, const OpenWorldStrategy()), | 116 backend, compiler.resolution, const OpenWorldStrategy()), |
| 111 new ResolutionWorkItemBuilder(compiler.resolution), | 117 new KernelWorkItemBuilder(compiler), |
| 112 'enqueuer from kernel'); | 118 'enqueuer from kernel'); |
| 113 ClosedWorld closedWorld = computeClosedWorld(compiler, enqueuer); | 119 ClosedWorld closedWorld = computeClosedWorld( |
| 120 compiler.reporter, enqueuer, compiler.elementEnvironment); |
| 114 BackendUsage backendUsage = compiler.backend.backendUsageBuilder.close(); | 121 BackendUsage backendUsage = compiler.backend.backendUsageBuilder.close(); |
| 115 checkResolutionEnqueuers( | 122 checkResolutionEnqueuers( |
| 116 backendUsage, backendUsage, compiler.enqueuer.resolution, enqueuer, | 123 backendUsage, backendUsage, compiler.enqueuer.resolution, enqueuer, |
| 117 typeEquivalence: (ResolutionDartType a, ResolutionDartType b) { | 124 typeEquivalence: (ResolutionDartType a, ResolutionDartType b) { |
| 118 return areTypesEquivalent(unalias(a), unalias(b)); | 125 return areTypesEquivalent(unalias(a), unalias(b)); |
| 119 }, elementFilter: (Element element) { | 126 }, elementFilter: (Element element) { |
| 120 if (element is ConstructorElement && element.isRedirectingFactory) { | 127 if (element is ConstructorElement && element.isRedirectingFactory) { |
| 121 // Redirecting factory constructors are skipped in kernel. | 128 // Redirecting factory constructors are skipped in kernel. |
| 122 return false; | 129 return false; |
| 123 } | 130 } |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 156 backend.customElementsResolutionAnalysis, | 163 backend.customElementsResolutionAnalysis, |
| 157 backend.lookupMapResolutionAnalysis, | 164 backend.lookupMapResolutionAnalysis, |
| 158 backend.mirrorsResolutionAnalysis, | 165 backend.mirrorsResolutionAnalysis, |
| 159 new TypeVariableResolutionAnalysis(compiler.elementEnvironment, | 166 new TypeVariableResolutionAnalysis(compiler.elementEnvironment, |
| 160 backend.impacts, backend.backendUsageBuilder), | 167 backend.impacts, backend.backendUsageBuilder), |
| 161 backend.nativeResolutionEnqueuer, | 168 backend.nativeResolutionEnqueuer, |
| 162 compiler.deferredLoadTask, | 169 compiler.deferredLoadTask, |
| 163 backend.kernelTask); | 170 backend.kernelTask); |
| 164 } | 171 } |
| 165 | 172 |
| 166 EnqueuerListener createKernelResolutionEnqueuerListener(CompilerOptions options, | 173 ClosedWorld computeClosedWorld(DiagnosticReporter reporter, |
| 167 DeferredLoadTask deferredLoadTask, KernelWorldBuilder worldBuilder) { | 174 ResolutionEnqueuer enqueuer, ElementEnvironment elementEnvironment) { |
| 168 ElementEnvironment elementEnvironment = worldBuilder.elementEnvironment; | 175 enqueuer.open(const ImpactStrategy(), elementEnvironment.mainFunction, |
| 169 CommonElements commonElements = worldBuilder.commonElements; | 176 elementEnvironment.libraries); |
| 170 BackendHelpers helpers = | 177 enqueuer.forEach((WorkItem work) { |
| 171 new BackendHelpers(elementEnvironment, commonElements); | 178 enqueuer.applyImpact(work.run(), impactSource: work.element); |
| 172 BackendImpacts impacts = new BackendImpacts(options, commonElements, helpers); | 179 }); |
| 173 | 180 return enqueuer.worldBuilder.closeWorld(reporter); |
| 174 // TODO(johnniwinther): Create Kernel based implementations for these: | |
| 175 NativeBasicData nativeBasicData; | |
| 176 RuntimeTypesNeedBuilder rtiNeedBuilder; | |
| 177 MirrorsDataBuilder mirrorsDataBuilder; | |
| 178 CustomElementsResolutionAnalysis customElementsResolutionAnalysis; | |
| 179 LookupMapResolutionAnalysis lookupMapResolutionAnalysis; | |
| 180 MirrorsResolutionAnalysis mirrorsResolutionAnalysis; | |
| 181 | |
| 182 BackendClasses backendClasses = new JavaScriptBackendClasses( | |
| 183 elementEnvironment, helpers, nativeBasicData); | |
| 184 InterceptorDataBuilder interceptorDataBuilder = | |
| 185 new InterceptorDataBuilderImpl( | |
| 186 nativeBasicData, helpers, elementEnvironment, commonElements); | |
| 187 BackendUsageBuilder backendUsageBuilder = | |
| 188 new BackendUsageBuilderImpl(commonElements, helpers); | |
| 189 NoSuchMethodRegistry noSuchMethodRegistry = new NoSuchMethodRegistry( | |
| 190 helpers, new KernelNoSuchMethodResolver(worldBuilder)); | |
| 191 NativeResolutionEnqueuer nativeResolutionEnqueuer = | |
| 192 new NativeResolutionEnqueuer( | |
| 193 options, | |
| 194 elementEnvironment, | |
| 195 commonElements, | |
| 196 helpers, | |
| 197 backendClasses, | |
| 198 backendUsageBuilder, | |
| 199 new KernelNativeClassResolver(worldBuilder)); | |
| 200 | |
| 201 return new ResolutionEnqueuerListener( | |
| 202 options, | |
| 203 elementEnvironment, | |
| 204 commonElements, | |
| 205 helpers, | |
| 206 impacts, | |
| 207 backendClasses, | |
| 208 nativeBasicData, | |
| 209 interceptorDataBuilder, | |
| 210 backendUsageBuilder, | |
| 211 rtiNeedBuilder, | |
| 212 mirrorsDataBuilder, | |
| 213 noSuchMethodRegistry, | |
| 214 customElementsResolutionAnalysis, | |
| 215 lookupMapResolutionAnalysis, | |
| 216 mirrorsResolutionAnalysis, | |
| 217 new TypeVariableResolutionAnalysis( | |
| 218 elementEnvironment, impacts, backendUsageBuilder), | |
| 219 nativeResolutionEnqueuer, | |
| 220 deferredLoadTask); | |
| 221 } | 181 } |
| 222 | 182 |
| 223 ClosedWorld computeClosedWorld(Compiler compiler, ResolutionEnqueuer enqueuer) { | 183 class KernelWorkItemBuilder implements WorkItemBuilder { |
| 224 enqueuer.open(const ImpactStrategy(), compiler.mainFunction, | 184 final Compiler _compiler; |
| 225 compiler.libraryLoader.libraries); | 185 |
| 226 enqueuer.forEach((work) { | 186 KernelWorkItemBuilder(this._compiler); |
| 227 MemberElement element = work.element; | 187 |
| 228 ResolutionImpact resolutionImpact = build(compiler, element.resolvedAst); | 188 @override |
| 229 WorldImpact worldImpact = compiler.backend.impactTransformer | 189 WorkItem createWorkItem(MemberEntity entity) { |
| 230 .transformResolutionImpact(enqueuer, resolutionImpact); | 190 return new KernelWorkItem( |
| 231 enqueuer.applyImpact(worldImpact, impactSource: element); | 191 _compiler, _compiler.backend.impactTransformer, entity); |
| 232 }); | 192 } |
| 233 return enqueuer.worldBuilder.closeWorld(compiler.reporter); | |
| 234 } | 193 } |
| 194 |
| 195 class KernelWorkItem implements ResolutionWorkItem { |
| 196 final Compiler _compiler; |
| 197 final ImpactTransformer _impactTransformer; |
| 198 final MemberElement element; |
| 199 |
| 200 KernelWorkItem(this._compiler, this._impactTransformer, this.element); |
| 201 |
| 202 @override |
| 203 WorldImpact run() { |
| 204 ResolutionImpact resolutionImpact = build(_compiler, element.resolvedAst); |
| 205 return _impactTransformer.transformResolutionImpact(resolutionImpact); |
| 206 } |
| 207 } |
| OLD | NEW |