Search in sources :

Example 41 with LogicNode

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

the class MethodCallTargetNode method tryCheckCastSingleImplementor.

private boolean tryCheckCastSingleImplementor(ValueNode receiver, TypeReference speculatedType) {
    ResolvedJavaType singleImplementor = speculatedType.getType();
    if (singleImplementor != null) {
        ResolvedJavaMethod singleImplementorMethod = singleImplementor.resolveConcreteMethod(targetMethod(), invoke().getContextType());
        if (singleImplementorMethod != null) {
            /**
             * We have an invoke on an interface with a single implementor. We can replace this
             * with an invoke virtual.
             *
             * To do so we need to ensure two properties: 1) the receiver must implement the
             * interface (declaredReceiverType). The verifier does not prove this so we need a
             * dynamic check. 2) we need to ensure that there is still only one implementor of
             * this interface, i.e. that we are calling the right method. We could do this with
             * an assumption but as we need an instanceof check anyway we can verify both
             * properties by checking of the receiver is an instance of the single implementor.
             */
            ValueAnchorNode anchor = new ValueAnchorNode(null);
            if (anchor != null) {
                graph().add(anchor);
                graph().addBeforeFixed(invoke().asNode(), anchor);
            }
            LogicNode condition = graph().addOrUniqueWithInputs(InstanceOfNode.create(speculatedType, receiver, getProfile(), anchor));
            FixedGuardNode guard = graph().add(new FixedGuardNode(condition, DeoptimizationReason.OptimizedTypeCheckViolated, DeoptimizationAction.InvalidateRecompile, false));
            graph().addBeforeFixed(invoke().asNode(), guard);
            ValueNode valueNode = graph().addOrUnique(new PiNode(receiver, StampFactory.objectNonNull(speculatedType), guard));
            arguments().set(0, valueNode);
            if (speculatedType.isExact()) {
                setInvokeKind(InvokeKind.Special);
            } else {
                setInvokeKind(InvokeKind.Virtual);
            }
            setTargetMethod(singleImplementorMethod);
            return true;
        }
    }
    return false;
}
Also used : FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) ValueAnchorNode(org.graalvm.compiler.nodes.extended.ValueAnchorNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) PiNode(org.graalvm.compiler.nodes.PiNode) ResolvedJavaType(jdk.vm.ci.meta.ResolvedJavaType) ResolvedJavaMethod(jdk.vm.ci.meta.ResolvedJavaMethod)

Example 42 with LogicNode

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

the class ConvertDeoptimizeToGuardPhase method propagateFixed.

