Search in sources :

Example 6 with ControlFlowGraph

use of org.graalvm.compiler.nodes.cfg.ControlFlowGraph in project graal by oracle.

the class ReentrantBlockIteratorTest method getVisitedBlocksInOrder.

private List<Block> getVisitedBlocksInOrder(String snippet) {
    StructuredGraph graph = parseEager(snippet, AllowAssumptions.YES);
    // after FSA to ensure HIR loop data structure does not contain loop exits
    graph.setGuardsStage(GuardsStage.AFTER_FSA);
    ArrayList<Block> blocks = new ArrayList<>();
    class VoidState {
    }
    final VoidState voidState = new VoidState();
    BlockIteratorClosure<VoidState> closure = new BlockIteratorClosure<VoidState>() {

        @Override
        protected VoidState getInitialState() {
            return voidState;
        }

        @Override
        protected VoidState processBlock(Block block, VoidState currentState) {
            // remember the visit order
            blocks.add(block);
            return currentState;
        }

        @Override
        protected VoidState merge(Block merge, List<VoidState> states) {
            return voidState;
        }

        @Override
        protected VoidState cloneState(VoidState oldState) {
            return voidState;
        }

        @Override
        protected List<VoidState> processLoop(Loop<Block> loop, VoidState initialState) {
            return ReentrantBlockIterator.processLoop(this, loop, initialState).exitStates;
        }
    };
    ControlFlowGraph cfg = ControlFlowGraph.compute(graph, true, true, true, false);
    ReentrantBlockIterator.apply(closure, cfg.getStartBlock());
    // schedule for IGV
    new SchedulePhase(graph.getOptions()).apply(graph);
    return blocks;
}
Also used : Loop(org.graalvm.compiler.core.common.cfg.Loop) BlockIteratorClosure(org.graalvm.compiler.phases.graph.ReentrantBlockIterator.BlockIteratorClosure) SchedulePhase(org.graalvm.compiler.phases.schedule.SchedulePhase) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) ArrayList(java.util.ArrayList) Block(org.graalvm.compiler.nodes.cfg.Block) ArrayList(java.util.ArrayList) List(java.util.List)

Example 7 with ControlFlowGraph

use of org.graalvm.compiler.nodes.cfg.ControlFlowGraph in project graal by oracle.

the class SimpleCFGTest method testImplies.

@Test
public void testImplies() {
    OptionValues options = getInitialOptions();
    DebugContext debug = DebugContext.create(options, new GraalDebugHandlersFactory(getSnippetReflection()));
    StructuredGraph graph = new StructuredGraph.Builder(options, debug, AllowAssumptions.YES).build();
    EndNode trueEnd = graph.add(new EndNode());
    EndNode falseEnd = graph.add(new EndNode());
    AbstractBeginNode trueBegin = graph.add(new BeginNode());
    trueBegin.setNext(trueEnd);
    AbstractBeginNode falseBegin = graph.add(new BeginNode());
    falseBegin.setNext(falseEnd);
    IfNode ifNode = graph.add(new IfNode(null, trueBegin, falseBegin, 0.5));
    graph.start().setNext(ifNode);
    AbstractMergeNode merge = graph.add(new MergeNode());
    merge.addForwardEnd(trueEnd);
    merge.addForwardEnd(falseEnd);
    ReturnNode returnNode = graph.add(new ReturnNode(null));
    merge.setNext(returnNode);
    dumpGraph(graph);
    ControlFlowGraph cfg = ControlFlowGraph.compute(graph, true, true, true, true);
    Block[] blocks = cfg.getBlocks();
    // check number of blocks
    assertDeepEquals(4, blocks.length);
    // check block - node assignment
    assertDeepEquals(blocks[0], cfg.blockFor(graph.start()));
    assertDeepEquals(blocks[0], cfg.blockFor(ifNode));
    assertDeepEquals(blocks[1], cfg.blockFor(trueBegin));
    assertDeepEquals(blocks[1], cfg.blockFor(trueEnd));
    assertDeepEquals(blocks[2], cfg.blockFor(falseBegin));
    assertDeepEquals(blocks[2], cfg.blockFor(falseEnd));
    assertDeepEquals(blocks[3], cfg.blockFor(merge));
    assertDeepEquals(blocks[3], cfg.blockFor(returnNode));
    // check dominators
    assertDominator(blocks[0], null);
    assertDominator(blocks[1], blocks[0]);
    assertDominator(blocks[2], blocks[0]);
    assertDominator(blocks[3], blocks[0]);
    // check dominated
    assertDominatedSize(blocks[0], 3);
    assertDominatedSize(blocks[1], 0);
    assertDominatedSize(blocks[2], 0);
    assertDominatedSize(blocks[3], 0);
    // check postdominators
    assertPostdominator(blocks[0], blocks[3]);
    assertPostdominator(blocks[1], blocks[3]);
    assertPostdominator(blocks[2], blocks[3]);
    assertPostdominator(blocks[3], null);
}
Also used : OptionValues(org.graalvm.compiler.options.OptionValues) DebugContext(org.graalvm.compiler.debug.DebugContext) IfNode(org.graalvm.compiler.nodes.IfNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) GraalDebugHandlersFactory(org.graalvm.compiler.printer.GraalDebugHandlersFactory) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) MergeNode(org.graalvm.compiler.nodes.MergeNode) ReturnNode(org.graalvm.compiler.nodes.ReturnNode) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) EndNode(org.graalvm.compiler.nodes.EndNode) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) BeginNode(org.graalvm.compiler.nodes.BeginNode) ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) Block(org.graalvm.compiler.nodes.cfg.Block) Test(org.junit.Test)

