Search in sources :

Example 1 with Guard

use of org.graalvm.compiler.nodeinfo.InputType.Guard in project graal by oracle.

the class MultiGuardNode method simplify.

@Override
public void simplify(SimplifierTool tool) {
    if (usages().filter(node -> node instanceof ValueAnchorNode).isNotEmpty()) {
        /*
             * For ValueAnchorNode usages, we can optimize MultiGuardNodes away if they depend on
             * zero or one floating nodes (as opposed to fixed nodes).
             */
        Node singleFloatingGuard = null;
        for (ValueNode guard : guards) {
            if (GraphUtil.isFloatingNode(guard)) {
                if (singleFloatingGuard == null) {
                    singleFloatingGuard = guard;
                } else if (singleFloatingGuard != guard) {
                    return;
                }
            }
        }
        for (Node usage : usages().snapshot()) {
            if (usage instanceof ValueAnchorNode) {
                usage.replaceFirstInput(this, singleFloatingGuard);
                tool.addToWorkList(usage);
            }
        }
        if (usages().isEmpty()) {
            GraphUtil.killWithUnusedFloatingInputs(this);
        }
    }
}
Also used : SIZE_0(org.graalvm.compiler.nodeinfo.NodeSize.SIZE_0) FloatingNode(org.graalvm.compiler.nodes.calc.FloatingNode) CYCLES_0(org.graalvm.compiler.nodeinfo.NodeCycles.CYCLES_0) NodeInfo(org.graalvm.compiler.nodeinfo.NodeInfo) GraphUtil(org.graalvm.compiler.nodes.util.GraphUtil) Simplifiable(org.graalvm.compiler.nodes.spi.Simplifiable) CanonicalizerTool(org.graalvm.compiler.nodes.spi.CanonicalizerTool) Guard(org.graalvm.compiler.nodeinfo.InputType.Guard) NodeBitMap(org.graalvm.compiler.graph.NodeBitMap) SimplifierTool(org.graalvm.compiler.nodes.spi.SimplifierTool) EconomicSet(org.graalvm.collections.EconomicSet) NodeInputList(org.graalvm.compiler.graph.NodeInputList) LIRLowerable(org.graalvm.compiler.nodes.spi.LIRLowerable) NodeLIRBuilderTool(org.graalvm.compiler.nodes.spi.NodeLIRBuilderTool) ArrayList(java.util.ArrayList) Canonicalizable(org.graalvm.compiler.nodes.spi.Canonicalizable) ValueNode(org.graalvm.compiler.nodes.ValueNode) StampFactory(org.graalvm.compiler.core.common.type.StampFactory) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) NodeClass(org.graalvm.compiler.graph.NodeClass) Node(org.graalvm.compiler.graph.Node) FloatingNode(org.graalvm.compiler.nodes.calc.FloatingNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) Node(org.graalvm.compiler.graph.Node) ValueNode(org.graalvm.compiler.nodes.ValueNode)

Example 2 with Guard

use of org.graalvm.compiler.nodeinfo.InputType.Guard in project graal by oracle.

the class PEGraphDecoder method finishInlining.