@SuppressWarnings("try")
private void propagateFixed(FixedNode from, StaticDeoptimizingNode deopt, LoweringProvider loweringProvider) {
    Node current = from;
    while (current != null) {
        if (GraalOptions.GuardPriorities.getValue(from.getOptions()) && current instanceof FixedGuardNode) {
            FixedGuardNode otherGuard = (FixedGuardNode) current;
            if (otherGuard.computePriority().isHigherPriorityThan(deopt.computePriority())) {
                moveAsDeoptAfter(otherGuard, deopt);
                return;
            }
        } else if (current instanceof AbstractBeginNode) {
            if (current instanceof AbstractMergeNode) {
                AbstractMergeNode mergeNode = (AbstractMergeNode) current;
                FixedNode next = mergeNode.next();
                while (mergeNode.isAlive()) {
                    AbstractEndNode end = mergeNode.forwardEnds().first();
                    propagateFixed(end, deopt, loweringProvider);
                }
                assert next.isAlive();
                propagateFixed(next, deopt, loweringProvider);
                return;
            } else if (current.predecessor() instanceof IfNode) {
                IfNode ifNode = (IfNode) current.predecessor();
                // Prioritize the source position of the IfNode
                try (DebugCloseable closable = ifNode.withNodeSourcePosition()) {
                    StructuredGraph graph = ifNode.graph();
                    LogicNode conditionNode = ifNode.condition();
                    boolean negateGuardCondition = current == ifNode.trueSuccessor();
                    FixedGuardNode guard = graph.add(new FixedGuardNode(conditionNode, deopt.getReason(), deopt.getAction(), deopt.getSpeculation(), negateGuardCondition));
                    FixedWithNextNode pred = (FixedWithNextNode) ifNode.predecessor();
                    AbstractBeginNode survivingSuccessor;
                    if (negateGuardCondition) {
                        survivingSuccessor = ifNode.falseSuccessor();
                    } else {
                        survivingSuccessor = ifNode.trueSuccessor();
                    }
                    graph.removeSplitPropagate(ifNode, survivingSuccessor);
                    Node newGuard = guard;
                    if (survivingSuccessor instanceof LoopExitNode) {
                        newGuard = ProxyNode.forGuard(guard, (LoopExitNode) survivingSuccessor, graph);
                    }
                    survivingSuccessor.replaceAtUsages(InputType.Guard, newGuard);
                    graph.getDebug().log("Converting deopt on %-5s branch of %s to guard for remaining branch %s.", negateGuardCondition, ifNode, survivingSuccessor);
                    FixedNode next = pred.next();
                    pred.setNext(guard);
                    guard.setNext(next);
                    SimplifierTool simplifierTool = GraphUtil.getDefaultSimplifier(null, null, null, false, graph.getAssumptions(), graph.getOptions(), loweringProvider);
                    survivingSuccessor.simplify(simplifierTool);
                    return;
                }
            } else if (current.predecessor() == null || current.predecessor() instanceof ControlSplitNode) {
                assert current.predecessor() != null || (current instanceof StartNode && current == ((AbstractBeginNode) current).graph().start());
                moveAsDeoptAfter((AbstractBeginNode) current, deopt);
                return;
            }
        }
        current = current.predecessor();
    }
}
Also used : FixedWithNextNode(org.graalvm.compiler.nodes.FixedWithNextNode) StartNode(org.graalvm.compiler.nodes.StartNode) LoopExitNode(org.graalvm.compiler.nodes.LoopExitNode) CompareNode(org.graalvm.compiler.nodes.calc.CompareNode) GuardNode(org.graalvm.compiler.nodes.GuardNode) ValuePhiNode(org.graalvm.compiler.nodes.ValuePhiNode) ConstantNode(org.graalvm.compiler.nodes.ConstantNode) StartNode(org.graalvm.compiler.nodes.StartNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) ControlSplitNode(org.graalvm.compiler.nodes.ControlSplitNode) StaticDeoptimizingNode(org.graalvm.compiler.nodes.StaticDeoptimizingNode) DeoptimizeNode(org.graalvm.compiler.nodes.DeoptimizeNode) FixedNode(org.graalvm.compiler.nodes.FixedNode) IfNode(org.graalvm.compiler.nodes.IfNode) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) AbstractEndNode(org.graalvm.compiler.nodes.AbstractEndNode) FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) LoopExitNode(org.graalvm.compiler.nodes.LoopExitNode) Node(org.graalvm.compiler.graph.Node) EndNode(org.graalvm.compiler.nodes.EndNode) FixedWithNextNode(org.graalvm.compiler.nodes.FixedWithNextNode) ProxyNode(org.graalvm.compiler.nodes.ProxyNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) FixedNode(org.graalvm.compiler.nodes.FixedNode) IfNode(org.graalvm.compiler.nodes.IfNode) SimplifierTool(org.graalvm.compiler.graph.spi.SimplifierTool) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) AbstractEndNode(org.graalvm.compiler.nodes.AbstractEndNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) ControlSplitNode(org.graalvm.compiler.nodes.ControlSplitNode) DebugCloseable(org.graalvm.compiler.debug.DebugCloseable)

Example 43 with LogicNode

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

the class ConvertDeoptimizeToGuardPhase method trySplitFixedGuard.

private void trySplitFixedGuard(FixedGuardNode fixedGuard, PhaseContext context) {
    LogicNode condition = fixedGuard.condition();
    if (condition instanceof CompareNode) {
        CompareNode compare = (CompareNode) condition;
        ValueNode x = compare.getX();
        ValuePhiNode xPhi = (x instanceof ValuePhiNode) ? (ValuePhiNode) x : null;
        if (x instanceof ConstantNode || xPhi != null) {
            ValueNode y = compare.getY();
            ValuePhiNode yPhi = (y instanceof ValuePhiNode) ? (ValuePhiNode) y : null;
            if (y instanceof ConstantNode || yPhi != null) {
                processFixedGuardAndPhis(fixedGuard, context, compare, x, xPhi, y, yPhi);
            }
        }
    }
}
Also used : ConstantNode(org.graalvm.compiler.nodes.ConstantNode) CompareNode(org.graalvm.compiler.nodes.calc.CompareNode) ValuePhiNode(org.graalvm.compiler.nodes.ValuePhiNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) LogicNode(org.graalvm.compiler.nodes.LogicNode)

Example 44 with LogicNode

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

the class ExpandLogicPhase method processNormalizeCompareNode.