Example 8 with ControlFlowGraph

use of org.graalvm.compiler.nodes.cfg.ControlFlowGraph in project graal by oracle.

the class LoopEx method nodesInLoopBranch.

public void nodesInLoopBranch(NodeBitMap branchNodes, AbstractBeginNode branch) {
    EconomicSet<AbstractBeginNode> blocks = EconomicSet.create();
    Collection<AbstractBeginNode> exits = new LinkedList<>();
    Queue<Block> work = new LinkedList<>();
    ControlFlowGraph cfg = loopsData().getCFG();
    work.add(cfg.blockFor(branch));
    while (!work.isEmpty()) {
        Block b = work.remove();
        if (loop().getExits().contains(b)) {
            assert !exits.contains(b.getBeginNode());
            exits.add(b.getBeginNode());
        } else if (blocks.add(b.getBeginNode())) {
            Block d = b.getDominatedSibling();
            while (d != null) {
                if (loop.getBlocks().contains(d)) {
                    work.add(d);
                }
                d = d.getDominatedSibling();
            }
        }
    }
    LoopFragment.computeNodes(branchNodes, branch.graph(), blocks, exits);
}
Also used : ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) Block(org.graalvm.compiler.nodes.cfg.Block) LinkedList(java.util.LinkedList) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode)

Example 9 with ControlFlowGraph

use of org.graalvm.compiler.nodes.cfg.ControlFlowGraph in project graal by oracle.

the class BinaryGraphPrinter method nodeProperties.

@Override
@SuppressWarnings({ "unchecked", "rawtypes" })
public void nodeProperties(GraphInfo info, Node node, Map<String, Object> props) {
    node.getDebugProperties((Map) props);
    Graph graph = info.graph;
    ControlFlowGraph cfg = info.cfg;
    NodeMap<Block> nodeToBlocks = info.nodeToBlocks;
    if (cfg != null && DebugOptions.PrintGraphProbabilities.getValue(graph.getOptions()) && node instanceof FixedNode) {
        try {
            props.put("probability", cfg.blockFor(node).probability());
        } catch (Throwable t) {
            props.put("probability", 0.0);
            props.put("probability-exception", t);
        }
    }
    try {
        props.put("NodeCost-Size", node.estimatedNodeSize());
        props.put("NodeCost-Cycles", node.estimatedNodeCycles());
    } catch (Throwable t) {
        props.put("node-cost-exception", t.getMessage());
    }
    if (nodeToBlocks != null) {
        Object block = getBlockForNode(node, nodeToBlocks);
        if (block != null) {
            props.put("node-to-block", block);
        }
    }
    if (node instanceof ControlSinkNode) {
        props.put("category", "controlSink");
    } else if (node instanceof ControlSplitNode) {
        props.put("category", "controlSplit");
    } else if (node instanceof AbstractMergeNode) {
        props.put("category", "merge");
    } else if (node instanceof AbstractBeginNode) {
        props.put("category", "begin");
    } else if (node instanceof AbstractEndNode) {
        props.put("category", "end");
    } else if (node instanceof FixedNode) {
        props.put("category", "fixed");
    } else if (node instanceof VirtualState) {
        props.put("category", "state");
    } else if (node instanceof PhiNode) {
        props.put("category", "phi");
    } else if (node instanceof ProxyNode) {
        props.put("category", "proxy");
    } else {
        if (node instanceof ConstantNode) {
            ConstantNode cn = (ConstantNode) node;
            updateStringPropertiesForConstant((Map) props, cn);
        }
        props.put("category", "floating");
    }
    if (getSnippetReflectionProvider() != null) {
        for (Map.Entry<String, Object> prop : props.entrySet()) {
            if (prop.getValue() instanceof JavaConstantFormattable) {
                props.put(prop.getKey(), ((JavaConstantFormattable) prop.getValue()).format(this));
            }
        }
    }
}
Also used : ProxyNode(org.graalvm.compiler.nodes.ProxyNode) PhiNode(org.graalvm.compiler.nodes.PhiNode) FixedNode(org.graalvm.compiler.nodes.FixedNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) VirtualState(org.graalvm.compiler.nodes.VirtualState) ControlSinkNode(org.graalvm.compiler.nodes.ControlSinkNode) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) Graph(org.graalvm.compiler.graph.Graph) ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) CachedGraph(org.graalvm.compiler.graph.CachedGraph) ConstantNode(org.graalvm.compiler.nodes.ConstantNode) ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) AbstractEndNode(org.graalvm.compiler.nodes.AbstractEndNode) Block(org.graalvm.compiler.nodes.cfg.Block) ControlSplitNode(org.graalvm.compiler.nodes.ControlSplitNode) Map(java.util.Map) NodeMap(org.graalvm.compiler.graph.NodeMap) BlockMap(org.graalvm.compiler.core.common.cfg.BlockMap) JavaConstantFormattable(org.graalvm.compiler.nodes.util.JavaConstantFormattable)

