| OLD | NEW |
| 1 library dart2js.unsugar_cps; | 1 library dart2js.unsugar_cps; |
| 2 | 2 |
| 3 import '../../cps_ir/cps_ir_nodes.dart'; | 3 import '../../cps_ir/cps_ir_nodes.dart'; |
| 4 | 4 |
| 5 import '../../cps_ir/optimizers.dart' show ParentVisitor; | 5 import '../../cps_ir/optimizers.dart' show ParentVisitor; |
| 6 import '../../constants/values.dart'; | 6 import '../../constants/values.dart'; |
| 7 import '../../elements/elements.dart'; | 7 import '../../elements/elements.dart'; |
| 8 import '../../io/source_information.dart'; | 8 import '../../io/source_information.dart'; |
| 9 import '../../js_backend/codegen/glue.dart'; | 9 import '../../js_backend/codegen/glue.dart'; |
| 10 import '../../universe/universe.dart' show Selector; | 10 import '../../universe/universe.dart' show Selector; |
| (...skipping 13 matching lines...) Expand all Loading... |
| 24 InterceptorEntity(this.interceptedVariable); | 24 InterceptorEntity(this.interceptedVariable); |
| 25 | 25 |
| 26 String get name => interceptedVariable.name + '_'; | 26 String get name => interceptedVariable.name + '_'; |
| 27 } | 27 } |
| 28 | 28 |
| 29 | 29 |
| 30 /// Rewrites the initial CPS IR to make Dart semantics explicit and inserts | 30 /// Rewrites the initial CPS IR to make Dart semantics explicit and inserts |
| 31 /// special nodes that respect JavaScript behavior. | 31 /// special nodes that respect JavaScript behavior. |
| 32 /// | 32 /// |
| 33 /// Performs the following rewrites: | 33 /// Performs the following rewrites: |
| 34 /// - Rewrite [IsTrue] in a [Branch] to do boolean conversion. | |
| 35 /// - Add interceptors at call sites that use interceptor calling convention. | 34 /// - Add interceptors at call sites that use interceptor calling convention. |
| 36 /// - Add explicit receiver argument for methods that are called in interceptor | 35 /// - Add explicit receiver argument for methods that are called in interceptor |
| 37 /// calling convention. | 36 /// calling convention. |
| 38 /// - Convert two-parameter exception handlers to one-parameter ones. | 37 /// - Convert two-parameter exception handlers to one-parameter ones. |
| 39 class UnsugarVisitor extends RecursiveVisitor { | 38 class UnsugarVisitor extends RecursiveVisitor { |
| 40 Glue _glue; | 39 Glue _glue; |
| 41 ParentVisitor _parentVisitor = new ParentVisitor(); | 40 ParentVisitor _parentVisitor = new ParentVisitor(); |
| 42 | 41 |
| 43 Parameter thisParameter; | 42 Parameter thisParameter; |
| 44 Parameter explicitReceiverParameter; | 43 Parameter explicitReceiverParameter; |
| (...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 133 Primitive nullPrimitive = nullConstant; | 132 Primitive nullPrimitive = nullConstant; |
| 134 Primitive test = new ApplyBuiltinOperator( | 133 Primitive test = new ApplyBuiltinOperator( |
| 135 BuiltinOperator.Identical, | 134 BuiltinOperator.Identical, |
| 136 <Primitive>[function.parameters.single, nullPrimitive], | 135 <Primitive>[function.parameters.single, nullPrimitive], |
| 137 function.parameters.single.sourceInformation); | 136 function.parameters.single.sourceInformation); |
| 138 | 137 |
| 139 Expression newBody = | 138 Expression newBody = |
| 140 new LetCont.many(<Continuation>[returnFalse, originalBody], | 139 new LetCont.many(<Continuation>[returnFalse, originalBody], |
| 141 new LetPrim(nullPrimitive, | 140 new LetPrim(nullPrimitive, |
| 142 new LetPrim(test, | 141 new LetPrim(test, |
| 143 new Branch( | 142 new Branch.loose(test, returnFalse, originalBody)))); |
| 144 new IsTrue(test), | |
| 145 returnFalse, | |
| 146 originalBody)))); | |
| 147 function.body = newBody; | 143 function.body = newBody; |
| 148 } | 144 } |
| 149 | 145 |
| 150 /// Insert a static call to [function] at the point of [node] with result | 146 /// Insert a static call to [function] at the point of [node] with result |
| 151 /// [result]. | 147 /// [result]. |
| 152 /// | 148 /// |
| 153 /// Rewrite [node] to | 149 /// Rewrite [node] to |
| 154 /// | 150 /// |
| 155 /// let cont continuation(result) = node | 151 /// let cont continuation(result) = node |
| 156 /// in invoke function arguments continuation | 152 /// in invoke function arguments continuation |
| (...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 274 ..interceptedClasses.addAll(_glue.getInterceptedClassesOn(selector)); | 270 ..interceptedClasses.addAll(_glue.getInterceptedClassesOn(selector)); |
| 275 if (receiver.hint != null) { | 271 if (receiver.hint != null) { |
| 276 newReceiver.hint = new InterceptorEntity(receiver.hint); | 272 newReceiver.hint = new InterceptorEntity(receiver.hint); |
| 277 } | 273 } |
| 278 insertLetPrim(newReceiver, contBinding); | 274 insertLetPrim(newReceiver, contBinding); |
| 279 } | 275 } |
| 280 node.arguments.insert(0, node.receiver); | 276 node.arguments.insert(0, node.receiver); |
| 281 node.receiver = new Reference<Primitive>(newReceiver); | 277 node.receiver = new Reference<Primitive>(newReceiver); |
| 282 } | 278 } |
| 283 | 279 |
| 284 processBranch(Branch node) { | |
| 285 // TODO(karlklose): implement the checked mode part of boolean conversion. | |
| 286 InteriorNode parent = node.parent; | |
| 287 IsTrue condition = node.condition; | |
| 288 | |
| 289 // Do not rewrite conditions that are foreign code. | |
| 290 // It is redundant, and causes infinite recursion (if not optimized) | |
| 291 // in the implementation of identical, which itself contains a condition. | |
| 292 Primitive value = condition.value.definition; | |
| 293 if (value is Parameter && value.parent is Continuation) { | |
| 294 Continuation cont = value.parent; | |
| 295 if (cont.hasExactlyOneUse && cont.firstRef.parent is ForeignCode) { | |
| 296 ForeignCode foreign = cont.firstRef.parent; | |
| 297 if (foreign.type.containsOnlyBool(_glue.classWorld)) { | |
| 298 return; | |
| 299 } | |
| 300 } | |
| 301 } | |
| 302 | |
| 303 Primitive t = trueConstant; | |
| 304 Primitive i = new ApplyBuiltinOperator( | |
| 305 BuiltinOperator.Identical, | |
| 306 <Primitive>[condition.value.definition, t], | |
| 307 condition.value.definition.sourceInformation); | |
| 308 LetPrim newNode = new LetPrim(t, | |
| 309 new LetPrim(i, | |
| 310 new Branch(new IsTrue(i), | |
| 311 node.trueContinuation.definition, | |
| 312 node.falseContinuation.definition))); | |
| 313 condition.value.unlink(); | |
| 314 node.trueContinuation.unlink(); | |
| 315 node.falseContinuation.unlink(); | |
| 316 parent.body = newNode; | |
| 317 } | |
| 318 | |
| 319 processInterceptor(Interceptor node) { | 280 processInterceptor(Interceptor node) { |
| 320 _glue.registerSpecializedGetInterceptor(node.interceptedClasses); | 281 _glue.registerSpecializedGetInterceptor(node.interceptedClasses); |
| 321 } | 282 } |
| 322 } | 283 } |
| OLD | NEW |