| 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 part of ssa; | 5 part of ssa; |
| 6 | 6 |
| 7 /** | 7 /** |
| 8 * A special element for the extra parameter taken by intercepted | 8 * A special element for the extra parameter taken by intercepted |
| 9 * methods. We need to override [Element.computeType] because our | 9 * methods. We need to override [Element.computeType] because our |
| 10 * optimizers may look at its declared type. | 10 * optimizers may look at its declared type. |
| (...skipping 2226 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2237 stack.add(graph.addConstant(folded)); | 2237 stack.add(graph.addConstant(folded)); |
| 2238 return; | 2238 return; |
| 2239 } | 2239 } |
| 2240 } | 2240 } |
| 2241 | 2241 |
| 2242 HInvokeDynamicMethod result = | 2242 HInvokeDynamicMethod result = |
| 2243 buildInvokeDynamic(node, elements.getSelector(node), operand, []); | 2243 buildInvokeDynamic(node, elements.getSelector(node), operand, []); |
| 2244 pushWithPosition(result, node); | 2244 pushWithPosition(result, node); |
| 2245 } | 2245 } |
| 2246 | 2246 |
| 2247 void visitBinary( | 2247 void visitBinary(HInstruction left, |
| 2248 HInstruction left, Operator op, HInstruction right, Send send) { | 2248 Operator op, |
| 2249 Selector selector = null; | 2249 HInstruction right, |
| 2250 // TODO(ngeoffray): The resolver creates these selectors already | 2250 Selector selector, |
| 2251 // but does not put them on the [send] instruction. | 2251 Send send) { |
| 2252 switch (op.source.stringValue) { | 2252 switch (op.source.stringValue) { |
| 2253 case "+": | |
| 2254 case "+=": | |
| 2255 case "++": | |
| 2256 selector = new Selector.binaryOperator(const SourceString('+')); | |
| 2257 break; | |
| 2258 case "-": | |
| 2259 case "-=": | |
| 2260 case "--": | |
| 2261 selector = new Selector.binaryOperator(const SourceString('-')); | |
| 2262 break; | |
| 2263 case "*": | |
| 2264 case "*=": | |
| 2265 selector = new Selector.binaryOperator(const SourceString('*')); | |
| 2266 break; | |
| 2267 case "/": | |
| 2268 case "/=": | |
| 2269 selector = new Selector.binaryOperator(const SourceString('/')); | |
| 2270 break; | |
| 2271 case "~/": | |
| 2272 case "~/=": | |
| 2273 selector = new Selector.binaryOperator(const SourceString('~/')); | |
| 2274 break; | |
| 2275 case "%": | |
| 2276 case "%=": | |
| 2277 selector = new Selector.binaryOperator(const SourceString('%')); | |
| 2278 break; | |
| 2279 case "<<": | |
| 2280 case "<<=": | |
| 2281 selector = new Selector.binaryOperator(const SourceString('<<')); | |
| 2282 break; | |
| 2283 case ">>": | |
| 2284 case ">>=": | |
| 2285 selector = new Selector.binaryOperator(const SourceString('>>')); | |
| 2286 break; | |
| 2287 case "|": | |
| 2288 case "|=": | |
| 2289 selector = new Selector.binaryOperator(const SourceString('|')); | |
| 2290 break; | |
| 2291 case "&": | |
| 2292 case "&=": | |
| 2293 selector = new Selector.binaryOperator(const SourceString('&')); | |
| 2294 break; | |
| 2295 case "^": | |
| 2296 case "^=": | |
| 2297 selector = new Selector.binaryOperator(const SourceString('^')); | |
| 2298 break; | |
| 2299 case "==": | |
| 2300 case "!=": | |
| 2301 selector = new Selector.binaryOperator(const SourceString('==')); | |
| 2302 break; | |
| 2303 case "<": | |
| 2304 selector = new Selector.binaryOperator(const SourceString('<')); | |
| 2305 break; | |
| 2306 case "<=": | |
| 2307 selector = new Selector.binaryOperator(const SourceString('<=')); | |
| 2308 break; | |
| 2309 case ">": | |
| 2310 selector = new Selector.binaryOperator(const SourceString('>')); | |
| 2311 break; | |
| 2312 case ">=": | |
| 2313 selector = new Selector.binaryOperator(const SourceString('>=')); | |
| 2314 break; | |
| 2315 case "===": | 2253 case "===": |
| 2316 pushWithPosition(new HIdentity(left, right), op); | 2254 pushWithPosition(new HIdentity(left, right), op); |
| 2317 return; | 2255 return; |
| 2318 case "!==": | 2256 case "!==": |
| 2319 HIdentity eq = new HIdentity(left, right); | 2257 HIdentity eq = new HIdentity(left, right); |
| 2320 add(eq); | 2258 add(eq); |
| 2321 pushWithPosition(new HNot(eq), op); | 2259 pushWithPosition(new HNot(eq), op); |
| 2322 return; | 2260 return; |
| 2323 default: | |
| 2324 compiler.internalError("Unexpected operator $op", node: op); | |
| 2325 break; | |
| 2326 } | 2261 } |
| 2327 | 2262 |
| 2328 pushWithPosition( | 2263 pushWithPosition( |
| 2329 buildInvokeDynamic(send, selector, left, [right]), | 2264 buildInvokeDynamic(send, selector, left, [right]), |
| 2330 op); | 2265 op); |
| 2331 if (op.source.stringValue == '!=') { | 2266 if (op.source.stringValue == '!=') { |
| 2332 pushWithPosition(new HNot(popBoolified()), op); | 2267 pushWithPosition(new HNot(popBoolified()), op); |
| 2333 } | 2268 } |
| 2334 } | 2269 } |
| 2335 | 2270 |
| (...skipping 16 matching lines...) Expand all Loading... |
| 2352 | 2287 |
| 2353 /** | 2288 /** |
| 2354 * Returns a set of interceptor classes that contain a member whose | 2289 * Returns a set of interceptor classes that contain a member whose |
| 2355 * signature matches the given [selector]. | 2290 * signature matches the given [selector]. |
| 2356 */ | 2291 */ |
| 2357 Set<ClassElement> getInterceptedClassesOn(Selector selector) { | 2292 Set<ClassElement> getInterceptedClassesOn(Selector selector) { |
| 2358 return backend.getInterceptedClassesOn(selector); | 2293 return backend.getInterceptedClassesOn(selector); |
| 2359 } | 2294 } |
| 2360 | 2295 |
| 2361 void generateInstanceGetterWithCompiledReceiver(Send send, | 2296 void generateInstanceGetterWithCompiledReceiver(Send send, |
| 2297 Selector selector, |
| 2362 HInstruction receiver) { | 2298 HInstruction receiver) { |
| 2363 assert(Elements.isInstanceSend(send, elements)); | 2299 assert(Elements.isInstanceSend(send, elements)); |
| 2364 // TODO(kasperl): This is a convoluted way of checking if we're | |
| 2365 // generating code for a compound assignment. If we are, we need | |
| 2366 // to get the selector from the mapping for the AST selector node. | |
| 2367 Selector selector = (send.asSendSet() == null) | |
| 2368 ? elements.getSelector(send) | |
| 2369 : elements.getSelector(send.selector); | |
| 2370 assert(selector.isGetter()); | 2300 assert(selector.isGetter()); |
| 2371 SourceString getterName = selector.name; | 2301 SourceString getterName = selector.name; |
| 2372 Set<ClassElement> interceptedClasses = getInterceptedClassesOn(selector); | 2302 Set<ClassElement> interceptedClasses = getInterceptedClassesOn(selector); |
| 2373 | 2303 |
| 2374 bool hasGetter = compiler.world.hasAnyUserDefinedGetter(selector); | 2304 bool hasGetter = compiler.world.hasAnyUserDefinedGetter(selector); |
| 2375 HInstruction instruction; | 2305 HInstruction instruction; |
| 2376 if (interceptedClasses != null) { | 2306 if (interceptedClasses != null) { |
| 2377 // If we're using an interceptor class, emit a call to the | 2307 // If we're using an interceptor class, emit a call to the |
| 2378 // interceptor method and then the actual dynamic call on the | 2308 // interceptor method and then the actual dynamic call on the |
| 2379 // interceptor object. | 2309 // interceptor object. |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2412 } | 2342 } |
| 2413 // TODO(5346): Try to avoid the need for calling [declaration] before | 2343 // TODO(5346): Try to avoid the need for calling [declaration] before |
| 2414 // creating an [HStatic]. | 2344 // creating an [HStatic]. |
| 2415 push(new HStatic(element.declaration)); | 2345 push(new HStatic(element.declaration)); |
| 2416 if (element.isGetter()) { | 2346 if (element.isGetter()) { |
| 2417 push(new HInvokeStatic(<HInstruction>[pop()], HType.UNKNOWN)); | 2347 push(new HInvokeStatic(<HInstruction>[pop()], HType.UNKNOWN)); |
| 2418 } | 2348 } |
| 2419 } | 2349 } |
| 2420 } else if (Elements.isInstanceSend(send, elements)) { | 2350 } else if (Elements.isInstanceSend(send, elements)) { |
| 2421 HInstruction receiver = generateInstanceSendReceiver(send); | 2351 HInstruction receiver = generateInstanceSendReceiver(send); |
| 2422 generateInstanceGetterWithCompiledReceiver(send, receiver); | 2352 generateInstanceGetterWithCompiledReceiver( |
| 2353 send, elements.getSelector(send), receiver); |
| 2423 } else if (Elements.isStaticOrTopLevelFunction(element)) { | 2354 } else if (Elements.isStaticOrTopLevelFunction(element)) { |
| 2424 // TODO(5346): Try to avoid the need for calling [declaration] before | 2355 // TODO(5346): Try to avoid the need for calling [declaration] before |
| 2425 // creating an [HStatic]. | 2356 // creating an [HStatic]. |
| 2426 push(new HStatic(element.declaration)); | 2357 push(new HStatic(element.declaration)); |
| 2427 // TODO(ahe): This should be registered in codegen. | 2358 // TODO(ahe): This should be registered in codegen. |
| 2428 compiler.enqueuer.codegen.registerGetOfStaticFunction(element); | 2359 compiler.enqueuer.codegen.registerGetOfStaticFunction(element); |
| 2429 } else if (Elements.isErroneousElement(element)) { | 2360 } else if (Elements.isErroneousElement(element)) { |
| 2430 // An erroneous element indicates an unresolved static getter. | 2361 // An erroneous element indicates an unresolved static getter. |
| 2431 generateThrowNoSuchMethod(send, | 2362 generateThrowNoSuchMethod(send, |
| 2432 getTargetName(element, 'get'), | 2363 getTargetName(element, 'get'), |
| (...skipping 272 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2705 DartType type = elements.getType(typeAnnotation); | 2636 DartType type = elements.getType(typeAnnotation); |
| 2706 HInstruction converted = expression.convertType( | 2637 HInstruction converted = expression.convertType( |
| 2707 compiler, type, HTypeConversion.CAST_TYPE_CHECK); | 2638 compiler, type, HTypeConversion.CAST_TYPE_CHECK); |
| 2708 if (converted != expression) add(converted); | 2639 if (converted != expression) add(converted); |
| 2709 stack.add(converted); | 2640 stack.add(converted); |
| 2710 } else { | 2641 } else { |
| 2711 visit(node.receiver); | 2642 visit(node.receiver); |
| 2712 visit(node.argumentsNode); | 2643 visit(node.argumentsNode); |
| 2713 var right = pop(); | 2644 var right = pop(); |
| 2714 var left = pop(); | 2645 var left = pop(); |
| 2715 visitBinary(left, op, right, node); | 2646 visitBinary(left, op, right, elements.getSelector(node), node); |
| 2716 } | 2647 } |
| 2717 } | 2648 } |
| 2718 | 2649 |
| 2719 void addDynamicSendArgumentsToList(Send node, List<HInstruction> list) { | 2650 void addDynamicSendArgumentsToList(Send node, List<HInstruction> list) { |
| 2720 Selector selector = elements.getSelector(node); | 2651 Selector selector = elements.getSelector(node); |
| 2721 if (selector.namedArgumentCount == 0) { | 2652 if (selector.namedArgumentCount == 0) { |
| 2722 addGenericSendArgumentsToList(node.arguments, list); | 2653 addGenericSendArgumentsToList(node.arguments, list); |
| 2723 } else { | 2654 } else { |
| 2724 // Visit positional arguments and add them to the list. | 2655 // Visit positional arguments and add them to the list. |
| 2725 Link<Node> arguments = node.arguments; | 2656 Link<Node> arguments = node.arguments; |
| (...skipping 386 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3112 Element element = elements[node]; | 3043 Element element = elements[node]; |
| 3113 if (element != null && identical(element, currentElement)) { | 3044 if (element != null && identical(element, currentElement)) { |
| 3114 graph.isRecursiveMethod = true; | 3045 graph.isRecursiveMethod = true; |
| 3115 } | 3046 } |
| 3116 super.visitSend(node); | 3047 super.visitSend(node); |
| 3117 } | 3048 } |
| 3118 | 3049 |
| 3119 visitSuperSend(Send node) { | 3050 visitSuperSend(Send node) { |
| 3120 Selector selector = elements.getSelector(node); | 3051 Selector selector = elements.getSelector(node); |
| 3121 Element element = elements[node]; | 3052 Element element = elements[node]; |
| 3122 if (element == null) return generateSuperNoSuchMethodSend(node); | 3053 if (Elements.isUnresolved(element)) { |
| 3054 return generateSuperNoSuchMethodSend(node); |
| 3055 } |
| 3123 // TODO(5346): Try to avoid the need for calling [declaration] before | 3056 // TODO(5346): Try to avoid the need for calling [declaration] before |
| 3124 // creating an [HStatic]. | 3057 // creating an [HStatic]. |
| 3125 HInstruction target = new HStatic(element.declaration); | 3058 HInstruction target = new HStatic(element.declaration); |
| 3126 HInstruction context = localsHandler.readThis(); | 3059 HInstruction context = localsHandler.readThis(); |
| 3127 add(target); | 3060 add(target); |
| 3128 var inputs = <HInstruction>[target, context]; | 3061 var inputs = <HInstruction>[target, context]; |
| 3129 if (node.isPropertyAccess) { | 3062 if (node.isPropertyAccess) { |
| 3130 push(new HInvokeSuper(inputs)); | 3063 push(new HInvokeSuper(inputs)); |
| 3131 } else if (element.isFunction() || element.isGenerativeConstructor()) { | 3064 } else if (element.isFunction() || element.isGenerativeConstructor()) { |
| 3132 // TODO(5347): Try to avoid the need for calling [implementation] before | 3065 // TODO(5347): Try to avoid the need for calling [implementation] before |
| (...skipping 486 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3619 bool isPrefix = !node.isPostfix; | 3552 bool isPrefix = !node.isPostfix; |
| 3620 if (isCompoundAssignment) { | 3553 if (isCompoundAssignment) { |
| 3621 value = pop(); | 3554 value = pop(); |
| 3622 index = pop(); | 3555 index = pop(); |
| 3623 } else { | 3556 } else { |
| 3624 index = pop(); | 3557 index = pop(); |
| 3625 value = graph.addConstantInt(1, constantSystem); | 3558 value = graph.addConstantInt(1, constantSystem); |
| 3626 } | 3559 } |
| 3627 | 3560 |
| 3628 HInvokeDynamicMethod left = buildInvokeDynamic( | 3561 HInvokeDynamicMethod left = buildInvokeDynamic( |
| 3629 node, new Selector.index(), receiver, [index]); | 3562 node, |
| 3563 elements.getGetterSelectorInComplexSendSet(node), |
| 3564 receiver, |
| 3565 <HInstruction>[index]); |
| 3630 add(left); | 3566 add(left); |
| 3631 visitBinary(left, op, value, node); | 3567 visitBinary(left, op, value, |
| 3568 elements.getOperatorSelectorInComplexSendSet(node), node); |
| 3632 value = pop(); | 3569 value = pop(); |
| 3633 HInvokeDynamicMethod assign = buildInvokeDynamic( | 3570 HInvokeDynamicMethod assign = buildInvokeDynamic( |
| 3634 node, new Selector.indexSet(), receiver, [index, value]); | 3571 node, elements.getSelector(node), receiver, [index, value]); |
| 3635 add(assign); | 3572 add(assign); |
| 3636 if (isPrefix) { | 3573 if (isPrefix) { |
| 3637 stack.add(value); | 3574 stack.add(value); |
| 3638 } else { | 3575 } else { |
| 3639 stack.add(left); | 3576 stack.add(left); |
| 3640 } | 3577 } |
| 3641 } | 3578 } |
| 3642 } else if (const SourceString("=") == op.source) { | 3579 } else if (const SourceString("=") == op.source) { |
| 3643 Link<Node> link = node.arguments; | 3580 Link<Node> link = node.arguments; |
| 3644 assert(!link.isEmpty && link.tail.isEmpty); | 3581 assert(!link.isEmpty && link.tail.isEmpty); |
| 3645 visit(link.head); | 3582 visit(link.head); |
| 3646 HInstruction value = pop(); | 3583 HInstruction value = pop(); |
| 3647 generateSetter(node, element, value); | 3584 generateSetter(node, element, value); |
| 3648 } else if (identical(op.source.stringValue, "is")) { | 3585 } else if (identical(op.source.stringValue, "is")) { |
| 3649 compiler.internalError("is-operator as SendSet", node: op); | 3586 compiler.internalError("is-operator as SendSet", node: op); |
| 3650 } else { | 3587 } else { |
| 3651 assert(const SourceString("++") == op.source || | 3588 assert(const SourceString("++") == op.source || |
| 3652 const SourceString("--") == op.source || | 3589 const SourceString("--") == op.source || |
| 3653 node.assignmentOperator.source.stringValue.endsWith("=")); | 3590 node.assignmentOperator.source.stringValue.endsWith("=")); |
| 3654 bool isCompoundAssignment = !node.arguments.isEmpty; | 3591 bool isCompoundAssignment = !node.arguments.isEmpty; |
| 3655 bool isPrefix = !node.isPostfix; // Compound assignments are prefix. | 3592 bool isPrefix = !node.isPostfix; // Compound assignments are prefix. |
| 3656 | 3593 |
| 3657 // [receiver] is only used if the node is an instance send. | 3594 // [receiver] is only used if the node is an instance send. |
| 3658 HInstruction receiver = null; | 3595 HInstruction receiver = null; |
| 3659 if (Elements.isInstanceSend(node, elements)) { | 3596 if (Elements.isInstanceSend(node, elements)) { |
| 3660 receiver = generateInstanceSendReceiver(node); | 3597 receiver = generateInstanceSendReceiver(node); |
| 3661 generateInstanceGetterWithCompiledReceiver(node, receiver); | 3598 generateInstanceGetterWithCompiledReceiver( |
| 3599 node, elements.getGetterSelectorInComplexSendSet(node), receiver); |
| 3662 } else { | 3600 } else { |
| 3663 generateGetter(node, elements[node.selector]); | 3601 generateGetter(node, elements[node.selector]); |
| 3664 } | 3602 } |
| 3665 HInstruction left = pop(); | 3603 HInstruction left = pop(); |
| 3666 HInstruction right; | 3604 HInstruction right; |
| 3667 if (isCompoundAssignment) { | 3605 if (isCompoundAssignment) { |
| 3668 visit(node.argumentsNode); | 3606 visit(node.argumentsNode); |
| 3669 right = pop(); | 3607 right = pop(); |
| 3670 } else { | 3608 } else { |
| 3671 right = graph.addConstantInt(1, constantSystem); | 3609 right = graph.addConstantInt(1, constantSystem); |
| 3672 } | 3610 } |
| 3673 visitBinary(left, op, right, node); | 3611 visitBinary(left, op, right, |
| 3612 elements.getOperatorSelectorInComplexSendSet(node), node); |
| 3674 HInstruction operation = pop(); | 3613 HInstruction operation = pop(); |
| 3675 assert(operation != null); | 3614 assert(operation != null); |
| 3676 if (Elements.isInstanceSend(node, elements)) { | 3615 if (Elements.isInstanceSend(node, elements)) { |
| 3677 assert(receiver != null); | 3616 assert(receiver != null); |
| 3678 generateInstanceSetterWithCompiledReceiver(node, receiver, operation); | 3617 generateInstanceSetterWithCompiledReceiver(node, receiver, operation); |
| 3679 } else { | 3618 } else { |
| 3680 assert(receiver == null); | 3619 assert(receiver == null); |
| 3681 generateSetter(node, element, operation); | 3620 generateSetter(node, element, operation); |
| 3682 } | 3621 } |
| 3683 if (!isPrefix) { | 3622 if (!isPrefix) { |
| (...skipping 225 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3909 // Generate a structure equivalent to: | 3848 // Generate a structure equivalent to: |
| 3910 // Iterator<E> $iter = <iterable>.iterator; | 3849 // Iterator<E> $iter = <iterable>.iterator; |
| 3911 // while ($iter.moveNext()) { | 3850 // while ($iter.moveNext()) { |
| 3912 // E <declaredIdentifier> = $iter.current; | 3851 // E <declaredIdentifier> = $iter.current; |
| 3913 // <body> | 3852 // <body> |
| 3914 // } | 3853 // } |
| 3915 | 3854 |
| 3916 // The iterator is shared between initializer, condition and body. | 3855 // The iterator is shared between initializer, condition and body. |
| 3917 HInstruction iterator; | 3856 HInstruction iterator; |
| 3918 void buildInitializer() { | 3857 void buildInitializer() { |
| 3919 SourceString iteratorName = const SourceString("iterator"); | 3858 Selector selector = elements.getIteratorSelector(node); |
| 3920 Selector selector = | |
| 3921 new Selector.getter(iteratorName, currentElement.getLibrary()); | |
| 3922 Set<ClassElement> interceptedClasses = getInterceptedClassesOn(selector); | 3859 Set<ClassElement> interceptedClasses = getInterceptedClassesOn(selector); |
| 3923 visit(node.expression); | 3860 visit(node.expression); |
| 3924 HInstruction receiver = pop(); | 3861 HInstruction receiver = pop(); |
| 3925 bool hasGetter = compiler.world.hasAnyUserDefinedGetter(selector); | 3862 bool hasGetter = compiler.world.hasAnyUserDefinedGetter(selector); |
| 3926 if (interceptedClasses == null) { | 3863 if (interceptedClasses == null) { |
| 3927 iterator = | 3864 iterator = |
| 3928 new HInvokeDynamicGetter(selector, null, receiver, !hasGetter); | 3865 new HInvokeDynamicGetter(selector, null, receiver, !hasGetter); |
| 3929 } else { | 3866 } else { |
| 3930 HInterceptor interceptor = | 3867 HInterceptor interceptor = |
| 3931 invokeInterceptor(interceptedClasses, receiver, null); | 3868 invokeInterceptor(interceptedClasses, receiver, null); |
| 3932 iterator = | 3869 iterator = |
| 3933 new HInvokeDynamicGetter(selector, null, interceptor, !hasGetter); | 3870 new HInvokeDynamicGetter(selector, null, interceptor, !hasGetter); |
| 3934 // Add the receiver as an argument to the getter call on the | 3871 // Add the receiver as an argument to the getter call on the |
| 3935 // interceptor. | 3872 // interceptor. |
| 3936 iterator.inputs.add(receiver); | 3873 iterator.inputs.add(receiver); |
| 3937 } | 3874 } |
| 3938 add(iterator); | 3875 add(iterator); |
| 3939 } | 3876 } |
| 3940 HInstruction buildCondition() { | 3877 HInstruction buildCondition() { |
| 3941 SourceString name = const SourceString('moveNext'); | 3878 Selector selector = elements.getMoveNextSelector(node); |
| 3942 Selector selector = new Selector.call( | |
| 3943 name, currentElement.getLibrary(), 0); | |
| 3944 push(new HInvokeDynamicMethod(selector, <HInstruction>[iterator])); | 3879 push(new HInvokeDynamicMethod(selector, <HInstruction>[iterator])); |
| 3945 return popBoolified(); | 3880 return popBoolified(); |
| 3946 } | 3881 } |
| 3947 void buildBody() { | 3882 void buildBody() { |
| 3948 SourceString name = const SourceString('current'); | 3883 Selector call = elements.getCurrentSelector(node); |
| 3949 Selector call = new Selector.getter(name, currentElement.getLibrary()); | |
| 3950 bool hasGetter = compiler.world.hasAnyUserDefinedGetter(call); | 3884 bool hasGetter = compiler.world.hasAnyUserDefinedGetter(call); |
| 3951 push(new HInvokeDynamicGetter(call, null, iterator, !hasGetter)); | 3885 push(new HInvokeDynamicGetter(call, null, iterator, !hasGetter)); |
| 3952 | 3886 |
| 3953 Element variable; | 3887 Element variable; |
| 3954 if (node.declaredIdentifier.asSend() != null) { | 3888 if (node.declaredIdentifier.asSend() != null) { |
| 3955 variable = elements[node.declaredIdentifier]; | 3889 variable = elements[node.declaredIdentifier]; |
| 3956 } else { | 3890 } else { |
| 3957 assert(node.declaredIdentifier.asVariableDefinitions() != null); | 3891 assert(node.declaredIdentifier.asVariableDefinitions() != null); |
| 3958 VariableDefinitions variableDefinitions = node.declaredIdentifier; | 3892 VariableDefinitions variableDefinitions = node.declaredIdentifier; |
| 3959 variable = elements[variableDefinitions.definitions.nodes.head]; | 3893 variable = elements[variableDefinitions.definitions.nodes.head]; |
| (...skipping 1071 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5031 new HSubGraphBlockInformation(elseBranch.graph)); | 4965 new HSubGraphBlockInformation(elseBranch.graph)); |
| 5032 | 4966 |
| 5033 HBasicBlock conditionStartBlock = conditionBranch.block; | 4967 HBasicBlock conditionStartBlock = conditionBranch.block; |
| 5034 conditionStartBlock.setBlockFlow(info, joinBlock); | 4968 conditionStartBlock.setBlockFlow(info, joinBlock); |
| 5035 SubGraph conditionGraph = conditionBranch.graph; | 4969 SubGraph conditionGraph = conditionBranch.graph; |
| 5036 HIf branch = conditionGraph.end.last; | 4970 HIf branch = conditionGraph.end.last; |
| 5037 assert(branch is HIf); | 4971 assert(branch is HIf); |
| 5038 branch.blockInformation = conditionStartBlock.blockFlow; | 4972 branch.blockInformation = conditionStartBlock.blockFlow; |
| 5039 } | 4973 } |
| 5040 } | 4974 } |
| OLD | NEW |