1use super::*;
2
3impl Interpreter {
4 pub fn exec_items(&mut self, items: &[TopLevel]) -> Result<Value, RuntimeError> {
5 for item in items {
6 match item {
7 TopLevel::FnDef(fd) => self.exec_fn_def(fd)?,
8 TopLevel::Module(_) => {}
9 TopLevel::Verify(_) => {}
10 TopLevel::Decision(_) => {}
11 TopLevel::TypeDef(td) => self.register_type_def(td),
12 TopLevel::EffectSet { .. } => {}
13 TopLevel::Stmt(s) => {
14 self.exec_stmt(s)?;
15 }
16 }
17 }
18 Ok(Value::Unit)
19 }
20
21 pub fn register_type_def(&mut self, td: &TypeDef) {
23 match td {
24 TypeDef::Sum {
25 name: type_name,
26 variants,
27 ..
28 } => {
29 let mut members = HashMap::new();
30 for variant in variants {
31 if variant.fields.is_empty() {
32 members.insert(
34 variant.name.clone(),
35 Value::Variant {
36 type_name: type_name.clone(),
37 variant: variant.name.clone(),
38 fields: vec![].into(),
39 },
40 );
41 } else {
42 members.insert(
44 variant.name.clone(),
45 Value::Builtin(format!("__ctor:{}:{}", type_name, variant.name)),
46 );
47 }
48 }
49 self.define(
50 type_name.clone(),
51 Value::Namespace {
52 name: type_name.clone(),
53 members,
54 },
55 );
56 }
57 TypeDef::Product { name, fields, .. } => {
58 let schema = fields.iter().map(|(field, _)| field.clone()).collect();
62 self.record_schemas.insert(name.clone(), schema);
63 }
64 }
65 }
66
67 pub fn exec_fn_def(&mut self, fd: &FnDef) -> Result<(), RuntimeError> {
68 let val = Value::Fn(Rc::new(crate::value::FunctionValue {
69 name: Rc::new(fd.name.clone()),
70 params: Rc::new(fd.params.clone()),
71 return_type: Rc::new(fd.return_type.clone()),
72 effects: Rc::new(fd.effects.clone()),
73 body: Rc::clone(&fd.body),
74 lowered_body: super::lowered::lower_fn_body(fd.body.as_ref()),
75 resolution: fd.resolution.clone(),
76 memo_eligible: self.memo_fns.contains(&fd.name),
77 home_globals: None,
78 }));
79 self.define(fd.name.clone(), val);
80 Ok(())
81 }
82
83 pub fn exec_stmt(&mut self, stmt: &Stmt) -> Result<Value, RuntimeError> {
84 match stmt {
85 Stmt::Binding(name, _, expr) => {
86 let val = self.eval_expr(expr)?;
87 self.define(name.clone(), val);
88 Ok(Value::Unit)
89 }
90 Stmt::Expr(expr) => self.eval_expr(expr),
91 }
92 }
93
94 pub fn exec_body(&mut self, stmts: &[Stmt]) -> Result<Value, RuntimeError> {
95 let mut last = Value::Unit;
96 for stmt in stmts {
97 last = self.exec_stmt(stmt)?;
98 }
99 Ok(last)
100 }
101
102 pub fn run_file(&mut self, source: &str) -> Result<Value, RuntimeError> {
103 let mut items = parse_source(source).map_err(RuntimeError::Error)?;
104 crate::resolver::resolve_program(&mut items);
105
106 for item in &items {
108 match item {
109 TopLevel::FnDef(fd) => self.exec_fn_def(fd)?,
110 TopLevel::Stmt(s) => {
111 self.exec_stmt(s)?;
112 }
113 _ => {}
114 }
115 }
116
117 let main_fn = self.lookup("main");
119 if let Ok(fn_val) = main_fn {
120 let allowed = Self::callable_declared_effects(&fn_val);
121 self.call_value_with_effects_pub(fn_val, vec![], "<main>", allowed)?;
122 }
123
124 Ok(Value::Unit)
125 }
126}