| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, 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.ir_builder; | 5 library dart2js.ir_builder; |
| 6 | 6 |
| 7 import '../compile_time_constants.dart' show BackendConstantEnvironment; | 7 import '../compile_time_constants.dart' show BackendConstantEnvironment; |
| 8 import '../constants/constant_system.dart'; | 8 import '../constants/constant_system.dart'; |
| 9 import '../constants/expressions.dart'; | 9 import '../constants/expressions.dart'; |
| 10 import '../constants/values.dart' show ConstantValue, PrimitiveConstantValue; | 10 import '../constants/values.dart' show ConstantValue, PrimitiveConstantValue; |
| (...skipping 381 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 392 final BackendConstantEnvironment constants; | 392 final BackendConstantEnvironment constants; |
| 393 | 393 |
| 394 ConstantSystem get constantSystem => constants.constantSystem; | 394 ConstantSystem get constantSystem => constants.constantSystem; |
| 395 | 395 |
| 396 /// A stack of collectors for breaks. | 396 /// A stack of collectors for breaks. |
| 397 final List<JumpCollector> breakCollectors = <JumpCollector>[]; | 397 final List<JumpCollector> breakCollectors = <JumpCollector>[]; |
| 398 | 398 |
| 399 /// A stack of collectors for continues. | 399 /// A stack of collectors for continues. |
| 400 final List<JumpCollector> continueCollectors = <JumpCollector>[]; | 400 final List<JumpCollector> continueCollectors = <JumpCollector>[]; |
| 401 | 401 |
| 402 final List<ConstDeclaration> localConstants = <ConstDeclaration>[]; | |
| 403 | |
| 404 final ExecutableElement currentElement; | 402 final ExecutableElement currentElement; |
| 405 | 403 |
| 406 final ir.Continuation returnContinuation = new ir.Continuation.retrn(); | 404 final ir.Continuation returnContinuation = new ir.Continuation.retrn(); |
| 407 ir.Parameter _thisParameter; | 405 ir.Parameter _thisParameter; |
| 408 ir.Parameter enclosingMethodThisParameter; | 406 ir.Parameter enclosingMethodThisParameter; |
| 409 | 407 |
| 410 final List<ir.Parameter> functionParameters = <ir.Parameter>[]; | 408 final List<ir.Parameter> functionParameters = <ir.Parameter>[]; |
| 411 | 409 |
| 412 IrBuilderSharedState(this.constants, this.currentElement); | 410 IrBuilderSharedState(this.constants, this.currentElement); |
| 413 | 411 |
| (...skipping 177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 591 } | 589 } |
| 592 | 590 |
| 593 /// Creates a parameter for [local] and adds it to the current environment. | 591 /// Creates a parameter for [local] and adds it to the current environment. |
| 594 ir.Parameter createLocalParameter(Local local) { | 592 ir.Parameter createLocalParameter(Local local) { |
| 595 ir.Parameter parameter = new ir.Parameter(local); | 593 ir.Parameter parameter = new ir.Parameter(local); |
| 596 _parameters.add(parameter); | 594 _parameters.add(parameter); |
| 597 environment.extend(local, parameter); | 595 environment.extend(local, parameter); |
| 598 return parameter; | 596 return parameter; |
| 599 } | 597 } |
| 600 | 598 |
| 601 /// Adds the constant [variableElement] to the environment with [value] as its | |
| 602 /// constant value. | |
| 603 void declareLocalConstant(LocalVariableElement variableElement, | |
| 604 ConstantExpression value) { | |
| 605 state.localConstants.add(new ConstDeclaration(variableElement, value)); | |
| 606 } | |
| 607 | |
| 608 /// Plug an expression into the 'hole' in the context being accumulated. The | 599 /// Plug an expression into the 'hole' in the context being accumulated. The |
| 609 /// empty context (just a hole) is represented by root (and current) being | 600 /// empty context (just a hole) is represented by root (and current) being |
| 610 /// null. Since the hole in the current context is filled by this function, | 601 /// null. Since the hole in the current context is filled by this function, |
| 611 /// the new hole must be in the newly added expression---which becomes the | 602 /// the new hole must be in the newly added expression---which becomes the |
| 612 /// new value of current. | 603 /// new value of current. |
| 613 void add(ir.Expression expr) { | 604 void add(ir.Expression expr) { |
| 614 assert(isOpen); | 605 assert(isOpen); |
| 615 if (_root == null) { | 606 if (_root == null) { |
| 616 _root = _current = expr; | 607 _root = _current = expr; |
| 617 } else { | 608 } else { |
| (...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 668 ir.Primitive _buildInvokeCall(ir.Primitive target, | 659 ir.Primitive _buildInvokeCall(ir.Primitive target, |
| 669 CallStructure callStructure, | 660 CallStructure callStructure, |
| 670 List<ir.Definition> arguments, | 661 List<ir.Definition> arguments, |
| 671 {SourceInformation sourceInformation}) { | 662 {SourceInformation sourceInformation}) { |
| 672 Selector selector = callStructure.callSelector; | 663 Selector selector = callStructure.callSelector; |
| 673 return _buildInvokeDynamic(target, selector, arguments, | 664 return _buildInvokeDynamic(target, selector, arguments, |
| 674 sourceInformation: sourceInformation); | 665 sourceInformation: sourceInformation); |
| 675 } | 666 } |
| 676 | 667 |
| 677 | 668 |
| 678 /// Create a [ir.Constant] from [constant] and add it to the CPS term. | 669 /// Create a [ir.Constant] from [value] and add it to the CPS term. |
| 679 // TODO(johnniwinther): Remove [value] when [ConstantValue] can be computed | 670 ir.Constant buildConstant(ConstantValue value) { |
| 680 // directly from [constant]. | |
| 681 ir.Constant buildConstant(ConstantExpression constant, ConstantValue value) { | |
| 682 assert(isOpen); | 671 assert(isOpen); |
| 683 return addPrimitive(new ir.Constant(constant, value)); | 672 return addPrimitive(new ir.Constant(value)); |
| 684 } | 673 } |
| 685 | 674 |
| 686 /// Create an integer constant and add it to the CPS term. | 675 /// Create an integer constant and add it to the CPS term. |
| 687 ir.Constant buildIntegerConstant(int value) { | 676 ir.Constant buildIntegerConstant(int value) { |
| 688 return buildConstant( | 677 return buildConstant(state.constantSystem.createInt(value)); |
| 689 new IntConstantExpression(value), | |
| 690 state.constantSystem.createInt(value)); | |
| 691 } | 678 } |
| 692 | 679 |
| 693 /// Create a double constant and add it to the CPS term. | 680 /// Create a double constant and add it to the CPS term. |
| 694 ir.Constant buildDoubleConstant(double value) { | 681 ir.Constant buildDoubleConstant(double value) { |
| 695 return buildConstant( | 682 return buildConstant(state.constantSystem.createDouble(value)); |
| 696 new DoubleConstantExpression(value), | |
| 697 state.constantSystem.createDouble(value)); | |
| 698 } | 683 } |
| 699 | 684 |
| 700 /// Create a Boolean constant and add it to the CPS term. | 685 /// Create a Boolean constant and add it to the CPS term. |
| 701 ir.Constant buildBooleanConstant(bool value) { | 686 ir.Constant buildBooleanConstant(bool value) { |
| 702 return buildConstant( | 687 return buildConstant(state.constantSystem.createBool(value)); |
| 703 new BoolConstantExpression(value), | |
| 704 state.constantSystem.createBool(value)); | |
| 705 } | 688 } |
| 706 | 689 |
| 707 /// Create a null constant and add it to the CPS term. | 690 /// Create a null constant and add it to the CPS term. |
| 708 ir.Constant buildNullConstant() { | 691 ir.Constant buildNullConstant() { |
| 709 return buildConstant( | 692 return buildConstant(state.constantSystem.createNull()); |
| 710 new NullConstantExpression(), | |
| 711 state.constantSystem.createNull()); | |
| 712 } | 693 } |
| 713 | 694 |
| 714 /// Create a string constant and add it to the CPS term. | 695 /// Create a string constant and add it to the CPS term. |
| 715 ir.Constant buildStringConstant(String value) { | 696 ir.Constant buildStringConstant(String value) { |
| 716 return buildConstant( | 697 return buildConstant( |
| 717 new StringConstantExpression(value), | |
| 718 state.constantSystem.createString(new ast.DartString.literal(value))); | 698 state.constantSystem.createString(new ast.DartString.literal(value))); |
| 719 } | 699 } |
| 720 | 700 |
| 721 /// Create a string constant and add it to the CPS term. | 701 /// Create a string constant and add it to the CPS term. |
| 722 ir.Constant buildDartStringConstant(ast.DartString value) { | 702 ir.Constant buildDartStringConstant(ast.DartString value) { |
| 723 return buildConstant( | 703 return buildConstant(state.constantSystem.createString(value)); |
| 724 new StringConstantExpression(value.slowToString()), | |
| 725 state.constantSystem.createString(value)); | |
| 726 } | 704 } |
| 727 | 705 |
| 728 /// Creates a non-constant list literal of the provided [type] and with the | 706 /// Creates a non-constant list literal of the provided [type] and with the |
| 729 /// provided [values]. | 707 /// provided [values]. |
| 730 ir.Primitive buildListLiteral(InterfaceType type, | 708 ir.Primitive buildListLiteral(InterfaceType type, |
| 731 Iterable<ir.Primitive> values) { | 709 Iterable<ir.Primitive> values) { |
| 732 assert(isOpen); | 710 assert(isOpen); |
| 733 return addPrimitive(new ir.LiteralList(type, values.toList())); | 711 return addPrimitive(new ir.LiteralList(type, values.toList())); |
| 734 } | 712 } |
| 735 | 713 |
| (...skipping 347 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1083 } | 1061 } |
| 1084 | 1062 |
| 1085 /// Create a constructor invocation of [element] on [type] where the | 1063 /// Create a constructor invocation of [element] on [type] where the |
| 1086 /// constructor name and argument structure are defined by [callStructure] and | 1064 /// constructor name and argument structure are defined by [callStructure] and |
| 1087 /// the argument values are defined by [arguments]. | 1065 /// the argument values are defined by [arguments]. |
| 1088 ir.Primitive buildConstructorInvocation(FunctionElement element, | 1066 ir.Primitive buildConstructorInvocation(FunctionElement element, |
| 1089 CallStructure callStructure, | 1067 CallStructure callStructure, |
| 1090 DartType type, | 1068 DartType type, |
| 1091 List<ir.Primitive> arguments); | 1069 List<ir.Primitive> arguments); |
| 1092 | 1070 |
| 1093 /// Create a string concatenation of the [arguments]. | 1071 ir.Primitive buildStringify(ir.Primitive argument); |
| 1072 |
| 1073 /// Concatenate string values. |
| 1074 /// |
| 1075 /// The arguments must be strings; usually a call to [buildStringify] is |
| 1076 /// needed to ensure the proper conversion takes places. |
| 1094 ir.Primitive buildStringConcatenation(List<ir.Primitive> arguments) { | 1077 ir.Primitive buildStringConcatenation(List<ir.Primitive> arguments) { |
| 1095 assert(isOpen); | 1078 assert(isOpen); |
| 1096 return _continueWithExpression( | 1079 return addPrimitive(new ir.ApplyBuiltinOperator( |
| 1097 (k) => new ir.ConcatenateStrings(arguments, k)); | 1080 ir.BuiltinOperator.StringConcatenate, |
| 1081 arguments)); |
| 1098 } | 1082 } |
| 1099 | 1083 |
| 1100 /// Create an invocation of the `call` method of [functionExpression], where | 1084 /// Create an invocation of the `call` method of [functionExpression], where |
| 1101 /// the structure of arguments are given by [callStructure]. | 1085 /// the structure of arguments are given by [callStructure]. |
| 1102 ir.Primitive buildCallInvocation( | 1086 ir.Primitive buildCallInvocation( |
| 1103 ir.Primitive functionExpression, | 1087 ir.Primitive functionExpression, |
| 1104 CallStructure callStructure, | 1088 CallStructure callStructure, |
| 1105 List<ir.Definition> arguments, | 1089 List<ir.Definition> arguments, |
| 1106 {SourceInformation sourceInformation}) { | 1090 {SourceInformation sourceInformation}) { |
| 1107 return _buildInvokeCall(functionExpression, callStructure, arguments, | 1091 return _buildInvokeCall(functionExpression, callStructure, arguments, |
| (...skipping 886 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1994 // ! e is translated as e ? false : true | 1978 // ! e is translated as e ? false : true |
| 1995 | 1979 |
| 1996 // Add a continuation parameter for the result of the expression. | 1980 // Add a continuation parameter for the result of the expression. |
| 1997 ir.Parameter resultParameter = new ir.Parameter(null); | 1981 ir.Parameter resultParameter = new ir.Parameter(null); |
| 1998 | 1982 |
| 1999 ir.Continuation joinContinuation = new ir.Continuation([resultParameter]); | 1983 ir.Continuation joinContinuation = new ir.Continuation([resultParameter]); |
| 2000 ir.Continuation thenContinuation = new ir.Continuation([]); | 1984 ir.Continuation thenContinuation = new ir.Continuation([]); |
| 2001 ir.Continuation elseContinuation = new ir.Continuation([]); | 1985 ir.Continuation elseContinuation = new ir.Continuation([]); |
| 2002 | 1986 |
| 2003 ir.Constant makeBoolConstant(bool value) { | 1987 ir.Constant makeBoolConstant(bool value) { |
| 2004 return new ir.Constant( | 1988 return new ir.Constant(state.constantSystem.createBool(value)); |
| 2005 new BoolConstantExpression(value), | |
| 2006 state.constantSystem.createBool(value)); | |
| 2007 } | 1989 } |
| 2008 | 1990 |
| 2009 ir.Constant trueConstant = makeBoolConstant(true); | 1991 ir.Constant trueConstant = makeBoolConstant(true); |
| 2010 ir.Constant falseConstant = makeBoolConstant(false); | 1992 ir.Constant falseConstant = makeBoolConstant(false); |
| 2011 | 1993 |
| 2012 thenContinuation.body = new ir.LetPrim(falseConstant) | 1994 thenContinuation.body = new ir.LetPrim(falseConstant) |
| 2013 ..plug(new ir.InvokeContinuation(joinContinuation, [falseConstant])); | 1995 ..plug(new ir.InvokeContinuation(joinContinuation, [falseConstant])); |
| 2014 elseContinuation.body = new ir.LetPrim(trueConstant) | 1996 elseContinuation.body = new ir.LetPrim(trueConstant) |
| 2015 ..plug(new ir.InvokeContinuation(joinContinuation, [trueConstant])); | 1997 ..plug(new ir.InvokeContinuation(joinContinuation, [trueConstant])); |
| 2016 | 1998 |
| (...skipping 532 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2549 ir.Primitive condition = _buildCheckNull(receiver); | 2531 ir.Primitive condition = _buildCheckNull(receiver); |
| 2550 return buildConditional(condition, (_) => receiver, buildSend); | 2532 return buildConditional(condition, (_) => receiver, buildSend); |
| 2551 } | 2533 } |
| 2552 | 2534 |
| 2553 /// Creates a type test checking whether [value] is null. | 2535 /// Creates a type test checking whether [value] is null. |
| 2554 ir.Primitive _buildCheckNull(ir.Primitive value) { | 2536 ir.Primitive _buildCheckNull(ir.Primitive value) { |
| 2555 assert(isOpen); | 2537 assert(isOpen); |
| 2556 ir.Primitive right = buildNullConstant(); | 2538 ir.Primitive right = buildNullConstant(); |
| 2557 return addPrimitive(new ir.Identical(value, right)); | 2539 return addPrimitive(new ir.Identical(value, right)); |
| 2558 } | 2540 } |
| 2541 |
| 2542 /// Convert the given value to a string. |
| 2543 ir.Primitive buildStringify(ir.Primitive value) { |
| 2544 return buildStaticFunctionInvocation( |
| 2545 program.stringifyFunction, |
| 2546 new CallStructure.unnamed(1), |
| 2547 <ir.Primitive>[value]); |
| 2548 } |
| 2559 } | 2549 } |
| 2560 | 2550 |
| 2561 | 2551 |
| 2562 /// Location of a variable relative to a given closure. | 2552 /// Location of a variable relative to a given closure. |
| 2563 class ClosureLocation { | 2553 class ClosureLocation { |
| 2564 /// If not `null`, this location is [box].[field]. | 2554 /// If not `null`, this location is [box].[field]. |
| 2565 /// The location of [box] can be obtained separately from an | 2555 /// The location of [box] can be obtained separately from an |
| 2566 /// enclosing [ClosureEnvironment] or [ClosureScope]. | 2556 /// enclosing [ClosureEnvironment] or [ClosureScope]. |
| 2567 /// If `null`, then the location is [field] on the enclosing function object. | 2557 /// If `null`, then the location is [field] on the enclosing function object. |
| 2568 final BoxLocal box; | 2558 final BoxLocal box; |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2630 } | 2620 } |
| 2631 | 2621 |
| 2632 class SwitchCaseInfo { | 2622 class SwitchCaseInfo { |
| 2633 final List<ir.Primitive> constants = <ir.Primitive>[]; | 2623 final List<ir.Primitive> constants = <ir.Primitive>[]; |
| 2634 final SubbuildFunction buildBody; | 2624 final SubbuildFunction buildBody; |
| 2635 | 2625 |
| 2636 SwitchCaseInfo(this.buildBody); | 2626 SwitchCaseInfo(this.buildBody); |
| 2637 | 2627 |
| 2638 void addConstant(ir.Primitive constant) => constants.add(constant); | 2628 void addConstant(ir.Primitive constant) => constants.add(constant); |
| 2639 } | 2629 } |
| OLD | NEW |