Mercurial > hg > truffle
changeset 22224:776dc0a09749
Truffle/Instrumentation: Javadoc
author | Michael Van De Vanter <michael.van.de.vanter@oracle.com> |
---|---|
date | Sat, 19 Sep 2015 13:56:42 -0700 |
parents | 964e789e17f7 |
children | a0fa69e3e60e |
files | truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrumenter.java truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Probe.java |
diffstat | 2 files changed, 90 insertions(+), 78 deletions(-) [+] |
line wrap: on
line diff
--- a/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrumenter.java Sat Sep 19 13:26:06 2015 -0700 +++ b/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Instrumenter.java Sat Sep 19 13:56:42 2015 -0700 @@ -110,7 +110,8 @@ } /** - * Returns {@code true} if the node can be "instrumented" by {@linkplain #probe(Node) probing}. + * Returns {@code true} if the AST node can be "instrumented" by {@linkplain #probe(Node) + * Probing}. * <p> * <b>Note:</b> instrumentation requires a appropriate {@linkplain #createWrapperNode(Node) * WrapperNode}. @@ -120,11 +121,11 @@ } /** - * For nodes that are {@linkplain #isInstrumentable() instrumentable}, this method must return - * an {@linkplain Node AST node} that: + * For AST nodes that are {@linkplain #isInstrumentable() instrumentable}, returns a + * <em>wrapper node</em> that: * <ol> * <li>implements {@link WrapperNode}</li> - * <li>has the node argument as it's child, and</li> + * <li>has the node as its single child, and</li> * <li>whose type is safe for replacement of the node in the parent.</li> * </ol> * @@ -135,13 +136,19 @@ } /** - * Enables {@linkplain Instrument instrumentation} of a node, where the node is presumed to be - * part of a well-formed Truffle AST that is not being executed. If this node has not already - * been probed, modifies the AST by inserting a {@linkplain WrapperNode wrapper node} between - * the node and its parent; the wrapper node must be provided by implementations of - * {@link Node#createWrapperNode()}. No more than one {@link Probe} may be associated with a - * node, so a {@linkplain WrapperNode wrapper} may not wrap another {@linkplain WrapperNode - * wrapper}. + * Prepares an AST node for {@linkplain Instrument instrumentation}, where the node is presumed + * to be part of a well-formed Truffle AST that has not yet been executed. + * <p> + * <em>Probing</em> a node is idempotent: + * <ul> + * <li>If the node has not been Probed, modifies the AST by first inserting a + * {@linkplain #createWrapperNode(Node) wrapper node} between the node and its parent and then + * returning the newly created Probe associated with the wrapper.</li> + * <li>If the node has been Probed, returns the Probe associated with its existing wrapper.</li> + * <li>No more than one {@link Probe} may be associated with a node, so a wrapper may not wrap + * another wrapper.</li> + * </ul> + * It is a runtime error to attempt Probing an AST node with no parent. * * @return a (possibly newly created) {@link Probe} associated with this node. * @throws ProbeException (unchecked) when a probe cannot be created, leaving the AST unchanged
--- a/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Probe.java Sat Sep 19 13:26:06 2015 -0700 +++ b/truffle/com.oracle.truffle.api/src/com/oracle/truffle/api/instrument/Probe.java Sat Sep 19 13:56:42 2015 -0700 @@ -43,61 +43,21 @@ /** * A <em>binding</em> between: * <ol> - * <li>A program location in an executing Truffle AST (corresponding to a {@link SourceSection}), - * and</li> - * <li>A dynamically managed collection of "attached" {@linkplain Instrument Instruments} that - * receive event notifications on behalf of external clients.</li> + * <li>A <em>guest language program location</em> in an executing Truffle AST (corresponding to a + * {@link SourceSection}), and</li> + * <li>A dynamically managed collection of <em>attached</em> {@linkplain Instrument Instruments} + * that receive event notifications from the Probe's AST location on behalf of external clients.</li> * </ol> + * <strong>Note</strong>:The relationship must be with an AST <em>location</em>, not a specific + * {@link Node}, because ASTs are routinely <em>cloned</em> at runtime. An AST <em>location</em> is + * best represented as the {@link SourceSection} from which the original AST Node was created. * <p> * Client-oriented documentation for the use of Probes is available online at <a * HREF="https://wiki.openjdk.java.net/display/Graal/Finding+Probes" >https://wiki.openjdk.java. * net/display/Graal/Finding+Probes</a> * <p> - * <h4>Implementation notes:</h4> - * <p> - * <ul> - * <li>A Probe must be permanently associated with a <em>program location</em>, defined by a - * particular {@link SourceSection}, even though: - * <ul> - * <li>that location is represented in an AST as a {@link Node}, which might be replaced through - * optimizations such as specialization, and</li> - * <li>Truffle may <em>clone</em> the AST so that the location is actually represented by multiple - * Nodes in multiple ASTs.</li> - * </ul> - * </li> * - * <li>The effect of the binding is to intercept {@linkplain TruffleEvents execution events} - * arriving at the "probed" AST Node and notify each attached {@link Instrument} before execution is - * allowed to proceed to the child and again after execution completes.</li> - * - * <li>The method {@link Instrumenter#probe(Node)} creates a Probe on an AST Node; redundant calls - * return the same Probe.</li> - * - * <li>The "probing" of a Truffle AST must be done after the AST is complete (i.e. parent pointers - * correctly assigned), but before any cloning or executions. This is done by applying instances of - * {@link ASTProber} provided by each language implementation, combined with any instances - * registered by tools via {@link Instrumenter#registerASTProber(ASTProber)}. Once registered, these - * will be applied automatically to every newly created AST.</li> - * - * <li>The "probing" of an AST Node is implemented by insertion of a {@link ProbeNode.WrapperNode} - * into the AST (as new parent of the Node being probed), together with an associated - * {@link ProbeNode} that routes execution events at the probed Node to all the - * {@linkplain Instrument Instruments} attached to the Probe's <em>instrument chain</em>.</li> - * - * <li>When Truffle clones an AST, any attached WrapperNodes and ProbeNodes are cloned as well, - * together with their attached instrument chains. Each Probe instance intercepts cloning events and - * keeps track of all AST copies.</li> - * - * <li>All attached {@link InstrumentationNode}s effectively become part of the running program: - * <ul> - * <li>Good News: instrumentation code implicitly benefits from every kind of Truffle optimization.</li> - * <li>Bad News: instrumentation code must be implemented carefully to avoid interfering with any - * Truffle optimizations.</li> - * </ul> - * </li> - * - * </ul> - * + * @see Instrumenter * @see Instrument * @see ASTProber * @see ProbeListener @@ -141,7 +101,51 @@ @CompilationFinal private boolean isAfterTrapActive = false; /** - * Intended for use only by {@link ProbeNode}. + * Constructor for use only by {@link ProbeNode}. + * <p> + * <h4>Probe Implementation notes:</h4> + * <p> + * <ul> + * <li>A Probe must be permanently associated with a <em>program location</em>, defined by a + * particular {@link SourceSection}, even though: + * <ul> + * <li>that location is represented in an AST as a {@link Node}, which might be replaced through + * optimizations such as specialization, and</li> + * <li>Truffle may <em>clone</em> the AST so that the location is actually represented by + * multiple Nodes in multiple ASTs.</li> + * </ul> + * </li> + * <li>The effect of the binding is to intercept {@linkplain TruffleEvents execution events} + * arriving at the "probed" AST Node and notify each attached {@link Instrument} before + * execution is allowed to proceed to the child and again after execution completes.</li> + * + * <li>The method {@link Instrumenter#probe(Node)} creates a Probe on an AST Node; redundant + * calls return the same Probe.</li> + * + * <li>The "probing" of a Truffle AST must be done after the AST is complete (i.e. parent + * pointers correctly assigned), but before any cloning or executions. This is done by applying + * instances of {@link ASTProber} provided by each language implementation, combined with any + * instances registered by tools via {@link Instrumenter#registerASTProber(ASTProber)}. Once + * registered, these will be applied automatically to every newly created AST.</li> + * + * <li>The "probing" of an AST Node is implemented by insertion of a + * {@link ProbeNode.WrapperNode} into the AST (as new parent of the Node being probed), together + * with an associated {@link ProbeNode} that routes execution events at the probed Node to all + * the {@linkplain Instrument Instruments} attached to the Probe's <em>instrument chain</em>.</li> + * + * <li>When Truffle clones an AST, any attached WrapperNodes and ProbeNodes are cloned as well, + * together with their attached instrument chains. Each Probe instance intercepts cloning events + * and keeps track of all AST copies.</li> + * + * <li>All attached {@link InstrumentationNode}s effectively become part of the running program: + * <ul> + * <li>Good News: instrumentation code implicitly benefits from every kind of Truffle + * optimization.</li> + * <li>Bad News: instrumentation code must be implemented carefully to avoid interfering with + * any Truffle optimizations.</li> + * </ul> + * </li> + * </ul> */ Probe(Instrumenter instrumenter, Class<? extends TruffleLanguage> l, ProbeNode probeNode, SourceSection sourceSection) { this.instrumenter = instrumenter; @@ -151,22 +155,6 @@ } /** - * Is this node tagged as belonging to a particular human-sensible category of language - * constructs? - */ - public boolean isTaggedAs(SyntaxTag tag) { - assert tag != null; - return tags.contains(tag); - } - - /** - * In which user-sensible categories has this node been tagged (<em>empty set</em> if none). - */ - public Collection<SyntaxTag> getSyntaxTags() { - return Collections.unmodifiableCollection(tags); - } - - /** * Adds a {@linkplain SyntaxTag tag} to the set of tags associated with this {@link Probe}; * {@code no-op} if already in the set. */ @@ -198,6 +186,23 @@ } /** + * Is the <em>Probed node</em> tagged as belonging to a particular human-sensible category of + * language constructs? + */ + public boolean isTaggedAs(SyntaxTag tag) { + assert tag != null; + return tags.contains(tag); + } + + /** + * In which user-sensible categories has the <em>Probed node</em> been tagged ( + * <em>empty set</em> if none). + */ + public Collection<SyntaxTag> getSyntaxTags() { + return Collections.unmodifiableCollection(tags); + } + + /** * Adds instrumentation at this Probe. * * @param instrument an instrument not yet attached to a probe @@ -221,8 +226,8 @@ } /** - * Gets the {@link SourceSection} associated with the Guest Language AST node being - * instrumented, possibly {@code null}. + * Gets the {@link SourceSection} associated with the <en>Probed AST node</em>, possibly + * {@code null}. */ public SourceSection getProbedSourceSection() { return sourceSection;