1use crate::block::BlockScopes;
6use crate::err::RuntimeErrorKind;
7use crate::prelude::RuntimeError;
8use crate::prelude::{ValueReference, VariableValue};
9use seq_map::SeqMap;
10use std::fmt::Debug;
11use std::{cell::RefCell, collections::HashMap, rc::Rc};
12use swamp_script_core_extra::extra::SparseValueId;
13use swamp_script_core_extra::grid::Grid;
14use swamp_script_core_extra::map2::Map2;
15use swamp_script_core_extra::prelude::ValueError;
16use swamp_script_core_extra::value::ValueRef;
17use swamp_script_core_extra::value::{Value, convert_vec_to_rc_refcell, format_value};
18use swamp_script_node::Node;
19use swamp_script_semantic::prelude::*;
20use swamp_script_semantic::{ArgumentExpressionOrLocation, LocationAccess, LocationAccessKind};
21use swamp_script_semantic::{
22 BinaryOperatorKind, CompoundOperatorKind, ConstantId, ForPattern, Function,
23 MutOrImmutableExpression, NormalPattern, PatternElement, PostfixKind, SingleLocationExpression,
24 SingleLocationExpressionKind, UnaryOperatorKind,
25};
26use swamp_script_semantic::{ExternalFunctionId, Postfix};
27use swamp_script_source_map_lookup::SourceMapLookup;
28use swamp_script_types::{EnumVariantType, Type, TypeForParameter, same_anon_struct_ref};
29
30pub mod err;
31
32mod block;
33pub mod prelude;
34pub mod value_both;
35pub mod value_ref;
36
37impl From<ValueError> for RuntimeError {
38 fn from(value: ValueError) -> Self {
39 Self {
40 kind: RuntimeErrorKind::ValueError(value),
41 node: Node::default(),
42 }
43 }
44}
45
46type RawFunctionFn<C> = dyn FnMut(&[VariableValue], &mut C) -> Result<Value, RuntimeError>;
47
48type FunctionFn<C> = Box<RawFunctionFn<C>>;
49
50#[derive(Debug)]
51pub enum FunctionData {
52 Internal(InternalFunctionDefinitionRef),
53 External(ExternalFunctionId),
54}
55
56pub struct EvalExternalFunction<C> {
57 pub func: FunctionFn<C>,
58 pub id: ExternalFunctionId,
59}
60
61impl<C> Debug for EvalExternalFunction<C> {
62 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
63 write!(f, "external_fn {}", self.id)
64 }
65}
66
67pub type EvalExternalFunctionRef<C> = Rc<RefCell<EvalExternalFunction<C>>>;
68
69#[derive(Debug)]
70pub enum ValueWithSignal {
71 Value(Value),
72 Return(Value),
73 Break,
74 Continue,
75}
76
77impl TryFrom<ValueWithSignal> for Value {
78 type Error = String;
79
80 fn try_from(value: ValueWithSignal) -> Result<Self, Self::Error> {
81 match value {
82 ValueWithSignal::Value(v) => Ok(v),
83 ValueWithSignal::Return(v) => Ok(v),
84 ValueWithSignal::Break => Err("break can not be converted".to_string()),
85 ValueWithSignal::Continue => Err("continue can not be converted".to_string()),
86 }
87 }
88}
89
90#[derive(Default)]
91struct FunctionScope {
92 saved_block_scope: BlockScopes,
93}
94
95#[derive(Debug, Default)]
96pub struct ExternalFunctions<C> {
97 external_functions_by_id: HashMap<ExternalFunctionId, EvalExternalFunctionRef<C>>,
99}
100
101#[derive(Debug)]
102pub struct Constants {
103 pub values: Vec<Value>,
104}
105
106impl Default for Constants {
107 fn default() -> Self {
108 Self::new()
109 }
110}
111
112impl Constants {
113 #[must_use]
114 pub fn lookup_constant_value(&self, id: ConstantId) -> &Value {
115 let x = &self.values[id as usize];
116 debug_assert_ne!(*x, Value::Unit, "illegal constant");
117 x
118 }
119
120 pub fn set(&mut self, id: ConstantId, value: Value) {
121 self.values[id as usize] = value;
122 }
123
124 #[must_use]
125 pub fn new() -> Self {
126 let arr: [Value; 256] = core::array::from_fn(|_| Value::Unit);
127 Self {
128 values: arr.to_vec(),
129 }
130 }
131}
132
133impl<C> ExternalFunctions<C> {
134 #[must_use]
135 pub fn new() -> Self {
136 Self {
137 external_functions_by_id: HashMap::new(),
138 }
139 }
140
141 pub fn register_external_function(
142 &mut self,
143 function_id: ExternalFunctionId,
144 handler: impl FnMut(&[VariableValue], &mut C) -> Result<Value, RuntimeError> + 'static,
145 ) -> Result<(), String> {
146 let external_func = EvalExternalFunction {
147 func: Box::new(handler),
148 id: function_id,
149 };
150
151 let external_func_ref = Rc::new(RefCell::new(external_func));
152
153 self.external_functions_by_id
154 .insert(function_id, external_func_ref);
155
156 Ok(())
157 }
158}
159
160pub fn eval_module<C>(
161 externals: &ExternalFunctions<C>,
162 constants: &Constants,
163 root_expression: &Expression,
164 debug_source_map: Option<&dyn SourceMapLookup>,
165 context: &mut C,
166) -> Result<Value, RuntimeError> {
167 let mut interpreter = Interpreter::<C>::new(externals, constants, context);
168 interpreter.debug_source_map = debug_source_map;
169 let value_with_signal = interpreter.evaluate_expression_with_signal(root_expression)?;
170 value_with_signal.try_into().map_err(|_| RuntimeError {
171 node: Node::default(),
172 kind: RuntimeErrorKind::CouldNotConvertFromSignal,
173 })
174}
175
176pub fn eval_constants<C>(
177 externals: &ExternalFunctions<C>,
178 eval_constants: &mut Constants,
179 program_state: &ProgramState,
180 context: &mut C,
181) -> Result<(), RuntimeError> {
182 for constant in &program_state.constants_in_dependency_order {
183 let mut interpreter = Interpreter::<C>::new(externals, eval_constants, context);
184 let value = interpreter.evaluate_expression(&constant.expr)?;
185 eval_constants.set(constant.id, value);
186 }
187
188 Ok(())
189}
190
191pub fn util_execute_function<C>(
192 externals: &ExternalFunctions<C>,
193 constants: &Constants,
194 func: &InternalFunctionDefinitionRef,
195 arguments: &[VariableValue],
196 context: &mut C,
197 debug_source_map: Option<&dyn SourceMapLookup>,
198) -> Result<Value, RuntimeError> {
199 let mut interpreter = Interpreter::<C>::new(externals, constants, context);
200 interpreter.debug_source_map = debug_source_map;
201 interpreter.bind_parameters(
202 &func.body.node,
203 &func.signature.signature.parameters,
204 arguments,
205 )?;
206 let value = interpreter.evaluate_expression(&func.body)?;
207 interpreter.current_block_scopes.clear();
208 interpreter.function_scope_stack.clear();
209 Ok(value)
210}
211
212pub fn util_execute_expression<C>(
213 externals: &ExternalFunctions<C>,
214 constants: &Constants,
215 expr: &Expression,
216 context: &mut C,
217 debug_source_map: Option<&dyn SourceMapLookup>,
218) -> Result<Value, RuntimeError> {
219 let mut interpreter = Interpreter::<C>::new(externals, constants, context);
220 interpreter.debug_source_map = debug_source_map;
221 let value = interpreter.evaluate_expression(expr)?;
222 interpreter.current_block_scopes.clear();
223 interpreter.function_scope_stack.clear();
224 Ok(value)
225}
226
227pub fn util_execute_member_function_mut<C>(
228 externals: &ExternalFunctions<C>,
229 constants: &Constants,
230 fn_def: &InternalFunctionDefinitionRef,
231 self_value_ref: ValueRef,
232 arguments: &[Value],
233 context: &mut C,
234 debug_source_map: Option<&dyn SourceMapLookup>,
235) -> Result<Value, RuntimeError> {
236 let mut complete_arguments = Vec::new();
237 complete_arguments.push(VariableValue::Reference(self_value_ref));
238 for arg in arguments {
239 complete_arguments.push(VariableValue::Value(arg.clone()));
240 }
241
242 let value = util_execute_function(
243 externals,
244 constants,
245 fn_def,
246 &complete_arguments,
247 context,
248 debug_source_map,
249 )?;
250
251 Ok(value)
252}
253
254pub struct Interpreter<'a, C> {
255 function_scope_stack: Vec<FunctionScope>,
256 current_block_scopes: BlockScopes,
257 constants: &'a Constants,
258 externals: &'a ExternalFunctions<C>,
259 context: &'a mut C,
260 debug_source_map: Option<&'a dyn SourceMapLookup>,
261 depth: usize,
262}
263
264impl<'a, C> Interpreter<'a, C> {
265 pub fn new(
266 externals: &'a ExternalFunctions<C>,
267 constants: &'a Constants,
268 context: &'a mut C,
269 ) -> Self {
270 Self {
271 function_scope_stack: vec![FunctionScope::default()],
272 current_block_scopes: BlockScopes::default(),
273 externals,
274 context,
275 debug_source_map: None,
276 constants,
277 depth: 0,
278 }
279 }
280
281 #[inline]
282 fn push_function_scope(&mut self) {
283 self.function_scope_stack.push(FunctionScope {
284 saved_block_scope: self.current_block_scopes.clone(),
285 });
286
287 self.current_block_scopes.clear();
288 self.push_block_scope();
289 }
290
291 #[inline]
292 fn push_block_scope(&mut self) {
293 self.current_block_scopes.push();
294 }
295
296 #[inline]
297 fn pop_block_scope(&mut self) {
298 self.current_block_scopes.pop();
299 }
300
301 #[inline]
302 fn pop_function_scope(&mut self) {
303 debug_assert_ne!(self.function_scope_stack.len(), 1, "you popped too far");
304 let last_one = self.function_scope_stack.pop().expect("pop function scope");
305 self.current_block_scopes = last_one.saved_block_scope;
306 }
307
308 fn bind_parameters(
309 &mut self,
310 node: &Node,
311 params: &[TypeForParameter],
312 args: &[VariableValue],
313 ) -> Result<(), RuntimeError> {
314 for (index, (param, arg)) in params.iter().zip(args).enumerate() {
315 let complete_value = if param.is_mutable {
316 match arg {
317 VariableValue::Reference(_r) => {
318 arg.clone()
320 }
321 _ => return Err(self.create_err(RuntimeErrorKind::ArgumentIsNotMutable, node)),
322 }
323 } else {
324 match arg {
325 VariableValue::Reference(r) => VariableValue::Value(r.borrow().clone()),
326 VariableValue::Value(v) => VariableValue::Value(v.clone()),
327 }
328 };
329
330 self.current_block_scopes
331 .set_local_var_ex(index, complete_value, param.is_mutable)?;
332 }
333
334 Ok(())
335 }
336 fn evaluate_function_call(
337 &mut self,
338 function_expression: &Expression,
339 arguments: &[ArgumentExpressionOrLocation],
340 ) -> Result<Value, RuntimeError> {
341 let func_val = self.evaluate_expression(function_expression)?;
342 let evaluated_args = self.evaluate_args(arguments)?;
343
344 match &func_val {
345 Value::InternalFunction(internal_func_ref) => {
346 self.push_function_scope();
347
348 self.bind_parameters(
349 &internal_func_ref.body.node,
350 &internal_func_ref.signature.signature.parameters,
351 &evaluated_args,
352 )?;
353
354 let result = self.evaluate_expression(&internal_func_ref.body)?;
355
356 self.pop_function_scope();
357
358 Ok(result)
359 }
360
361 Value::ExternalFunction(external_function_ref) => {
362 let external_function_id = &external_function_ref.id;
363 let mut func = self
364 .externals
365 .external_functions_by_id
366 .get(&external_function_id)
367 .ok_or(self.create_err(
368 RuntimeErrorKind::MissingExternalFunction(*external_function_id),
369 &function_expression.node,
370 ))?
371 .borrow_mut();
372
373 (func.func)(&evaluated_args, self.context)
374 }
375 _ => Err(self.create_err(
376 RuntimeErrorKind::ExpectedFunction,
377 &function_expression.node,
378 )),
379 }
380 }
381
382 fn evaluate_location_chain(
383 &mut self,
384 node: &Node,
385 start_value_reference: ValueRef,
386 chain_items: &Vec<LocationAccess>,
387 ) -> Result<ValueRef, RuntimeError> {
388 let mut value_ref = start_value_reference;
389 for chain in chain_items {
390 value_ref = {
391 match &chain.kind {
392 LocationAccessKind::FieldIndex(_resolved_node, index) => {
393 let borrowed = value_ref.borrow();
394
395 let (_struct_ref, fields) = borrowed
396 .expect_anon_struct()
397 .map_err(|_| self.create_err(RuntimeErrorKind::ExpectedStruct, node))?;
398 fields[*index].clone()
399 }
400 LocationAccessKind::IntrinsicCallMut(intrinsic_fn, arguments) => self
401 .eval_intrinsic_postfix_mut_return(
402 node,
403 &value_ref,
404 intrinsic_fn,
405 arguments,
406 )?,
407 }
408 };
409 }
410
411 Ok(value_ref)
412 }
413
414 fn evaluate_location(
415 &mut self,
416 found_location_expr: &SingleLocationExpression,
417 ) -> Result<ValueRef, RuntimeError> {
418 let variable_ref = self
419 .current_block_scopes
420 .lookup_variable_mut_ref(&found_location_expr.starting_variable)?;
421
422 let value_ref = self.evaluate_location_chain(
423 &found_location_expr.node,
424 variable_ref.clone(),
425 &found_location_expr.access_chain,
426 )?;
427
428 let converted_value_ref = match &found_location_expr.kind {
429 SingleLocationExpressionKind::MutVariableRef => value_ref,
430 SingleLocationExpressionKind::MutStructFieldRef(_base_expression, _resolved_access) => {
431 value_ref
432 }
433 };
434
435 Ok(converted_value_ref)
436 }
437
438 fn evaluate_mut_or_immutable_expression(
439 &mut self,
440 expr: &MutOrImmutableExpression,
441 ) -> Result<VariableValue, RuntimeError> {
442 let var_value = match &expr.expression_or_location {
443 ArgumentExpressionOrLocation::Location(loc) => {
444 VariableValue::Reference(self.evaluate_location(loc)?)
445 }
446 ArgumentExpressionOrLocation::Expression(expr) => {
447 VariableValue::Value(self.evaluate_expression(expr)?)
448 }
449 };
450 Ok(var_value)
451 }
452
453 fn evaluate_argument(
454 &mut self,
455 expr: &ArgumentExpressionOrLocation,
456 ) -> Result<VariableValue, RuntimeError> {
457 let var_value = match expr {
458 ArgumentExpressionOrLocation::Location(mutable_location) => {
459 VariableValue::Reference(self.evaluate_location(mutable_location)?)
460 }
461 ArgumentExpressionOrLocation::Expression(expr) => {
462 let value = self.evaluate_expression(expr)?;
463 VariableValue::Value(value)
464 }
465 };
466
467 Ok(var_value)
468 }
469
470 fn evaluate_args(
471 &mut self,
472 args: &[ArgumentExpressionOrLocation],
473 ) -> Result<Vec<VariableValue>, RuntimeError> {
474 let mut evaluated = Vec::with_capacity(args.len());
475
476 for argument_expression in args {
477 let mem_value = self.evaluate_argument(argument_expression)?;
478 evaluated.push(mem_value);
479 }
480
481 Ok(evaluated)
482 }
483
484 fn evaluate_expressions(&mut self, exprs: &[Expression]) -> Result<Vec<Value>, RuntimeError> {
485 let mut values = vec![];
486 for expr in exprs {
487 let value = self.evaluate_expression(expr)?;
488 values.push(value);
489 }
490
491 Ok(values)
492 }
493
494 fn evaluate_while_loop(
495 &mut self,
496 condition: &BooleanExpression,
497 body: &Expression,
498 ) -> Result<ValueWithSignal, RuntimeError> {
499 let mut result = Value::Unit;
500 while self
501 .evaluate_expression(&condition.expression)?
502 .is_truthy()
503 .unwrap()
504 {
506 match self.evaluate_expression_with_signal(body) {
507 Err(e) => return Err(e),
508 Ok(signal) => match signal {
509 ValueWithSignal::Value(v) => result = v,
510 ValueWithSignal::Break => {
511 break;
512 }
513 ValueWithSignal::Return(v) => return Ok(ValueWithSignal::Return(v)),
514 ValueWithSignal::Continue => {}
515 },
516 }
517 }
518
519 Ok(ValueWithSignal::Value(result))
520 }
521
522 fn evaluate_block(
523 &mut self,
524 expressions: &Vec<Expression>,
525 ) -> Result<ValueWithSignal, RuntimeError> {
526 let mut result = Value::Unit;
527
528 self.push_block_scope();
529 for expression in expressions {
530 match self.evaluate_expression_with_signal(&expression)? {
531 ValueWithSignal::Value(v) => result = v,
532 ValueWithSignal::Return(v) => return Ok(ValueWithSignal::Return(v)),
533 ValueWithSignal::Break => return Ok(ValueWithSignal::Break),
534 ValueWithSignal::Continue => return Ok(ValueWithSignal::Continue),
535 }
536 }
537 self.pop_block_scope();
538 Ok(ValueWithSignal::Value(result))
539 }
540
541 fn evaluate_for_loop_mutable(
542 &mut self,
543 pattern: &ForPattern,
544 iterator_expr: &Iterable,
545 body: &Expression,
546 ) -> Result<ValueWithSignal, RuntimeError> {
547 let mut result = Value::Unit;
548
549 let iterator_value_mem =
550 self.evaluate_mut_or_immutable_expression(&iterator_expr.resolved_expression)?;
551 let iterator_value = match iterator_value_mem {
552 VariableValue::Value(_) => {
553 return Err(self.create_err(RuntimeErrorKind::ArgumentIsNotMutable, &body.node));
554 }
555 VariableValue::Reference(value_ref) => value_ref,
556 };
557
558 match pattern {
559 ForPattern::Single(var_ref) => {
560 self.push_block_scope();
561
562 for value in ValueReference(iterator_value).into_iter_mut()? {
563 self.current_block_scopes.initialize_var_mut(var_ref, value);
565
566 match self.evaluate_expression_with_signal(body)? {
567 ValueWithSignal::Value(v) => result = v,
568 ValueWithSignal::Return(v) => return Ok(ValueWithSignal::Return(v)),
569 ValueWithSignal::Break => break,
570 ValueWithSignal::Continue => continue,
571 }
572 }
573
574 self.pop_block_scope();
575 }
576
577 ForPattern::Pair(first_ref, second_ref) => {
578 self.push_block_scope();
579
580 for (key, value_reference) in
581 ValueReference(iterator_value).into_iter_mut_pairs()?
582 {
583 self.current_block_scopes.initialize_var(
586 first_ref.scope_index,
587 first_ref.variable_index,
588 key,
589 false,
590 );
591 self.current_block_scopes
592 .initialize_var_mut(second_ref, value_reference.0);
593
594 match self.evaluate_expression_with_signal(body)? {
595 ValueWithSignal::Value(v) => result = v,
596 ValueWithSignal::Return(v) => return Ok(ValueWithSignal::Return(v)),
597 ValueWithSignal::Break => break,
598 ValueWithSignal::Continue => continue,
599 }
600 }
601
602 self.pop_block_scope();
603 }
604 }
605
606 Ok(ValueWithSignal::Value(result))
607 }
608
609 fn evaluate_for_loop(
610 &mut self,
611 pattern: &ForPattern,
612 iterator_expr: &Iterable,
613 body: &Expression,
614 ) -> Result<ValueWithSignal, RuntimeError> {
615 let mut result = Value::Unit;
616
617 let iterator_value =
618 self.evaluate_mut_or_immutable_expression(&iterator_expr.resolved_expression)?;
619
620 match pattern {
621 ForPattern::Single(var_ref) => {
622 self.push_block_scope();
623
624 for value in iterator_value.into_iter()? {
625 self.current_block_scopes.initialize_var(
627 var_ref.scope_index,
628 var_ref.variable_index,
629 value,
630 var_ref.is_mutable(),
631 );
632
633 match self.evaluate_expression_with_signal(body)? {
634 ValueWithSignal::Value(v) => result = v,
635 ValueWithSignal::Return(v) => {
636 self.pop_block_scope();
637 return Ok(ValueWithSignal::Return(v));
638 }
639 ValueWithSignal::Break => break,
640 ValueWithSignal::Continue => continue,
641 }
642 }
643
644 self.pop_block_scope();
645 }
646
647 ForPattern::Pair(first_ref, second_ref) => {
648 self.push_block_scope();
649
650 for (key, value) in iterator_value.into_iter_pairs()? {
653 self.current_block_scopes.initialize_var(
656 first_ref.scope_index,
657 first_ref.variable_index,
658 key,
659 false,
660 );
661 self.current_block_scopes.initialize_var(
662 second_ref.scope_index,
663 second_ref.variable_index,
664 value,
665 false,
666 );
667
668 match self.evaluate_expression_with_signal(body)? {
669 ValueWithSignal::Value(v) => result = v,
670 ValueWithSignal::Return(v) => return Ok(ValueWithSignal::Return(v)),
671 ValueWithSignal::Break => break,
672 ValueWithSignal::Continue => continue,
673 }
674 }
675
676 self.pop_block_scope();
677 }
678 }
679
680 Ok(ValueWithSignal::Value(result))
681 }
682
683 #[allow(unused)]
684 fn debug_expr(&self, expr: &Expression) {
685 if let Some(debug_source_map) = self.debug_source_map {
686 let source_line = debug_source_map.get_text(&expr.node);
687 eprintln!("{:?}:\n {}", expr.kind, source_line);
688 }
690 }
691
692 #[inline]
693 #[allow(clippy::too_many_lines)]
694 fn evaluate_expression_with_signal(
695 &mut self,
696 expr: &Expression,
697 ) -> Result<ValueWithSignal, RuntimeError> {
698 match &expr.kind {
699 ExpressionKind::WhileLoop(condition, body) => self.evaluate_while_loop(condition, body),
700
701 ExpressionKind::ForLoop(pattern, iterator_expr, body) => {
702 if pattern.is_mutable() {
703 self.evaluate_for_loop_mutable(pattern, iterator_expr, body)
704 } else {
705 self.evaluate_for_loop(pattern, iterator_expr, body)
706 }
707 }
708
709 ExpressionKind::If(condition, consequences, optional_alternative) => {
710 let cond_value = self.evaluate_expression(&condition.expression)?;
711 if cond_value.is_truthy()? {
712 self.evaluate_expression_with_signal(consequences)
713 } else if let Some(alternative) = optional_alternative {
714 self.evaluate_expression_with_signal(alternative)
715 } else {
716 Ok(ValueWithSignal::Value(Value::Unit))
717 }
718 }
719
720 ExpressionKind::Block(expressions) => self.evaluate_block(expressions),
721
722 ExpressionKind::When(bindings, true_block, maybe_else_block) => {
723 let mut all_are_some = true;
724 let mut all_expressions = Vec::new();
725 for binding in bindings {
726 let source = self.evaluate_mut_or_immutable_expression(&binding.expr)?;
727 match source.to_value() {
728 Value::Option(boxed_val) => {
729 match boxed_val {
730 Some(found_val) => {
731 let variable_value = match source {
732 VariableValue::Value(_) => {
733 VariableValue::Value(found_val.borrow().clone())
735 }
736 VariableValue::Reference(_var_ref) => {
737 VariableValue::Reference(found_val)
739 }
740 };
741 all_expressions.push(variable_value);
742 }
743 _ => {
744 all_are_some = false;
745 break;
747 }
748 }
749 }
750 _ => {
751 return Err(self
752 .create_err(RuntimeErrorKind::ExpectedOptional, &true_block.node));
753 }
754 }
755 }
756
757 if all_are_some {
758 self.push_block_scope();
759
760 for (binding, value) in bindings.iter().zip(all_expressions) {
761 self.current_block_scopes
762 .initialize_var_mem(&binding.variable, value)?;
763 }
764
765 let result = self.evaluate_expression_with_signal(true_block)?;
766 self.pop_block_scope();
767
768 Ok(result)
769 } else if let Some(else_block) = maybe_else_block {
770 self.evaluate_expression_with_signal(else_block)
771 } else {
772 Ok(ValueWithSignal::Value(Value::Unit))
773 }
774 }
775
776 _ => Ok(ValueWithSignal::Value(self.evaluate_expression(expr)?)),
777 }
778 }
779
780 #[allow(clippy::too_many_lines)]
782 #[inline]
783 fn evaluate_expression(&mut self, expr: &Expression) -> Result<Value, RuntimeError> {
784 self.depth += 1;
785 let value = match &expr.kind {
786 ExpressionKind::WhileLoop(_condition, _body) => {
788 panic!("should have been handled earlier")
789 }
790
791 ExpressionKind::ForLoop(_pattern, _iterator_expr, _body) => {
792 panic!("should have been handled earlier")
793 }
794
795 ExpressionKind::Literal(lit) => self.evaluate_literal(&expr.node, lit)?,
797
798 ExpressionKind::StructInstantiation(struct_instantiation) => {
799 let mut field_values =
801 Vec::with_capacity(struct_instantiation.source_order_expressions.len());
802 field_values.resize_with(
803 struct_instantiation.source_order_expressions.len(),
804 Default::default,
805 );
806
807 for (array_index, field_expr) in &struct_instantiation.source_order_expressions {
809 let value = self.evaluate_expression(field_expr)?;
810 field_values[*array_index] = value;
811 }
812
813 Value::NamedStruct(
814 struct_instantiation.struct_type_ref.clone(),
815 convert_vec_to_rc_refcell(field_values),
816 )
817 }
818
819 ExpressionKind::AnonymousStructLiteral(struct_instantiation) => {
820 let mut field_values =
822 Vec::with_capacity(struct_instantiation.source_order_expressions.len());
823 field_values.resize_with(
824 struct_instantiation.source_order_expressions.len(),
825 Default::default,
826 );
827
828 for (array_index, field_expr) in &struct_instantiation.source_order_expressions {
830 let value = self.evaluate_expression(field_expr)?;
831 field_values[*array_index] = value;
832 }
833
834 Value::AnonymousStruct(
835 struct_instantiation.anonymous_struct_type.clone(),
836 convert_vec_to_rc_refcell(field_values),
837 )
838 }
839
840 ExpressionKind::VariableDefinition(target_var, source_expr) => {
842 let source_value_or_reference =
843 self.evaluate_mut_or_immutable_expression(source_expr)?;
844
845 self.current_block_scopes
846 .initialize_var_mem(target_var, source_value_or_reference.clone())?;
847
848 source_value_or_reference.to_value().clone()
849 }
850
851 ExpressionKind::VariableReassignment(variable_ref, source_expr) => {
852 let new_value = self.evaluate_mut_or_immutable_expression(source_expr)?;
853
854 self.current_block_scopes
855 .overwrite_existing_var_mem(variable_ref, new_value)?;
856
857 Value::Unit
858 }
859 ExpressionKind::ConstantAccess(constant) => {
861 self.constants.lookup_constant_value(constant.id).clone()
862 }
863
864 ExpressionKind::Assignment(mut_location_expr, source_expr) => {
865 let value_ref = self.evaluate_location(&mut_location_expr.0)?;
866 let source_value = self.evaluate_expression(source_expr)?;
867
868 *value_ref.borrow_mut() = source_value;
869
870 Value::Unit
871 }
872
873 ExpressionKind::CompoundAssignment(mut_location_expr, op, source_expr) => {
874 let value_ref = self.evaluate_location(&mut_location_expr.0)?;
875 let source_value = self.evaluate_expression(source_expr)?;
876
877 self.apply_compound_operator(
878 &expr.node,
879 &mut value_ref.borrow_mut(),
880 op,
881 &source_value,
882 )?;
883
884 Value::Unit
885 }
886
887 ExpressionKind::BinaryOp(binary_operator) => {
889 let left_val = self.evaluate_expression(&binary_operator.left)?;
890 let right_val = self.evaluate_expression(&binary_operator.right)?;
891 self.evaluate_binary_op(&expr.node, left_val, &binary_operator.kind, right_val)?
892 }
893
894 ExpressionKind::UnaryOp(unary_operator) => {
895 let left_val = self.evaluate_expression(&unary_operator.left)?;
896 self.evaluate_unary_op(&expr.node, &unary_operator.kind, left_val)?
897 }
898
899 ExpressionKind::FunctionValueCall(_signature, expr, arguments) => {
901 self.evaluate_function_call(expr, arguments)?
902 }
903
904 ExpressionKind::IntrinsicCallEx(intrinsic, arguments) => {
905 self.eval_intrinsic(&expr.node, intrinsic, arguments)?
906 }
907
908 ExpressionKind::Block(statements) => {
909 self.evaluate_block(statements)?.try_into().unwrap() }
911
912 ExpressionKind::InterpolatedString(parts) => {
913 let mut result = String::new();
914
915 for part in parts {
916 match part {
917 StringPart::Literal(_resolved_node, text) => {
918 result.push_str(text);
919 }
920 StringPart::Interpolation(expr, format_spec) => {
921 let value = self.evaluate_expression(expr)?;
922 let formatted = format_spec.as_ref().map_or_else(
923 || value.convert_to_string_if_needed(),
924 |spec| format_value(&value, &spec.kind).unwrap(),
925 );
926 result.push_str(&formatted);
927 }
928 }
929 }
930
931 Value::String(result)
932 }
933
934 ExpressionKind::Match(resolved_match) => self.eval_match(resolved_match)?,
935 ExpressionKind::Guard(guards) => self.eval_guard(&expr.node, guards)?,
936
937 ExpressionKind::InternalFunctionAccess(fetch_function) => {
938 Value::InternalFunction(fetch_function.clone())
939 }
940
941 ExpressionKind::ExternalFunctionAccess(fetch_function) => {
942 self.externals
943 .external_functions_by_id
944 .get(&fetch_function.id)
945 .expect("should have external function ref");
946 Value::ExternalFunction(fetch_function.clone())
947 }
948
949 ExpressionKind::Option(inner) => match inner {
950 None => Value::Option(None),
951 Some(expression) => {
952 let v = self.evaluate_expression(expression)?;
953 match v {
954 Value::Option(_) => {
955 panic!("unnecessary wrap!, should be investigated");
956 }
957 _ => Value::Option(Some(Rc::new(RefCell::new(v)))),
958 }
959 }
960 },
961
962 ExpressionKind::CoerceOptionToBool(expression) => {
964 let value = self.evaluate_expression(expression)?;
965 match value {
966 Value::Option(inner) => Value::Bool(inner.is_some()),
967 _ => {
968 return Err(
969 self.create_err(RuntimeErrorKind::CoerceOptionToBoolFailed, &expr.node)
970 );
971 }
972 }
973 }
974
975 ExpressionKind::If(condition, consequences, optional_alternative) => {
976 let cond_value = self.evaluate_expression(&condition.expression)?;
977 if cond_value.is_truthy().unwrap() {
978 self.evaluate_expression(consequences)?
980 } else if let Some(alternative) = optional_alternative {
981 self.evaluate_expression(alternative)?
982 } else {
983 Value::Unit
984 }
985 }
986
987 ExpressionKind::When(bindings, true_block, maybe_else_block) => {
988 let mut all_are_some = true;
989 let mut all_expressions = Vec::new();
990 for binding in bindings {
991 let source = self.evaluate_mut_or_immutable_expression(&binding.expr)?;
992 match source.to_value() {
993 Value::Option(boxed_val) => match boxed_val {
994 Some(found_val) => {
995 all_expressions.push(found_val.borrow().clone());
996 }
997 _ => {
998 all_are_some = false;
999 break;
1000 }
1001 },
1002 _ => {
1003 return Err(self
1004 .create_err(RuntimeErrorKind::ExpectedOptional, &true_block.node));
1005 }
1006 }
1007 }
1008
1009 if all_are_some {
1010 self.push_block_scope();
1011
1012 for (binding, value) in bindings.iter().zip(all_expressions) {
1013 self.current_block_scopes.initialize_var(
1014 binding.variable.scope_index,
1015 binding.variable.variable_index,
1016 value,
1017 binding.variable.is_mutable(),
1018 );
1019 }
1020
1021 let result = self.evaluate_expression(true_block)?;
1022 self.pop_block_scope();
1023
1024 result
1025 } else if let Some(else_block) = maybe_else_block {
1026 self.evaluate_expression(else_block)?
1027 } else {
1028 Value::Unit
1029 }
1030 }
1031
1032 ExpressionKind::TupleDestructuring(variable_refs, _, expr) => {
1033 let value = self.evaluate_expression(expr)?;
1034 if let Value::Tuple(_tuple_ref, values) = value {
1035 if variable_refs.len() > values.len() {
1036 return Err(self.create_err(RuntimeErrorKind::NotAnArray, &expr.node));
1037 }
1038 for (index, variable_ref) in variable_refs.iter().enumerate() {
1039 let value = &values[index].borrow().clone();
1040 self.current_block_scopes.initialize_var(
1041 variable_ref.scope_index,
1042 variable_ref.variable_index,
1043 value.clone(),
1044 false,
1045 );
1046 }
1047 }
1048 Value::Unit
1049 }
1050 ExpressionKind::VariableAccess(variable_ref) => {
1051 let temp = self.current_block_scopes.lookup_var_value(variable_ref);
1052 debug_assert_ne!(temp, Value::Unit);
1053 temp
1054 }
1055 ExpressionKind::PostfixChain(start, parts) => {
1056 let value_ref = self.eval_chain(&expr.node, start, parts)?;
1057 let x = value_ref.borrow().clone();
1058 x
1059 }
1060 ExpressionKind::IntrinsicFunctionAccess(_) => panic!(
1061 "Intrinsic Function Access should have been converted to IntrinsicFunctionCalls before eval"
1062 ),
1063
1064 ExpressionKind::Lambda(a, b) => Value::Lambda(a.to_vec(), b.clone()),
1065 };
1066
1067 self.depth -= 1;
1068
1069 Ok(value)
1072 }
1073
1074 fn evaluate_literal(&mut self, node: &Node, lit: &Literal) -> Result<Value, RuntimeError> {
1075 let v = match lit {
1076 Literal::IntLiteral(n) => Value::Int(*n),
1077 Literal::FloatLiteral(f) => Value::Float(*f),
1078 Literal::StringLiteral(s) => Value::String(s.clone()),
1079 Literal::BoolLiteral(b) => Value::Bool(*b),
1080
1081 Literal::EnumVariantLiteral(enum_type, enum_variant_type, data) => {
1082 let variant_container_value: Value = match enum_variant_type {
1083 EnumVariantType::Tuple(tuple_type) => match data {
1084 EnumLiteralData::Tuple(tuple_expressions) => {
1085 let eval_expressions = self.evaluate_expressions(tuple_expressions)?;
1086 let value_refs = values_to_value_refs_owned(eval_expressions);
1087 Value::EnumVariantTuple(
1088 enum_type.clone(),
1089 tuple_type.clone(),
1090 value_refs,
1091 )
1092 }
1093 _ => panic!("wrong container type {data:?}"),
1094 },
1095
1096 EnumVariantType::Struct(struct_type_ref) => match data {
1097 EnumLiteralData::Struct(source_order_field_values) => {
1098 let mut field_values =
1099 Vec::with_capacity(source_order_field_values.len());
1100 field_values
1101 .resize_with(source_order_field_values.len(), Default::default);
1102 for (index, resolved_expression) in source_order_field_values {
1103 let value = self.evaluate_expression(resolved_expression)?;
1104 field_values[*index] = Rc::new(RefCell::new(value));
1105 }
1106 Value::EnumVariantStruct(
1107 enum_type.clone(),
1108 struct_type_ref.clone(),
1109 field_values,
1110 )
1111 }
1112 _ => panic!("wrong container type"),
1113 },
1114
1115 EnumVariantType::Nothing(data) => {
1116 Value::EnumVariantSimple(enum_type.clone(), data.clone())
1117 }
1118 };
1119 variant_container_value
1120 }
1121
1122 Literal::TupleLiteral(tuple_type, resolved_expressions) => {
1123 let values = self.evaluate_expressions(resolved_expressions)?;
1124 Value::Tuple(tuple_type.clone(), convert_vec_to_rc_refcell(values))
1125 }
1126
1127 Literal::Slice(element_type, expressions) => {
1128 let values = self.evaluate_expressions(expressions)?;
1129 Value::Slice(element_type.clone(), convert_vec_to_rc_refcell(values))
1130 }
1131
1132 Literal::SlicePair(slice_pair_type, expressions) => {
1133 let mut items = SeqMap::new();
1134 for (key, value) in expressions {
1135 let key_val = self.evaluate_expression(key)?;
1136 let value_val = self.evaluate_expression(value)?;
1137 items
1138 .insert(key_val, Rc::new(RefCell::new(value_val)))
1139 .map_err(|_err| {
1140 self.create_err(
1141 RuntimeErrorKind::NonUniqueKeysInMapLiteralDetected,
1142 node,
1143 )
1144 })?;
1145 }
1146 Value::SlicePair(slice_pair_type.clone(), items)
1147 }
1148
1149 Literal::NoneLiteral => Value::Option(None),
1150 };
1151 Ok(v)
1152 }
1153
1154 #[allow(clippy::too_many_lines)]
1155 fn eval_intrinsic_postfix_mut_return(
1156 &mut self,
1157 node: &Node,
1158 value_ref: &ValueRef,
1159 intrinsic_function: &IntrinsicFunction,
1161 arguments: &[Expression],
1162 ) -> Result<ValueRef, RuntimeError> {
1163 let val = match &intrinsic_function {
1165 IntrinsicFunction::VecSubscriptMut => match &mut *value_ref.borrow_mut() {
1166 Value::Vec(_type_id, vector) => {
1167 let index = self.evaluate_expression(&arguments[0])?;
1168 let index_int = index.expect_int()?;
1169 vector[index_int as usize].clone()
1170 }
1171 _ => {
1172 return Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1173 }
1174 },
1175 IntrinsicFunction::MapSubscriptMut => match &mut *value_ref.borrow_mut() {
1176 Value::Map(_type_id, seq_map) => {
1177 let key_value = self.evaluate_expression(&arguments[0])?;
1178 let maybe_value = seq_map.get_mut(&key_value);
1179 maybe_value.unwrap().clone()
1180 }
1181 _ => {
1182 return Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1183 }
1184 },
1185
1186 IntrinsicFunction::MapSubscriptMutCreateIfNeeded => {
1187 match &mut *value_ref.borrow_mut() {
1188 Value::Map(_type_id, seq_map) => {
1189 let key_value = self.evaluate_expression(&arguments[0])?;
1190 let maybe_value = seq_map.get_mut(&key_value);
1191 if let Some(ref found) = maybe_value {
1192 maybe_value.unwrap().clone()
1193 } else {
1194 let empty_value = Rc::new(RefCell::new(Value::Int(0)));
1195 seq_map.insert(key_value, empty_value.clone()).unwrap();
1196 empty_value.clone()
1197 }
1198 }
1199 _ => {
1200 return Err(
1201 self.create_err(RuntimeErrorKind::OperationRequiresArray, node)
1202 )?;
1203 }
1204 }
1205 }
1206 _ => panic!(
1207 "{}",
1208 format!("missing intrinsic {intrinsic_function:?} that returns mut. please add it")
1209 ),
1210 };
1211
1212 Ok(val)
1213 }
1214
1215 #[allow(clippy::too_many_lines)]
1216 fn eval_intrinsic(
1217 &mut self,
1218 node: &Node,
1219 intrinsic_function: &IntrinsicFunction,
1220 arguments: &[ArgumentExpressionOrLocation],
1221 ) -> Result<Value, RuntimeError> {
1222 self.eval_intrinsic_internal(node, intrinsic_function, arguments)
1223 }
1224
1225 fn prepare_lambda(
1226 &mut self,
1227 arguments: &[&Expression],
1228 ) -> Result<(Vec<VariableRef>, Expression), RuntimeError> {
1229 let lambda_value = self.evaluate_expression(arguments[0])?;
1230 let Value::Lambda(variables, lambda_expression) = lambda_value else {
1231 panic!("need lambda value");
1232 };
1233
1234 self.pop_function_scope();
1235
1236 self.push_block_scope();
1237
1238 Ok((variables, *lambda_expression))
1239 }
1240
1241 fn prepare_lambda_and_initialize_variables(
1242 &mut self,
1243 arguments: &[&Expression],
1244 ) -> Result<(Vec<VariableRef>, Expression), RuntimeError> {
1245 let (variable_infos, expression) = self.prepare_lambda(arguments)?;
1246
1247 for target_var_info in &variable_infos {
1248 self.current_block_scopes.initialize_var(
1249 target_var_info.scope_index,
1250 target_var_info.variable_index,
1251 Value::Int(0),
1252 true,
1253 );
1254 }
1255
1256 Ok((variable_infos, expression))
1257 }
1258
1259 fn clean_up_lambda(&mut self) {
1260 self.pop_block_scope();
1261 self.push_function_scope(); }
1263
1264 #[allow(clippy::too_many_lines)]
1265 fn eval_intrinsic_internal(
1266 &mut self,
1267 node: &Node,
1268 intrinsic_function: &IntrinsicFunction,
1269 expressions: &[ArgumentExpressionOrLocation],
1270 ) -> Result<Value, RuntimeError> {
1271 let value_ref = if expressions.is_empty() {
1273 ValueRef::new(RefCell::new(Value::Unit))
1274 } else {
1275 self.evaluate_argument(&expressions[0])?.to_value_ref()
1276 };
1277
1278 let mut arguments = Vec::new();
1279 if expressions.len() > 1 {
1280 for arg in &expressions[1..] {
1281 match arg {
1282 ArgumentExpressionOrLocation::Location(_loc) => panic!("not supported"),
1283 ArgumentExpressionOrLocation::Expression(expr) => arguments.push(expr),
1284 }
1285 }
1286 }
1287
1288 let val = match &intrinsic_function {
1289 IntrinsicFunction::VecRemoveIndex => {
1290 let index_val = self.evaluate_expression(&arguments[0])?;
1291 let Value::Int(index) = index_val else {
1292 return Err(self.create_err(RuntimeErrorKind::ArgumentIsNotMutable, node));
1293 };
1294
1295 match &mut *value_ref.borrow_mut() {
1296 Value::Vec(_type_id, vector) => {
1297 vector.remove(index as usize);
1298 }
1299 _ => {
1300 Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1301 }
1302 }
1303
1304 Value::Unit
1305 }
1306
1307 IntrinsicFunction::VecClear => {
1308 match &mut *value_ref.borrow_mut() {
1309 Value::Vec(_type_id, vector) => {
1310 vector.clear();
1311 }
1312 _ => {
1313 Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1314 }
1315 }
1316 Value::Unit
1317 }
1318
1319 IntrinsicFunction::VecFromSlice => {
1320 let (slice_type, values) = value_ref.borrow().expect_slice()?;
1321 Value::Vec(slice_type, values)
1322 }
1323
1324 IntrinsicFunction::VecPush => {
1325 match &mut *value_ref.borrow_mut() {
1326 Value::Vec(_type_id, vector) => {
1327 let value_to_add = self.evaluate_expression(&arguments[0])?;
1328 vector.push(Rc::new(RefCell::new(value_to_add)));
1329 }
1330 _ => {
1331 Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1332 }
1333 }
1334 Value::Unit
1335 }
1336
1337 IntrinsicFunction::VecSubscript => match &mut *value_ref.borrow_mut() {
1338 Value::Vec(_type_id, vector) => {
1339 let index = self.evaluate_expression(&arguments[0])?;
1340 let index_int = index.expect_int()?;
1341 let maybe_value = vector.get(index_int as usize);
1342 if let Some(found_value) = maybe_value {
1343 found_value.borrow().clone()
1344 } else {
1345 return Err(self.create_err(
1346 RuntimeErrorKind::VecIndexOutOfBoundsError {
1347 tried: index_int,
1348 size: vector.len(),
1349 },
1350 node,
1351 ));
1352 }
1353 }
1354 _ => {
1355 return Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1356 }
1357 },
1358
1359 IntrinsicFunction::VecSubscriptRange => match &mut *value_ref.borrow_mut() {
1360 Value::Vec(type_id, vector) => {
1361 let range_struct = self.evaluate_expression(arguments[0])?;
1362 let Value::NamedStruct(_, fields) = range_struct else {
1363 panic!("range is wrong");
1364 };
1365
1366 let start = fields[0].borrow().expect_int()?;
1367 let end = fields[1].borrow().expect_int()?;
1368 let is_inclusive = fields[2].borrow().expect_bool()?;
1369
1370 let values = if is_inclusive {
1371 vector[start as usize..=end as usize].to_vec()
1372 } else {
1373 vector[start as usize..end as usize].to_vec()
1374 };
1375
1376 Value::Vec(type_id.clone(), values)
1377 }
1378 _ => {
1379 return Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1380 }
1381 },
1382
1383 IntrinsicFunction::VecLen => match &mut *value_ref.borrow_mut() {
1384 Value::Vec(_type_id, vector) => {
1385 let length = vector.len();
1386 Value::Int(length as i32)
1387 }
1388 _ => Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?,
1389 },
1390
1391 IntrinsicFunction::VecFor => {
1392 let (variables, lambda_expression) =
1393 self.prepare_lambda_and_initialize_variables(&*arguments)?;
1394
1395 let target_var_info = &variables[0];
1396
1397 self.current_block_scopes.initialize_var(
1398 target_var_info.scope_index,
1399 target_var_info.variable_index,
1400 Value::Int(0),
1401 true,
1402 );
1403
1404 let Value::Vec(_vec_type, items) = &mut *value_ref.borrow_mut() else {
1405 panic!("borrow self");
1406 };
1407
1408 for item in items {
1409 self.current_block_scopes.overwrite_existing_var(
1410 target_var_info.scope_index,
1411 target_var_info.variable_index,
1412 item.borrow().clone(),
1413 )?;
1414
1415 self.evaluate_expression(&lambda_expression)?;
1416 }
1417
1418 self.clean_up_lambda();
1419
1420 Value::Unit
1421 }
1422
1423 IntrinsicFunction::VecWhile => {
1424 let (variables, lambda_expression) =
1425 self.prepare_lambda_and_initialize_variables(&arguments)?;
1426
1427 let target_var_info = &variables[0];
1428
1429 let Value::Vec(_vec_type, items) = &mut *value_ref.borrow_mut() else {
1430 panic!("borrow self");
1431 };
1432 for item in items {
1433 self.current_block_scopes.overwrite_existing_var(
1434 target_var_info.scope_index,
1435 target_var_info.variable_index,
1436 item.borrow().clone(),
1437 )?;
1438
1439 let result = self.evaluate_expression(&lambda_expression)?;
1440 let should_continue = result.expect_bool()?;
1441 if !should_continue {
1442 break;
1443 }
1444 }
1445
1446 self.clean_up_lambda();
1447
1448 Value::Unit
1449 }
1450
1451 IntrinsicFunction::VecFind => {
1452 let (variables, lambda_expression) =
1453 self.prepare_lambda_and_initialize_variables(&arguments)?;
1454
1455 let target_var_info = &variables[0];
1456
1457 let Value::Vec(_vec_type, items) = &mut *value_ref.borrow_mut() else {
1458 panic!("borrow self");
1459 };
1460
1461 let mut final_result = Value::Option(None);
1462 for item in items {
1463 self.current_block_scopes.overwrite_existing_var(
1464 target_var_info.scope_index,
1465 target_var_info.variable_index,
1466 item.borrow().clone(),
1467 )?;
1468
1469 let result = self.evaluate_expression(&lambda_expression)?;
1470 let Value::Option(ref inner) = result else {
1471 panic!("must have option value");
1472 };
1473 if inner.is_some() {
1474 final_result = result;
1475 break;
1476 }
1477 }
1478
1479 self.clean_up_lambda();
1480
1481 final_result
1482 }
1483
1484 IntrinsicFunction::VecIsEmpty => match &mut *value_ref.borrow_mut() {
1485 Value::Vec(_type_id, vector) => Value::Bool(vector.len() == 0),
1486 _ => Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?,
1487 },
1488 IntrinsicFunction::VecPop => match &mut *value_ref.borrow_mut() {
1489 Value::Vec(_type_id, vector) => {
1490 let maybe_val = vector.pop();
1491 if let Some(found_value) = maybe_val {
1492 found_value.borrow().clone()
1493 } else {
1494 return Err(self.create_err(RuntimeErrorKind::StackCouldNotBePopped, node));
1495 }
1496 }
1497 _ => Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?,
1498 },
1499
1500 IntrinsicFunction::MapCreate => Value::Map(Type::Unit, SeqMap::new()),
1501
1502 IntrinsicFunction::MapFromSlicePair => {
1503 let borrow = value_ref.borrow();
1504 let (slice_pair_type, seq_map) = borrow.expect_slice_pair()?;
1505 Value::Map(slice_pair_type, seq_map.clone())
1506 }
1507
1508 IntrinsicFunction::MapHas => {
1509 let index_val = self.evaluate_expression(&arguments[0])?;
1510
1511 match value_ref.borrow().clone() {
1512 Value::Map(_key_type, ref seq_map) => {
1513 let has_key = seq_map.contains_key(&index_val);
1514 Value::Bool(has_key)
1515 }
1516 _ => {
1517 return Err(self.create_err(RuntimeErrorKind::NotAMap, node));
1518 }
1519 }
1520 }
1521
1522 IntrinsicFunction::MapLen => match value_ref.borrow().clone() {
1523 Value::Map(_key_type, ref seq_map) => Value::Int(seq_map.len() as i32),
1524 _ => {
1525 return Err(self.create_err(RuntimeErrorKind::NotAMap, node));
1526 }
1527 },
1528 IntrinsicFunction::MapIsEmpty => match &mut *value_ref.borrow_mut() {
1529 Value::Vec(_type_id, seq_map) => Value::Bool(seq_map.len() == 0),
1530 _ => Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?,
1531 },
1532 IntrinsicFunction::MapSubscript => match value_ref.borrow().clone() {
1533 Value::Map(_type_id, seq_map) => {
1534 let key_value = self.evaluate_expression(arguments[0])?;
1535 let maybe_value = seq_map.get(&key_value);
1536 if let Some(found_value) = maybe_value {
1537 found_value.borrow().clone()
1538 } else {
1539 return Err(self.create_err(RuntimeErrorKind::MapKeyNonExisting, node));
1540 }
1541 }
1542 _ => {
1543 return Err(self.create_err(RuntimeErrorKind::OperationRequiresArray, node))?;
1544 }
1545 },
1546 IntrinsicFunction::MapRemove => {
1547 let index_val = self.evaluate_expression(arguments[0])?;
1548
1549 let result = {
1550 let mut borrowed = value_ref.borrow_mut();
1551 match &mut *borrowed {
1552 Value::Map(_key_type, seq_map) => {
1553 seq_map.remove(&index_val);
1554 Value::Unit
1563 }
1564 _ => {
1565 return Err(self.create_err(RuntimeErrorKind::NotAMap, node));
1566 }
1567 }
1568 };
1569 result
1570 }
1571
1572 IntrinsicFunction::Map2Create => Value::Map2(Map2::new()),
1574
1575 IntrinsicFunction::Map2Remove => {
1576 let column_val = self.evaluate_expression(&arguments[0])?;
1577 let row_val = self.evaluate_expression(&arguments[1])?;
1578
1579 let result = {
1580 let mut borrowed = value_ref.borrow_mut();
1581 match &mut *borrowed {
1582 Value::Map2(map2) => {
1583 map2.remove(&column_val, &row_val);
1584 Value::Unit
1585 }
1586 _ => {
1587 return Err(self.create_err(RuntimeErrorKind::NotAMap2, node));
1588 }
1589 }
1590 };
1591 result
1592 }
1593
1594 IntrinsicFunction::Map2Insert => {
1595 let column_val = self.evaluate_expression(&arguments[0])?;
1596 let row_val = self.evaluate_expression(&arguments[1])?;
1597 let value_to_insert = self.evaluate_expression(&arguments[2])?;
1598
1599 let result = {
1600 let mut borrowed = value_ref.borrow_mut();
1601 match &mut *borrowed {
1602 Value::Map2(map2) => {
1603 map2.insert(
1604 column_val,
1605 row_val,
1606 Rc::new(RefCell::new(value_to_insert)),
1607 );
1608 Value::Unit
1609 }
1610 _ => {
1611 return Err(self.create_err(RuntimeErrorKind::NotAMap2, node));
1612 }
1613 }
1614 };
1615 result
1616 }
1617
1618 IntrinsicFunction::Map2Has => {
1619 let column_val = self.evaluate_expression(arguments[0])?;
1620 let row_val = self.evaluate_expression(arguments[1])?;
1621
1622 let result = {
1623 let mut borrowed = value_ref.borrow();
1624 match &*borrowed {
1625 Value::Map2(map2) => {
1626 let has_cell = map2.has(&column_val, &row_val);
1627 Value::Bool(has_cell)
1628 }
1629 _ => {
1630 return Err(self.create_err(RuntimeErrorKind::NotAMap2, node));
1631 }
1632 }
1633 };
1634 result
1635 }
1636
1637 IntrinsicFunction::Map2Get => {
1638 let column_val = self.evaluate_expression(arguments[0])?;
1639 let row_val = self.evaluate_expression(arguments[1])?;
1640
1641 let result = {
1642 let mut borrowed = value_ref.borrow();
1643 match &*borrowed {
1644 Value::Map2(map2) => {
1645 let cell_value = map2.get(&column_val, &row_val).unwrap();
1646 cell_value.borrow().clone()
1647 }
1648 _ => {
1649 return Err(self.create_err(RuntimeErrorKind::NotAMap2, node));
1650 }
1651 }
1652 };
1653 result
1654 }
1655
1656 IntrinsicFunction::Map2GetColumn => {
1657 let column_val = self.evaluate_expression(&arguments[0])?;
1658
1659 let result = {
1660 let mut borrowed = value_ref.borrow();
1661 match &*borrowed {
1662 Value::Map2(map2) => {
1663 let column_map = map2.get_column(&column_val).unwrap();
1664 Value::Map(Type::Unit, column_map.clone())
1665 }
1666 _ => {
1667 return Err(self.create_err(RuntimeErrorKind::NotAMap2, node));
1668 }
1669 }
1670 };
1671 result
1672 }
1673
1674 IntrinsicFunction::Map2GetRow => {
1675 let row_val = self.evaluate_expression(&arguments[0])?;
1676
1677 let result = {
1678 let mut borrowed = value_ref.borrow();
1679 match &*borrowed {
1680 Value::Map2(map2) => {
1681 let row_map = map2.get_row(&row_val).unwrap();
1682 Value::Map(Type::Unit, row_map.clone())
1683 }
1684 _ => {
1685 return Err(self.create_err(RuntimeErrorKind::NotAMap2, node));
1686 }
1687 }
1688 };
1689 result
1690 }
1691
1692 IntrinsicFunction::SparseAdd => {
1693 let mut borrowed = value_ref.borrow_mut();
1694
1695 match &mut *borrowed {
1696 Value::Sparse(_type, found) => {
1697 let resolved_value = self.evaluate_expression(&arguments[0])?;
1698 let id_value = found.add(resolved_value);
1699
1700 id_value
1701 }
1702 _ => {
1703 return Err(self.create_err(RuntimeErrorKind::NotSparseValue, node));
1704 }
1705 }
1706 }
1707
1708 IntrinsicFunction::SparseRemove => {
1709 let mut borrowed = value_ref.borrow_mut();
1710
1711 match &mut *borrowed {
1712 Value::Sparse(_type, found) => {
1713 let id_value = self.evaluate_expression(&arguments[0])?;
1714 match id_value.downcast_rust::<SparseValueId>() {
1715 Some(found_id) => {
1716 found.remove(&found_id.borrow());
1717 }
1718 _ => {
1719 return Err(self.create_err(RuntimeErrorKind::NotSparseValue, node));
1720 }
1721 }
1722 }
1723 _ => {
1724 return Err(self.create_err(RuntimeErrorKind::NotSparseValue, node));
1725 }
1726 }
1727
1728 Value::Unit
1729 }
1730 IntrinsicFunction::SparseSubscript => {
1731 let borrowed = value_ref.borrow();
1732
1733 match &*borrowed {
1734 Value::Sparse(_type, found) => {
1735 let id_value = self.evaluate_expression(arguments[0])?; match id_value.downcast_rust::<SparseValueId>() {
1737 Some(found_id) => match found.get(&found_id.borrow()) {
1738 Some(found_value) => Value::Option(Some(found_value.clone())),
1739 _ => Value::Option(None),
1740 },
1741 _ => {
1742 return Err(self.create_err(RuntimeErrorKind::NotSparseId, node));
1743 }
1744 }
1745 }
1746 _ => {
1747 return Err(self.create_err(RuntimeErrorKind::NotSparseId, node));
1748 }
1749 }
1750 }
1751
1752 IntrinsicFunction::GridCreate => {
1754 let width_value = value_ref.borrow().expect_int()?;
1755 let height_value = self
1756 .evaluate_expression(arguments[0])
1757 .unwrap()
1758 .expect_int()?;
1759
1760 let initial_value = self.evaluate_expression(arguments[1])?;
1761
1762 Value::Grid(Grid::new(
1763 width_value as usize,
1764 height_value as usize,
1765 Rc::new(RefCell::new(initial_value)),
1766 ))
1767 }
1768
1769 IntrinsicFunction::GridSet => {
1770 let Value::Grid(ref mut mut_grid) = *value_ref.borrow_mut() else {
1771 panic!("should be grid")
1772 };
1773 let x_value = self.evaluate_expression(arguments[0])?.expect_int()?;
1774 let y_value = self.evaluate_expression(arguments[1])?.expect_int()?;
1775 let grid_value = self.evaluate_expression(arguments[2])?;
1776
1777 mut_grid.set(
1778 x_value as usize,
1779 y_value as usize,
1780 Rc::new(RefCell::new(grid_value)),
1781 );
1782
1783 Value::Unit
1784 }
1785
1786 IntrinsicFunction::GridGet => {
1787 let Value::Grid(ref mut_grid) = *value_ref.borrow() else {
1788 panic!("should be grid")
1789 };
1790 let x_value = self.evaluate_expression(arguments[0])?.expect_int()?;
1791 let y_value = self.evaluate_expression(arguments[1])?.expect_int()?;
1792
1793 mut_grid
1794 .get(x_value as usize, y_value as usize)
1795 .unwrap()
1796 .borrow()
1797 .clone()
1798 }
1799
1800 IntrinsicFunction::GridGetColumn => {
1801 let Value::Grid(ref grid) = *value_ref.borrow() else {
1802 panic!("should be grid")
1803 };
1804 let x_value = self.evaluate_expression(arguments[0])?.expect_int()?;
1805
1806 let column_items = grid.column(x_value as usize).unwrap();
1807
1808 Value::Vec(Type::Unit, column_items)
1809 }
1810
1811 IntrinsicFunction::FloatRound => match value_ref.borrow().clone() {
1812 Value::Float(f) => Value::Int(f.round().into()),
1813 _ => {
1814 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1815 }
1816 },
1817 IntrinsicFunction::FloatFloor => match value_ref.borrow().clone() {
1818 Value::Float(f) => Value::Int(f.floor().into()),
1819 _ => {
1820 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1821 }
1822 },
1823 IntrinsicFunction::FloatSign => match value_ref.borrow().clone() {
1824 Value::Float(f) => {
1825 let signum = if f.inner() < 0 {
1826 -1
1827 } else if f.inner() > 0 {
1828 1
1829 } else {
1830 0
1831 };
1832 Value::Float(Fp::from(signum as i16))
1833 }
1834 _ => {
1835 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1836 }
1837 },
1838 IntrinsicFunction::FloatAbs => match value_ref.borrow().clone() {
1839 Value::Float(f) => Value::Float(f.abs()),
1840 _ => {
1841 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1842 }
1843 },
1844 IntrinsicFunction::FloatCos => match value_ref.borrow().clone() {
1845 Value::Float(f) => Value::Float(f.cos()),
1846 _ => {
1847 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1848 }
1849 },
1850 IntrinsicFunction::FloatAcos => match value_ref.borrow().clone() {
1851 Value::Float(f) => Value::Float(f.acos()),
1852 _ => {
1853 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1854 }
1855 },
1856 IntrinsicFunction::FloatSin => match value_ref.borrow().clone() {
1857 Value::Float(f) => Value::Float(f.sin()),
1858 _ => {
1859 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1860 }
1861 },
1862 IntrinsicFunction::FloatAsin => match value_ref.borrow().clone() {
1863 Value::Float(f) => Value::Float(f.asin()),
1864 _ => {
1865 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1866 }
1867 },
1868 IntrinsicFunction::FloatSqrt => match value_ref.borrow().clone() {
1869 Value::Float(f) => Value::Float(f.sqrt()),
1870 _ => {
1871 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1872 }
1873 },
1874 IntrinsicFunction::FloatMin => {
1875 let min_value = self.evaluate_expression(&arguments[0])?;
1876 match (value_ref.borrow().clone(), min_value) {
1877 (Value::Float(f), Value::Float(min_f)) => Value::Float(f.min(min_f)),
1878 _ => {
1879 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1880 }
1881 }
1882 }
1883
1884 IntrinsicFunction::FloatMax => {
1885 let max_value = self.evaluate_expression(arguments[0])?;
1886 match (value_ref.borrow().clone(), max_value) {
1887 (Value::Float(f), Value::Float(max_f)) => Value::Float(f.max(max_f)),
1888 _ => {
1889 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1890 }
1891 }
1892 }
1893
1894 IntrinsicFunction::FloatAtan2 => {
1895 let x_value = self.evaluate_expression(arguments[0])?;
1896 match (value_ref.borrow().clone(), x_value) {
1897 (Value::Float(_y_f), Value::Float(_x_f)) => {
1898 Value::Float(Fp::from(-9999)) }
1900 _ => {
1901 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1902 }
1903 }
1904 }
1905
1906 IntrinsicFunction::FloatClamp => {
1907 let min_value = self.evaluate_expression(arguments[0])?;
1908 let max_value = self.evaluate_expression(arguments[1])?;
1909 match (value_ref.borrow().clone(), min_value, max_value) {
1910 (Value::Float(f), Value::Float(min_f), Value::Float(max_f)) => {
1911 Value::Float(f.clamp(min_f, max_f))
1912 }
1913 _ => {
1914 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1915 }
1916 }
1917 }
1918
1919 IntrinsicFunction::FloatRnd => match value_ref.borrow().clone() {
1920 Value::Float(f) => {
1921 let new_raw = squirrel_prng::squirrel_noise5(f.inner() as u32, 0);
1922 Value::Int(new_raw as i32)
1923 }
1924 _ => {
1925 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1926 }
1927 },
1928 IntrinsicFunction::IntAbs => match value_ref.borrow().clone() {
1929 Value::Int(i) => Value::Int(i.abs()),
1930 _ => {
1931 return Err(self.create_err(RuntimeErrorKind::ExpectedFloat, node));
1932 }
1933 },
1934 IntrinsicFunction::IntClamp => {
1935 let min_value = self.evaluate_expression(arguments[0])?;
1936 let max_value = self.evaluate_expression(arguments[1])?;
1937 match (value_ref.borrow().clone(), min_value, max_value) {
1938 (Value::Int(i), Value::Int(min_i), Value::Int(max_i)) => {
1939 Value::Int(i.clamp(min_i, max_i))
1940 }
1941 _ => {
1942 return Err(self.create_err(RuntimeErrorKind::ExpectedInt, node));
1943 }
1944 }
1945 }
1946
1947 IntrinsicFunction::IntMin => {
1948 let max_value = self.evaluate_expression(arguments[0])?;
1949 match (value_ref.borrow().clone(), max_value) {
1950 (Value::Int(i), Value::Int(min_i)) => Value::Int(i.min(min_i)),
1951 _ => {
1952 return Err(self.create_err(RuntimeErrorKind::ExpectedInt, node));
1953 }
1954 }
1955 }
1956
1957 IntrinsicFunction::IntMax => {
1958 let max_value = self.evaluate_expression(&arguments[0])?;
1959 match (value_ref.borrow().clone(), max_value) {
1960 (Value::Int(i), Value::Int(max_i)) => Value::Int(i.max(max_i)),
1961 _ => {
1962 return Err(self.create_err(RuntimeErrorKind::ExpectedInt, node));
1963 }
1964 }
1965 }
1966
1967 IntrinsicFunction::IntRnd => match value_ref.borrow().clone() {
1968 Value::Int(i) => Value::Int(squirrel_prng::squirrel_noise5(i as u32, 0) as i32),
1969 _ => {
1970 return Err(self.create_err(RuntimeErrorKind::ExpectedInt, node));
1971 }
1972 },
1973 IntrinsicFunction::IntToFloat => match value_ref.borrow().clone() {
1974 Value::Int(i) => Value::Float(Fp::from(i as i16)),
1975 _ => {
1976 return Err(self.create_err(RuntimeErrorKind::ExpectedInt, node));
1977 }
1978 },
1979 IntrinsicFunction::StringLen => match value_ref.borrow().clone() {
1980 Value::String(s) => Value::Int(s.len().try_into().expect("string len overflow")),
1981 _ => {
1982 return Err(self.create_err(RuntimeErrorKind::ExpectedString, node));
1983 }
1984 },
1985 IntrinsicFunction::Float2Magnitude => match value_ref.borrow().clone() {
1986 Value::Tuple(_tuple_ref, values) => {
1987 if values.len() != 2 {
1988 return Err(self.create_err(
1989 RuntimeErrorKind::WrongNumberOfArguments(2, values.len()),
1990 node,
1991 ));
1992 }
1993 match (
1994 values[0].as_ref().borrow().clone(),
1995 values[1].as_ref().borrow().clone(),
1996 ) {
1997 (Value::Float(a), Value::Float(b)) => {
1998 let a_raw: i64 = a.inner() as i64;
1999 let b_raw: i64 = b.inner() as i64;
2000
2001 let i64_magnitude = i64_sqrt(a_raw * a_raw + b_raw * b_raw);
2002
2003 let new_fp = Fp::from_raw(
2004 i32::try_from(i64_magnitude).expect("wrong with i64_sqrt"),
2005 );
2006 Value::Float(new_fp)
2007 }
2008 _ => {
2009 return Err(
2010 self.create_err(RuntimeErrorKind::ExpectedTwoFloatTuple, node)
2011 );
2012 }
2013 }
2014 }
2015 _ => {
2016 return Err(self.create_err(RuntimeErrorKind::ExpectedTwoFloatTuple, node));
2017 }
2018 },
2019 _ => todo!("{intrinsic_function:?} not implemented"),
2020 };
2021
2022 Ok(val)
2023 }
2024
2025 #[allow(clippy::too_many_lines)]
2026 fn eval_chain(
2027 &mut self,
2028 node: &Node,
2029 start: &Expression,
2030 parts: &[Postfix],
2031 ) -> Result<ValueRef, RuntimeError> {
2032 let (mut val_ref, mut is_mutable) = match &start.kind {
2033 ExpressionKind::VariableAccess(start_var) => {
2034 let start_variable_value = self.current_block_scopes.get_var(start_var);
2035
2036 match start_variable_value {
2037 VariableValue::Value(value) => {
2038 debug_assert_ne!(*value, Value::Unit);
2039 (Rc::new(RefCell::new(value.clone())), false)
2040 }
2041 VariableValue::Reference(value_ref) => {
2042 debug_assert_ne!(value_ref.borrow().clone(), Value::Unit);
2043 (value_ref.clone(), true)
2044 }
2045 }
2046 }
2047 _ => (
2048 Rc::new(RefCell::new(self.evaluate_expression(start)?)),
2049 false,
2050 ),
2051 };
2052
2053 let mut has_value_but_should_be_considered_as_option = false;
2054 let mut optional_chaining_has_failed = false;
2055
2056 for part in parts {
2057 if let PostfixKind::NoneCoalescingOperator(default_expression) = &part.kind {
2058 val_ref = {
2059 let borrowed = val_ref.borrow();
2060
2061 match &*borrowed {
2062 Value::Option(found_option) => match &found_option {
2063 Some(some_value) => some_value.clone(),
2064 _ => {
2065 let default_value = self.evaluate_expression(default_expression)?;
2066 Rc::new(RefCell::new(default_value))
2067 }
2068 },
2069 _ => {
2070 if has_value_but_should_be_considered_as_option {
2071 val_ref.clone()
2072 } else {
2073 return Err(
2074 self.create_err(RuntimeErrorKind::ExpectedOptional, &part.node)
2075 );
2076 }
2077 }
2078 }
2079 };
2080
2081 is_mutable = false;
2082 has_value_but_should_be_considered_as_option = false;
2083 optional_chaining_has_failed = false;
2084 } else if optional_chaining_has_failed {
2085 continue;
2086 }
2087 match &part.kind {
2088 PostfixKind::NoneCoalescingOperator(_default_expression) => {
2089 }
2091
2092 PostfixKind::StructField(expected_struct_type, index) => {
2093 let (encountered_struct_type, fields) = {
2094 let brw = val_ref.borrow();
2095 let (struct_ref, fields_ref) = brw.expect_anon_struct().map_err(|_| {
2096 self.create_err(RuntimeErrorKind::PostfixChainError, &part.node)
2097 })?;
2098 (struct_ref.clone(), fields_ref.clone())
2099 };
2100
2101 debug_assert!(same_anon_struct_ref(
2102 &encountered_struct_type,
2103 expected_struct_type
2104 ));
2105 val_ref = fields[*index].clone();
2106 }
2107
2108 PostfixKind::MemberCall(function_ref, arguments) => {
2109 let val =
2110 self.eval_member_call(node, &val_ref, is_mutable, function_ref, arguments)?;
2111
2112 val_ref = Rc::new(RefCell::new(val));
2113 is_mutable = false;
2114 }
2115 PostfixKind::FunctionCall(arguments) => {
2116 let val = self.eval_function_call(node, &val_ref, arguments)?;
2117
2118 val_ref = Rc::new(RefCell::new(val));
2119 is_mutable = false;
2120 }
2121
2122 PostfixKind::OptionalChainingOperator => {
2124 val_ref = {
2125 let borrowed = val_ref.borrow();
2126
2127 match borrowed.clone() {
2128 Value::Option(found_option) => {
2129 if let Some(found) = found_option {
2130 found
2131 } else {
2132 optional_chaining_has_failed = true;
2133 Rc::new(RefCell::new(Value::Option(None)))
2134 }
2135 }
2136 _ => {
2137 return Err(
2138 self.create_err(RuntimeErrorKind::ExpectedOptional, &part.node)
2139 );
2140 }
2141 }
2142 };
2143
2144 is_mutable = false;
2145 has_value_but_should_be_considered_as_option = true;
2146 }
2147 }
2148 }
2149
2150 if has_value_but_should_be_considered_as_option {
2151 match &*val_ref.borrow() {
2152 Value::Option(_) => {}
2153 _ => {
2154 return Ok(Rc::new(RefCell::new(Value::Option(Some(val_ref.clone())))));
2155 }
2156 };
2157 }
2158
2159 Ok(val_ref)
2160 }
2161
2162 fn eval_function_call(
2163 &mut self,
2164 node: &Node,
2165 function_val: &ValueRef,
2166 arguments: &[ArgumentExpressionOrLocation],
2167 ) -> Result<Value, RuntimeError> {
2168 let resolved_fn = match function_val.borrow().clone() {
2169 Value::InternalFunction(x) => Function::Internal(x),
2170 Value::ExternalFunction(external_fn) => Function::External(external_fn),
2171 _ => panic!("no function to call"),
2172 };
2173
2174 let parameters = &resolved_fn.signature().parameters;
2175 debug_assert_eq!(
2177 arguments.len(),
2178 parameters.len(),
2179 "wrong number of arguments"
2180 );
2181
2182 let resolved_arguments = self.evaluate_args(arguments)?;
2183
2184 let result_val = match &resolved_fn {
2185 Function::Internal(internal_function) => {
2186 self.push_function_scope();
2187
2188 self.bind_parameters(node, parameters, &resolved_arguments)?;
2189 let result = self.evaluate_expression(&internal_function.body)?;
2190 self.pop_function_scope();
2191
2192 result
2193 }
2194 Function::External(external_func) => {
2195 let mut func = self
2196 .externals
2197 .external_functions_by_id
2198 .get(&external_func.id)
2199 .expect("member call: external function missing")
2200 .borrow_mut();
2201 (func.func)(&resolved_arguments, self.context)?
2202 }
2203 };
2204
2205 Ok(result_val)
2206 }
2207
2208 #[inline]
2209 fn eval_member_call(
2210 &mut self,
2211 node: &Node,
2212 self_value_ref: &ValueRef,
2213 is_mutable: bool,
2214 function_ref: &FunctionRef,
2215 arguments: &[ArgumentExpressionOrLocation],
2216 ) -> Result<Value, RuntimeError> {
2217 let parameters = &function_ref.signature().parameters;
2218
2219 let self_var_value = if parameters[0].is_mutable {
2220 if !is_mutable {
2221 return Err(self.create_err(RuntimeErrorKind::ArgumentIsNotMutable, node));
2222 }
2223 VariableValue::Reference(self_value_ref.clone())
2224 } else {
2225 VariableValue::Value(self_value_ref.borrow().clone())
2226 };
2227
2228 let mut member_call_arguments = Vec::new();
2229 member_call_arguments.push(self_var_value); member_call_arguments.extend(self.evaluate_args(arguments)?);
2231
2232 assert_eq!(
2234 member_call_arguments.len(),
2235 parameters.len(),
2236 "wrong number of arguments"
2237 );
2238
2239 let result_val = match &**function_ref {
2240 Function::Internal(internal_function) => {
2241 self.push_function_scope();
2242 self.bind_parameters(node, parameters, &member_call_arguments)?;
2243 let result = self.evaluate_expression(&internal_function.body)?;
2244 self.pop_function_scope();
2245
2246 result
2247 }
2248 Function::External(external_func) => {
2249 let mut func = self
2250 .externals
2251 .external_functions_by_id
2252 .get(&external_func.id)
2253 .expect("member call: external function missing")
2254 .borrow_mut();
2255 (func.func)(&member_call_arguments, self.context)?
2256 }
2257 };
2258
2259 Ok(result_val)
2260 }
2261
2262 fn eval_guard(&mut self, node: &Node, guards: &[Guard]) -> Result<Value, RuntimeError> {
2263 for guard in guards {
2264 let should_evaluate = if let Some(found_clause) = &guard.condition {
2265 self.evaluate_expression(&found_clause.expression)?
2266 .is_truthy()?
2267 } else {
2268 true
2269 };
2270
2271 if should_evaluate {
2272 return self.evaluate_expression(&guard.result);
2273 }
2274 }
2275
2276 Err(self.create_err(RuntimeErrorKind::MustHaveGuardArmThatMatches, node))
2277 }
2278
2279 #[inline]
2280 #[allow(clippy::too_many_lines, clippy::cognitive_complexity)]
2281 fn eval_match(&mut self, resolved_match: &Match) -> Result<Value, RuntimeError> {
2282 let actual_value = self.evaluate_mut_or_immutable_expression(&resolved_match.expression)?;
2283 let value_ref = actual_value.to_value_ref();
2284
2285 for arm in &resolved_match.arms {
2286 match &arm.pattern {
2287 Pattern::Wildcard(_node) => return self.evaluate_expression(&arm.expression),
2288 Pattern::Normal(normal_pattern, maybe_guard) => {
2289 if let Some(found_guard) = maybe_guard {
2290 if !self
2291 .evaluate_expression(&found_guard.expression)?
2292 .is_truthy()?
2293 {
2295 continue;
2296 }
2297 }
2298
2299 let immutable_value = actual_value.to_value();
2300
2301 match &normal_pattern {
2302 NormalPattern::PatternList(elements) => {
2303 return Ok(self.eval_normal_pattern_list(
2304 elements,
2305 &arm.expression,
2306 value_ref.clone(),
2307 )?);
2308 }
2309 NormalPattern::EnumPattern(enum_variant_ref, pattern_elements) => {
2310 let maybe_found_match = self.eval_normal_pattern_enum(
2311 pattern_elements.as_ref(),
2312 &arm.expression,
2313 enum_variant_ref,
2314 value_ref.clone(),
2315 )?;
2316
2317 if let Some(found_match) = maybe_found_match {
2318 return Ok(found_match);
2319 }
2320 }
2321
2322 NormalPattern::Literal(lit) => match (lit, &immutable_value) {
2323 (Literal::IntLiteral(a), Value::Int(b)) if a == b => {
2324 return self.evaluate_expression(&arm.expression);
2325 }
2326 (Literal::FloatLiteral(a), Value::Float(b)) if a == b => {
2327 return self.evaluate_expression(&arm.expression);
2328 }
2329 (Literal::StringLiteral(a), Value::String(b)) if *a == *b => {
2330 return self.evaluate_expression(&arm.expression);
2331 }
2332 (Literal::BoolLiteral(a), Value::Bool(b)) if a == b => {
2333 return self.evaluate_expression(&arm.expression);
2334 }
2335 (
2336 Literal::TupleLiteral(_a_type_ref, a_values),
2337 Value::Tuple(_b_type_ref, b_values),
2338 ) if self.expressions_equal_to_values(a_values, b_values)? => {
2339 return self.evaluate_expression(&arm.expression);
2340 }
2341 _ => {}
2342 },
2343 }
2344 }
2345 }
2346 }
2347
2348 panic!("must match one of the match arms!");
2349 }
2350
2351 fn eval_normal_pattern_list(
2352 &mut self,
2353 elements: &[PatternElement],
2354 expression_to_evaluate: &Expression,
2355 value_ref: ValueRef,
2356 ) -> Result<Value, RuntimeError> {
2357 if elements.len() == 1 {
2359 return match &elements[0] {
2360 PatternElement::Variable(var_ref)
2361 | PatternElement::VariableWithFieldIndex(var_ref, _) => {
2362 self.push_block_scope();
2363 self.current_block_scopes
2364 .initialize_var_mut(var_ref, value_ref);
2365 let result = self.evaluate_expression(expression_to_evaluate);
2366 self.pop_block_scope();
2367 result
2368 }
2369 PatternElement::Wildcard(_) => {
2370 self.evaluate_expression(expression_to_evaluate)
2372 }
2373 };
2374 }
2375
2376 if let Value::Tuple(_tuple_type_ref, values) = value_ref.borrow_mut().clone() {
2377 debug_assert_eq!(
2378 elements.len(),
2379 values.len(),
2380 "must use all elements in tuple"
2381 );
2382 self.push_block_scope();
2383
2384 for (element, _inside_value) in elements.iter().zip(values.iter()) {
2385 match element {
2386 PatternElement::Variable(var_ref) => {
2387 self.current_block_scopes
2388 .initialize_var_mut(var_ref, value_ref.clone());
2389 }
2390 PatternElement::VariableWithFieldIndex(var_ref, _) => {
2391 self.current_block_scopes
2392 .initialize_var_mut(var_ref, value_ref.clone());
2393 }
2394 PatternElement::Wildcard(_) => {
2395 continue;
2397 }
2398 }
2399 }
2400
2401 let result = self.evaluate_expression(expression_to_evaluate);
2402 self.pop_block_scope();
2403
2404 return result;
2405 }
2406 panic!("should not get here")
2407 }
2408
2409 fn eval_normal_pattern_enum(
2410 &mut self,
2411 maybe_elements: Option<&Vec<PatternElement>>,
2412 expression_to_evaluate: &Expression,
2413 variant_ref: &EnumVariantType,
2414 value_ref: ValueRef,
2415 ) -> Result<Option<Value>, RuntimeError> {
2416 match value_ref.borrow_mut().clone() {
2417 Value::EnumVariantTuple(_enum_type, value_tuple_type, values) => {
2418 if variant_ref.common().container_index != value_tuple_type.common.container_index {
2420 return Ok(None); }
2422
2423 if let Some(elements) = maybe_elements {
2424 debug_assert_eq!(elements.len(), values.len());
2425 self.push_block_scope();
2426
2427 for (element, value) in elements.iter().zip(values.iter()) {
2428 match element {
2429 PatternElement::Variable(var_ref) => {
2430 self.current_block_scopes
2431 .initialize_var_mut(var_ref, value.clone());
2432 }
2433 PatternElement::VariableWithFieldIndex(var_ref, _) => {
2434 self.current_block_scopes
2435 .initialize_var_mut(var_ref, value.clone());
2436 }
2437 PatternElement::Wildcard(_) => continue,
2438 }
2439 }
2440
2441 let result = self.evaluate_expression(expression_to_evaluate);
2442 self.pop_block_scope();
2443 return Ok(Option::from(result?));
2444 }
2445 }
2446 Value::EnumVariantStruct(_enum_type, value_enum_struct_type, values) => {
2447 if value_enum_struct_type.common.container_index
2448 == variant_ref.common().container_index
2449 {
2450 if let Some(elements) = maybe_elements {
2451 self.push_block_scope();
2452
2453 for element in elements {
2454 if let PatternElement::VariableWithFieldIndex(var_ref, field_index) =
2455 element
2456 {
2457 let value = &values[*field_index];
2458 self.current_block_scopes.init_var_ref(var_ref, value);
2459 }
2460 }
2461
2462 let result = self.evaluate_expression(expression_to_evaluate);
2463 self.pop_block_scope();
2464 return Ok(Some(result?));
2465 }
2466 }
2467 }
2468
2469 Value::EnumVariantSimple(_enum_type, value_variant_ref) => {
2470 if value_variant_ref.common.container_index == variant_ref.common().container_index
2471 && maybe_elements.is_none()
2472 {
2473 return Ok(Some(self.evaluate_expression(expression_to_evaluate)?));
2474 }
2475 }
2476 _ => {
2477 panic!("could not find enum variant, serious error")
2478 }
2479 }
2480
2481 Ok(None)
2482 }
2483
2484 #[inline(always)]
2485 const fn modulo(a: i32, b: i32) -> i32 {
2486 ((a % b) + b) % b
2487 }
2488
2489 #[inline(always)]
2490 const fn modulo_fp(a: Fp, b: Fp) -> Fp {
2491 let raw = ((a.inner() % b.inner()) + b.inner()) % b.inner();
2492 Fp::from_raw(raw)
2493 }
2494
2495 #[allow(clippy::too_many_lines)]
2496 fn evaluate_binary_op(
2497 &self,
2498 node: &Node,
2499 left_val: Value,
2500 op: &BinaryOperatorKind,
2501 right_val: Value,
2502 ) -> Result<Value, RuntimeError> {
2503 let result: Value = match (&left_val, op, &right_val) {
2504 (Value::Int(a), BinaryOperatorKind::Add, Value::Int(b)) => Value::Int(a + b),
2506 (Value::Int(a), BinaryOperatorKind::Subtract, Value::Int(b)) => Value::Int(a - b),
2507 (Value::Int(a), BinaryOperatorKind::Multiply, Value::Int(b)) => Value::Int(a * b),
2508 (Value::Int(a), BinaryOperatorKind::Divide, Value::Int(b)) => {
2509 if *b == 0 {
2510 return Err(self.create_err(RuntimeErrorKind::DivideByZero, node));
2511 }
2512 Value::Int(a / b)
2513 }
2514 (Value::Int(a), BinaryOperatorKind::Modulo, Value::Int(b)) => {
2515 Value::Int(Self::modulo(*a, *b))
2516 }
2517 (Value::Int(a), BinaryOperatorKind::Equal, Value::Int(b)) => Value::Bool(a == b),
2518 (Value::Int(a), BinaryOperatorKind::NotEqual, Value::Int(b)) => Value::Bool(a != b),
2519 (Value::Int(a), BinaryOperatorKind::LessThan, Value::Int(b)) => Value::Bool(a < b),
2520 (Value::Int(a), BinaryOperatorKind::GreaterThan, Value::Int(b)) => Value::Bool(a > b),
2521 (Value::Int(a), BinaryOperatorKind::LessEqual, Value::Int(b)) => Value::Bool(a <= b),
2522 (Value::Int(a), BinaryOperatorKind::GreaterEqual, Value::Int(b)) => Value::Bool(a >= b),
2523
2524 (Value::Float(a), BinaryOperatorKind::Equal, Value::Float(b)) => Value::Bool(a == b),
2526 (Value::Float(a), BinaryOperatorKind::NotEqual, Value::Float(b)) => Value::Bool(a != b),
2527
2528 (Value::Float(a), BinaryOperatorKind::Add, Value::Float(b)) => Value::Float(*a + *b),
2529 (Value::Float(a), BinaryOperatorKind::Subtract, Value::Float(b)) => {
2530 Value::Float(*a - *b)
2531 }
2532 (Value::Float(a), BinaryOperatorKind::Multiply, Value::Float(b)) => {
2533 Value::Float(*a * *b)
2534 }
2535 (Value::Float(a), BinaryOperatorKind::Divide, Value::Float(b)) => {
2536 if b.abs().inner() <= 400 {
2537 return Err(self.create_err(RuntimeErrorKind::DivideByZero, node));
2538 }
2539 Value::Float(*a / *b)
2540 }
2541 (Value::Float(a), BinaryOperatorKind::Modulo, Value::Float(b)) => {
2542 Value::Float(Self::modulo_fp(*a, *b))
2543 }
2544
2545 (Value::Float(a), BinaryOperatorKind::GreaterThan, Value::Float(b)) => {
2546 Value::Bool(a > b)
2547 }
2548 (Value::Float(a), BinaryOperatorKind::GreaterEqual, Value::Float(b)) => {
2549 Value::Bool(a >= b)
2550 }
2551 (Value::Float(a), BinaryOperatorKind::LessThan, Value::Float(b)) => Value::Bool(a < b),
2552 (Value::Float(a), BinaryOperatorKind::LessEqual, Value::Float(b)) => {
2553 Value::Bool(a <= b)
2554 }
2555
2556 (Value::Bool(a), BinaryOperatorKind::LogicalAnd, Value::Bool(b)) => {
2558 Value::Bool(*a && *b)
2559 }
2560 (Value::Bool(a), BinaryOperatorKind::LogicalOr, Value::Bool(b)) => {
2561 Value::Bool(*a || *b)
2562 }
2563
2564 (Value::RustValue(_, left), BinaryOperatorKind::Equal, Value::RustValue(_, right)) => {
2568 let left_borrow = left.borrow();
2569 let right_borrow = right.borrow();
2570 let equal = left_borrow.eq_dyn(&**right_borrow);
2571 Value::Bool(equal)
2572 }
2573 (
2574 Value::RustValue(_, left),
2575 BinaryOperatorKind::NotEqual,
2576 Value::RustValue(_, right),
2577 ) => {
2578 let left_borrow = left.borrow();
2579 let right_borrow = right.borrow();
2580 let equal = left_borrow.eq_dyn(&**right_borrow);
2581 Value::Bool(!equal)
2582 }
2583
2584 (Value::String(a), BinaryOperatorKind::Add, Value::String(b)) => {
2586 Value::String(a.to_owned() + b)
2587 }
2588 (Value::String(a), BinaryOperatorKind::Equal, Value::String(b)) => Value::Bool(a == b),
2589
2590 (Value::String(a), BinaryOperatorKind::Add, Value::Int(b)) => {
2591 Value::String(a.to_owned() + &(*b).to_string())
2592 }
2593 (Value::Int(a), BinaryOperatorKind::Add, Value::String(b)) => {
2594 Value::String(a.to_string() + b)
2595 }
2596
2597 (
2599 Value::EnumVariantSimple(_a_enum_type, a),
2600 BinaryOperatorKind::Equal,
2601 Value::EnumVariantSimple(_b_enum_type, b),
2602 ) => Value::Bool(a == b),
2603 (
2604 Value::EnumVariantSimple(_a_enum_type, a),
2605 BinaryOperatorKind::NotEqual,
2606 Value::EnumVariantSimple(_b_enum_type, b),
2607 ) => Value::Bool(a != b),
2608
2609 (Value::Bool(a), BinaryOperatorKind::Equal, Value::Bool(b)) => Value::Bool(a == b),
2611 (Value::Bool(a), BinaryOperatorKind::NotEqual, Value::Bool(b)) => Value::Bool(a != b),
2612
2613 (Value::Option(a), BinaryOperatorKind::Equal, Value::Option(b)) => Value::Bool(a == b),
2614
2615 _ => {
2616 panic!("invalid binary operation"); }
2618 };
2619
2620 Ok(result)
2621 }
2622
2623 fn evaluate_unary_op(
2624 &self,
2625 node: &Node,
2626 op: &UnaryOperatorKind,
2627 val: Value,
2628 ) -> Result<Value, RuntimeError> {
2629 match (op, val) {
2630 (UnaryOperatorKind::Negate, Value::Int(n)) => Ok(Value::Int(-n)),
2631 (UnaryOperatorKind::Negate, Value::Float(n)) => Ok(Value::Float(-n)),
2632 (UnaryOperatorKind::Not, Value::Bool(b)) => Ok(Value::Bool(!b)),
2633 _ => Err(self.create_err(RuntimeErrorKind::DivideByZero, node)),
2634 }
2635 }
2636
2637 fn expressions_equal_to_values(
2638 &mut self,
2639 p0: &[Expression],
2640 p1: &[ValueRef],
2641 ) -> Result<bool, RuntimeError> {
2642 for (a, b_value) in p0.iter().zip(p1.iter()) {
2643 let a_value = self.evaluate_expression(a)?;
2644
2645 if a_value != *b_value.borrow() {
2646 return Ok(false);
2647 }
2648 }
2649
2650 Ok(true)
2651 }
2652
2653 #[inline]
2654 fn apply_compound_operator(
2655 &self,
2656 node: &Node,
2657 target: &mut Value,
2658 operator: &CompoundOperatorKind,
2659 source: &Value,
2660 ) -> Result<(), RuntimeError> {
2661 match operator {
2662 CompoundOperatorKind::Mul => {
2663 *target = self.evaluate_binary_op(
2664 node,
2665 target.clone(),
2666 &BinaryOperatorKind::Multiply,
2667 source.clone(),
2668 )?;
2669 }
2670 CompoundOperatorKind::Div => {
2671 *target = self.evaluate_binary_op(
2672 node,
2673 target.clone(),
2674 &BinaryOperatorKind::Divide,
2675 source.clone(),
2676 )?;
2677 }
2678 CompoundOperatorKind::Add => {
2679 *target = self.evaluate_binary_op(
2680 node,
2681 target.clone(),
2682 &BinaryOperatorKind::Add,
2683 source.clone(),
2684 )?;
2685 }
2686 CompoundOperatorKind::Sub => {
2687 *target = self.evaluate_binary_op(
2688 node,
2689 target.clone(),
2690 &BinaryOperatorKind::Subtract,
2691 source.clone(),
2692 )?;
2693 }
2694 CompoundOperatorKind::Modulo => {
2695 *target = self.evaluate_binary_op(
2696 node,
2697 target.clone(),
2698 &BinaryOperatorKind::Modulo,
2699 source.clone(),
2700 )?;
2701 }
2702 }
2703 Ok(())
2704 }
2705
2706 fn create_err(&self, kind: RuntimeErrorKind, node: &Node) -> RuntimeError {
2707 RuntimeError {
2708 node: node.clone(),
2709 kind,
2710 }
2711 }
2712
2713 }
2766
2767#[inline]
2768#[must_use]
2769pub fn i64_sqrt(v: i64) -> i64 {
2770 const MAX_ITERATIONS: usize = 40;
2771 const TOLERANCE: i64 = 2;
2772
2773 debug_assert!(v >= 0, "negative numbers are undefined for sqrt() {v}");
2774
2775 if v == 0 {
2776 return v;
2777 }
2778
2779 let mut guess = v / 2;
2780
2781 for _ in 0..MAX_ITERATIONS {
2782 let next_guess = (guess + v / guess) / 2;
2783
2784 if (next_guess - guess).abs() <= TOLERANCE {
2786 return next_guess;
2787 }
2788
2789 guess = next_guess;
2790 }
2791
2792 guess }
2794
2795#[allow(unused)]
2796#[must_use]
2797pub fn values_to_value_refs(values: &[Value]) -> Vec<ValueRef> {
2798 let mut items = Vec::new();
2799
2800 for x in values.iter().cloned() {
2801 items.push(Rc::new(RefCell::new(x)));
2802 }
2803
2804 items
2805}
2806
2807#[must_use]
2808pub fn values_to_value_refs_owned(values: Vec<Value>) -> Vec<ValueRef> {
2809 values
2810 .into_iter()
2811 .map(|x| Rc::new(RefCell::new(x)))
2812 .collect()
2813}
2814
2815#[must_use]
2816pub fn wrap_in_option(maybe: Option<&ValueRef>) -> ValueRef {
2817 maybe.map_or_else(
2818 || Rc::new(RefCell::new(Value::Option(None))),
2819 |x| Rc::new(RefCell::new(Value::Option(Some(x.clone())))),
2820 )
2821}