changeset 21355:442b57a7f208

Truffle/Instrumentation: change the signature for creation of Advanced instruments, refactor how the callback listener is managed.
author Michael Van De Vanter <michael.van.de.vanter@oracle.com>
date Tue, 12 May 2015 16:06:00 -0700
parents 575032310b2c
children e34bc00733d1
files graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/InstrumentationPartialEvaluationTest.java graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/AdvancedInstrumentTest.java graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentResultListener.java graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRoot.java graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRootFactory.java graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrument.java
diffstat 6 files changed, 38 insertions(+), 46 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/InstrumentationPartialEvaluationTest.java	Tue May 12 14:48:33 2015 -0700
+++ b/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/InstrumentationPartialEvaluationTest.java	Tue May 12 16:06:00 2015 -0700
@@ -212,13 +212,12 @@
         root.adoptChildren();
         Probe testProbe = result.probe();
         // A factory that could insert a AdvancedInstrumentRoot into the AST, but which never does.
-        Instrument instrument = Instrument.create(new AdvancedInstrumentRootFactory(null) {
+        Instrument instrument = Instrument.create(null, new AdvancedInstrumentRootFactory() {
 
-            @Override
             public AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node) {
                 return null;
             }
-        }, null);
+        }, "test AdvancedInstrument");
         testProbe.attach(instrument);
 
         // It all gets compiled away
@@ -233,13 +232,12 @@
         rootTestNode.adoptChildren();
         Probe testProbe = resultTestNode.probe();
         // Factory inserts a AdvancedInstrumentRoot with empty methods into instrumentation .
-        Instrument instrument = Instrument.create(new AdvancedInstrumentRootFactory(null) {
+        Instrument instrument = Instrument.create(null, new AdvancedInstrumentRootFactory() {
 
             @Override
             public AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node) {
                 return new AdvancedInstrumentRoot() {
 
-                    @Override
                     public String instrumentationInfo() {
                         return null;
                     }
@@ -250,7 +248,7 @@
                     }
                 };
             }
-        }, null);
+        }, "test AdvancedInstrument");
         testProbe.attach(instrument);
 
         // It all gets compiled away.