@Override
protected void finishInlining(MethodScope is) {
    PEMethodScope inlineScope = (PEMethodScope) is;
    ResolvedJavaMethod inlineMethod = inlineScope.method;
    PEMethodScope methodScope = inlineScope.caller;
    LoopScope loopScope = inlineScope.callerLoopScope;
    InvokeData invokeData = inlineScope.invokeData;
    Invoke invoke = invokeData.invoke;
    FixedNode invokeNode = invoke.asFixedNode();
    ValueNode exceptionValue = null;
    int returnNodeCount = 0;
    int unwindNodeCount = 0;
    List<ControlSinkNode> returnAndUnwindNodes = inlineScope.returnAndUnwindNodes;
    for (int i = 0; i < returnAndUnwindNodes.size(); i++) {
        FixedNode fixedNode = returnAndUnwindNodes.get(i);
        if (fixedNode instanceof ReturnNode) {
            returnNodeCount++;
        } else if (fixedNode.isAlive()) {
            assert fixedNode instanceof UnwindNode;
            unwindNodeCount++;
        }
    }
    if (unwindNodeCount > 0) {
        FixedNode unwindReplacement;
        if (invoke instanceof InvokeWithExceptionNode) {
            /* Decoding continues for the exception handler. */
            unwindReplacement = makeStubNode(methodScope, loopScope, invokeData.exceptionNextOrderId);
        } else {
            /* No exception handler available, so the only thing we can do is deoptimize. */
            unwindReplacement = graph.add(new DeoptimizeNode(DeoptimizationAction.InvalidateRecompile, DeoptimizationReason.NotCompiledExceptionHandler));
        }
        if (unwindNodeCount == 1) {
            /* Only one UnwindNode, we can use the exception directly. */
            UnwindNode unwindNode = getSingleMatchingNode(returnAndUnwindNodes, returnNodeCount > 0, UnwindNode.class);
            exceptionValue = unwindNode.exception();
            unwindNode.replaceAndDelete(unwindReplacement);
        } else {
            /*
                 * More than one UnwindNode. This can happen with the loop explosion strategy
                 * FULL_EXPLODE_UNTIL_RETURN, where we keep exploding after the loop and therefore
                 * also explode exception paths. Merge the exception in a similar way as multiple
                 * return values.
                 */
            MergeNode unwindMergeNode = graph.add(new MergeNode());
            exceptionValue = InliningUtil.mergeValueProducers(unwindMergeNode, getMatchingNodes(returnAndUnwindNodes, returnNodeCount > 0, UnwindNode.class, unwindNodeCount), null, unwindNode -> unwindNode.exception());
            unwindMergeNode.setNext(unwindReplacement);
            ensureExceptionStateDecoded(inlineScope);
            unwindMergeNode.setStateAfter(inlineScope.exceptionState.duplicateModified(JavaKind.Object, JavaKind.Object, exceptionValue, null));
        }
        if (invoke instanceof InvokeWithExceptionNode) {
            /*
                 * Exceptionobject nodes are begin nodes, i.e., they can be used as guards/anchors
                 * thus we need to ensure nodes decoded later have a correct guarding/anchoring node
                 * in place, i.e., the exception value must be a node that can be used like the
                 * original node as value, guard and anchor.
                 *
                 * The node unwindReplacement is a stub, its not yet processed thus we insert our
                 * artificial anchor before it.
                 */
            assert unwindReplacement != exceptionValue : "Unschedulable unwind replacement";
            FixedAnchorNode anchor = graph.add(new FixedAnchorNode(exceptionValue));
            graph.addBeforeFixed(unwindReplacement, anchor);
            exceptionValue = anchor;
            assert anchor.predecessor() != null;
        }
    }
    assert invoke.next() == null;
    assert !(invoke instanceof InvokeWithExceptionNode) || ((InvokeWithExceptionNode) invoke).exceptionEdge() == null;
    ValueNode returnValue;
    if (returnNodeCount == 0) {
        returnValue = null;
    } else if (returnNodeCount == 1) {
        ReturnNode returnNode = getSingleMatchingNode(returnAndUnwindNodes, unwindNodeCount > 0, ReturnNode.class);
        returnValue = returnNode.result();
        BeginNode prevBegin = null;
        if (returnNode.predecessor() instanceof BeginNode) {
            // Try to reuse the previous begin node instead of creating another one.
            prevBegin = (BeginNode) returnNode.predecessor();
        }
        FixedNode n = nodeAfterInvoke(methodScope, loopScope, invokeData, prevBegin);
        if (n == prevBegin) {
            // Reusing the previous BeginNode; just remove the ReturnNode.
            returnNode.replaceAtPredecessor(null);
            returnNode.safeDelete();
        } else {
            returnNode.replaceAndDelete(n);
        }
    } else {
        AbstractMergeNode merge = graph.add(new MergeNode());
        merge.setStateAfter((FrameState) ensureNodeCreated(methodScope, loopScope, invokeData.stateAfterOrderId));
        returnValue = InliningUtil.mergeReturns(merge, getMatchingNodes(returnAndUnwindNodes, unwindNodeCount > 0, ReturnNode.class, returnNodeCount));
        FixedNode n = nodeAfterInvoke(methodScope, loopScope, invokeData, null);
        merge.setNext(n);
    }
    invokeNode.replaceAtUsages(returnValue);
    /*
         * Usage the handles that we have on the return value and the exception to update the
         * orderId->Node table.
         */
    registerNode(loopScope, invokeData.invokeOrderId, returnValue, true, true);
    if (invoke instanceof InvokeWithExceptionNode) {
        registerNode(loopScope, invokeData.exceptionOrderId, exceptionValue, true, true);
    }
    if (inlineScope.exceptionPlaceholderNode != null) {
        inlineScope.exceptionPlaceholderNode.replaceAtUsagesAndDelete(exceptionValue);
    }
    deleteInvoke(invoke);
    assert exceptionValue == null || exceptionValue instanceof FixedAnchorNode && exceptionValue.predecessor() != null;
    for (InlineInvokePlugin plugin : inlineInvokePlugins) {
        plugin.notifyAfterInline(inlineMethod);
    }
}
Also used : Arrays(java.util.Arrays) ResolvedJavaType(jdk.vm.ci.meta.ResolvedJavaType) InputType(org.graalvm.compiler.nodeinfo.InputType) ResolvedJavaField(jdk.vm.ci.meta.ResolvedJavaField) Canonicalizable(org.graalvm.compiler.nodes.spi.Canonicalizable) Map(java.util.Map) BeginNode(org.graalvm.compiler.nodes.BeginNode) MonitorIdNode(org.graalvm.compiler.nodes.java.MonitorIdNode) MethodCallTargetNode(org.graalvm.compiler.nodes.java.MethodCallTargetNode) NodeSourcePosition(org.graalvm.compiler.graph.NodeSourcePosition) CYCLES_0(org.graalvm.compiler.nodeinfo.NodeCycles.CYCLES_0) OptionKey(org.graalvm.compiler.options.OptionKey) NodeView(org.graalvm.compiler.nodes.NodeView) Fold(org.graalvm.compiler.api.replacements.Fold) Stamp(org.graalvm.compiler.core.common.type.Stamp) JavaType(jdk.vm.ci.meta.JavaType) FrameState(org.graalvm.compiler.nodes.FrameState) GraphBuilderContext(org.graalvm.compiler.nodes.graphbuilderconf.GraphBuilderContext) GuardingNode(org.graalvm.compiler.nodes.extended.GuardingNode) ControlSinkNode(org.graalvm.compiler.nodes.ControlSinkNode) IntegerSwitchNode(org.graalvm.compiler.nodes.extended.IntegerSwitchNode) IntrinsicContext(org.graalvm.compiler.nodes.graphbuilderconf.IntrinsicContext) OptionType(org.graalvm.compiler.options.OptionType) IterableNodeType(org.graalvm.compiler.graph.IterableNodeType) AnchoringNode(org.graalvm.compiler.nodes.extended.AnchoringNode) StateSplit(org.graalvm.compiler.nodes.StateSplit) Guard(org.graalvm.compiler.nodeinfo.InputType.Guard) InvokeWithExceptionNode(org.graalvm.compiler.nodes.InvokeWithExceptionNode) ArrayList(java.util.ArrayList) CYCLES_IGNORED(org.graalvm.compiler.nodeinfo.NodeCycles.CYCLES_IGNORED) NodeClass(org.graalvm.compiler.graph.NodeClass) MergeNode(org.graalvm.compiler.nodes.MergeNode) InvocationPlugin(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugin) Assumptions(jdk.vm.ci.meta.Assumptions) SIZE_0(org.graalvm.compiler.nodeinfo.NodeSize.SIZE_0) DeoptimizeNode(org.graalvm.compiler.nodes.DeoptimizeNode) FixedNode(org.graalvm.compiler.nodes.FixedNode) NodeInfo(org.graalvm.compiler.nodeinfo.NodeInfo) AbstractEndNode(org.graalvm.compiler.nodes.AbstractEndNode) CoreProvidersDelegate(org.graalvm.compiler.nodes.spi.CoreProvidersDelegate) PluginReplacementInterface(org.graalvm.compiler.nodes.PluginReplacementInterface) DeoptBciSupplier(org.graalvm.compiler.nodes.DeoptBciSupplier) MemoryKill(org.graalvm.compiler.nodes.memory.MemoryKill) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) GeneratedInvocationPlugin(org.graalvm.compiler.nodes.graphbuilderconf.GeneratedInvocationPlugin) InlineInfo(org.graalvm.compiler.nodes.graphbuilderconf.InlineInvokePlugin.InlineInfo) NewInstanceNode(org.graalvm.compiler.nodes.java.NewInstanceNode) SIZE_IGNORED(org.graalvm.compiler.nodeinfo.NodeSize.SIZE_IGNORED) LoopExplosionKind(org.graalvm.compiler.nodes.graphbuilderconf.LoopExplosionPlugin.LoopExplosionKind) DeoptimizationReason(jdk.vm.ci.meta.DeoptimizationReason) BytecodeProvider(org.graalvm.compiler.bytecode.BytecodeProvider) BytecodeFrame(jdk.vm.ci.code.BytecodeFrame) EncodedGraph(org.graalvm.compiler.nodes.EncodedGraph) InvocationPluginReceiver(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugins.InvocationPluginReceiver) NodeIntrinsic(org.graalvm.compiler.graph.Node.NodeIntrinsic) InvocationPlugins(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugins) DeoptimizationAction(jdk.vm.ci.meta.DeoptimizationAction) NodePlugin(org.graalvm.compiler.nodes.graphbuilderconf.NodePlugin) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) Formatter(java.util.Formatter) StampFactory(org.graalvm.compiler.core.common.type.StampFactory) JavaKind(jdk.vm.ci.meta.JavaKind) Option(org.graalvm.compiler.options.Option) DebugCloseable(org.graalvm.compiler.debug.DebugCloseable) URI(java.net.URI) NewMultiArrayNode(org.graalvm.compiler.nodes.java.NewMultiArrayNode) SimplifyingGraphDecoder(org.graalvm.compiler.nodes.SimplifyingGraphDecoder) LoadIndexedNode(org.graalvm.compiler.nodes.java.LoadIndexedNode) SourceLanguagePositionProvider(org.graalvm.compiler.graph.SourceLanguagePositionProvider) GraphBuilderPhase(org.graalvm.compiler.java.GraphBuilderPhase) ReturnNode(org.graalvm.compiler.nodes.ReturnNode) CallTargetNode(org.graalvm.compiler.nodes.CallTargetNode) IfNode(org.graalvm.compiler.nodes.IfNode) GraphUtil(org.graalvm.compiler.nodes.util.GraphUtil) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) SourceLanguagePosition(org.graalvm.compiler.graph.SourceLanguagePosition) Bytecode(org.graalvm.compiler.bytecode.Bytecode) JavaConstant(jdk.vm.ci.meta.JavaConstant) ValueNode(org.graalvm.compiler.nodes.ValueNode) List(java.util.List) GraalError.unimplemented(org.graalvm.compiler.debug.GraalError.unimplemented) Anchor(org.graalvm.compiler.nodeinfo.InputType.Anchor) GraalError(org.graalvm.compiler.debug.GraalError) NewArrayNode(org.graalvm.compiler.nodes.java.NewArrayNode) ControlFlowGraph(org.graalvm.compiler.nodes.cfg.ControlFlowGraph) LoadFieldNode(org.graalvm.compiler.nodes.java.LoadFieldNode) PermanentBailoutException(org.graalvm.compiler.core.common.PermanentBailoutException) LoopExplosionPlugin(org.graalvm.compiler.nodes.graphbuilderconf.LoopExplosionPlugin) Architecture(jdk.vm.ci.code.Architecture) BailoutException(jdk.vm.ci.code.BailoutException) HashMap(java.util.HashMap) InlineInvokePlugin(org.graalvm.compiler.nodes.graphbuilderconf.InlineInvokePlugin) ExceptionObjectNode(org.graalvm.compiler.nodes.java.ExceptionObjectNode) InliningUtil(org.graalvm.compiler.phases.common.inlining.InliningUtil) InvokeKind(org.graalvm.compiler.nodes.CallTargetNode.InvokeKind) ControlSplitNode(org.graalvm.compiler.nodes.ControlSplitNode) DebugContext(org.graalvm.compiler.debug.DebugContext) CFGVerifier(org.graalvm.compiler.core.common.cfg.CFGVerifier) InvokeNode(org.graalvm.compiler.nodes.InvokeNode) StampTool(org.graalvm.compiler.nodes.type.StampTool) ParameterNode(org.graalvm.compiler.nodes.ParameterNode) ParameterPlugin(org.graalvm.compiler.nodes.graphbuilderconf.ParameterPlugin) OptionValues(org.graalvm.compiler.options.OptionValues) StoreIndexedNode(org.graalvm.compiler.nodes.java.StoreIndexedNode) TimerKey(org.graalvm.compiler.debug.TimerKey) CoreProviders(org.graalvm.compiler.nodes.spi.CoreProviders) StampPair(org.graalvm.compiler.core.common.type.StampPair) UnwindNode(org.graalvm.compiler.nodes.UnwindNode) Invoke(org.graalvm.compiler.nodes.Invoke) WithExceptionNode(org.graalvm.compiler.nodes.WithExceptionNode) BytecodeExceptionNode(org.graalvm.compiler.nodes.extended.BytecodeExceptionNode) StoreFieldNode(org.graalvm.compiler.nodes.java.StoreFieldNode) Node(org.graalvm.compiler.graph.Node) FixedWithNextNode(org.graalvm.compiler.nodes.FixedWithNextNode) ResolvedJavaMethod(jdk.vm.ci.meta.ResolvedJavaMethod) FixedNode(org.graalvm.compiler.nodes.FixedNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) InlineInvokePlugin(org.graalvm.compiler.nodes.graphbuilderconf.InlineInvokePlugin) FrameState(org.graalvm.compiler.nodes.FrameState) ControlSinkNode(org.graalvm.compiler.nodes.ControlSinkNode) Invoke(org.graalvm.compiler.nodes.Invoke) MergeNode(org.graalvm.compiler.nodes.MergeNode) AbstractMergeNode(org.graalvm.compiler.nodes.AbstractMergeNode) ReturnNode(org.graalvm.compiler.nodes.ReturnNode) InvokeWithExceptionNode(org.graalvm.compiler.nodes.InvokeWithExceptionNode) BeginNode(org.graalvm.compiler.nodes.BeginNode) AbstractBeginNode(org.graalvm.compiler.nodes.AbstractBeginNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) DeoptimizeNode(org.graalvm.compiler.nodes.DeoptimizeNode) UnwindNode(org.graalvm.compiler.nodes.UnwindNode) ResolvedJavaMethod(jdk.vm.ci.meta.ResolvedJavaMethod)

Aggregations

ArrayList (java.util.ArrayList)2 StampFactory (org.graalvm.compiler.core.common.type.StampFactory)2 Node (org.graalvm.compiler.graph.Node)2 NodeClass (org.graalvm.compiler.graph.NodeClass)2 URI (java.net.URI)1 Arrays (java.util.Arrays)1 Formatter (java.util.Formatter)1 HashMap (java.util.HashMap)1 List (java.util.List)1 Map (java.util.Map)1 ConcurrentHashMap (java.util.concurrent.ConcurrentHashMap)1 Architecture (jdk.vm.ci.code.Architecture)1 BailoutException (jdk.vm.ci.code.BailoutException)1 BytecodeFrame (jdk.vm.ci.code.BytecodeFrame)1 Assumptions (jdk.vm.ci.meta.Assumptions)1 DeoptimizationAction (jdk.vm.ci.meta.DeoptimizationAction)1 DeoptimizationReason (jdk.vm.ci.meta.DeoptimizationReason)1 JavaConstant (jdk.vm.ci.meta.JavaConstant)1 JavaKind (jdk.vm.ci.meta.JavaKind)1 JavaType (jdk.vm.ci.meta.JavaType)1