Search in sources :

Example 11 with ObjectStamp

use of org.graalvm.compiler.core.common.type.ObjectStamp in project graal by oracle.

the class AMD64HotSpotAddressLowering method improveUncompression.

@Override
protected final boolean improveUncompression(AMD64AddressNode addr, CompressionNode compression, ValueNode other) {
    CompressEncoding encoding = compression.getEncoding();
    Scale scale = Scale.fromShift(encoding.getShift());
    if (scale == null) {
        return false;
    }
    if (heapBaseRegister != null && encoding.getBase() == heapBase) {
        if ((!generatePIC || compression.stamp(NodeView.DEFAULT) instanceof ObjectStamp) && other == null) {
            // With PIC it is only legal to do for oops since the base value may be
            // different at runtime.
            ValueNode base = compression.graph().unique(new HeapBaseNode(heapBaseRegister));
            addr.setBase(base);
        } else {
            return false;
        }
    } else if (encoding.getBase() != 0 || (generatePIC && compression.stamp(NodeView.DEFAULT) instanceof KlassPointerStamp)) {
        if (generatePIC) {
            if (other == null) {
                ValueNode base = compression.graph().unique(new GraalHotSpotVMConfigNode(config, config.MARKID_NARROW_KLASS_BASE_ADDRESS, JavaKind.Long));
                addr.setBase(base);
            } else {
                return false;
            }
        } else {
            if (updateDisplacement(addr, encoding.getBase(), false)) {
                addr.setBase(other);
            } else {
                return false;
            }
        }
    } else {
        addr.setBase(other);
    }
    addr.setScale(scale);
    addr.setIndex(compression.getValue());
    return true;
}
Also used : GraalHotSpotVMConfigNode(org.graalvm.compiler.hotspot.nodes.GraalHotSpotVMConfigNode) ObjectStamp(org.graalvm.compiler.core.common.type.ObjectStamp) KlassPointerStamp(org.graalvm.compiler.hotspot.nodes.type.KlassPointerStamp) CompressEncoding(org.graalvm.compiler.core.common.CompressEncoding) ValueNode(org.graalvm.compiler.nodes.ValueNode) Scale(org.graalvm.compiler.asm.amd64.AMD64Address.Scale)

Example 12 with ObjectStamp

use of org.graalvm.compiler.core.common.type.ObjectStamp in project graal by oracle.

the class IntrinsifyMethodHandlesInvocationPlugin method processInvokeWithMethodHandle.

