OLD | NEW |
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, 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 js_backend; | 5 part of js_backend; |
6 | 6 |
7 /// [ConstantCompilerTask] for compilation of constants for the JavaScript | 7 /// [ConstantCompilerTask] for compilation of constants for the JavaScript |
8 /// backend. | 8 /// backend. |
9 /// | 9 /// |
10 /// Since this task needs to distinguish between frontend and backend constants | 10 /// Since this task needs to distinguish between frontend and backend constants |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
108 final Set<ConstantValue> compiledConstants = new Set<ConstantValue>(); | 108 final Set<ConstantValue> compiledConstants = new Set<ConstantValue>(); |
109 | 109 |
110 // TODO(johnniwinther): Move this to the backend constant handler. | 110 // TODO(johnniwinther): Move this to the backend constant handler. |
111 /** Caches the statics where the initial value cannot be eagerly compiled. */ | 111 /** Caches the statics where the initial value cannot be eagerly compiled. */ |
112 final Set<VariableElement> lazyStatics = new Set<VariableElement>(); | 112 final Set<VariableElement> lazyStatics = new Set<VariableElement>(); |
113 | 113 |
114 // Constants computed for constant expressions. | 114 // Constants computed for constant expressions. |
115 final Map<Node, ConstantExpression> nodeConstantMap = | 115 final Map<Node, ConstantExpression> nodeConstantMap = |
116 new Map<Node, ConstantExpression>(); | 116 new Map<Node, ConstantExpression>(); |
117 | 117 |
| 118 // Constants computed for metadata. |
| 119 final Map<MetadataAnnotation, ConstantExpression> metadataConstantMap = |
| 120 new Map<MetadataAnnotation, ConstantExpression>(); |
| 121 |
118 JavaScriptConstantCompiler(Compiler compiler) | 122 JavaScriptConstantCompiler(Compiler compiler) |
119 : super(compiler, JAVA_SCRIPT_CONSTANT_SYSTEM); | 123 : super(compiler, JAVA_SCRIPT_CONSTANT_SYSTEM); |
120 | 124 |
121 ConstantExpression compileVariableWithDefinitions( | 125 ConstantExpression compileVariableWithDefinitions( |
122 VariableElement element, TreeElements definitions, | 126 VariableElement element, TreeElements definitions, |
123 {bool isConst: false, bool checkType: true}) { | 127 {bool isConst: false, bool checkType: true}) { |
124 if (!isConst && lazyStatics.contains(element)) { | 128 if (!isConst && lazyStatics.contains(element)) { |
125 return null; | 129 return null; |
126 } | 130 } |
127 ConstantExpression value = super.compileVariableWithDefinitions( | 131 ConstantExpression value = super.compileVariableWithDefinitions( |
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
201 | 205 |
202 ConstantExpression getConstantForNode(Node node, TreeElements definitions) { | 206 ConstantExpression getConstantForNode(Node node, TreeElements definitions) { |
203 ConstantExpression constant = nodeConstantMap[node]; | 207 ConstantExpression constant = nodeConstantMap[node]; |
204 if (constant != null) { | 208 if (constant != null) { |
205 return constant; | 209 return constant; |
206 } | 210 } |
207 return definitions.getConstant(node); | 211 return definitions.getConstant(node); |
208 } | 212 } |
209 | 213 |
210 ConstantValue getConstantValueForMetadata(MetadataAnnotation metadata) { | 214 ConstantValue getConstantValueForMetadata(MetadataAnnotation metadata) { |
211 return getConstantValue(metadata.constant); | 215 return getConstantValue(metadataConstantMap[metadata]); |
| 216 } |
| 217 |
| 218 ConstantExpression compileMetadata( |
| 219 MetadataAnnotation metadata, Node node, TreeElements elements) { |
| 220 ConstantExpression constant = |
| 221 super.compileMetadata(metadata, node, elements); |
| 222 metadataConstantMap[metadata] = constant; |
| 223 return constant; |
212 } | 224 } |
213 | 225 |
214 void forgetElement(Element element) { | 226 void forgetElement(Element element) { |
215 super.forgetElement(element); | 227 super.forgetElement(element); |
216 const ForgetConstantElementVisitor().visit(element, this); | 228 const ForgetConstantElementVisitor().visit(element, this); |
217 if (element is AstElement && element.hasNode) { | 229 if (element is AstElement && element.hasNode) { |
218 element.node.accept(new ForgetConstantNodeVisitor(this)); | 230 element.node.accept(new ForgetConstantNodeVisitor(this)); |
219 } | 231 } |
220 } | 232 } |
| 233 |
| 234 @override |
| 235 ConstantValue getConstantValue(ConstantExpression expression) { |
| 236 assert(invariant(CURRENT_ELEMENT_SPANNABLE, expression != null, |
| 237 message: "ConstantExpression is null in getConstantValue.")); |
| 238 // TODO(johhniwinther): ensure expressions have been evaluated at this |
| 239 // point. This can't be enabled today due to dartbug.com/26406. |
| 240 if (compiler.serialization.supportsDeserialization) { |
| 241 evaluate(expression); |
| 242 } |
| 243 ConstantValue value = super.getConstantValue(expression); |
| 244 if (value == null && |
| 245 expression != null && |
| 246 expression.kind == ConstantExpressionKind.ERRONEOUS) { |
| 247 // TODO(johnniwinther): When the Dart constant system sees a constant |
| 248 // expression as erroneous but the JavaScript constant system finds it ok |
| 249 // we have store a constant value for the erroneous constant expression. |
| 250 // Ensure the computed constant expressions are always the same; that only |
| 251 // the constant values may be different. |
| 252 value = new NullConstantValue(); |
| 253 } |
| 254 return value; |
| 255 } |
221 } | 256 } |
222 | 257 |
223 class ForgetConstantElementVisitor | 258 class ForgetConstantElementVisitor |
224 extends BaseElementVisitor<dynamic, JavaScriptConstantCompiler> { | 259 extends BaseElementVisitor<dynamic, JavaScriptConstantCompiler> { |
225 const ForgetConstantElementVisitor(); | 260 const ForgetConstantElementVisitor(); |
226 | 261 |
227 void visitElement(Element e, JavaScriptConstantCompiler constants) { | 262 void visitElement(Element e, JavaScriptConstantCompiler constants) { |
228 for (MetadataAnnotation data in e.implementation.metadata) { | 263 for (MetadataAnnotation data in e.implementation.metadata) { |
| 264 constants.metadataConstantMap.remove(data); |
229 if (data.hasNode) { | 265 if (data.hasNode) { |
230 data.node.accept(new ForgetConstantNodeVisitor(constants)); | 266 data.node.accept(new ForgetConstantNodeVisitor(constants)); |
231 } | 267 } |
232 } | 268 } |
233 } | 269 } |
234 | 270 |
235 void visitFunctionElement( | 271 void visitFunctionElement( |
236 FunctionElement e, JavaScriptConstantCompiler constants) { | 272 FunctionElement e, JavaScriptConstantCompiler constants) { |
237 super.visitFunctionElement(e, constants); | 273 super.visitFunctionElement(e, constants); |
238 if (e.hasFunctionSignature) { | 274 if (e.hasFunctionSignature) { |
(...skipping 14 matching lines...) Expand all Loading... |
253 // TODO(ahe): This doesn't belong here. Rename this class and generalize. | 289 // TODO(ahe): This doesn't belong here. Rename this class and generalize. |
254 var closureClassMap = constants | 290 var closureClassMap = constants |
255 .compiler.closureToClassMapper.closureMappingCache | 291 .compiler.closureToClassMapper.closureMappingCache |
256 .remove(node); | 292 .remove(node); |
257 if (closureClassMap != null) { | 293 if (closureClassMap != null) { |
258 closureClassMap | 294 closureClassMap |
259 .removeMyselfFrom(constants.compiler.enqueuer.codegen.universe); | 295 .removeMyselfFrom(constants.compiler.enqueuer.codegen.universe); |
260 } | 296 } |
261 } | 297 } |
262 } | 298 } |
OLD | NEW |