Interpreter.invoke and captured values

Paul Sandoz paul.sandoz at oracle.com
Thu Oct 10 23:45:12 UTC 2024


Recently Maurizio encountered a nasty issue when using the Interpreter to interpret the code model of a capturing lambda expression - the captured runtime arguments were unintentionally included in the var args list. That’s hard to debug.

The captured runtime arguments is represented as a map of captured symbolic value to associated captured runtime value. It is most commonly obtained from a Quoted instance and just passed along to the Interpreter.invoke method. The map is ordered on the order of captured symbolic values first used when encountered by traversing the model.

Currently captured values are not supported by the bytecode generator when generating bytecode for the code model of a lambda expression. (They are supported for code models that contain lambda expressions.) When we support that it would be nice to have some consistency.

It is tempting to support just one list of arguments, first containing the sequence of actual arguments and then containing the sequence of captured arguments (in order). However it is a pain to concatenate two sequences into one sequence e.g.,

  Quoted q = …
  Map<Value, Object> capturedValues = q.capturedValues();

  var args = new ArrayList<>(List.of(a, b, c));
  args.addAll(capturedValues.values());
  var r = Interpreter.invoke(lookup, lambdaOp, args);

Maybe we just live with that for now?

—

Separately we should clarify the distinction between captured symbolic values and captured runtime values. Capturing does seem an applicable term to use in both cases - symbolic and runtime. Given some operation, O say, it may capture a symbolic value, a value which dominates O and is used by a descendant operation. That can apply conceptually to the modeling of any nested language construct, and therefore it can apply to anything we can quote in a model and expose as a Quoted instance. It is not limited to the modeling of lambda expressions, where users will be familiar with lambdas capturing the values of final or effectively final variables. But, it’s easy to see how users might get confused.

Paul.



More information about the babylon-dev mailing list