glowdust 0.0.1

A DBMS with a data model based on functions and pattern matching
Documentation
use crate::compiler::value::parameters::Variable;
use crate::compiler::value::values::{FunctionDefinitionObject, TypeDefinition, Value};
use std::collections::HashMap;

#[derive(Debug, Clone, Eq, PartialEq, Default)]
pub struct Bytecode {
    pub bytes: Vec<u8>,
    pub lines: Vec<usize>,
    pub(crate) labels: HashMap<String, usize>,
}

impl Bytecode {
    pub fn new() -> Self {
        Bytecode::default()
    }

    pub fn new_from_bytes(bytes: Vec<u8>) -> Self {
        Bytecode {
            bytes,
            lines: vec![],
            labels: HashMap::new(),
        }
    }

    pub fn len(&self) -> usize {
        self.bytes.len()
    }

    pub fn is_empty(&self) -> bool {
        self.bytes.is_empty()
    }

    pub fn get(&self, index: usize) -> u8 {
        *self.bytes.get(index).unwrap()
    }

    pub fn bytes(&mut self, mut bytes: Vec<u8>) -> usize {
        self.bytes.append(&mut bytes);
        self.bytes.len().saturating_sub(1)
    }

    pub fn byte(&mut self, byte: u8) -> usize {
        let last_used_line = match self.lines.last() {
            None => 0,
            Some(line) => *line,
        };
        self.byte_and_line(byte, last_used_line)
    }

    pub fn byte_and_line(&mut self, byte: u8, line: usize) -> usize {
        self.lines.push(line);
        self.bytes.push(byte);
        self.bytes.len().saturating_sub(1)
    }

    pub fn clear(&mut self) {
        self.bytes.clear();
        self.lines.clear();
        self.labels.clear();
    }
}

#[derive(Debug, Clone, Eq, PartialEq, Default)]
pub struct Executable {
    pub script_bytecode: Bytecode,
    pub script_constants: Vec<Value>,
    pub script_variables: Vec<Variable>,
    pub function_definitions: HashMap<String, Vec<FunctionDefinitionObject>>,
    pub type_definitions: Vec<TypeDefinition>,
}

impl Executable {
    pub fn as_fdo(&self) -> FunctionDefinitionObject {
        FunctionDefinitionObject {
            variables: self.script_variables.clone(),
            constants: self.script_constants.clone(),
            formal_arguments: vec![], // no formal arguments (for now) for script. I assume it would be the environment?
            bytecode: self.script_bytecode.clone(),
            name: "top level script".to_string(),
        }
    }
}