| OLD | NEW |
| 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2015, 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 dart2js.js_emitter.lazy_emitter; | 5 library dart2js.js_emitter.startup_emitter; |
| 6 | 6 |
| 7 import 'package:js_runtime/shared/embedded_names.dart' show | 7 import 'package:js_runtime/shared/embedded_names.dart' show |
| 8 JsBuiltin, | 8 JsBuiltin, |
| 9 METADATA, | 9 METADATA, |
| 10 TYPES; | 10 TYPES; |
| 11 | 11 |
| 12 import '../program_builder/program_builder.dart' show ProgramBuilder; | 12 import '../program_builder/program_builder.dart' show ProgramBuilder; |
| 13 import '../model.dart'; | 13 import '../model.dart'; |
| 14 import 'model_emitter.dart'; | 14 import 'model_emitter.dart'; |
| 15 import '../../common.dart'; | 15 import '../../common.dart'; |
| 16 import '../../elements/elements.dart' show FieldElement; | 16 import '../../elements/elements.dart' show FieldElement; |
| 17 import '../../js/js.dart' as js; | 17 import '../../js/js.dart' as js; |
| 18 | 18 |
| 19 import '../../js_backend/js_backend.dart' show | 19 import '../../js_backend/js_backend.dart' show |
| 20 JavaScriptBackend, | 20 JavaScriptBackend, |
| 21 Namer; | 21 Namer; |
| 22 | 22 |
| 23 import '../js_emitter.dart' show | 23 import '../js_emitter.dart' show |
| 24 NativeEmitter; | 24 NativeEmitter; |
| 25 | 25 |
| 26 import '../js_emitter.dart' as emitterTask show | 26 import '../js_emitter.dart' as emitterTask show |
| 27 Emitter; | 27 Emitter; |
| 28 | 28 |
| 29 import '../../util/util.dart' show | 29 import '../../util/util.dart' show |
| 30 NO_LOCATION_SPANNABLE; | 30 NO_LOCATION_SPANNABLE; |
| 31 | 31 |
| 32 class Emitter implements emitterTask.Emitter { | 32 class Emitter implements emitterTask.Emitter { |
| 33 final Compiler _compiler; | 33 final Compiler _compiler; |
| 34 final Namer namer; | 34 final Namer namer; |
| 35 final ModelEmitter _emitter; | 35 final ModelEmitter _emitter; |
| 36 | 36 |
| 37 JavaScriptBackend get _backend => _compiler.backend; | 37 JavaScriptBackend get _backend => _compiler.backend; |
| 38 | 38 |
| 39 Emitter(Compiler compiler, Namer namer, NativeEmitter nativeEmitter) | 39 Emitter(Compiler compiler, Namer namer, NativeEmitter nativeEmitter) |
| 40 : this._compiler = compiler, | 40 : this._compiler = compiler, |
| 41 this.namer = namer, | 41 this.namer = namer, |
| 42 _emitter = new ModelEmitter(compiler, namer, nativeEmitter); | 42 _emitter = new ModelEmitter(compiler, namer, nativeEmitter); |
| 43 | 43 |
| 44 @override | 44 @override |
| 45 int emitProgram(ProgramBuilder programBuilder) { | 45 int emitProgram(ProgramBuilder programBuilder) { |
| 46 Program program = programBuilder.buildProgram(); | 46 Program program = programBuilder.buildProgram(); |
| 47 return _emitter.emitProgram(program); | 47 return _emitter.emitProgram(program); |
| 48 } | 48 } |
| 49 | 49 |
| 50 // TODO(floitsch): copied from full emitter. Adjust or share. | |
| 51 @override | 50 @override |
| 52 bool isConstantInlinedOrAlreadyEmitted(ConstantValue constant) { | 51 bool isConstantInlinedOrAlreadyEmitted(ConstantValue constant) { |
| 53 return _emitter.isConstantInlinedOrAlreadyEmitted(constant); | 52 return _emitter.isConstantInlinedOrAlreadyEmitted(constant); |
| 54 } | 53 } |
| 55 | 54 |
| 56 // TODO(floitsch): copied from full emitter. Adjust or share. | |
| 57 @override | 55 @override |
| 58 int compareConstants(ConstantValue a, ConstantValue b) { | 56 int compareConstants(ConstantValue a, ConstantValue b) { |
| 59 return _emitter.compareConstants(a, b); | 57 return _emitter.compareConstants(a, b); |
| 60 } | 58 } |
| 61 | 59 |
| 62 @override | 60 @override |
| 63 js.Expression constantReference(ConstantValue value) { | 61 js.Expression constantReference(ConstantValue value) { |
| 64 return _emitter.generateConstantReference(value); | 62 return _emitter.generateConstantReference(value); |
| 65 } | 63 } |
| 66 | 64 |
| (...skipping 11 matching lines...) Expand all Loading... |
| 78 js.PropertyAccess _globalPropertyAccess(Element element) { | 76 js.PropertyAccess _globalPropertyAccess(Element element) { |
| 79 js.Name name = namer.globalPropertyName(element); | 77 js.Name name = namer.globalPropertyName(element); |
| 80 js.PropertyAccess pa = new js.PropertyAccess( | 78 js.PropertyAccess pa = new js.PropertyAccess( |
| 81 new js.VariableUse(namer.globalObjectFor(element)), name); | 79 new js.VariableUse(namer.globalObjectFor(element)), name); |
| 82 return pa; | 80 return pa; |
| 83 } | 81 } |
| 84 | 82 |
| 85 @override | 83 @override |
| 86 js.Expression isolateLazyInitializerAccess(FieldElement element) { | 84 js.Expression isolateLazyInitializerAccess(FieldElement element) { |
| 87 return js.js('#.#', [namer.globalObjectFor(element), | 85 return js.js('#.#', [namer.globalObjectFor(element), |
| 88 namer.lazyInitializerName(element)]); | 86 namer.lazyInitializerName(element)]); |
| 89 } | 87 } |
| 90 | 88 |
| 91 @override | 89 @override |
| 92 js.Expression isolateStaticClosureAccess(FunctionElement element) { | 90 js.Expression isolateStaticClosureAccess(FunctionElement element) { |
| 93 return _emitter.generateStaticClosureAccess(element); | 91 return _emitter.generateStaticClosureAccess(element); |
| 94 } | 92 } |
| 95 | 93 |
| 96 @override | 94 @override |
| 97 js.PropertyAccess staticFieldAccess(FieldElement element) { | 95 js.PropertyAccess staticFieldAccess(FieldElement element) { |
| 98 return _globalPropertyAccess(element); | 96 return _globalPropertyAccess(element); |
| (...skipping 12 matching lines...) Expand all Loading... |
| 111 @override | 109 @override |
| 112 js.PropertyAccess prototypeAccess(ClassElement element, | 110 js.PropertyAccess prototypeAccess(ClassElement element, |
| 113 bool hasBeenInstantiated) { | 111 bool hasBeenInstantiated) { |
| 114 js.Expression constructor = | 112 js.Expression constructor = |
| 115 hasBeenInstantiated ? constructorAccess(element) : typeAccess(element); | 113 hasBeenInstantiated ? constructorAccess(element) : typeAccess(element); |
| 116 return js.js('#.prototype', constructor); | 114 return js.js('#.prototype', constructor); |
| 117 } | 115 } |
| 118 | 116 |
| 119 @override | 117 @override |
| 120 js.Expression interceptorClassAccess(ClassElement element) { | 118 js.Expression interceptorClassAccess(ClassElement element) { |
| 121 // Some interceptors are eagerly constructed. However, native interceptors | 119 return _globalPropertyAccess(element); |
| 122 // aren't. | |
| 123 return js.js('#.ensureResolved()', _globalPropertyAccess(element)); | |
| 124 } | 120 } |
| 125 | 121 |
| 126 @override | 122 @override |
| 127 js.Expression typeAccess(Element element) { | 123 js.Expression typeAccess(Element element) { |
| 128 // TODO(floitsch): minify 'ensureResolved'. | 124 return _globalPropertyAccess(element); |
| 129 // TODO(floitsch): don't emit `ensureResolved` for eager classes. | |
| 130 return js.js('#.ensureResolved()', _globalPropertyAccess(element)); | |
| 131 } | 125 } |
| 132 | 126 |
| 133 @override | 127 @override |
| 134 js.Template templateForBuiltin(JsBuiltin builtin) { | 128 js.Template templateForBuiltin(JsBuiltin builtin) { |
| 135 String typeNameProperty = ModelEmitter.typeNameProperty; | 129 String typeNameProperty = ModelEmitter.typeNameProperty; |
| 136 | 130 |
| 137 switch (builtin) { | 131 switch (builtin) { |
| 138 case JsBuiltin.dartObjectConstructor: | 132 case JsBuiltin.dartObjectConstructor: |
| 139 return js.js.expressionTemplateYielding( | 133 return js.js.expressionTemplateYielding( |
| 140 typeAccess(_compiler.objectClass)); | 134 typeAccess(_compiler.objectClass)); |
| 141 | 135 |
| 142 case JsBuiltin.isCheckPropertyToJsConstructorName: | 136 case JsBuiltin.isCheckPropertyToJsConstructorName: |
| 143 int isPrefixLength = namer.operatorIsPrefix.length; | 137 int isPrefixLength = namer.operatorIsPrefix.length; |
| 144 return js.js.expressionTemplateFor('#.substring($isPrefixLength)'); | 138 return js.js.expressionTemplateFor('#.substring($isPrefixLength)'); |
| 145 | 139 |
| 146 case JsBuiltin.isFunctionType: | 140 case JsBuiltin.isFunctionType: |
| 147 return _backend.rti.representationGenerator.templateForIsFunctionType; | 141 return _backend.rti.representationGenerator.templateForIsFunctionType; |
| 148 | 142 |
| 149 case JsBuiltin.rawRtiToJsConstructorName: | 143 case JsBuiltin.rawRtiToJsConstructorName: |
| 150 return js.js.expressionTemplateFor("#.$typeNameProperty"); | 144 return js.js.expressionTemplateFor("#.$typeNameProperty"); |
| 151 | 145 |
| 152 case JsBuiltin.rawRuntimeType: | 146 case JsBuiltin.rawRuntimeType: |
| 153 return js.js.expressionTemplateFor("#.constructor"); | 147 return js.js.expressionTemplateFor("#.constructor"); |
| 154 | 148 |
| 155 case JsBuiltin.createFunctionTypeRti: | 149 case JsBuiltin.createFunctionTypeRti: |
| 156 return _backend.rti.representationGenerator | 150 return _backend.rti.representationGenerator |
| 157 .templateForCreateFunctionType; | 151 .templateForCreateFunctionType; |
| 158 | 152 |
| 159 case JsBuiltin.isSubtype: | 153 case JsBuiltin.isSubtype: |
| 160 // TODO(floitsch): move this closer to where is-check properties are | 154 // TODO(floitsch): move this closer to where is-check properties are |
| 161 // built. | 155 // built. |
| 162 String isPrefix = namer.operatorIsPrefix; | 156 String isPrefix = namer.operatorIsPrefix; |
| 163 return js.js.expressionTemplateFor("('$isPrefix' + #) in #.prototype"); | 157 return js.js.expressionTemplateFor("('$isPrefix' + #) in #.prototype"); |
| 164 | 158 |
| 165 case JsBuiltin.isGivenTypeRti: | 159 case JsBuiltin.isGivenTypeRti: |
| 166 return js.js.expressionTemplateFor('#.$typeNameProperty === #'); | 160 return js.js.expressionTemplateFor('#.$typeNameProperty === #'); |
| 167 | 161 |
| 168 case JsBuiltin.getMetadata: | 162 case JsBuiltin.getMetadata: |
| 169 return _emitter.templateForReadMetadata; | 163 String metadataAccess = |
| 164 _emitter.generateEmbeddedGlobalAccessString(METADATA); |
| 165 return js.js.expressionTemplateFor("$metadataAccess[#]"); |
| 170 | 166 |
| 171 case JsBuiltin.getType: | 167 case JsBuiltin.getType: |
| 172 return _emitter.templateForReadType; | 168 String typesAccess = |
| 169 _emitter.generateEmbeddedGlobalAccessString(TYPES); |
| 170 return js.js.expressionTemplateFor("$typesAccess[#]"); |
| 173 | 171 |
| 174 default: | 172 default: |
| 175 _compiler.internalError(NO_LOCATION_SPANNABLE, | 173 _compiler.internalError(NO_LOCATION_SPANNABLE, |
| 176 "Unhandled Builtin: $builtin"); | 174 "Unhandled Builtin: $builtin"); |
| 177 return null; | 175 return null; |
| 178 } | 176 } |
| 179 } | 177 } |
| 180 | 178 |
| 181 @override | 179 @override |
| 182 void invalidateCaches() { | 180 void invalidateCaches() { |
| 183 } | 181 } |
| 184 } | 182 } |
| OLD | NEW |