use crate::{obj::prelude::*, vm::consts::*}; use shredder::EmptyScan; #[derive(Debug, PartialEq, Clone, Copy)] pub enum Inst { /// Push a literal symbol object to the stack. PushSym(Sym), /// Push a const value reference to the stack. PushConst(ConstHandle), /// Looks up and pushes a local value. LoadLocal(Name), /// Looks up and pushes a global value. LoadGlobal(Name), /// Pop a value from the stack, possibly into a local symbol. PopLocal(Option), /// Pop a value from the stack, possibly into a global symbol. PopGlobal(Option), /// Pops a symbol value and an object reference. /// /// This will get an attr from the object reference pointed to by the symbol. GetAttr(Sym), /// Pops a target reference and a source reference from the stack. /// /// The target reference will have the given symbol attribute assigned to the source. /// /// In code, it would look like this: /// /// `target.symbol = source` /// SetAttr(Sym), /// Jump to a given address in the current function unconditionally. Jump(usize), /// Jump to a given address in the current function if the condition flag is true. /// /// The condition flag may be set by an internal function. JumpTrue(usize), /// Calls a function with the supplied number of arguments. /// /// The stack, from bottom to top, should contain the function followed by the arguments. /// /// After the function has returned, the VM will have popped the arguments and function /// pointer, and the return value will be on top of the stack. Call(usize), /// Indexes a value, e.g. a list or a dict. /// /// The stack, from bottom to top, should have the expression being indexed, and then the /// indexed value. Index, /// Pops the top value from the stack, and returns from the function, using the popped value as /// a return value. Return, /// Replaces the top stack value with its negation applied. UnNeg, /// Replaces the top stack value with its absolute value applied. UnPos, /// Pops the top two items off of the stack, and applies the binary addition operator to them, /// pushing the result to the stack. BinPlus, /// Pops the top two items off of the stack, and applies the binary subtraction operator to /// them, pushing the result to the stack. BinMinus, /// Pops the top two items off of the stack, and applies the binary multiplication operator to /// them, pushing the result to the stack. BinMul, /// Pops the top two items off of the stack, and applies the binary division operator to them, /// pushing the result to the stack. BinDiv, /// Pops the top two items off of the stack, and applies the boolean equality operator to them, /// pushing the result to the stack. BinEq, /// Pops the top two items off of the stack, and applies the boolean inequality operator to /// them, pushing the result to the stack. BinNeq, /// Pops the top two items off of the stack, and applies the boolean less-than operator to /// them, pushing the result to the stack. BinLt, /// Pops the top two items off of the stack, and applies the binary less-than or equals /// operator to them, pushing the result to the stack. BinLe, /// Pops the top two items off of the stack, and applies the boolean greater-than operator to /// them, pushing the result to the stack. BinGt, /// Pops the top two items off of the stack, and applies the binary greater-than or equals /// operator to them, pushing the result to the stack. BinGe, /// Pops the top two items off of the stack, and applies the boolean and operator to them, /// pushing the result to the stack. BinAnd, /// Pops the top two items off of the stack, and applies the boolean or operator to them, /// pushing the result to the stack. BinOr, } // // impl Inst // impl Inst { pub fn name(&self) -> &'static str { match self { Inst::PushSym(_) => "PUSH_SYM", Inst::PushConst(_) => "PUSH_CONST", Inst::LoadLocal(_) => "LOAD_LOCAL", Inst::LoadGlobal(_) => "LOAD_GLOBAL", Inst::PopLocal(_) => "POP_LOCAL", Inst::PopGlobal(_) => "POP_GLOBAL", Inst::GetAttr(_) => "GET_ATTR", Inst::SetAttr(_) => "SET_ATTR", Inst::Jump(_) => "JUMP", Inst::JumpTrue(_) => "JUMP_TRUE", Inst::Call(_) => "CALL", Inst::Index => "INDEX", Inst::Return => "RETURN", Inst::UnNeg => "UN_NEG", Inst::UnPos => "UN_POS", Inst::BinPlus => "BIN_PLUS", Inst::BinMinus => "BIN_MINUS", Inst::BinMul => "BIN_MUL", Inst::BinDiv => "BIN_DIV", Inst::BinEq => "BIN_EQ", Inst::BinNeq => "BIN_NEQ", Inst::BinLt => "BIN_LT", Inst::BinLe => "BIN_LE", Inst::BinGt => "BIN_GT", Inst::BinGe => "BIN_GE", Inst::BinAnd => "BIN_AND", Inst::BinOr => "BIN_OR", } } } impl EmptyScan for Inst {}