# HG changeset patch # User Doug Simon # Date 1423242229 -3600 # Node ID e99be967a753cd6e5c70452eeb93ff6826b9f468 # Parent df3561f7c9ad05a6f429a6b8a4d41cfa1c8c3d78 renamed TruffleGraphBuilderPluginsProvider to TruffleGraphBuilderPlugins to reflect the fact that it is no longer a service provider diff -r df3561f7c9ad -r e99be967a753 graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java --- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java Fri Feb 06 18:00:51 2015 +0100 +++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java Fri Feb 06 18:03:49 2015 +0100 @@ -218,7 +218,7 @@ for (GraphBuilderPluginsProvider p : sl) { p.registerPlugins(providers.getMetaAccess(), plugins); } - new TruffleGraphBuilderPluginsProvider().registerPlugins(providers.getMetaAccess(), plugins); + TruffleGraphBuilderPlugins.registerPlugins(providers.getMetaAccess(), plugins); new GraphBuilderPhase.Instance(providers.getMetaAccess(), providers.getStampProvider(), new Assumptions(false), providers.getConstantReflection(), newConfig, plugins, TruffleCompilerImpl.Optimizations).apply(graph); Debug.dump(graph, "After FastPE"); diff -r df3561f7c9ad -r e99be967a753 graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/substitutions/TruffleGraphBuilderPlugins.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/substitutions/TruffleGraphBuilderPlugins.java Fri Feb 06 18:03:49 2015 +0100 @@ -0,0 +1,215 @@ +/* + * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.graal.truffle.substitutions; + +import static java.lang.Character.*; + +import java.util.concurrent.*; + +import com.oracle.graal.api.code.*; +import com.oracle.graal.api.meta.*; +import com.oracle.graal.compiler.common.calc.*; +import com.oracle.graal.compiler.common.type.*; +import com.oracle.graal.java.*; +import com.oracle.graal.java.GraphBuilderPlugins.InvocationPlugin; +import com.oracle.graal.java.GraphBuilderPlugins.Registration; +import com.oracle.graal.java.GraphBuilderPlugins.Registration.Receiver; +import com.oracle.graal.nodes.*; +import com.oracle.graal.nodes.calc.*; +import com.oracle.graal.nodes.extended.*; +import com.oracle.graal.truffle.*; +import com.oracle.graal.truffle.nodes.*; +import com.oracle.graal.truffle.nodes.frame.*; +import com.oracle.truffle.api.*; +import com.oracle.truffle.api.frame.*; + +/** + * Provider of {@link GraphBuilderPlugin}s for Truffle classes. + */ +public class TruffleGraphBuilderPlugins { + public static void registerPlugins(MetaAccessProvider metaAccess, GraphBuilderPlugins plugins) { + + // CompilerDirectives.class + Registration r = new Registration(plugins, metaAccess, CompilerDirectives.class); + r.register0("inInterpreter", new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder) { + builder.push(Kind.Boolean.getStackKind(), builder.append(ConstantNode.forBoolean(false))); + return true; + } + }); + r.register0("inCompiledCode", new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder) { + builder.push(Kind.Boolean.getStackKind(), builder.append(ConstantNode.forBoolean(true))); + return true; + } + }); + r.register0("transferToInterpreter", new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder) { + builder.append(new DeoptimizeNode(DeoptimizationAction.None, DeoptimizationReason.TransferToInterpreter)); + return true; + } + }); + r.register0("transferToInterpreterAndInvalidate", new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder) { + builder.append(new DeoptimizeNode(DeoptimizationAction.InvalidateReprofile, DeoptimizationReason.TransferToInterpreter)); + return true; + } + }); + r.register1("interpreterOnly", Runnable.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode arg) { + return true; + } + }); + r.register1("interpreterOnly", Callable.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode arg) { + return true; + } + }); + r.register2("injectBranchProbability", double.class, boolean.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode probability, ValueNode condition) { + builder.append(new BranchProbabilityNode(probability, condition)); + return true; + } + }); + r.register1("bailout", String.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode message) { + if (message.isConstant()) { + throw new BailoutException(message.asConstant().toValueString()); + } + throw new BailoutException("bailout (message is not compile-time constant, so no additional information is available)"); + } + }); + r.register1("isCompilationConstant", Object.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode value) { + if ((value instanceof BoxNode ? ((BoxNode) value).getValue() : value).isConstant()) { + builder.push(Kind.Boolean.getStackKind(), builder.append(ConstantNode.forBoolean(true))); + return true; + } + return false; + } + }); + r.register1("materialize", Object.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode value) { + builder.append(new ForceMaterializeNode(value)); + return true; + } + }); + + // OptimizedCallTarget.class + r = new Registration(plugins, metaAccess, OptimizedCallTarget.class); + r.register2("createFrame", FrameDescriptor.class, Object[].class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode arg1, ValueNode arg2) { + builder.push(Kind.Object, builder.append(new NewFrameNode(StampFactory.exactNonNull(metaAccess.lookupJavaType(FrameWithoutBoxing.class)), arg1, arg2))); + return true; + } + }); + + // FrameWithoutBoxing.class + r = new Registration(plugins, metaAccess, FrameWithoutBoxing.class); + r.register1("materialize", Receiver.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode frame) { + builder.append(new MaterializeFrameNode(frame)); + return true; + } + }); + r.register4("unsafeCast", Object.class, Class.class, boolean.class, boolean.class, new InvocationPlugin() { + public boolean apply(GraphBuilderContext builder, ValueNode object, ValueNode clazz, ValueNode condition, ValueNode nonNull) { + if (clazz.isConstant() && nonNull.isConstant()) { + ConstantReflectionProvider constantReflection = builder.getConstantReflection(); + ResolvedJavaType javaType = constantReflection.asJavaType(clazz.asConstant()); + if (javaType == null) { + builder.push(Kind.Object, object); + } else { + Stamp piStamp = StampFactory.declaredTrusted(javaType, nonNull.asJavaConstant().asInt() != 0); + ConditionAnchorNode valueAnchorNode = builder.append(new ConditionAnchorNode(CompareNode.createCompareNode(object.graph(), Condition.EQ, condition, + ConstantNode.forBoolean(true, object.graph())))); + PiNode piCast = builder.append(new PiNode(object, piStamp, valueAnchorNode)); + builder.push(Kind.Object, piCast); + } + return true; + } + // TODO: should we throw GraalInternalError.shouldNotReachHere() here? + return false; + } + }); + for (Kind kind : new Kind[]{Kind.Boolean, Kind.Byte, Kind.Int, Kind.Long, Kind.Float, Kind.Double, Kind.Object}) { + String kindName = kind.getJavaName(); + kindName = toUpperCase(kindName.charAt(0)) + kindName.substring(1); + String getName = "unsafeGet" + kindName; + String putName = "unsafePut" + kindName; + r.register4(getName, Object.class, long.class, boolean.class, Object.class, new CustomizedUnsafeLoadPlugin(kind)); + r.register4(putName, Object.class, long.class, kind == Kind.Object ? Object.class : kind.toJavaClass(), Object.class, new CustomizedUnsafeStorePlugin(kind)); + } + } + + static class CustomizedUnsafeLoadPlugin implements InvocationPlugin { + + private final Kind returnKind; + + public CustomizedUnsafeLoadPlugin(Kind returnKind) { + this.returnKind = returnKind; + } + + public boolean apply(GraphBuilderContext builder, ValueNode object, ValueNode offset, ValueNode condition, ValueNode location) { + if (location.isConstant()) { + LocationIdentity locationIdentity; + if (location.isNullConstant()) { + locationIdentity = LocationIdentity.ANY_LOCATION; + } else { + locationIdentity = ObjectLocationIdentity.create(location.asJavaConstant()); + } + CompareNode compare = builder.append(CompareNode.createCompareNode(Condition.EQ, condition, ConstantNode.forBoolean(true, object.graph()))); + builder.push(returnKind.getStackKind(), builder.append(new UnsafeLoadNode(object, offset, returnKind, locationIdentity, compare))); + return true; + } + // TODO: should we throw GraalInternalError.shouldNotReachHere() here? + return false; + } + } + + static class CustomizedUnsafeStorePlugin implements InvocationPlugin { + + private final Kind kind; + + public CustomizedUnsafeStorePlugin(Kind kind) { + this.kind = kind; + } + + public boolean apply(GraphBuilderContext builder, ValueNode object, ValueNode offset, ValueNode value, ValueNode location) { + ValueNode locationArgument = location; + if (locationArgument.isConstant()) { + LocationIdentity locationIdentity; + if (locationArgument.isNullConstant()) { + locationIdentity = LocationIdentity.ANY_LOCATION; + } else { + locationIdentity = ObjectLocationIdentity.create(locationArgument.asJavaConstant()); + } + + builder.append(new UnsafeStoreNode(object, offset, value, kind, locationIdentity, null)); + return true; + } + // TODO: should we throw GraalInternalError.shouldNotReachHere() here? + return false; + } + } +} diff -r df3561f7c9ad -r e99be967a753 graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/substitutions/TruffleGraphBuilderPluginsProvider.java --- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/substitutions/TruffleGraphBuilderPluginsProvider.java Fri Feb 06 18:00:51 2015 +0100 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,215 +0,0 @@ -/* - * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved. - * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. - * - * This code is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License version 2 only, as - * published by the Free Software Foundation. - * - * This code is distributed in the hope that it will be useful, but WITHOUT - * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or - * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License - * version 2 for more details (a copy is included in the LICENSE file that - * accompanied this code). - * - * You should have received a copy of the GNU General Public License version - * 2 along with this work; if not, write to the Free Software Foundation, - * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. - * - * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA - * or visit www.oracle.com if you need additional information or have any - * questions. - */ -package com.oracle.graal.truffle.substitutions; - -import static java.lang.Character.*; - -import java.util.concurrent.*; - -import com.oracle.graal.api.code.*; -import com.oracle.graal.api.meta.*; -import com.oracle.graal.compiler.common.calc.*; -import com.oracle.graal.compiler.common.type.*; -import com.oracle.graal.java.*; -import com.oracle.graal.java.GraphBuilderPlugins.InvocationPlugin; -import com.oracle.graal.java.GraphBuilderPlugins.Registration; -import com.oracle.graal.java.GraphBuilderPlugins.Registration.Receiver; -import com.oracle.graal.nodes.*; -import com.oracle.graal.nodes.calc.*; -import com.oracle.graal.nodes.extended.*; -import com.oracle.graal.truffle.*; -import com.oracle.graal.truffle.nodes.*; -import com.oracle.graal.truffle.nodes.frame.*; -import com.oracle.truffle.api.*; -import com.oracle.truffle.api.frame.*; - -/** - * Provider of {@link GraphBuilderPlugin}s for Truffle classes. - */ -public class TruffleGraphBuilderPluginsProvider implements GraphBuilderPluginsProvider { - public void registerPlugins(MetaAccessProvider metaAccess, GraphBuilderPlugins plugins) { - - // CompilerDirectives.class - Registration r = new Registration(plugins, metaAccess, CompilerDirectives.class); - r.register0("inInterpreter", new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder) { - builder.push(Kind.Boolean.getStackKind(), builder.append(ConstantNode.forBoolean(false))); - return true; - } - }); - r.register0("inCompiledCode", new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder) { - builder.push(Kind.Boolean.getStackKind(), builder.append(ConstantNode.forBoolean(true))); - return true; - } - }); - r.register0("transferToInterpreter", new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder) { - builder.append(new DeoptimizeNode(DeoptimizationAction.None, DeoptimizationReason.TransferToInterpreter)); - return true; - } - }); - r.register0("transferToInterpreterAndInvalidate", new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder) { - builder.append(new DeoptimizeNode(DeoptimizationAction.InvalidateReprofile, DeoptimizationReason.TransferToInterpreter)); - return true; - } - }); - r.register1("interpreterOnly", Runnable.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode arg) { - return true; - } - }); - r.register1("interpreterOnly", Callable.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode arg) { - return true; - } - }); - r.register2("injectBranchProbability", double.class, boolean.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode probability, ValueNode condition) { - builder.append(new BranchProbabilityNode(probability, condition)); - return true; - } - }); - r.register1("bailout", String.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode message) { - if (message.isConstant()) { - throw new BailoutException(message.asConstant().toValueString()); - } - throw new BailoutException("bailout (message is not compile-time constant, so no additional information is available)"); - } - }); - r.register1("isCompilationConstant", Object.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode value) { - if ((value instanceof BoxNode ? ((BoxNode) value).getValue() : value).isConstant()) { - builder.push(Kind.Boolean.getStackKind(), builder.append(ConstantNode.forBoolean(true))); - return true; - } - return false; - } - }); - r.register1("materialize", Object.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode value) { - builder.append(new ForceMaterializeNode(value)); - return true; - } - }); - - // OptimizedCallTarget.class - r = new Registration(plugins, metaAccess, OptimizedCallTarget.class); - r.register2("createFrame", FrameDescriptor.class, Object[].class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode arg1, ValueNode arg2) { - builder.push(Kind.Object, builder.append(new NewFrameNode(StampFactory.exactNonNull(metaAccess.lookupJavaType(FrameWithoutBoxing.class)), arg1, arg2))); - return true; - } - }); - - // FrameWithoutBoxing.class - r = new Registration(plugins, metaAccess, FrameWithoutBoxing.class); - r.register1("materialize", Receiver.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode frame) { - builder.append(new MaterializeFrameNode(frame)); - return true; - } - }); - r.register4("unsafeCast", Object.class, Class.class, boolean.class, boolean.class, new InvocationPlugin() { - public boolean apply(GraphBuilderContext builder, ValueNode object, ValueNode clazz, ValueNode condition, ValueNode nonNull) { - if (clazz.isConstant() && nonNull.isConstant()) { - ConstantReflectionProvider constantReflection = builder.getConstantReflection(); - ResolvedJavaType javaType = constantReflection.asJavaType(clazz.asConstant()); - if (javaType == null) { - builder.push(Kind.Object, object); - } else { - Stamp piStamp = StampFactory.declaredTrusted(javaType, nonNull.asJavaConstant().asInt() != 0); - ConditionAnchorNode valueAnchorNode = builder.append(new ConditionAnchorNode(CompareNode.createCompareNode(object.graph(), Condition.EQ, condition, - ConstantNode.forBoolean(true, object.graph())))); - PiNode piCast = builder.append(new PiNode(object, piStamp, valueAnchorNode)); - builder.push(Kind.Object, piCast); - } - return true; - } - // TODO: should we throw GraalInternalError.shouldNotReachHere() here? - return false; - } - }); - for (Kind kind : new Kind[]{Kind.Boolean, Kind.Byte, Kind.Int, Kind.Long, Kind.Float, Kind.Double, Kind.Object}) { - String kindName = kind.getJavaName(); - kindName = toUpperCase(kindName.charAt(0)) + kindName.substring(1); - String getName = "unsafeGet" + kindName; - String putName = "unsafePut" + kindName; - r.register4(getName, Object.class, long.class, boolean.class, Object.class, new CustomizedUnsafeLoadPlugin(kind)); - r.register4(putName, Object.class, long.class, kind == Kind.Object ? Object.class : kind.toJavaClass(), Object.class, new CustomizedUnsafeStorePlugin(kind)); - } - } - - static class CustomizedUnsafeLoadPlugin implements InvocationPlugin { - - private final Kind returnKind; - - public CustomizedUnsafeLoadPlugin(Kind returnKind) { - this.returnKind = returnKind; - } - - public boolean apply(GraphBuilderContext builder, ValueNode object, ValueNode offset, ValueNode condition, ValueNode location) { - if (location.isConstant()) { - LocationIdentity locationIdentity; - if (location.isNullConstant()) { - locationIdentity = LocationIdentity.ANY_LOCATION; - } else { - locationIdentity = ObjectLocationIdentity.create(location.asJavaConstant()); - } - CompareNode compare = builder.append(CompareNode.createCompareNode(Condition.EQ, condition, ConstantNode.forBoolean(true, object.graph()))); - builder.push(returnKind.getStackKind(), builder.append(new UnsafeLoadNode(object, offset, returnKind, locationIdentity, compare))); - return true; - } - // TODO: should we throw GraalInternalError.shouldNotReachHere() here? - return false; - } - } - - static class CustomizedUnsafeStorePlugin implements InvocationPlugin { - - private final Kind kind; - - public CustomizedUnsafeStorePlugin(Kind kind) { - this.kind = kind; - } - - public boolean apply(GraphBuilderContext builder, ValueNode object, ValueNode offset, ValueNode value, ValueNode location) { - ValueNode locationArgument = location; - if (locationArgument.isConstant()) { - LocationIdentity locationIdentity; - if (locationArgument.isNullConstant()) { - locationIdentity = LocationIdentity.ANY_LOCATION; - } else { - locationIdentity = ObjectLocationIdentity.create(locationArgument.asJavaConstant()); - } - - builder.append(new UnsafeStoreNode(object, offset, value, kind, locationIdentity, null)); - return true; - } - // TODO: should we throw GraalInternalError.shouldNotReachHere() here? - return false; - } - } -}