-
Notifications
You must be signed in to change notification settings - Fork 323
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Inline Execution #8148
Inline Execution #8148
Conversation
...ment-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala
Outdated
Show resolved
Hide resolved
...polyglot/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala
Outdated
Show resolved
Hide resolved
...runtime-instrument-common/src/main/java/org/enso/interpreter/service/ExecutionCallbacks.java
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
According to Marcin, this is what we should do...
...polyglot/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala
Outdated
Show resolved
Hide resolved
...ment-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala
Outdated
Show resolved
Hide resolved
...ment-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala
Outdated
Show resolved
Hide resolved
fc5a0c3
to
1bba491
Compare
...polyglot/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala
Show resolved
Hide resolved
...polyglot/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala
Show resolved
Hide resolved
...polyglot/src/test/scala/org/enso/interpreter/test/instrument/RuntimeVisualizationsTest.scala
Show resolved
Hide resolved
...rument-id-execution/src/main/java/org/enso/interpreter/instrument/IdExecutionInstrument.java
Outdated
Show resolved
Hide resolved
...ime/src/main/java/org/enso/interpreter/node/expression/builtin/meta/InstrumentorBuiltin.java
Outdated
Show resolved
Hide resolved
engine/runtime/src/main/java/org/enso/interpreter/runtime/Module.java
Outdated
Show resolved
Hide resolved
engine/runtime/src/main/java/org/enso/interpreter/runtime/Module.java
Outdated
Show resolved
Hide resolved
...nstrument-common/src/main/java/org/enso/interpreter/instrument/job/ExecuteExpressionJob.java
Show resolved
Hide resolved
...t-common/src/main/java/org/enso/interpreter/instrument/command/ExecuteExpressionCommand.java
Show resolved
Hide resolved
...runtime-instrument-common/src/main/java/org/enso/interpreter/service/ExecutionCallbacks.java
Outdated
Show resolved
Hide resolved
...ment-common/src/main/scala/org/enso/interpreter/instrument/job/ProgramExecutionSupport.scala
Outdated
Show resolved
Hide resolved
1bba491
to
a77971e
Compare
val compilerOutput = runCompilerPhasesInline(ir, newContext) | ||
runErrorHandlingInline(compilerOutput, source, newContext) | ||
Some((newContext, compilerOutput, source)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Doing flatMap
and then Some
is strange. map
is better.
...runtime-instrument-common/src/main/java/org/enso/interpreter/service/ExecutionCallbacks.java
Show resolved
Hide resolved
engine/polyglot-api/src/main/java/org/enso/polyglot/debugger/IdExecutionService.java
Outdated
Show resolved
Hide resolved
...rument-id-execution/src/main/java/org/enso/interpreter/instrument/IdExecutionInstrument.java
Outdated
Show resolved
Hide resolved
...rument-id-execution/src/main/java/org/enso/interpreter/instrument/IdExecutionInstrument.java
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The current state looks OK to me - the changes seems mostly cosmetic. I will leave the final word to @JaroslavTulach
idExecutionInstrument.map( | ||
service -> | ||
service.bind( | ||
module, call.getFunction().getCallTarget(), callbacks, this.timer)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@4e6 spent quite a long time to explain me that there are multiple visualizations hidden behind this single bind. With such information it is clear that my original API design proposal cannot work. Here is the modified one:
diff --git engine/polyglot-api/src/main/java/org/enso/polyglot/debugger/IdExecutionService.java engine/polyglot-api/src/main/java/org/enso/polyglot/debugger/IdExecutionService.java
index fc8e712796..eac7025a08 100644
--- engine/polyglot-api/src/main/java/org/enso/polyglot/debugger/IdExecutionService.java
+++ engine/polyglot-api/src/main/java/org/enso/polyglot/debugger/IdExecutionService.java
@@ -9,37 +9,56 @@ import java.util.UUID;
public interface IdExecutionService {
String INSTRUMENT_ID = "id-value-extractor";
+ public abstract class Info {
+ protected Info() {
+ assert getClass().getName().equals("org.enso....InfoImpl");
+ }
+
+ /** @return UUID of the node, never {@code null} */
+ public abstract UUID getUuid();
+ /** @return associated result or {@code null} if there is no associated result */
+ public abstract Object getResult();
+
+ /** @return {@code true} when the result is panic, {@code false} otherwise */
+ public abstract boolean isPanic();
+
+ /** @return time (in nanoseconds) needed to compute the result or {@code -1} when not available */
+ public abstract long getElapsedTime();
+
+ /** Evaluates given code in the context of current UUID location.
+ * @param code the Enso code to evaluate
+ * @return result of the evaluation
+ */
+ public abstract Object eval(String code);
+ }
+
public interface Callbacks {
/**
* Finds out previously computed result for given id. If a result is returned, then the
* execution of given node is skipped and the value is returned back.
*
- * @param nodeId identification of the node to be computed
+ * @param info info with UUID the node to be computed
* @return {@code null} should the execution of the node be performed; any other value to skip
* the execution and return the value as a result.
*/
- Object findCachedResult(Object materializedFrame, Object node, UUID nodeId);
+ Object findCachedResult(Info info);
/**
* Notifies when an execution of a node is over.
*
- * @param nodeId expression node id that has been computed
- * @param result the just computed result
- * @param isPanic was the result a panic?
- * @param nanoElapsedTime how long it took to compute the result?
+ * @param info info with node id, {@link Info#getResult()}, {@link Info#isPanic()} and {@link Info#getElapsedTime()}
*/
- void updateCachedResult(UUID nodeId, Object result, boolean isPanic, long nanoElapsedTime);
+ void updateCachedResult(Info info);
/**
* Notification when a returned value is a function.
*
- * @param nodeId identification of the node to be computed
- * @param result info about function call
+ * @param info with identification of the node and {@link Info#getResult() info about function call}
* @return {@code null} should the execution of the node be performed; any other value to skip
* the execution and return the value as a result.
*/
- Object onFunctionReturn(UUID nodeId, TruffleObject result);
+ Object onFunctionReturn(Info info);
}
/**
The new suggestion adds Info.eval(String)
method which can be used by visualization to evaluate any code at given UUID location. Each visualization with associated expression can call this method with its own code to evaluate. The implementation inserts EvalNode
into IdExecutionEventNode
and uses it to evaluate the code.
There is a new Info
class - an implementation of API vs. SPI pattern which is going to be implemented by IdExecutionInstrument
and will have a reference to appropriate IdExecutionEventNode
. Having an Info
class there shall help us with future evolution of additional arguments - shall more of them be needed.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- I am concerned about "speed" of
eval
at current state. Please measure. - I'd like to keep consistency of
Meta.Instrumentor
- add the same functionality there - otherwise OK, approving.
fun1 x = x.to_text | ||
``` | ||
|
||
- You can execute an expression in the context of a function body. In this case, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
- You can execute an expression in the context of a function body. In this case, | |
- You can execute an expression in the context of 'main' function body. In this case, |
``` | ||
|
||
- You can execute an expression in the context of a function body. In this case, | ||
the `expressionId` should point to the body of a function. E.g. in the context |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the `expressionId` should point to the body of a function. E.g. in the context | |
the `expressionId` should point to the body of the `main` function. Then the available symbols |
|
||
- You can execute an expression in the context of a function body. In this case, | ||
the `expressionId` should point to the body of a function. E.g. in the context | ||
of `main` available symbols are `operator1`, `operator2` and `fun1`. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
of `main` available symbols are `operator1`, `operator2` and `fun1`. | |
are `operator1`, `operator2` and `fun1`. |
* @return {@code null} should the execution of the node be performed; any other value to skip | ||
* the execution and return the value as a result. | ||
*/ | ||
Object onFunctionReturn(UUID nodeId, TruffleObject result); | ||
Object onFunctionReturn(Info info); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you, @4e6, for trying to use this design with Info
.
Object visualizationResult = null; | ||
Throwable visualizationError = null; | ||
try { | ||
visualizationResult = info.eval(oneshotExpression.expression()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here is the usage of Info.eval
, OK.
...rument-id-execution/src/main/java/org/enso/interpreter/instrument/IdExecutionInstrument.java
Show resolved
Hide resolved
...ne/runtime/src/main/java/org/enso/interpreter/node/expression/builtin/meta/Instrumentor.java
Show resolved
Hide resolved
Fixes a random crash (*) during instrumentation. Notice how `onTailCallReturn` calls `onReturnValue` with `null` frame. Bonus: noticed that for some reason we weren't getting logs for `ExecutionService`. This turned out to be the problem with the logger name which by default was `[enso]` not `[enso.org.enso.interpreter.service.ExecutionService`] and there is some logic there that normalizes the name and assumed a dot after `enso`. This change fixes the logic. (*) ``` [enso.org.enso.interpreter.service.ExecutionService] Execution of function main failed (Cannot invoke "com.oracle.truffle.api.frame.VirtualFrame.materialize()" because "frame" is null). java.lang.NullPointerException: Cannot invoke "com.oracle.truffle.api.frame.VirtualFrame.materialize()" because "frame" is null at org.enso.interpreter.instrument.IdExecutionInstrument$IdEventNodeFactory$IdExecutionEventNode.onReturnValue(IdExecutionInstrument.java:246) at org.enso.interpreter.instrument.IdExecutionInstrument$IdEventNodeFactory$IdExecutionEventNode.onTailCallReturn(IdExecutionInstrument.java:274) at org.enso.interpreter.instrument.IdExecutionInstrument$IdEventNodeFactory$IdExecutionEventNode.onReturnExceptional(IdExecutionInstrument.java:258) at org.graalvm.truffle/com.oracle.truffle.api.instrumentation.ProbeNode$EventProviderChainNode.innerOnReturnExceptional(ProbeNode.java:1395) at org.graalvm.truffle/com.oracle.truffle.api.instrumentation.ProbeNode$EventChainNode.onReturnExceptional(ProbeNode.java:1031) at org.graalvm.truffle/com.oracle.truffle.api.instrumentation.ProbeNode.onReturnExceptionalOrUnwind(ProbeNode.java:296) at org.enso.interpreter.node.ExpressionNodeWrapper.executeGeneric(ExpressionNodeWrapper.java:119) at org.enso.interpreter.node.ClosureRootNode.execute(ClosureRootNode.java:85) at jdk.internal.vm.compiler/org.graalvm.compiler.truffle.runtime.OptimizedCallTarget.executeRootNode(OptimizedCallTarget.java:718) at jdk.internal.vm.compiler/org.graalvm.compiler.truffle.runtime.OptimizedCallTarget.profiledPERoot(OptimizedCallTarget.java:641) at jdk.internal.vm.compiler/org.graalvm.compiler.truffle.runtime.OptimizedCallTarget.callBoundary(OptimizedCallTarget.java:574) at jdk.internal.vm.compiler/org.graalvm.compiler.truffle.runtime.OptimizedCallTarget.doInvoke(OptimizedCallTarget.java:558) at jdk.internal.vm.compiler/org.graalvm.compiler.truffle.runtime.OptimizedCallTarget.callDirect(OptimizedCallTarget.java:504) at jdk.internal.vm.compiler/org.graalvm.compiler.truffle.runtime.OptimizedDirectCallNode.call(OptimizedDirectCallNode.java:69) at org.enso.interpreter.node.callable.thunk.ThunkExecutorNode.doCached(ThunkExecutorNode.java:69) at org.enso.interpreter.node.callable.thunk.ThunkExecutorNodeGen.executeAndSpecialize(ThunkExecutorNodeGen.java:207) at org.enso.interpreter.node.callable.thunk.ThunkExecutorNodeGen.executeThunk(ThunkExecutorNodeGen.java:167) ... ``` # Important Notes Fixes regressions introduced in #8148 and #8162
Pull Request Description
close #8132
Update the
executionContext/executeExpression
request to execute expressions in the local scope.Important Notes
Checklist
Please ensure that the following checklist has been satisfied before submitting the PR:
Scala,
Java,
and
Rust
style guides. In case you are using a language not listed above, follow the Rust style guide.