about summary refs log tree commit diff
path: root/tvix/eval/src/upvalues.rs
diff options
context:
space:
mode:
authorVincent Ambo <mail@tazj.in>2022-09-06T20·13+0300
committertazjin <tazjin@tvl.su>2022-09-11T12·26+0000
commit07ea30370e887b16228af0dccbe126010cce9e25 (patch)
treead5c3920c489dc0720ea778a63d7bb971889a886 /tvix/eval/src/upvalues.rs
parentd75b207a63492cb120bcdd918fcc4178dca2bc36 (diff)
refactor(tvix/eval): capture entire with_stack in upvalues r/4801
This completely rewrites the handling of "dynamic upvalues" to,
instead of resolving them at thunk/closure instantiation time (which
forces some values too early), capture the entire with stack of parent
contexts if it exists.

There are a couple of things in here that could be written more
efficiently, but I'm first working through this to get to a bug
related to with + recursion and the code complexity of some of the
optimisations is distracting.

Change-Id: Ia538e06c9146e3bf8decb9adf02dd726d2c651cf
Reviewed-on: https://cl.tvl.fyi/c/depot/+/6486
Tested-by: BuildkiteCI
Reviewed-by: sterni <sternenseemann@systemli.org>
Diffstat (limited to 'tvix/eval/src/upvalues.rs')
-rw-r--r--tvix/eval/src/upvalues.rs18
1 files changed, 18 insertions, 0 deletions
diff --git a/tvix/eval/src/upvalues.rs b/tvix/eval/src/upvalues.rs
index b51ef500e0..ddde8db95a 100644
--- a/tvix/eval/src/upvalues.rs
+++ b/tvix/eval/src/upvalues.rs
@@ -16,12 +16,14 @@ use crate::{opcode::UpvalueIdx, Value};
 #[derive(Clone, Debug)]
 pub struct Upvalues {
     upvalues: Vec<Value>,
+    with_stack: Option<Vec<Value>>,
 }
 
 impl Upvalues {
     pub fn with_capacity(count: usize) -> Self {
         Upvalues {
             upvalues: Vec::with_capacity(count),
+            with_stack: None,
         }
     }
 
@@ -29,6 +31,22 @@ impl Upvalues {
     pub fn push(&mut self, value: Value) {
         self.upvalues.push(value);
     }
+
+    /// Set the captured with stack.
+    pub fn set_with_stack(&mut self, with_stack: Vec<Value>) {
+        self.with_stack = Some(with_stack);
+    }
+
+    pub fn with_stack(&self) -> Option<&Vec<Value>> {
+        self.with_stack.as_ref()
+    }
+
+    pub fn with_stack_len(&self) -> usize {
+        match &self.with_stack {
+            None => 0,
+            Some(stack) => stack.len(),
+        }
+    }
 }
 
 impl Index<UpvalueIdx> for Upvalues {