private static void processNormalizeCompareNode(NormalizeCompareNode normalize) {
    LogicNode equalComp;
    LogicNode lessComp;
    StructuredGraph graph = normalize.graph();
    ValueNode x = normalize.getX();
    ValueNode y = normalize.getY();
    if (x.stamp(NodeView.DEFAULT) instanceof FloatStamp) {
        equalComp = graph.addOrUniqueWithInputs(FloatEqualsNode.create(x, y, NodeView.DEFAULT));
        lessComp = graph.addOrUniqueWithInputs(FloatLessThanNode.create(x, y, normalize.isUnorderedLess(), NodeView.DEFAULT));
    } else {
        equalComp = graph.addOrUniqueWithInputs(IntegerEqualsNode.create(x, y, NodeView.DEFAULT));
        lessComp = graph.addOrUniqueWithInputs(IntegerLessThanNode.create(x, y, NodeView.DEFAULT));
    }
    Stamp stamp = normalize.stamp(NodeView.DEFAULT);
    ConditionalNode equalValue = graph.unique(new ConditionalNode(equalComp, ConstantNode.forIntegerStamp(stamp, 0, graph), ConstantNode.forIntegerStamp(stamp, 1, graph)));
    ConditionalNode value = graph.unique(new ConditionalNode(lessComp, ConstantNode.forIntegerStamp(stamp, -1, graph), equalValue));
    normalize.replaceAtUsagesAndDelete(value);
}
Also used : ConditionalNode(org.graalvm.compiler.nodes.calc.ConditionalNode) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) FloatStamp(org.graalvm.compiler.core.common.type.FloatStamp) Stamp(org.graalvm.compiler.core.common.type.Stamp) ValueNode(org.graalvm.compiler.nodes.ValueNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) FloatStamp(org.graalvm.compiler.core.common.type.FloatStamp)

Example 45 with LogicNode

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

the class LoopTransformations method updatePreLoopLimit.

private static void updatePreLoopLimit(IfNode preLimit, InductionVariable preIv, CountedLoopInfo preCounted) {
    // Update the pre loops limit test
    StructuredGraph graph = preLimit.graph();
    LogicNode ifTest = preLimit.condition();
    CompareNode compareNode = (CompareNode) ifTest;
    ValueNode prePhi = preIv.valueNode();
    // Make new limit one iteration
    ValueNode initIv = preCounted.getStart();
    ValueNode newLimit = add(graph, initIv, preIv.strideNode());
    // Fetch the variable we are not replacing and configure the one we are
    ValueNode ub;
    if (compareNode.getX() == prePhi) {
        ub = compareNode.getY();
    } else if (compareNode.getY() == prePhi) {
        ub = compareNode.getX();
    } else {
        throw GraalError.shouldNotReachHere();
    }
    // Re-wire the condition with the new limit
    if (preIv.direction() == Direction.Up) {
        compareNode.replaceFirstInput(ub, graph.unique(new ConditionalNode(graph.unique(new IntegerLessThanNode(newLimit, ub)), newLimit, ub)));
    } else {
        compareNode.replaceFirstInput(ub, graph.unique(new ConditionalNode(graph.unique(new IntegerLessThanNode(ub, newLimit)), newLimit, ub)));
    }
}
Also used : ConditionalNode(org.graalvm.compiler.nodes.calc.ConditionalNode) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) CompareNode(org.graalvm.compiler.nodes.calc.CompareNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) IntegerLessThanNode(org.graalvm.compiler.nodes.calc.IntegerLessThanNode) LogicNode(org.graalvm.compiler.nodes.LogicNode)

Aggregations

LogicNode (org.graalvm.compiler.nodes.LogicNode)48 ValueNode (org.graalvm.compiler.nodes.ValueNode)37 FixedGuardNode (org.graalvm.compiler.nodes.FixedGuardNode)26 ConstantNode (org.graalvm.compiler.nodes.ConstantNode)11 StructuredGraph (org.graalvm.compiler.nodes.StructuredGraph)11 ResolvedJavaMethod (jdk.vm.ci.meta.ResolvedJavaMethod)10 ResolvedJavaType (jdk.vm.ci.meta.ResolvedJavaType)9 Stamp (org.graalvm.compiler.core.common.type.Stamp)9 IfNode (org.graalvm.compiler.nodes.IfNode)9 TypeReference (org.graalvm.compiler.core.common.type.TypeReference)8 LogicConstantNode (org.graalvm.compiler.nodes.LogicConstantNode)7 CompareNode (org.graalvm.compiler.nodes.calc.CompareNode)7 ConditionalNode (org.graalvm.compiler.nodes.calc.ConditionalNode)7 JavaConstant (jdk.vm.ci.meta.JavaConstant)6 AbstractBeginNode (org.graalvm.compiler.nodes.AbstractBeginNode)6 FixedNode (org.graalvm.compiler.nodes.FixedNode)6 LoopBeginNode (org.graalvm.compiler.nodes.LoopBeginNode)6 JavaKind (jdk.vm.ci.meta.JavaKind)5 ObjectStamp (org.graalvm.compiler.core.common.type.ObjectStamp)5 Node (org.graalvm.compiler.graph.Node)5