Chromium Code Reviews| Index: frog/leg/ssa/nodes.dart |
| diff --git a/frog/leg/ssa/nodes.dart b/frog/leg/ssa/nodes.dart |
| index e5a1e333d488a459740990958c650fe606e6d290..30acb23ef5be3679048679aa0a4a51bbcee859a9 100644 |
| --- a/frog/leg/ssa/nodes.dart |
| +++ b/frog/leg/ssa/nodes.dart |
| @@ -139,9 +139,11 @@ class HGraph { |
| return result; |
| } |
| - HBasicBlock addNewLoopHeaderBlock(List<LabelElement> labels) { |
| + HBasicBlock addNewLoopHeaderBlock(int type, |
| + TargetElement target, |
| + List<LabelElement> labels) { |
| HBasicBlock result = addNewBlock(); |
| - result.loopInformation = new HLoopInformation(result, labels); |
| + result.loopInformation = new HLoopInformation(type, result, target, labels); |
| return result; |
| } |
| @@ -322,6 +324,12 @@ class SubGraph { |
| } |
| } |
| +class SubExpression extends SubGraph { |
| + final HInstruction expression; |
| + const SubExpression(HBasicBlock start, HBasicBlock end, this.expression) |
| + : super(start, end); |
| +} |
| + |
| class HInstructionList { |
| HInstruction first = null; |
| HInstruction last = null; |
| @@ -647,7 +655,9 @@ class HBasicBlock extends HInstructionList implements Hashable { |
| } |
| } |
| -class HLabeledBlockInformation { |
| +interface HBlockInformation {} |
| + |
| +class HLabeledBlockInformation implements HBlockInformation { |
| final SubGraph body; |
| final HBasicBlock joinBlock; |
| final List<LabelElement> labels; |
| @@ -666,16 +676,43 @@ class HLabeledBlockInformation { |
| : this.labels = const<LabelElement>[]; |
| } |
| -class HLoopInformation { |
| +class LoopTypeVisitor extends AbstractVisitor { |
| + const LoopTypeVisitor(); |
| + int visitNode(Node node) { |
| + unreachable(); |
| + } |
| + int visitWhile(While node) => HLoopInformation.WHILE_LOOP; |
| + int visitFor(For node) => HLoopInformation.FOR_LOOP; |
| + int visitDoWhile(DoWhile node) => HLoopInformation.DO_WHILE_LOOP; |
| + int visitForIn(ForIn node) => HLoopInformation.FOR_IN_LOOP; |
| +} |
| + |
| +class HLoopInformation implements HBlockInformation { |
| + static final int WHILE_LOOP = 0; |
| + static final int FOR_LOOP = 1; |
| + static final int DO_WHILE_LOOP = 2; |
| + static final int FOR_IN_LOOP = 3; |
| + |
| + final int type; |
| final HBasicBlock header; |
| final List<HBasicBlock> blocks; |
| final List<HBasicBlock> backEdges; |
| final List<LabelElement> labels; |
| + final TargetElement target; |
| + SubGraph initializer = null; |
| + SubExpression condition = null; |
| + SubGraph body = null; |
| + SubGraph updates = null; |
| + HBasicBlock joinBlock; |
| - HLoopInformation(this.header, this.labels) |
| + HLoopInformation(this.type, this.header, this.target, this.labels) |
| : blocks = new List<HBasicBlock>(), |
| backEdges = new List<HBasicBlock>(); |
| + static int loopType(Node node) { |
| + return node.accept(const LoopTypeVisitor()); |
| + } |
| + |
| void addBackEdge(HBasicBlock predecessor) { |
| backEdges.add(predecessor); |
| addBlock(predecessor); |
| @@ -808,6 +845,8 @@ class HInstruction implements Hashable { |
| bool useGvn() => getFlag(FLAG_USE_GVN); |
| void setUseGvn() { setFlag(FLAG_USE_GVN); } |
| + // Does this node ootentially affect control flow. |
|
floitsch
2012/03/28 04:03:48
potentially
|
| + bool isControlFlow() => false; |
| bool isArray() => type.isArray(); |
| bool isBoolean() => type.isBoolean(); |
| @@ -991,6 +1030,8 @@ class HCheck extends HInstruction { |
| // TODO(floitsch): make class abstract instead of adding an abstract method. |
| abstract accept(HVisitor visitor); |
| + |
| + bool isControlFlow() => true; |
| } |
| class HTypeGuard extends HInstruction { |
| @@ -1012,6 +1053,8 @@ class HTypeGuard extends HInstruction { |
| HType computeType() => type; |
| bool hasExpectedType() => true; |
| + bool isControlFlow() => true; |
| + |
| accept(HVisitor visitor) => visitor.visitTypeGuard(this); |
| int typeCode() => 1; |
| bool typeEquals(other) => other is HTypeGuard; |
| @@ -1022,6 +1065,7 @@ class HBailoutTarget extends HInstruction { |
| final int state; |
| HBailoutTarget(this.state, inputs) : super(inputs); |
| accept(HVisitor visitor) => visitor.visitBailoutTarget(this); |
| + bool isControlFlow() => true; |
| } |
| class HBoundsCheck extends HCheck { |
| @@ -1076,6 +1120,7 @@ class HConditionalBranch extends HControlFlow { |
| class HControlFlow extends HInstruction { |
| HControlFlow(inputs) : super(inputs); |
| abstract toString(); |
| + bool isControlFlow() => true; |
| } |
| class HInvoke extends HInstruction { |