Example 10 with ControlFlowGraph

use of org.graalvm.compiler.nodes.cfg.ControlFlowGraph in project graal by oracle.

the class NodeCostUtil method computeGraphCycles.

@SuppressWarnings("try")
public static double computeGraphCycles(StructuredGraph graph, boolean fullSchedule) {
    Function<Block, Iterable<? extends Node>> blockToNodes;
    ControlFlowGraph cfg;
    if (fullSchedule) {
        SchedulePhase schedule = new SchedulePhase(SchedulePhase.SchedulingStrategy.LATEST_OUT_OF_LOOPS, true);
        schedule.apply(graph);
        cfg = graph.getLastSchedule().getCFG();
        blockToNodes = b -> graph.getLastSchedule().getBlockToNodesMap().get(b);
    } else {
        cfg = ControlFlowGraph.compute(graph, true, true, false, false);
        BlockMap<List<FixedNode>> nodes = new BlockMap<>(cfg);
        for (Block b : cfg.getBlocks()) {
            ArrayList<FixedNode> curNodes = new ArrayList<>();
            for (FixedNode node : b.getNodes()) {
                curNodes.add(node);
            }
            nodes.put(b, curNodes);
        }
        blockToNodes = b -> nodes.get(b);
    }
    double weightedCycles = 0D;
    DebugContext debug = graph.getDebug();
    try (DebugContext.Scope s = debug.scope("NodeCostSummary")) {
        for (Block block : cfg.getBlocks()) {
            for (Node n : blockToNodes.apply(block)) {
                double probWeighted = n.estimatedNodeCycles().value * block.probability();
                assert Double.isFinite(probWeighted);
                weightedCycles += probWeighted;
                if (debug.isLogEnabled()) {
                    debug.log("Node %s contributes cycles:%f size:%d to graph %s [block prob:%f]", n, n.estimatedNodeCycles().value * block.probability(), n.estimatedNodeSize().value, graph, block.probability());
                }
            }
        }
    }
    assert weightedCycles >= 0D;
    assert Double.isFinite(weightedCycles);
    return weightedCycles;
}
Also used : SchedulePhase(org.graalvm.compiler.phases.schedule.SchedulePhase) FixedNode(org.graalvm.compiler.nodes.FixedNode) Node(org.graalvm.compiler.graph.Node) ArrayList(java.util.ArrayList) FixedNode(org.graalvm.compiler.nodes.FixedNode) DebugContext(org.graalvm.compiler.debug.DebugContext) BlockMap(org.graalvm.compiler.core.common.cfg.BlockMap) ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) Block(org.graalvm.compiler.nodes.cfg.Block) ArrayList(java.util.ArrayList) List(java.util.List)

Aggregations

ControlFlowGraph (org.graalvm.compiler.nodes.cfg.ControlFlowGraph)17 Block (org.graalvm.compiler.nodes.cfg.Block)12 AbstractMergeNode (org.graalvm.compiler.nodes.AbstractMergeNode)6 FixedNode (org.graalvm.compiler.nodes.FixedNode)6 DebugContext (org.graalvm.compiler.debug.DebugContext)5 Node (org.graalvm.compiler.graph.Node)5 AbstractBeginNode (org.graalvm.compiler.nodes.AbstractBeginNode)5 StructuredGraph (org.graalvm.compiler.nodes.StructuredGraph)5 PhiNode (org.graalvm.compiler.nodes.PhiNode)4 ReturnNode (org.graalvm.compiler.nodes.ReturnNode)4 List (java.util.List)3 SchedulePhase (org.graalvm.compiler.phases.schedule.SchedulePhase)3 ArrayList (java.util.ArrayList)2 BlockMap (org.graalvm.compiler.core.common.cfg.BlockMap)2 NodeEventScope (org.graalvm.compiler.graph.Graph.NodeEventScope)2 LIR (org.graalvm.compiler.lir.LIR)2 AbstractEndNode (org.graalvm.compiler.nodes.AbstractEndNode)2 ConstantNode (org.graalvm.compiler.nodes.ConstantNode)2 EndNode (org.graalvm.compiler.nodes.EndNode)2 IfNode (org.graalvm.compiler.nodes.IfNode)2