Details
-
Type:
New Feature
-
Status:
Open
-
Priority:
Critical
-
Resolution: Unresolved
-
Affects Version/s: None
-
Fix Version/s: X10 2.3.2
-
Component/s: X10 Compiler: Front-end
-
Labels:None
-
Number of attachments :
Description
Some closures (in particular those generated by the lowerer to implement at and async) need to capture an lval instead of an rval. When generating code for such closures, the backends need to know whether it is the lval or rval of a variable that is being captured. The proposal is to split the closure environment capture information into two lists: lvals and rvals instead of one and then use that information instead of the asyncInit in the backends.
A test case that illustrates the various issues is appended. In particular, in TestValInitUsingAt in the two closures coming from the first set of at statements the lval is captured, but in the two closures coming from the second set of ats the rval is captured.
public class Hello { public static def main(args: Array[String]) { TestValInitUsingAt.testVal(); TestValInitUsingAt.testVar(); } } class TestValInitUsingAt { static def testVal() { val x_tmp1:Int; val p = here; at (p.next()) at (p) x_tmp1 = 2; val x = x_tmp1; Console.OUT.println("should be 2: "+x); at (p.next()) at (p) Console.OUT.println("should be 2: "+x_tmp1); } static def testVar() { var x_tmp2:Int; val p = here; at (p.next()) at (p) x_tmp2 = 2; val x = x_tmp2; Console.OUT.println("should be 2: "+x); x_tmp2 = 100; at (p.next()) { at (p) { Console.OUT.println("should be 100: "+x_tmp2); x_tmp2 = 200; Console.OUT.println("should be 200: "+x_tmp2); } } Console.OUT.println("should be 200: "+x_tmp2); } }
Issue Links
- depends upon
-
XTENLANG-2469
Implement new 'at' and 'athome' constructs.
-
-
XTENLANG-2660
Remove ability for code in an at statement/expr to assign a local variable declared outside the at statement/expr
-
- is depended upon by
-
XTENLANG-1942
Support definite-assignment (remote-init) using "at"
-
-
XTENLANG-2585
XTENLANG_2440 fails to run
-
This can be done in the frontend by providing the capture info as two sets: lvals and rvals. The frontend can detect that a variable is assigned inside an "at" or an "async" and add it to the lvals set. A use of the variable should be included in lvals if it's also assigned elsewhere in the closure and in rvals otherwise.
Currently, the frontend computes this information in a single pass and updates the capture sets on every occurrence of the variable. Unfortunately, the decision on whether to put a variable in the rvals set or the lvals set depends on the rest of the body of the closure (i.e., whether the variable will end up in the lvals set anyway). So this will be a change from the current mechanism – it can still be done in a single pass, but the information would have to be recorded as the body of the closure is processed, and then the maps would have to be constructed afterward.