@SuppressWarnings("try")
private void processInvokeWithMethodHandle(GraphBuilderContext b, BytecodeProvider bytecodeProvider, ResolvedJavaMethod methodHandleMethod, ValueNode[] methodHandleArguments) {
    Plugins graphBuilderPlugins = new Plugins(((ReplacementsImpl) originalProviders.getReplacements()).getGraphBuilderPlugins());
    registerInvocationPlugins(graphBuilderPlugins.getInvocationPlugins(), bytecodeProvider);
    graphBuilderPlugins.prependParameterPlugin(new MethodHandlesParameterPlugin(methodHandleArguments));
    graphBuilderPlugins.clearInlineInvokePlugins();
    graphBuilderPlugins.prependInlineInvokePlugin(new MethodHandlesInlineInvokePlugin());
    graphBuilderPlugins.prependNodePlugin(new MethodHandlePlugin(originalProviders.getConstantReflection().getMethodHandleAccess(), false));
    /* We do all the word type rewriting because parameters to the lambda can be word types. */
    SnippetReflectionProvider originalSnippetReflection = GraalAccess.getOriginalSnippetReflection();
    WordOperationPlugin wordOperationPlugin = new WordOperationPlugin(originalSnippetReflection, new WordTypes(originalProviders.getMetaAccess(), FrameAccess.getWordKind()));
    graphBuilderPlugins.appendInlineInvokePlugin(wordOperationPlugin);
    graphBuilderPlugins.appendTypePlugin(wordOperationPlugin);
    graphBuilderPlugins.appendTypePlugin(new TrustedInterfaceTypePlugin());
    graphBuilderPlugins.appendNodePlugin(wordOperationPlugin);
    GraphBuilderConfiguration graphBuilderConfig = GraphBuilderConfiguration.getSnippetDefault(graphBuilderPlugins);
    GraphBuilderPhase.Instance graphBuilder = new GraphBuilderPhase.Instance(originalProviders.getMetaAccess(), originalProviders.getStampProvider(), originalProviders.getConstantReflection(), originalProviders.getConstantFieldProvider(), graphBuilderConfig, OptimisticOptimizations.NONE, null);
    DebugContext debug = b.getDebug();
    StructuredGraph graph = new StructuredGraph.Builder(b.getOptions(), debug).method(toOriginal(methodHandleMethod)).build();
    try (DebugContext.Scope s = debug.scope("IntrinsifyMethodHandles", graph)) {
        graphBuilder.apply(graph);
        /*
             * We do not care about the improved type information from Pi nodes, so we just delete
             * them to simplify our graph.
             */
        for (PiNode pi : graph.getNodes(PiNode.TYPE)) {
            pi.replaceAndDelete(pi.object());
        }
        /*
             * Support for MethodHandle that adapt the input type to a more generic type, i.e., a
             * MethodHandle that does a dynamic type check on a parameter.
             */
        for (UnaryOpLogicNode node : graph.getNodes().filter(UnaryOpLogicNode.class).filter(v -> v instanceof IsNullNode || v instanceof InstanceOfNode)) {
            ValueNode value = node.getValue();
            if (value instanceof ParameterNode) {
                /*
                     * We just assume that the InstanceOfNode or IsNullNode are used in an If and
                     * the true-successor is actually the branch we want. If that assumption is
                     * wrong, nothing bad happens - we will just continue to report the invocation
                     * as unsupported because the updated stamp for the parameter will not simplify
                     * the graph.
                     */
                if (node instanceof InstanceOfNode) {
                    InstanceOfNode inst = (InstanceOfNode) node;
                    TypeReference typeRef = inst.type();
                    value.setStamp(new ObjectStamp(typeRef.getType(), typeRef.isExact(), !inst.allowsNull(), false));
                } else {
                    assert node instanceof IsNullNode;
                    ResolvedJavaType type = value.stamp(NodeView.DEFAULT).javaType(originalProviders.getMetaAccess());
                    value.setStamp(new ObjectStamp(type, false, /* non-null */
                    true, false));
                }
            }
        }
        /*
             * The canonicalizer converts unsafe field accesses for get/set method handles back to
             * high-level field load and store nodes.
             */
        new CanonicalizerPhase().apply(graph, new PhaseContext(originalProviders));
        for (FixedGuardNode guard : graph.getNodes(FixedGuardNode.TYPE)) {
            if (guard.next() instanceof AccessFieldNode && guard.condition() instanceof IsNullNode && guard.isNegated() && ((IsNullNode) guard.condition()).getValue() == ((AccessFieldNode) guard.next()).object()) {
                /*
                     * Method handles to load and stores fields have null checks. Remove them, since
                     * the null check is implicitly done by the field access.
                     */
                GraphUtil.removeFixedWithUnusedInputs(guard);
            }
        }
        debug.dump(DebugContext.VERY_DETAILED_LEVEL, graph, "Final intrinisfication graph");
        /*
             * After parsing (and recursive inlining during parsing), the graph must contain only
             * one invocation (and therefore only one MethodCallTargetNode), plus the parameters,
             * constants, start, and return nodes.
             */
        Node singleFunctionality = null;
        ReturnNode singleReturn = null;
        for (Node node : graph.getNodes()) {
            if (node == graph.start() || node instanceof ParameterNode || node instanceof ConstantNode || node instanceof FrameState) {
                /* Ignore the allowed framework around the nodes we care about. */
                continue;
            } else if (node instanceof Invoke) {
                /* We check the MethodCallTargetNode, so we can ignore the invoke. */
                continue;
            } else if ((node instanceof MethodCallTargetNode || node instanceof LoadFieldNode || node instanceof StoreFieldNode) && singleFunctionality == null) {
                singleFunctionality = node;
                continue;
            } else if (node instanceof ReturnNode && singleReturn == null) {
                singleReturn = (ReturnNode) node;
                continue;
            }
            throw new UnsupportedFeatureException("Invoke with MethodHandle argument could not be reduced to at most a single call: " + methodHandleMethod.format("%H.%n(%p)"));
        }
        if (singleFunctionality instanceof MethodCallTargetNode) {
            MethodCallTargetNode singleCallTarget = (MethodCallTargetNode) singleFunctionality;
            assert singleReturn.result() == null || singleReturn.result() == singleCallTarget.invoke();
            /*
                 * Replace the originalTarget with the replacementTarget. Note that the
                 * replacementTarget node belongs to a different graph than originalTarget, so we
                 * need to match parameter back to the original graph and allocate a new
                 * MethodCallTargetNode for the original graph.
                 */
            ValueNode[] replacedArguments = new ValueNode[singleCallTarget.arguments().size()];
            for (int i = 0; i < replacedArguments.length; i++) {
                replacedArguments[i] = lookup(b, methodHandleArguments, singleCallTarget.arguments().get(i));
            }
            b.handleReplacedInvoke(singleCallTarget.invokeKind(), lookup(singleCallTarget.targetMethod()), replacedArguments, false);
        } else if (singleFunctionality instanceof LoadFieldNode) {
            LoadFieldNode fieldLoad = (LoadFieldNode) singleFunctionality;
            b.addPush(b.getInvokeReturnType().getJavaKind(), LoadFieldNode.create(null, lookup(b, methodHandleArguments, fieldLoad.object()), lookup(fieldLoad.field())));
        } else if (singleFunctionality instanceof StoreFieldNode) {
            StoreFieldNode fieldStore = (StoreFieldNode) singleFunctionality;
            b.add(new StoreFieldNode(lookup(b, methodHandleArguments, fieldStore.object()), lookup(fieldStore.field()), lookup(b, methodHandleArguments, fieldStore.value())));
        } else if (singleReturn.result() != null) {
            /* Replace the invocation with he constant result. */
            JavaConstant constantResult = singleReturn.result().asJavaConstant();
            assert b.getInvokeReturnType().getJavaKind() == constantResult.getJavaKind();
            b.addPush(constantResult.getJavaKind(), ConstantNode.forConstant(lookup(constantResult), universeProviders.getMetaAccess()));
        } else {
            /* No invoke and no return value, so nothing to do. */
            assert b.getInvokeReturnType().getJavaKind() == JavaKind.Void;
        }
    } catch (Throwable ex) {
        throw debug.handle(ex);
    }
}
Also used : ObjectStamp(org.graalvm.compiler.core.common.type.ObjectStamp) MethodCallTargetNode(org.graalvm.compiler.nodes.java.MethodCallTargetNode) AccessFieldNode(org.graalvm.compiler.nodes.java.AccessFieldNode) ReturnNode(org.graalvm.compiler.nodes.ReturnNode) FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) PiNode(org.graalvm.compiler.nodes.PiNode) UnaryOpLogicNode(org.graalvm.compiler.nodes.UnaryOpLogicNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) IsNullNode(org.graalvm.compiler.nodes.calc.IsNullNode) FloatingNode(org.graalvm.compiler.nodes.calc.FloatingNode) LoadFieldNode(org.graalvm.compiler.nodes.java.LoadFieldNode) ConstantNode(org.graalvm.compiler.nodes.ConstantNode) InstanceOfNode(org.graalvm.compiler.nodes.java.InstanceOfNode) ParameterNode(org.graalvm.compiler.nodes.ParameterNode) StoreFieldNode(org.graalvm.compiler.nodes.java.StoreFieldNode) Node(org.graalvm.compiler.graph.Node) WordTypes(org.graalvm.compiler.word.WordTypes) JavaConstant(jdk.vm.ci.meta.JavaConstant) PiNode(org.graalvm.compiler.nodes.PiNode) FrameState(org.graalvm.compiler.nodes.FrameState) UnaryOpLogicNode(org.graalvm.compiler.nodes.UnaryOpLogicNode) ResolvedJavaType(jdk.vm.ci.meta.ResolvedJavaType) Invoke(org.graalvm.compiler.nodes.Invoke) PhaseContext(org.graalvm.compiler.phases.tiers.PhaseContext) SnippetReflectionProvider(org.graalvm.compiler.api.replacements.SnippetReflectionProvider) ConstantNode(org.graalvm.compiler.nodes.ConstantNode) StructuredGraph(org.graalvm.compiler.nodes.StructuredGraph) ParameterNode(org.graalvm.compiler.nodes.ParameterNode) TypeReference(org.graalvm.compiler.core.common.type.TypeReference) GraphBuilderPhase(org.graalvm.compiler.java.GraphBuilderPhase) InvocationPlugins(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugins) Plugins(org.graalvm.compiler.nodes.graphbuilderconf.GraphBuilderConfiguration.Plugins) StoreFieldNode(org.graalvm.compiler.nodes.java.StoreFieldNode) UnsupportedFeatureException(com.oracle.graal.pointsto.constraints.UnsupportedFeatureException) GraphBuilderConfiguration(org.graalvm.compiler.nodes.graphbuilderconf.GraphBuilderConfiguration) DebugContext(org.graalvm.compiler.debug.DebugContext) LoadFieldNode(org.graalvm.compiler.nodes.java.LoadFieldNode) TrustedInterfaceTypePlugin(com.oracle.svm.core.graal.phases.TrustedInterfaceTypePlugin) FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) ReturnNode(org.graalvm.compiler.nodes.ReturnNode) MethodCallTargetNode(org.graalvm.compiler.nodes.java.MethodCallTargetNode) IsNullNode(org.graalvm.compiler.nodes.calc.IsNullNode) AccessFieldNode(org.graalvm.compiler.nodes.java.AccessFieldNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) CanonicalizerPhase(org.graalvm.compiler.phases.common.CanonicalizerPhase) InstanceOfNode(org.graalvm.compiler.nodes.java.InstanceOfNode) MethodHandlePlugin(org.graalvm.compiler.replacements.MethodHandlePlugin) WordOperationPlugin(org.graalvm.compiler.word.WordOperationPlugin)

