package cd.ir; import cd.ir.Ast.Expr; import java.util.ArrayList; import java.util.List; /** * Represents the control flow graph of a single method. */ public class ControlFlowGraph { public BasicBlock start, end; public final List allBlocks = new ArrayList(); public int count() { return allBlocks.size(); } public BasicBlock newBlock() { BasicBlock blk = new BasicBlock(count()); allBlocks.add(blk); return blk; } /** * Given a list of basic blocks that do not yet have successors, * merges their control flows into a single successor and returns * the new successor. */ public BasicBlock join(BasicBlock... pred) { BasicBlock result = newBlock(); for (BasicBlock p : pred) { assert p.condition == null; assert p.successors.size() == 0; p.successors.add(result); result.predecessors.add(p); } return result; } /** * Terminates {@code blk} so that it evaluates {@code cond}, * and creates two new basic blocks, one for the case where * the result is true, and one for the case where the result is * false. */ public void terminateInCondition(BasicBlock blk, Expr cond) { assert blk.condition == null; assert blk.successors.size() == 0; blk.condition = cond; blk.successors.add(newBlock()); blk.successors.add(newBlock()); blk.trueSuccessor().predecessors.add(blk); blk.falseSuccessor().predecessors.add(blk); } public void connect(BasicBlock from, BasicBlock to) { to.predecessors.add(from); from.successors.add(to); } }