Mercurial > hg > graal-compiler
changeset 21357:acfc5e32e678
Merge with 6d5a198d23e67bb4b850ce1d74f5c338840cfe04
author | Michael Van De Vanter <michael.van.de.vanter@oracle.com> |
---|---|
date | Tue, 12 May 2015 18:04:53 -0700 |
parents | e34bc00733d1 (diff) 6d5a198d23e6 (current diff) |
children | 19801a65cf57 |
files | graal/com.oracle.graal.java/src/com/oracle/graal/java/AbstractBytecodeParser.java |
diffstat | 11 files changed, 337 insertions(+), 298 deletions(-) [+] |
line wrap: on
line diff
--- a/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/InstrumentationPartialEvaluationTest.java Tue May 12 23:26:16 2015 +0200 +++ b/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/InstrumentationPartialEvaluationTest.java Tue May 12 18:04:53 2015 -0700 @@ -205,19 +205,19 @@ } @Test - public void constantValueInertToolEvalNodeFactory() { + public void constantValueInertAdvancedInstrumentRootFactory() { FrameDescriptor fd = new FrameDescriptor(); AbstractTestNode result = new ConstantTestNode(42); RootTestNode root = new RootTestNode(fd, "constantValue", result); root.adoptChildren(); Probe testProbe = result.probe(); - // A factory that could insert a ToolEvalNode into the AST, but which never does. - Instrument instrument = Instrument.create(new ToolEvalNodeFactory() { + // A factory that could insert a AdvancedInstrumentRoot into the AST, but which never does. + Instrument instrument = Instrument.create(null, new AdvancedInstrumentRootFactory() { - public ToolEvalNode createToolEvalNode(Probe probe, Node node) { + public AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node) { return null; } - }, null); + }, null, "test AdvancedInstrument"); testProbe.attach(instrument); // It all gets compiled away @@ -225,29 +225,30 @@ } @Test - public void constantValueInertToolEvalNode() { + public void constantValueInertAdvancedInstrumentRoot() { FrameDescriptor fd = new FrameDescriptor(); AbstractTestNode resultTestNode = new ConstantTestNode(42); RootTestNode rootTestNode = new RootTestNode(fd, "constantValue", resultTestNode); rootTestNode.adoptChildren(); Probe testProbe = resultTestNode.probe(); - // A factory that inserts a ToolEvalNode with empty methods into the instrumentation chain. - Instrument instrument = Instrument.create(new ToolEvalNodeFactory() { + // Factory inserts a AdvancedInstrumentRoot with empty methods into instrumentation . + Instrument instrument = Instrument.create(null, new AdvancedInstrumentRootFactory() { - public ToolEvalNode createToolEvalNode(Probe probe, Node node) { - return new ToolEvalNode() { + @Override + public AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node) { + return new AdvancedInstrumentRoot() { public String instrumentationInfo() { return null; } @Override - public Object executeToolEvalNode(Node n, VirtualFrame frame) { + public Object executeRoot(Node n, VirtualFrame frame) { return null; } }; } - }, null); + }, null, "test AdvancedInstrument"); testProbe.attach(instrument); // It all gets compiled away. @@ -351,6 +352,7 @@ final boolean[] isCurrentlyCompiled = {false}; final Instrument optInstrument = Instrument.create(new Instrument.TruffleOptListener() { + @Override public void notifyIsCompiled(boolean isCompiled) { isCurrentlyCompiled[0] = isCompiled; }
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/AdvancedInstrumentTest.java Tue May 12 18:04:53 2015 -0700 @@ -0,0 +1,87 @@ +/* + * 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.truffle.api.test.instrument; + +import static org.junit.Assert.*; + +import org.junit.*; + +import com.oracle.truffle.api.*; +import com.oracle.truffle.api.instrument.*; +import com.oracle.truffle.api.nodes.*; +import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestAdditionNode; +import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestRootNode; +import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestValueNode; +import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestAdvancedInstrumentCounterRoot; + +/** + * Tests the kind of instrumentation where a client can provide an AST fragment to be + * <em>spliced</em> directly into the AST. + */ +public class AdvancedInstrumentTest { + + @Test + public void testAdvancedInstrumentListener() { + // Create a simple addition AST + final TruffleRuntime runtime = Truffle.getRuntime(); + final TestValueNode leftValueNode = new TestValueNode(6); + final TestValueNode rightValueNode = new TestValueNode(7); + final TestAdditionNode addNode = new TestAdditionNode(leftValueNode, rightValueNode); + final TestRootNode rootNode = new TestRootNode(addNode); + final CallTarget callTarget1 = runtime.createCallTarget(rootNode); + + // Ensure it executes correctly + assertEquals(13, callTarget1.call()); + + // Probe the addition node + final Probe probe = addNode.probe(); + + assertEquals(13, callTarget1.call()); + + // Attach a null factory; it never actually attaches a node. + final Instrument instrument = Instrument.create(null, new AdvancedInstrumentRootFactory() { + + public AdvancedInstrumentRoot createInstrumentRoot(Probe p, Node n) { + return null; + } + }, null, "test AdvancedInstrument"); + probe.attach(instrument); + + assertEquals(13, callTarget1.call()); + + final TestAdvancedInstrumentCounterRoot counter = new TestAdvancedInstrumentCounterRoot(); + + // Attach a factory that splices an execution counter into the AST. + probe.attach(Instrument.create(null, new AdvancedInstrumentRootFactory() { + + public AdvancedInstrumentRoot createInstrumentRoot(Probe p, Node n) { + return counter; + } + }, null, "test AdvancedInstrument")); + assertEquals(0, counter.getCount()); + + assertEquals(13, callTarget1.call()); + + assertEquals(1, counter.getCount()); + } +}
--- a/graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/InstrumentationTestNodes.java Tue May 12 23:26:16 2015 +0200 +++ b/graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/InstrumentationTestNodes.java Tue May 12 18:04:53 2015 -0700 @@ -167,12 +167,12 @@ } } - static class TestToolEvalCounterNode extends ToolEvalNode { + static class TestAdvancedInstrumentCounterRoot extends AdvancedInstrumentRoot { private long count; @Override - public Object executeToolEvalNode(Node node, VirtualFrame vFrame) { + public Object executeRoot(Node node, VirtualFrame vFrame) { count++; return null; }
--- a/graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/ToolEvalInstrumentTest.java Tue May 12 23:26:16 2015 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,89 +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.truffle.api.test.instrument; - -import static org.junit.Assert.*; - -import org.junit.*; - -import com.oracle.truffle.api.*; -import com.oracle.truffle.api.instrument.*; -import com.oracle.truffle.api.nodes.*; -import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestAdditionNode; -import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestRootNode; -import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestValueNode; -import com.oracle.truffle.api.test.instrument.InstrumentationTestNodes.TestToolEvalCounterNode; - -/** - * Tests the kind of instrumentation where a client can provide an AST fragment to be - * <em>spliced</em> directly into the AST. - */ -public class ToolEvalInstrumentTest { - - @Test - public void testSpliceInstrumentListener() { - // Create a simple addition AST - final TruffleRuntime runtime = Truffle.getRuntime(); - final TestValueNode leftValueNode = new TestValueNode(6); - final TestValueNode rightValueNode = new TestValueNode(7); - final TestAdditionNode addNode = new TestAdditionNode(leftValueNode, rightValueNode); - final TestRootNode rootNode = new TestRootNode(addNode); - final CallTarget callTarget1 = runtime.createCallTarget(rootNode); - - // Ensure it executes correctly - assertEquals(13, callTarget1.call()); - - // Probe the addition node - final Probe probe = addNode.probe(); - - assertEquals(13, callTarget1.call()); - - // Attach a null listener; it never actually attaches a node. - final Instrument instrument = Instrument.create(new ToolEvalNodeFactory() { - - public ToolEvalNode createToolEvalNode(Probe p, Node n) { - return null; - } - }, null); - probe.attach(instrument); - - assertEquals(13, callTarget1.call()); - - final TestToolEvalCounterNode counter = new TestToolEvalCounterNode(); - - // Attach a listener that splices an execution counter into the AST. - probe.attach(Instrument.create(new ToolEvalNodeFactory() { - - public ToolEvalNode createToolEvalNode(Probe p, Node n) { - return counter; - } - }, null)); - assertEquals(0, counter.getCount()); - - assertEquals(13, callTarget1.call()); - - assertEquals(1, counter.getCount()); - - } - -}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentResultListener.java Tue May 12 18:04:53 2015 -0700 @@ -0,0 +1,74 @@ +/* + * 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. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the LICENSE file that accompanied this code. + * + * 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.truffle.api.instrument; + +import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary; +import com.oracle.truffle.api.frame.*; +import com.oracle.truffle.api.nodes.*; + +/** + * Listener for receiving the result a client-provided {@linkplain AdvancedInstrumentRoot AST + * fragment}, when executed by a + * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, Class, String) + * Advanced Instrument}. + * + * @see Instrument + * @see AdvancedInstrumentRoot + * @see AdvancedInstrumentRootFactory + */ +public interface AdvancedInstrumentResultListener { + + /** + * Notifies listener that a client-provided {@linkplain AdvancedInstrumentRoot AST fragment} has + * been executed by an + * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, Class, String) + * Advanced Instrument} with the specified result, possibly {@code null}. + * <p> + * <strong>Note: </strong> Truffle will attempt to optimize implementations through partial + * evaluation; annotate with {@link TruffleBoundary} if this should not be permitted. + * + * @param node the guest-language AST node to which the host Instrument's {@link Probe} is + * attached + * @param vFrame execution frame at the guest-language AST node + * @param result the result of this AST fragment's execution + */ + void notifyResult(Node node, VirtualFrame vFrame, Object result); + + /** + * Notifies listener that execution of client-provided {@linkplain AdvancedInstrumentRoot AST + * fragment} filed during execution by a @linkplain + * Instrument#create(AdvancedInstrumentRootFactory, String) Advanced Instrument}. + * <p> + * <strong>Note: </strong> Truffle will attempt to optimize implementations through partial + * evaluation; annotate with {@link TruffleBoundary} if this should not be permitted. + * + * @param node the guest-language AST node to which the host Instrument's {@link Probe} is + * attached + * @param vFrame execution frame at the guest-language AST node + * @param ex the exception + */ + void notifyFailure(Node node, VirtualFrame vFrame, RuntimeException ex); + +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRoot.java Tue May 12 18:04:53 2015 -0700 @@ -0,0 +1,52 @@ +/* + * 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. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the LICENSE file that accompanied this code. + * + * 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.truffle.api.instrument; + +import com.oracle.truffle.api.frame.*; +import com.oracle.truffle.api.nodes.*; + +/** + * Root of a client-provided AST fragment that can be executed efficiently, subject to full Truffle + * optimization, by an + * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, Class, String) + * Advanced Instrument}. + * + * @see Instrument + * @see AdvancedInstrumentRootFactory + * @see AdvancedInstrumentResultListener + */ +public abstract class AdvancedInstrumentRoot extends Node implements InstrumentationNode { + + /** + * Executes this AST fragment on behalf of a client {@link Instrument}, just before the + * guest-language AST node to which the {@link Probe} holding the Instrument is executed. + * + * @param node the guest-language AST node to which the host Instrument's Probe is attached + * @param vFrame execution frame at the guest-language AST node + * @return the result of this AST fragment's execution + */ + public abstract Object executeRoot(Node node, VirtualFrame vFrame); + +}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRootFactory.java Tue May 12 18:04:53 2015 -0700 @@ -0,0 +1,52 @@ +/* + * 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. Oracle designates this + * particular file as subject to the "Classpath" exception as provided + * by Oracle in the LICENSE file that accompanied this code. + * + * 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.truffle.api.instrument; + +import com.oracle.truffle.api.nodes.*; + +/** + * Creator of {@linkplain AdvancedInstrumentRoot AST fragments} suitable for efficient execution, + * subject to full Truffle optimization, by an + * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, Class, String) + * Advanced Instrument}. + * + * @see Instrument + * @see AdvancedInstrumentRoot + */ +public interface AdvancedInstrumentRootFactory { + + /** + * Provider of {@linkplain AdvancedInstrumentRoot AST fragment} instances for efficient + * execution via instrumentation, subject to full Truffle optimization, at a {@linkplain Probe + * Probed} site in a guest-language AST. + * + * @param probe the Probe to which the Instrument requesting the AST fragment is attached + * @param node the guest-language AST location that is the context in which the requesting + * Instrument must execute the AST fragment. + * @return a newly created AST fragment suitable for execution, via instrumentation, in the + * execution context of the specified guest-language AST site. + */ + AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node); +}
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrument.java Tue May 12 23:26:16 2015 +0200 +++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrument.java Tue May 12 18:04:53 2015 -0700 @@ -127,16 +127,19 @@ } /** - * Creates a <em>Tool Eval Instrument</em>: this Instrument executes efficiently, subject to + * Creates an <em>Advanced Instrument</em>: this Instrument executes efficiently, subject to * full Truffle optimization, a client-provided AST fragment every time the Probed node is * entered. * - * @param toolEvalNodeFactory provider of AST fragments on behalf of the client + * @param resultListener optional client callback for results/failure notification + * @param rootFactory provider of AST fragments on behalf of the client + * @param requiredResultType optional requirement, any non-assignable result is reported to the + * the listener, if any, as a failure * @param instrumentInfo optional description of the instrument's role, intended for debugging. * @return a new instrument, ready for attachment at a probe */ - public static Instrument create(ToolEvalNodeFactory toolEvalNodeFactory, String instrumentInfo) { - return new ToolEvalInstrument(toolEvalNodeFactory, instrumentInfo); + public static Instrument create(AdvancedInstrumentResultListener resultListener, AdvancedInstrumentRootFactory rootFactory, Class<?> requiredResultType, String instrumentInfo) { + return new AdvancedInstrument(resultListener, rootFactory, requiredResultType, instrumentInfo); } // TODO (mlvdv) experimental @@ -379,22 +382,22 @@ * within a Probe's <em>instrumentation chain</em>, and thus directly in the executing Truffle * AST with potential for full optimization. */ - private static final class ToolEvalInstrument extends Instrument { + private static final class AdvancedInstrument extends Instrument { + + private final AdvancedInstrumentResultListener resultListener; + private final AdvancedInstrumentRootFactory rootFactory; + private final Class<?> requiredResultType; - /** - * Client-provided supplier of new node instances to attach. - */ - private final ToolEvalNodeFactory toolEvalNodeFactory; - - private ToolEvalInstrument(ToolEvalNodeFactory toolEvalNodeFactory, String instrumentInfo) { + private AdvancedInstrument(AdvancedInstrumentResultListener resultListener, AdvancedInstrumentRootFactory rootFactory, Class<?> requiredResultType, String instrumentInfo) { super(instrumentInfo); - this.toolEvalNodeFactory = toolEvalNodeFactory; - + this.resultListener = resultListener; + this.rootFactory = rootFactory; + this.requiredResultType = requiredResultType; } @Override AbstractInstrumentNode addToChain(AbstractInstrumentNode nextNode) { - return new ToolEvalNodeInstrumentNode(nextNode); + return new AdvancedInstrumentNode(nextNode); } @Override @@ -406,7 +409,7 @@ return instrumentNode.nextInstrumentNode; } // Match not at the head of the chain; remove it. - found = instrumentNode.removeFromChain(ToolEvalInstrument.this); + found = instrumentNode.removeFromChain(AdvancedInstrument.this); } if (!found) { throw new IllegalStateException("Couldn't find instrument node to remove: " + this); @@ -415,35 +418,59 @@ } /** - * Node that implements a {@link ToolEvalInstrument} in a particular AST. + * Node that implements a {@link AdvancedInstrument} in a particular AST. */ @NodeInfo(cost = NodeCost.NONE) - private final class ToolEvalNodeInstrumentNode extends AbstractInstrumentNode { + private final class AdvancedInstrumentNode extends AbstractInstrumentNode { - @Child private ToolEvalNode toolEvalNode; + @Child private AdvancedInstrumentRoot instrumentRoot; - private ToolEvalNodeInstrumentNode(AbstractInstrumentNode nextNode) { + private AdvancedInstrumentNode(AbstractInstrumentNode nextNode) { super(nextNode); } public void enter(Node node, VirtualFrame vFrame) { - if (toolEvalNode == null) { - final ToolEvalNode newToolEvalNodeNode = ToolEvalInstrument.this.toolEvalNodeFactory.createToolEvalNode(ToolEvalInstrument.this.probe, node); - if (newToolEvalNodeNode != null) { - toolEvalNode = newToolEvalNodeNode; - adoptChildren(); - ToolEvalInstrument.this.probe.invalidateProbeUnchanged(); + if (instrumentRoot == null) { + try { + final AdvancedInstrumentRoot newInstrumentRoot = AdvancedInstrument.this.rootFactory.createInstrumentRoot(AdvancedInstrument.this.probe, node); + if (newInstrumentRoot != null) { + instrumentRoot = newInstrumentRoot; + adoptChildren(); + AdvancedInstrument.this.probe.invalidateProbeUnchanged(); + } + } catch (RuntimeException ex) { + if (resultListener != null) { + resultListener.notifyFailure(node, vFrame, ex); + } } } - if (toolEvalNode != null) { - // TODO (mlvdv) should report exception ; non-trivial architectural change - toolEvalNode.executeToolEvalNode(node, vFrame); + if (instrumentRoot != null) { + try { + final Object result = instrumentRoot.executeRoot(node, vFrame); + if (resultListener != null) { + checkResultType(result); + resultListener.notifyResult(node, vFrame, result); + } + } catch (RuntimeException ex) { + if (resultListener != null) { + resultListener.notifyFailure(node, vFrame, ex); + } + } } if (nextInstrumentNode != null) { nextInstrumentNode.enter(node, vFrame); } } + private void checkResultType(Object result) { + if (requiredResultType == null) { + return; + } + if (result == null || !(requiredResultType.isAssignableFrom(result.getClass()))) { + throw new RuntimeException("Instrument result " + result.toString() + " not assignable to " + requiredResultType.getSimpleName()); + } + } + public void returnVoid(Node node, VirtualFrame vFrame) { if (nextInstrumentNode != null) { nextInstrumentNode.returnVoid(node, vFrame); @@ -464,7 +491,7 @@ public String instrumentationInfo() { final String info = getInstrumentInfo(); - return info != null ? info : toolEvalNodeFactory.getClass().getSimpleName(); + return info != null ? info : rootFactory.getClass().getSimpleName(); } } }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/ToolEvalNode.java Tue May 12 23:26:16 2015 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,51 +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. Oracle designates this - * particular file as subject to the "Classpath" exception as provided - * by Oracle in the LICENSE file that accompanied this code. - * - * 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.truffle.api.instrument; - -import com.oracle.truffle.api.frame.*; -import com.oracle.truffle.api.nodes.*; - -/** - * Root of a client-provided AST fragment that can be executed efficiently, subject to full Truffle - * optimization, by a {@linkplain Instrument#create(ToolEvalNodeFactory, String) Tool Eval - * Instrument}. - * - * @see Instrument - * @see ToolEvalNodeFactory - * @see ToolEvalResultListener - */ -public abstract class ToolEvalNode extends Node implements InstrumentationNode { - - /** - * Executes this AST fragment on behalf of a client {@link Instrument}, just before the - * guest-language AST node to which the {@link Probe} holding the Instrument is executed. - * - * @param node the guest-language AST node to which the host Instrument's Probe is attached - * @param vFrame execution frame at the guest-language AST node - * @return the result of this AST fragment's execution - */ - public abstract Object executeToolEvalNode(Node node, VirtualFrame vFrame); - -}
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/ToolEvalNodeFactory.java Tue May 12 23:26:16 2015 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,51 +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. Oracle designates this - * particular file as subject to the "Classpath" exception as provided - * by Oracle in the LICENSE file that accompanied this code. - * - * 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.truffle.api.instrument; - -import com.oracle.truffle.api.nodes.*; - -/** - * Creator of {@linkplain ToolEvalNode AST fragments} suitable for efficient execution, subject to - * full Truffle optimization, by a {@linkplain Instrument#create(ToolEvalNodeFactory, String) Tool - * Eval Instrument}. - * - * @see Instrument - * @see ToolEvalNode - */ -public interface ToolEvalNodeFactory { - - /** - * Provider of {@linkplain ToolEvalNode AST fragment} instances for efficient execution via - * instrumentation, subject to full Truffle optimization, at a {@linkplain Probe Probed} site in - * a guest-language AST. - * - * @param probe the Probe to which the Instrument requesting the AST fragment is attached - * @param node the guest-language AST location that is the context in which the requesting - * Instrument must execute the AST fragment. - * @return a newly created AST fragment suitable for execution, via instrumentation, in the - * execution context of the specified guest-language AST site. - */ - ToolEvalNode createToolEvalNode(Probe probe, Node node); -}
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/ToolEvalResultListener.java Tue May 12 23:26:16 2015 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,64 +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. Oracle designates this - * particular file as subject to the "Classpath" exception as provided - * by Oracle in the LICENSE file that accompanied this code. - * - * 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.truffle.api.instrument; - -import com.oracle.truffle.api.frame.*; -import com.oracle.truffle.api.nodes.*; - -/** - * Listener for receiving the result a client-provided {@linkplain ToolEvalNode AST fragment}, when - * executed by a {@linkplain Instrument#create(ToolEvalNodeFactory, String) Tool Eval Instrument}. - * - * @see Instrument - * @see ToolEvalNode - * @see ToolEvalNodeFactory - */ -public interface ToolEvalResultListener { - - /** - * Notifies listener that a client-provided {@linkplain ToolEvalNode AST fragment} has been - * executed by a {@linkplain Instrument#create(ToolEvalNodeFactory, String) Tool Eval - * Instrument} with the specified result, possibly {@code null}. - * - * @param node the guest-language AST node to which the host Instrument's {@link Probe} is - * attached - * @param vFrame execution frame at the guest-language AST node - * @param result the result of this AST fragment's execution - */ - void notifyToolEvalResult(Node node, VirtualFrame vFrame, Object result); - - /** - * Notifies listener that execution of client-provided {@linkplain ToolEvalNode AST fragment} - * filed during execution by a @linkplain Instrument#create(ToolEvalNodeFactory, String) Tool - * Eval Instrument}. - * - * @param node the guest-language AST node to which the host Instrument's {@link Probe} is - * attached - * @param vFrame execution frame at the guest-language AST node - * @param ex the exception - */ - void notifyToolEvalFailure(Node node, VirtualFrame vFrame, RuntimeException ex); - -}