Example 13 with ObjectStamp

use of org.graalvm.compiler.core.common.type.ObjectStamp in project graal by oracle.

the class JNINativeCallWrapperMethod method castObject.

private static ValueNode castObject(JNIGraphKit kit, ValueNode object, ResolvedJavaType type) {
    ValueNode casted = object;
    if (!type.isJavaLangObject()) {
        // safe cast to expected type
        TypeReference typeRef = TypeReference.createTrusted(kit.getAssumptions(), type);
        LogicNode condition = kit.append(InstanceOfNode.createAllowNull(typeRef, object, null, null));
        if (!condition.isTautology()) {
            ObjectStamp stamp = StampFactory.object(typeRef, false);
            FixedGuardNode fixedGuard = kit.append(new FixedGuardNode(condition, DeoptimizationReason.ClassCastException, DeoptimizationAction.None, false));
            casted = kit.append(PiNode.create(object, stamp, fixedGuard));
        }
    }
    return casted;
}
Also used : FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) ObjectStamp(org.graalvm.compiler.core.common.type.ObjectStamp) ValueNode(org.graalvm.compiler.nodes.ValueNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) TypeReference(org.graalvm.compiler.core.common.type.TypeReference)

Example 14 with ObjectStamp

use of org.graalvm.compiler.core.common.type.ObjectStamp in project graal by oracle.

