Search in sources :

Example 11 with ControlSinkNode

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

the class LoweringPhase method checkPostNodeLowering.

/**
 * Checks that lowering of a given node did not introduce any new {@link Lowerable} nodes that
 * could be lowered in the current {@link LoweringPhase}. Such nodes must be recursively lowered
 * as part of lowering {@code node}.
 *
 * @param node a node that was just lowered
 * @param preLoweringMark the graph mark before {@code node} was lowered
 * @param unscheduledUsages set of {@code node}'s usages that were unscheduled before it was
 *            lowered
 * @throws AssertionError if the check fails
 */
private static boolean checkPostNodeLowering(Node node, LoweringToolImpl loweringTool, Mark preLoweringMark, Collection<Node> unscheduledUsages) {
    StructuredGraph graph = (StructuredGraph) node.graph();
    Mark postLoweringMark = graph.getMark();
    NodeIterable<Node> newNodesAfterLowering = graph.getNewNodes(preLoweringMark);
    if (node instanceof FloatingNode) {
        if (!unscheduledUsages.isEmpty()) {
            for (Node n : newNodesAfterLowering) {
                assert !(n instanceof FixedNode) : node.graph() + ": cannot lower floatable node " + node + " as it introduces fixed node(s) but has the following unscheduled usages: " + unscheduledUsages;
            }
        }
    }
    for (Node n : newNodesAfterLowering) {
        if (n instanceof Lowerable) {
            ((Lowerable) n).lower(loweringTool);
            Mark mark = graph.getMark();
            assert postLoweringMark.equals(mark) : graph + ": lowering of " + node + " produced lowerable " + n + " that should have been recursively lowered as it introduces these new nodes: " + graph.getNewNodes(postLoweringMark).snapshot();
        }
        if (graph.isAfterFloatingReadPhase() && n instanceof MemoryCheckpoint && !(node instanceof MemoryCheckpoint) && !(node instanceof ControlSinkNode)) {
            /*
                 * The lowering introduced a MemoryCheckpoint but the current node isn't a
                 * checkpoint. This is only OK if the locations involved don't affect the memory
                 * graph or if the new kill location doesn't connect into the existing graph.
                 */
            boolean isAny = false;
            if (n instanceof MemoryCheckpoint.Single) {
                isAny = ((MemoryCheckpoint.Single) n).getLocationIdentity().isAny();
            } else {
                for (LocationIdentity ident : ((MemoryCheckpoint.Multi) n).getLocationIdentities()) {
                    if (ident.isAny()) {
                        isAny = true;
                    }
                }
            }
            if (isAny && n instanceof FixedWithNextNode) {
                /*
                     * Check if the next kill location leads directly to a ControlSinkNode in the
                     * new part of the graph. This is a fairly conservative test that could be made
                     * more general if required.
                     */
                FixedWithNextNode cur = (FixedWithNextNode) n;
                while (cur != null && graph.isNew(preLoweringMark, cur)) {
                    if (cur.next() instanceof ControlSinkNode) {
                        isAny = false;
                        break;
                    }
                    if (cur.next() instanceof FixedWithNextNode) {
                        cur = (FixedWithNextNode) cur.next();
                    } else {
                        break;
                    }
                }
            }
            assert !isAny : node + " " + n;
        }
    }
    return true;
}
Also used : FixedWithNextNode(org.graalvm.compiler.nodes.FixedWithNextNode) BeginNode(org.graalvm.compiler.nodes.BeginNode) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) GuardedNode(org.graalvm.compiler.nodes.extended.GuardedNode) GuardingNode(org.graalvm.compiler.nodes.extended.GuardingNode) ControlSinkNode(org.graalvm.compiler.nodes.ControlSinkNode) GuardNode(org.graalvm.compiler.nodes.GuardNode) FloatingNode(org.graalvm.compiler.nodes.calc.FloatingNode) AnchoringNode(org.graalvm.compiler.nodes.extended.AnchoringNode) FixedNode(org.graalvm.compiler.nodes.FixedNode) Node(org.graalvm.compiler.graph.Node) FixedWithNextNode(org.graalvm.compiler.nodes.FixedWithNextNode) PhiNode(org.graalvm.compiler.nodes.PhiNode) ProxyNode(org.graalvm.compiler.nodes.ProxyNode) Mark(org.graalvm.compiler.graph.Graph.Mark) FixedNode(org.graalvm.compiler.nodes.FixedNode) ControlSinkNode(org.graalvm.compiler.nodes.ControlSinkNode) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) MemoryCheckpoint(org.graalvm.compiler.nodes.memory.MemoryCheckpoint) FloatingNode(org.graalvm.compiler.nodes.calc.FloatingNode) LocationIdentity(org.graalvm.word.LocationIdentity) Lowerable(org.graalvm.compiler.nodes.spi.Lowerable)

