| 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 js_backend.backend; | 5 library js_backend.backend; |
| 6 | 6 |
| 7 import '../common.dart'; | 7 import '../common.dart'; |
| 8 import '../common/backend_api.dart' | 8 import '../common/backend_api.dart' |
| 9 show ForeignResolver, NativeRegistry, ImpactTransformer; | 9 show ForeignResolver, NativeRegistry, ImpactTransformer; |
| 10 import '../common/codegen.dart' show CodegenImpact, CodegenWorkItem; | 10 import '../common/codegen.dart' show CodegenWorkItem; |
| 11 import '../common/names.dart' show Uris; | 11 import '../common/names.dart' show Uris; |
| 12 import '../common/resolution.dart' show Resolution, Target; | 12 import '../common/resolution.dart' show Resolution, Target; |
| 13 import '../common/tasks.dart' show CompilerTask; | 13 import '../common/tasks.dart' show CompilerTask; |
| 14 import '../compiler.dart' show Compiler; | 14 import '../compiler.dart' show Compiler; |
| 15 import '../constants/constant_system.dart'; | 15 import '../constants/constant_system.dart'; |
| 16 import '../constants/expressions.dart'; | 16 import '../constants/expressions.dart'; |
| 17 import '../constants/values.dart'; | 17 import '../constants/values.dart'; |
| 18 import '../common_elements.dart' show CommonElements; | 18 import '../common_elements.dart' show CommonElements; |
| 19 import '../deferred_load.dart' show DeferredLoadTask; | 19 import '../deferred_load.dart' show DeferredLoadTask; |
| 20 import '../dump_info.dart' show DumpInfoTask; | 20 import '../dump_info.dart' show DumpInfoTask; |
| (...skipping 23 matching lines...) Expand all Loading... |
| 44 import '../library_loader.dart' show LoadedLibraries; | 44 import '../library_loader.dart' show LoadedLibraries; |
| 45 import '../native/native.dart' as native; | 45 import '../native/native.dart' as native; |
| 46 import '../native/resolver.dart'; | 46 import '../native/resolver.dart'; |
| 47 import '../ssa/ssa.dart' show SsaFunctionCompiler; | 47 import '../ssa/ssa.dart' show SsaFunctionCompiler; |
| 48 import '../tracer.dart'; | 48 import '../tracer.dart'; |
| 49 import '../tree/tree.dart'; | 49 import '../tree/tree.dart'; |
| 50 import '../types/types.dart'; | 50 import '../types/types.dart'; |
| 51 import '../universe/call_structure.dart' show CallStructure; | 51 import '../universe/call_structure.dart' show CallStructure; |
| 52 import '../universe/selector.dart' show Selector; | 52 import '../universe/selector.dart' show Selector; |
| 53 import '../universe/world_builder.dart'; | 53 import '../universe/world_builder.dart'; |
| 54 import '../universe/use.dart' show ConstantUse, StaticUse; | |
| 55 import '../universe/world_impact.dart' | 54 import '../universe/world_impact.dart' |
| 56 show ImpactStrategy, ImpactUseCase, WorldImpact, WorldImpactVisitor; | 55 show ImpactStrategy, ImpactUseCase, WorldImpact, WorldImpactVisitor; |
| 57 import '../util/util.dart'; | 56 import '../util/util.dart'; |
| 58 import '../world.dart' show ClosedWorld, ClosedWorldRefiner; | 57 import '../world.dart' show ClosedWorld, ClosedWorldRefiner; |
| 59 import 'annotations.dart'; | 58 import 'annotations.dart'; |
| 60 import 'backend_impact.dart'; | 59 import 'backend_impact.dart'; |
| 61 import 'backend_serialization.dart' show JavaScriptBackendSerialization; | 60 import 'backend_serialization.dart' show JavaScriptBackendSerialization; |
| 62 import 'backend_usage.dart'; | 61 import 'backend_usage.dart'; |
| 63 import 'checked_mode_helpers.dart'; | 62 import 'checked_mode_helpers.dart'; |
| 64 import 'codegen_listener.dart'; | 63 import 'codegen_listener.dart'; |
| (...skipping 266 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 331 return [commonElements.closureClass, commonElements.jsIndexableClass]; | 330 return [commonElements.closureClass, commonElements.jsIndexableClass]; |
| 332 } | 331 } |
| 333 | 332 |
| 334 FunctionCompiler functionCompiler; | 333 FunctionCompiler functionCompiler; |
| 335 | 334 |
| 336 CodeEmitterTask emitter; | 335 CodeEmitterTask emitter; |
| 337 | 336 |
| 338 /** | 337 /** |
| 339 * The generated code as a js AST for compiled methods. | 338 * The generated code as a js AST for compiled methods. |
| 340 */ | 339 */ |
| 341 final Map<MemberElement, jsAst.Expression> generatedCode = | 340 final Map<MemberEntity, jsAst.Expression> generatedCode = |
| 342 <MemberElement, jsAst.Expression>{}; | 341 <MemberEntity, jsAst.Expression>{}; |
| 343 | 342 |
| 344 FunctionInlineCache inlineCache = new FunctionInlineCache(); | 343 FunctionInlineCache inlineCache = new FunctionInlineCache(); |
| 345 | 344 |
| 346 /// If [true], the compiler will emit code that logs whenever a method is | 345 /// If [true], the compiler will emit code that logs whenever a method is |
| 347 /// called. When TRACE_METHOD is 'console' this will be logged | 346 /// called. When TRACE_METHOD is 'console' this will be logged |
| 348 /// directly in the JavaScript console. When TRACE_METHOD is 'post' the | 347 /// directly in the JavaScript console. When TRACE_METHOD is 'post' the |
| 349 /// information will be sent to a server via a POST request. | 348 /// information will be sent to a server via a POST request. |
| 350 static const String TRACE_METHOD = const String.fromEnvironment('traceCalls'); | 349 static const String TRACE_METHOD = const String.fromEnvironment('traceCalls'); |
| 351 static const bool TRACE_CALLS = | 350 static const bool TRACE_CALLS = |
| 352 TRACE_METHOD == 'post' || TRACE_METHOD == 'console'; | 351 TRACE_METHOD == 'post' || TRACE_METHOD == 'console'; |
| (...skipping 550 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 903 closedWorld.backendUsage, | 902 closedWorld.backendUsage, |
| 904 rtiNeed, | 903 rtiNeed, |
| 905 customElementsCodegenAnalysis, | 904 customElementsCodegenAnalysis, |
| 906 typeVariableCodegenAnalysis, | 905 typeVariableCodegenAnalysis, |
| 907 lookupMapAnalysis, | 906 lookupMapAnalysis, |
| 908 mirrorsCodegenAnalysis, | 907 mirrorsCodegenAnalysis, |
| 909 nativeCodegenEnqueuer)); | 908 nativeCodegenEnqueuer)); |
| 910 } | 909 } |
| 911 | 910 |
| 912 WorldImpact codegen(CodegenWorkItem work, ClosedWorld closedWorld) { | 911 WorldImpact codegen(CodegenWorkItem work, ClosedWorld closedWorld) { |
| 913 MemberElement element = work.element; | 912 MemberEntity element = work.element; |
| 914 if (compiler.elementHasCompileTimeError(element)) { | 913 if (compiler.elementHasCompileTimeError(element)) { |
| 915 DiagnosticMessage message = | 914 DiagnosticMessage message = |
| 916 // If there's more than one error, the first is probably most | 915 // If there's more than one error, the first is probably most |
| 917 // informative, as the following errors may be side-effects of the | 916 // informative, as the following errors may be side-effects of the |
| 918 // first error. | 917 // first error. |
| 919 compiler.elementsWithCompileTimeErrors[element].first; | 918 compiler.elementsWithCompileTimeErrors[element].first; |
| 920 String messageText = message.message.computeMessage(); | 919 String messageText = message.message.computeMessage(); |
| 921 jsAst.LiteralString messageLiteral = | 920 jsAst.LiteralString messageLiteral = |
| 922 js.escapedString("Compile time error in $element: $messageText"); | 921 js.escapedString("Compile time error in $element: $messageText"); |
| 923 generatedCode[element] = | 922 generatedCode[element] = |
| 924 js("function () { throw new Error(#); }", [messageLiteral]); | 923 js("function () { throw new Error(#); }", [messageLiteral]); |
| 925 return const CodegenImpact(); | |
| 926 } | |
| 927 var kind = element.kind; | |
| 928 if (kind == ElementKind.TYPEDEF) { | |
| 929 return const WorldImpact(); | 924 return const WorldImpact(); |
| 930 } | 925 } |
| 931 if (element.isConstructor && | 926 if (element.isConstructor && |
| 932 element.enclosingClass == commonElements.jsNullClass) { | 927 element.enclosingClass == commonElements.jsNullClass) { |
| 933 // Work around a problem compiling JSNull's constructor. | 928 // Work around a problem compiling JSNull's constructor. |
| 934 return const CodegenImpact(); | 929 return const WorldImpact(); |
| 935 } | |
| 936 if (kind.category == ElementCategory.VARIABLE) { | |
| 937 FieldElement variableElement = element; | |
| 938 ConstantExpression constant = variableElement.constant; | |
| 939 if (constant != null) { | |
| 940 ConstantValue initialValue = constants.getConstantValue(constant); | |
| 941 if (initialValue != null) { | |
| 942 work.registry.worldImpact | |
| 943 .registerConstantUse(new ConstantUse.init(initialValue)); | |
| 944 // We don't need to generate code for static or top-level | |
| 945 // variables. For instance variables, we may need to generate | |
| 946 // the checked setter. | |
| 947 if (Elements.isStaticOrTopLevel(element)) { | |
| 948 return _codegenImpactTransformer | |
| 949 .transformCodegenImpact(work.registry.worldImpact); | |
| 950 } | |
| 951 } else { | |
| 952 assert(invariant( | |
| 953 variableElement, | |
| 954 variableElement.isInstanceMember || | |
| 955 constant.isImplicit || | |
| 956 constant.isPotential, | |
| 957 message: "Constant expression without value: " | |
| 958 "${constant.toStructuredText()}.")); | |
| 959 } | |
| 960 } else { | |
| 961 // If the constant-handler was not able to produce a result we have to | |
| 962 // go through the builder (below) to generate the lazy initializer for | |
| 963 // the static variable. | |
| 964 // We also need to register the use of the cyclic-error helper. | |
| 965 work.registry.worldImpact.registerStaticUse(new StaticUse.staticInvoke( | |
| 966 commonElements.cyclicThrowHelper, CallStructure.ONE_ARG)); | |
| 967 } | |
| 968 } | 930 } |
| 969 | 931 |
| 970 jsAst.Fun function = functionCompiler.compile(work, closedWorld); | 932 jsAst.Fun function = functionCompiler.compile(work, closedWorld); |
| 971 if (function.sourceInformation == null) { | 933 if (function != null) { |
| 972 function = function.withSourceInformation( | 934 if (function.sourceInformation == null) { |
| 973 sourceInformationStrategy.buildSourceMappedMarker()); | 935 function = function.withSourceInformation( |
| 936 sourceInformationStrategy.buildSourceMappedMarker()); |
| 937 } |
| 938 generatedCode[element] = function; |
| 974 } | 939 } |
| 975 generatedCode[element] = function; | |
| 976 WorldImpact worldImpact = _codegenImpactTransformer | 940 WorldImpact worldImpact = _codegenImpactTransformer |
| 977 .transformCodegenImpact(work.registry.worldImpact); | 941 .transformCodegenImpact(work.registry.worldImpact); |
| 978 compiler.dumpInfoTask.registerImpact(element, worldImpact); | 942 compiler.dumpInfoTask.registerImpact(element, worldImpact); |
| 979 return worldImpact; | 943 return worldImpact; |
| 980 } | 944 } |
| 981 | 945 |
| 982 native.NativeResolutionEnqueuer get nativeResolutionEnqueuerForTesting => | 946 native.NativeResolutionEnqueuer get nativeResolutionEnqueuerForTesting => |
| 983 _nativeResolutionEnqueuer; | 947 _nativeResolutionEnqueuer; |
| 984 | 948 |
| 985 native.NativeEnqueuer get nativeCodegenEnqueuer => _nativeCodegenEnqueuer; | 949 native.NativeEnqueuer get nativeCodegenEnqueuer => _nativeCodegenEnqueuer; |
| (...skipping 446 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1432 | 1396 |
| 1433 bool canUseAliasedSuperMember(MemberEntity member, Selector selector) { | 1397 bool canUseAliasedSuperMember(MemberEntity member, Selector selector) { |
| 1434 return !selector.isGetter; | 1398 return !selector.isGetter; |
| 1435 } | 1399 } |
| 1436 | 1400 |
| 1437 /// Returns `true` if [member] is called from a subclass via `super`. | 1401 /// Returns `true` if [member] is called from a subclass via `super`. |
| 1438 bool isAliasedSuperMember(MemberEntity member) { | 1402 bool isAliasedSuperMember(MemberEntity member) { |
| 1439 return _aliasedSuperMembers.contains(member); | 1403 return _aliasedSuperMembers.contains(member); |
| 1440 } | 1404 } |
| 1441 } | 1405 } |
| OLD | NEW |