the class ObjectStampMeetTest method check.

private void check(Class<?> a, Class<?> b, Class<?> result) {
    Stamp aStamp = StampFactory.object(getType(a));
    Stamp bStamp = StampFactory.object(getType(b));
    ObjectStamp resultStamp = StampFactory.object(getType(result));
    Assert.assertEquals(resultStamp, meet(aStamp, bStamp));
}
Also used : ObjectStamp(org.graalvm.compiler.core.common.type.ObjectStamp) Stamp(org.graalvm.compiler.core.common.type.Stamp) ObjectStamp(org.graalvm.compiler.core.common.type.ObjectStamp)

Example 15 with ObjectStamp

use of org.graalvm.compiler.core.common.type.ObjectStamp in project graal by oracle.

the class StandardGraphBuilderPlugins method registerEdgesPlugins.

/**
 * Substitutions for improving the performance of some critical methods in {@link Edges}. These
 * substitutions improve the performance by forcing the relevant methods to be inlined
 * (intrinsification being a special form of inlining) and removing a checked cast.
 */
private static void registerEdgesPlugins(MetaAccessProvider metaAccess, InvocationPlugins plugins) {
    Registration r = new Registration(plugins, Edges.class);
    for (Class<?> c : new Class<?>[] { Node.class, NodeList.class }) {
        r.register2("get" + c.getSimpleName() + "Unsafe", Node.class, long.class, new InvocationPlugin() {

            @Override
            public boolean apply(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver, ValueNode node, ValueNode offset) {
                ObjectStamp stamp = StampFactory.object(TypeReference.createTrusted(b.getAssumptions(), metaAccess.lookupJavaType(c)));
                RawLoadNode value = b.add(new RawLoadNode(stamp, node, offset, LocationIdentity.any(), JavaKind.Object));
                b.addPush(JavaKind.Object, value);
                return true;
            }
        });
        r.register3("put" + c.getSimpleName() + "Unsafe", Node.class, long.class, c, new InvocationPlugin() {

            @Override
            public boolean apply(GraphBuilderContext b, ResolvedJavaMethod targetMethod, Receiver receiver, ValueNode node, ValueNode offset, ValueNode value) {
                b.add(new RawStoreNode(node, offset, value, JavaKind.Object, LocationIdentity.any()));
                return true;
            }
        });
    }
}
Also used : RawStoreNode(org.graalvm.compiler.nodes.extended.RawStoreNode) ObjectStamp(org.graalvm.compiler.core.common.type.ObjectStamp) RawLoadNode(org.graalvm.compiler.nodes.extended.RawLoadNode) DynamicNewInstanceNode(org.graalvm.compiler.nodes.java.DynamicNewInstanceNode) OpaqueNode(org.graalvm.compiler.nodes.debug.OpaqueNode) NarrowNode(org.graalvm.compiler.nodes.calc.NarrowNode) BindToRegisterNode(org.graalvm.compiler.nodes.debug.BindToRegisterNode) IntegerMulExactNode(org.graalvm.compiler.replacements.nodes.arithmetic.IntegerMulExactNode) SignExtendNode(org.graalvm.compiler.nodes.calc.SignExtendNode) ZeroExtendNode(org.graalvm.compiler.nodes.calc.ZeroExtendNode) RegisterFinalizerNode(org.graalvm.compiler.nodes.java.RegisterFinalizerNode) BoxNode(org.graalvm.compiler.nodes.extended.BoxNode) IntegerAddExactNode(org.graalvm.compiler.replacements.nodes.arithmetic.IntegerAddExactNode) EnsureVirtualizedNode(org.graalvm.compiler.nodes.virtual.EnsureVirtualizedNode) RawStoreNode(org.graalvm.compiler.nodes.extended.RawStoreNode) FixedGuardNode(org.graalvm.compiler.nodes.FixedGuardNode) LogicNode(org.graalvm.compiler.nodes.LogicNode) ValueNode(org.graalvm.compiler.nodes.ValueNode) VirtualizableInvokeMacroNode(org.graalvm.compiler.replacements.nodes.VirtualizableInvokeMacroNode) DynamicNewArrayNode(org.graalvm.compiler.nodes.java.DynamicNewArrayNode) UnsignedDivNode(org.graalvm.compiler.nodes.calc.UnsignedDivNode) UnsafeCompareAndSwapNode(org.graalvm.compiler.nodes.java.UnsafeCompareAndSwapNode) CompareNode(org.graalvm.compiler.nodes.calc.CompareNode) LoadFieldNode(org.graalvm.compiler.nodes.java.LoadFieldNode) IntegerSubExactNode(org.graalvm.compiler.replacements.nodes.arithmetic.IntegerSubExactNode) BranchProbabilityNode(org.graalvm.compiler.nodes.extended.BranchProbabilityNode) UnsafeMemoryStoreNode(org.graalvm.compiler.nodes.extended.UnsafeMemoryStoreNode) ConstantNode(org.graalvm.compiler.nodes.ConstantNode) ReinterpretNode(org.graalvm.compiler.nodes.calc.ReinterpretNode) ClassIsAssignableFromNode(org.graalvm.compiler.nodes.java.ClassIsAssignableFromNode) ControlFlowAnchorNode(org.graalvm.compiler.nodes.debug.ControlFlowAnchorNode) InstanceOfDynamicNode(org.graalvm.compiler.nodes.java.InstanceOfDynamicNode) IntegerEqualsNode(org.graalvm.compiler.nodes.calc.IntegerEqualsNode) AbsNode(org.graalvm.compiler.nodes.calc.AbsNode) RightShiftNode(org.graalvm.compiler.nodes.calc.RightShiftNode) ConditionalNode(org.graalvm.compiler.nodes.calc.ConditionalNode) DeoptimizeNode(org.graalvm.compiler.nodes.DeoptimizeNode) SpillRegistersNode(org.graalvm.compiler.nodes.debug.SpillRegistersNode) UnsafeMemoryLoadNode(org.graalvm.compiler.nodes.extended.UnsafeMemoryLoadNode) BlackholeNode(org.graalvm.compiler.nodes.debug.BlackholeNode) UnsignedRemNode(org.graalvm.compiler.nodes.calc.UnsignedRemNode) SqrtNode(org.graalvm.compiler.nodes.calc.SqrtNode) ReverseBytesNode(org.graalvm.compiler.replacements.nodes.ReverseBytesNode) MembarNode(org.graalvm.compiler.nodes.extended.MembarNode) GetClassNode(org.graalvm.compiler.nodes.extended.GetClassNode) Node(org.graalvm.compiler.graph.Node) UnboxNode(org.graalvm.compiler.nodes.extended.UnboxNode) NodeList(org.graalvm.compiler.graph.NodeList) Receiver(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugin.Receiver) RawLoadNode(org.graalvm.compiler.nodes.extended.RawLoadNode) GraphBuilderContext(org.graalvm.compiler.nodes.graphbuilderconf.GraphBuilderContext) Registration(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugins.Registration) ValueNode(org.graalvm.compiler.nodes.ValueNode) InvocationPlugin(org.graalvm.compiler.nodes.graphbuilderconf.InvocationPlugin) ResolvedJavaMethod(jdk.vm.ci.meta.ResolvedJavaMethod)