--- a/graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/AdvancedInstrumentTest.java	Tue May 12 14:48:33 2015 -0700
+++ b/graal/com.oracle.truffle.api.test/src/com/oracle/truffle/api/test/instrument/AdvancedInstrumentTest.java	Tue May 12 16:06:00 2015 -0700
@@ -41,7 +41,7 @@
 public class AdvancedInstrumentTest {
 
     @Test
-    public void testSpliceInstrumentListener() {
+    public void testAdvancedInstrumentListener() {
         // Create a simple addition AST
         final TruffleRuntime runtime = Truffle.getRuntime();
         final TestValueNode leftValueNode = new TestValueNode(6);
@@ -59,13 +59,12 @@
         assertEquals(13, callTarget1.call());
 
         // Attach a null factory; it never actually attaches a node.
-        final Instrument instrument = Instrument.create(new AdvancedInstrumentRootFactory(null) {
+        final Instrument instrument = Instrument.create(null, new AdvancedInstrumentRootFactory() {
 
-            @Override
             public AdvancedInstrumentRoot createInstrumentRoot(Probe p, Node n) {
                 return null;
             }
-        }, null);
+        }, "test AdvancedInstrument");
         probe.attach(instrument);
 
         assertEquals(13, callTarget1.call());
@@ -73,19 +72,16 @@
         final TestAdvancedInstrumentCounterRoot counter = new TestAdvancedInstrumentCounterRoot();
 
         // Attach a factory that splices an execution counter into the AST.
-        probe.attach(Instrument.create(new AdvancedInstrumentRootFactory(null) {
+        probe.attach(Instrument.create(null, new AdvancedInstrumentRootFactory() {
 
-            @Override
             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/src/com/oracle/truffle/api/instrument/AdvancedInstrumentResultListener.java	Tue May 12 14:48:33 2015 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentResultListener.java	Tue May 12 16:06:00 2015 -0700
@@ -31,7 +31,8 @@
 /**
  * Listener for receiving the result a client-provided {@linkplain AdvancedInstrumentRoot AST
  * fragment}, when executed by a
- * {@linkplain Instrument#create(AdvancedInstrumentRootFactory, String) Advanced Instrument}.
+ * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, String)
+ * Advanced Instrument}.
  *
  * @see Instrument
  * @see AdvancedInstrumentRoot
@@ -41,12 +42,13 @@
 
     /**
      * Notifies listener that a client-provided {@linkplain AdvancedInstrumentRoot AST fragment} has
-     * been executed by an {@linkplain Instrument#create(AdvancedInstrumentRootFactory, String)
+     * been executed by an
+     * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, 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
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRoot.java	Tue May 12 14:48:33 2015 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRoot.java	Tue May 12 16:06:00 2015 -0700
@@ -29,8 +29,9 @@
 
 /**
  * Root of a client-provided AST fragment that can be executed efficiently, subject to full Truffle
- * optimization, by an {@linkplain Instrument#create(AdvancedInstrumentRootFactory, String) Advanced
- * Instrument}.
+ * optimization, by an
+ * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, String)
+ * Advanced Instrument}.
  *
  * @see Instrument
  * @see AdvancedInstrumentRootFactory
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRootFactory.java	Tue May 12 14:48:33 2015 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/AdvancedInstrumentRootFactory.java	Tue May 12 16:06:00 2015 -0700
@@ -29,14 +29,13 @@
 /**
  * Creator of {@linkplain AdvancedInstrumentRoot AST fragments} suitable for efficient execution,
  * subject to full Truffle optimization, by an
- * {@linkplain Instrument#create(AdvancedInstrumentRootFactory, String) Advanced Instrument}.
+ * {@linkplain Instrument#create(AdvancedInstrumentResultListener, AdvancedInstrumentRootFactory, String)
+ * Advanced Instrument}.
  *
  * @see Instrument
  * @see AdvancedInstrumentRoot
  */
-public abstract class AdvancedInstrumentRootFactory {
-
-    private final AdvancedInstrumentResultListener resultListener;
+public interface AdvancedInstrumentRootFactory {
 
     /**
      * Provider of {@linkplain AdvancedInstrumentRoot AST fragment} instances for efficient
@@ -49,17 +48,5 @@
      * @return a newly created AST fragment suitable for execution, via instrumentation, in the
      *         execution context of the specified guest-language AST site.
      */
-    public abstract AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node);
-
-    /**
-     * Gets the listener, if one was specified, to notify with the result of executing every
-     * {@link AdvancedInstrumentRoot} created by this factory.
-     */
-    public final AdvancedInstrumentResultListener resultListener() {
-        return resultListener;
-    }
-
-    protected AdvancedInstrumentRootFactory(AdvancedInstrumentResultListener resultListener) {
-        this.resultListener = resultListener;
-    }
+    AdvancedInstrumentRoot createInstrumentRoot(Probe probe, Node node);
 }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrument.java	Tue May 12 14:48:33 2015 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrument.java	Tue May 12 16:06:00 2015 -0700
@@ -131,12 +131,13 @@
      * full Truffle optimization, a client-provided AST fragment every time the Probed node is
      * entered.
      *
+     * @param resultListener optional client callback for results/failure notification
      * @param rootFactory provider of AST fragments on behalf of the client
      * @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(AdvancedInstrumentRootFactory rootFactory, String instrumentInfo) {
-        return new AdvancedInstrument(rootFactory, instrumentInfo);
+    public static Instrument create(AdvancedInstrumentResultListener resultListener, AdvancedInstrumentRootFactory rootFactory, String instrumentInfo) {
+        return new AdvancedInstrument(resultListener, rootFactory, instrumentInfo);
     }
 
     // TODO (mlvdv) experimental
@@ -381,13 +382,15 @@
      */
     private static final class AdvancedInstrument extends Instrument {
 
+        private final AdvancedInstrumentResultListener resultListener;
         /**
          * Client-provided supplier of new node instances to attach.
          */
         private final AdvancedInstrumentRootFactory rootFactory;
 
-        private AdvancedInstrument(AdvancedInstrumentRootFactory rootFactory, String instrumentInfo) {
+        private AdvancedInstrument(AdvancedInstrumentResultListener resultListener, AdvancedInstrumentRootFactory rootFactory, String instrumentInfo) {
             super(instrumentInfo);
+            this.resultListener = resultListener;
             this.rootFactory = rootFactory;
 
         }
@@ -428,15 +431,20 @@
 
             public void enter(Node node, VirtualFrame vFrame) {
                 if (instrumentRoot == null) {
-                    final AdvancedInstrumentRoot newInstrumentRoot = AdvancedInstrument.this.rootFactory.createInstrumentRoot(AdvancedInstrument.this.probe, node);
-                    if (newInstrumentRoot != null) {
-                        instrumentRoot = newInstrumentRoot;
-                        adoptChildren();
-                        AdvancedInstrument.this.probe.invalidateProbeUnchanged();
+                    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 (instrumentRoot != null) {
-                    final AdvancedInstrumentResultListener resultListener = AdvancedInstrument.this.rootFactory.resultListener();
                     try {
                         final Object result = instrumentRoot.executeRoot(node, vFrame);
                         if (resultListener != null) {