Example 12 with ControlSinkNode

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

the class ValueMergeUtil method mergeValueProducers.

public static <T> ValueNode mergeValueProducers(AbstractMergeNode merge, List<? extends T> valueProducers, Function<T, FixedWithNextNode> lastInstrFunction, Function<T, ValueNode> valueFunction) {
    ValueNode singleResult = null;
    PhiNode phiResult = null;
    for (T valueProducer : valueProducers) {
        ValueNode result = valueFunction.apply(valueProducer);
        if (result != null) {
            if (phiResult == null && (singleResult == null || singleResult == result)) {
                /* Only one result value, so no need yet for a phi node. */
                singleResult = result;
            } else if (phiResult == null) {
                /* Found a second result value, so create phi node. */
                phiResult = merge.graph().addWithoutUnique(new ValuePhiNode(result.stamp(NodeView.DEFAULT).unrestricted(), merge));
                for (int i = 0; i < merge.forwardEndCount(); i++) {
                    phiResult.addInput(singleResult);
                }
                phiResult.addInput(result);
            } else {
                /* Multiple return values, just add to existing phi node. */
                phiResult.addInput(result);
            }
        }
        // create and wire up a new EndNode
        EndNode endNode = merge.graph().add(new EndNode());
        merge.addForwardEnd(endNode);
        if (lastInstrFunction == null) {
            assert valueProducer instanceof ReturnNode || valueProducer instanceof UnwindNode;
            ((ControlSinkNode) valueProducer).replaceAndDelete(endNode);
        } else {
            FixedWithNextNode lastInstr = lastInstrFunction.apply(valueProducer);
            lastInstr.setNext(endNode);
        }
    }
    if (phiResult != null) {
        assert phiResult.verify();
        phiResult.inferStamp();
        return phiResult;
    } else {
        return singleResult;
    }
}
Also used : ReturnNode(org.graalvm.compiler.nodes.ReturnNode) FixedWithNextNode(org.graalvm.compiler.nodes.FixedWithNextNode) ValuePhiNode(org.graalvm.compiler.nodes.ValuePhiNode) PhiNode(org.graalvm.compiler.nodes.PhiNode) EndNode(org.graalvm.compiler.nodes.EndNode) ValuePhiNode(org.graalvm.compiler.nodes.ValuePhiNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) UnwindNode(org.graalvm.compiler.nodes.UnwindNode) ControlSinkNode(org.graalvm.compiler.nodes.ControlSinkNode)

Aggregations

ControlSinkNode (org.graalvm.compiler.nodes.ControlSinkNode)12 FixedNode (org.graalvm.compiler.nodes.FixedNode)10 FixedWithNextNode (org.graalvm.compiler.nodes.FixedWithNextNode)10 AbstractMergeNode (org.graalvm.compiler.nodes.AbstractMergeNode)8 ControlSplitNode (org.graalvm.compiler.nodes.ControlSplitNode)7 EndNode (org.graalvm.compiler.nodes.EndNode)7 LoopBeginNode (org.graalvm.compiler.nodes.LoopBeginNode)7 AbstractBeginNode (org.graalvm.compiler.nodes.AbstractBeginNode)6 LoopEndNode (org.graalvm.compiler.nodes.LoopEndNode)6 Node (org.graalvm.compiler.graph.Node)5 ValueNode (org.graalvm.compiler.nodes.ValueNode)5 AbstractEndNode (org.graalvm.compiler.nodes.AbstractEndNode)4 PhiNode (org.graalvm.compiler.nodes.PhiNode)4 StructuredGraph (org.graalvm.compiler.nodes.StructuredGraph)4 Invoke (org.graalvm.compiler.nodes.Invoke)3 InvokeWithExceptionNode (org.graalvm.compiler.nodes.InvokeWithExceptionNode)3 MergeNode (org.graalvm.compiler.nodes.MergeNode)3 ReturnNode (org.graalvm.compiler.nodes.ReturnNode)3 Map (java.util.Map)2 Canonicalizable (org.graalvm.compiler.graph.spi.Canonicalizable)2