Aggregations

ObjectStamp (org.graalvm.compiler.core.common.type.ObjectStamp)31 ValueNode (org.graalvm.compiler.nodes.ValueNode)14 Stamp (org.graalvm.compiler.core.common.type.Stamp)12 ResolvedJavaType (jdk.vm.ci.meta.ResolvedJavaType)10 FixedGuardNode (org.graalvm.compiler.nodes.FixedGuardNode)8 Node (org.graalvm.compiler.graph.Node)6 ConstantNode (org.graalvm.compiler.nodes.ConstantNode)6 ParameterNode (org.graalvm.compiler.nodes.ParameterNode)6 PiNode (org.graalvm.compiler.nodes.PiNode)6 TypeReference (org.graalvm.compiler.core.common.type.TypeReference)5 LogicNode (org.graalvm.compiler.nodes.LogicNode)5 ResolvedJavaMethod (jdk.vm.ci.meta.ResolvedJavaMethod)4 JavaConstant (jdk.vm.ci.meta.JavaConstant)3 JavaType (jdk.vm.ci.meta.JavaType)3 AbstractBeginNode (org.graalvm.compiler.nodes.AbstractBeginNode)3 LoadHubNode (org.graalvm.compiler.nodes.extended.LoadHubNode)3 LoadFieldNode (org.graalvm.compiler.nodes.java.LoadFieldNode)3 MethodCallTargetNode (org.graalvm.compiler.nodes.java.MethodCallTargetNode)3 HotSpotResolvedObjectType (jdk.vm.ci.hotspot.HotSpotResolvedObjectType)2 Constant (jdk.vm.ci.meta.Constant)2