Amo/src/ir/evaluation.rs

39 lines
1.1 KiB
Rust

use std::{collections::HashMap, mem::Discriminant};
use super::{Identifier, value::Value, expr::Operation, types::Type};
#[derive(Debug, Default)]
pub struct ValueBindings<'a>(Option<&'a ValueBindings<'a>>, HashMap<u128, Value>);
impl<'a> ValueBindings<'a> {
pub fn bind(mut self, ident: &Identifier, value: Value) -> Self {
self.1.insert(ident.1 as u128, value);
self
}
pub fn lookup(&self, ident: &Identifier) -> Option<&Value> {
self.1.get(&(ident.1 as u128))
.or_else(|| self.0.and_then(|binding| binding.lookup(ident)))
}
pub fn nested_scope(&'a self) -> ValueBindings<'a> {
ValueBindings(Some(self), HashMap::new())
}
pub fn get_main(&self) -> Option<&Value> {
self.1.get(&3).or_else(|| self.0.and_then(ValueBindings::get_main))
}
}
pub enum EvaluateError {
UndefinedValue(Identifier),
EvaluatingZeroLengthExpr,
ArgumentCountMismatch(Operation, usize, usize),
FunctionArgumentCountMismatch(usize, usize),
TypeMismatch(Discriminant<Value>, Discriminant<Value>),
NoMain,
MainHasArgs,
}
pub type Result = std::result::Result<Value, EvaluateError>;