Skip to main content

celsium/typestack/
mod.rs

1use std::collections::LinkedList;
2mod mathops;
3use crate::{bytecode::BINOP, BuiltinTypes};
4
5#[derive(Debug, Clone)]
6pub struct TypeStack {
7    stack: LinkedList<BuiltinTypes>,
8}
9impl TypeStack {
10    pub fn new() -> TypeStack {
11        TypeStack {
12            stack: LinkedList::new(),
13        }
14    }
15    pub fn push(&mut self, pushable_type: BuiltinTypes) {
16        self.stack.push_back(pushable_type);
17    }
18    pub fn pop(&mut self) -> Option<BuiltinTypes> {
19        self.stack.pop_back()
20    }
21    pub fn peek(self) -> Option<BuiltinTypes>{
22        self.stack.back().cloned()
23    }
24    pub fn peek_level(self, depth: usize) -> Option<BuiltinTypes> {
25        self.stack.iter().nth_back(depth).cloned()
26    }
27    pub fn binop(&mut self, binop: BINOP) -> Option<BuiltinTypes> {
28        /*
29        Subtraction, multiplication, division and getting remainder
30        are identical in the way types ar handled
31        */
32        let result_type = match binop {
33            BINOP::Add => self.add(),
34            BINOP::Subtract => self.subtract(),
35            BINOP::Multiply => self.subtract(),
36            BINOP::Divide => self.subtract(),
37            BINOP::Remainder => self.subtract(),
38            BINOP::LessThan => self.compare(),
39            BINOP::LargerThan => self.compare(),
40            BINOP::LessOrEq => self.compare(),
41            BINOP::LargerOrEq => self.compare(),
42            BINOP::NotEq => self.compare(),
43            BINOP::Eq => self.compare(),
44            BINOP::And => self.compare(),
45            BINOP::Or => self.compare(),
46            BINOP::Xor => self.compare(),
47        };
48        if result_type.is_some() {
49            self.stack.push_back(result_type.clone().unwrap());
50            return result_type;
51        } else {
52            return None;
53        }
54    }
55}