368
368
eval_code(frame::Frame, code::Union{String, Expr})
369
369
370
370
Evaluate `code` in the context of `frame`, updating any local variables
371
- (including type parameters) that are reassigned in `code`. New local variables
371
+ (including type parameters) that are reassigned in `code`, however, new local variables
372
372
cannot be introduced.
373
+
374
+ ```jldoctest; setup=(using JuliaInterpreter; empty!(JuliaInterpreter.junk))
375
+ julia> foo(x, y) = x + y;
376
+
377
+ julia> frame = JuliaInterpreter.enter_call(foo, 1, 3);
378
+
379
+ julia> JuliaInterpreter.eval_code(frame, "x + y")
380
+ 4
381
+
382
+ julia> JuliaInterpreter.eval_code(frame, "x = 5");
383
+
384
+ julia> JuliaInterpreter.finish_and_return!(frame)
385
+ 8
386
+ ````
387
+
388
+ When variables are captured in closures (and thus gets wrapped in a `Core.Box`)
389
+ they will be automatically unwrapped and rewrapped upon evaluating them:
390
+
391
+ ```jldoctest
392
+ julia> function capture()
393
+ x = 1
394
+ f = ()->(x = 2) # x captured in closure and is thus a Core.Box
395
+ f()
396
+ x
397
+ end;
398
+
399
+ julia> frame = JuliaInterpreter.enter_call(capture);
400
+
401
+ julia> JuliaInterpreter.step_expr!(frame);
402
+
403
+ julia> JuliaInterpreter.step_expr!(frame);
404
+
405
+ julia> JuliaInterpreter.locals(frame)
406
+ 2-element Array{JuliaInterpreter.Variable,1}:
407
+ #self# = capture
408
+ x = Core.Box(1)
409
+
410
+ julia> JuliaInterpreter.eval_code(frame, "x")
411
+ 1
412
+
413
+ julia> JuliaInterpreter.eval_code(frame, "x = 2")
414
+ 2
415
+
416
+ julia> JuliaInterpreter.locals(frame)
417
+ 2-element Array{JuliaInterpreter.Variable,1}:
418
+ #self# = capture
419
+ x = Core.Box(2)
420
+ ```
373
421
"""
374
422
function eval_code end
375
423
@@ -386,7 +434,7 @@ function eval_code(frame::Frame, expr)
386
434
vars = filter (v -> v. name != Symbol (" " ), locals (frame))
387
435
res = gensym ()
388
436
eval_expr = Expr (:let ,
389
- Expr (:block , map (x-> Expr (:(= ), x... ), [(v. name, maybe_quote (v. value)) for v in vars])... ),
437
+ Expr (:block , map (x-> Expr (:(= ), x... ), [(v. name, maybe_quote (v. value isa Core . Box ? v . value . contents : v . value )) for v in vars])... ),
390
438
Expr (:block ,
391
439
Expr (:(= ), res, expr),
392
440
Expr (:tuple , res, Expr (:tuple , [v. name for v in vars]. .. ))
@@ -398,7 +446,7 @@ function eval_code(frame::Frame, expr)
398
446
frame. framedata. sparams[j] = res[i]
399
447
j += 1
400
448
else
401
- frame. framedata. locals[frame. framedata. last_reference[v. name]] = Some {Any} (res[i])
449
+ frame. framedata. locals[frame. framedata. last_reference[v. name]] = Some {Any} (v . value isa Core . Box ? Core . Box (res[i]) : res[i])
402
450
end
403
451
end
404
452
eval_res
0 commit comments