Back to working state

This commit is contained in:
JT
2021-09-03 06:21:37 +12:00
parent e1be8f61fc
commit 94687a7603
28 changed files with 170 additions and 116 deletions

View File

@ -1,6 +1,6 @@
use std::ops::{Index, IndexMut};
use crate::Statement;
use super::Statement;
#[derive(Debug, Clone)]
pub struct Block {

View File

@ -1,4 +1,5 @@
use crate::{DeclId, Expression, Span};
use super::Expression;
use crate::{DeclId, Span};
#[derive(Debug, Clone)]
pub struct Call {

View File

@ -1,4 +1,5 @@
use crate::{BlockId, Call, Expression, Operator, Signature, Span, VarId};
use super::{Call, Expression, Operator};
use crate::{BlockId, Signature, Span, VarId};
#[derive(Debug, Clone)]
pub enum Expr {

View File

@ -1,4 +1,5 @@
use crate::{BlockId, Expr, Operator, Signature, Span, Type, VarId};
use super::{Expr, Operator};
use crate::{BlockId, Signature, Span, Type, VarId};
#[derive(Debug, Clone)]
pub struct Expression {

View File

@ -0,0 +1,15 @@
mod block;
mod call;
mod expr;
mod expression;
mod operator;
mod pipeline;
mod statement;
pub use block::*;
pub use call::*;
pub use expr::*;
pub use expression::*;
pub use operator::*;
pub use pipeline::*;
pub use statement::*;

View File

@ -1,4 +1,4 @@
use crate::Expression;
use crate::ast::Expression;
#[derive(Debug, Clone)]
pub struct Pipeline {

View File

@ -1,4 +1,5 @@
use crate::{DeclId, Expression, Pipeline};
use super::{Expression, Pipeline};
use crate::DeclId;
#[derive(Debug, Clone)]
pub enum Statement {

View File

@ -0,0 +1,8 @@
use crate::ast::Call;
use crate::Span;
#[derive(Debug, Clone)]
pub struct UnevaluatedCallInfo {
pub args: Call,
pub name_span: Span,
}

View File

@ -1,4 +1,6 @@
use crate::{Example, Signature};
use crate::{BlockId, Example, ShellError, Signature, Value};
use super::CommandArgs;
pub trait Command {
fn name(&self) -> &str;
@ -13,6 +15,8 @@ pub trait Command {
""
}
fn run(&self, args: CommandArgs) -> Result<Value, ShellError>;
// fn run(&self, args: CommandArgs) -> Result<InputStream, ShellError> {
// let context = args.context.clone();
// let stream = self.run_with_actions(args)?;
@ -53,8 +57,8 @@ pub trait Command {
false
}
// Is a custom command i.e. def blah [] { }
fn is_custom(&self) -> bool {
false
// If command is a custom command i.e. def blah [] { }, get the block id
fn get_custom_command(&self) -> Option<BlockId> {
None
}
}

View File

@ -0,0 +1,7 @@
use super::{EvaluationContext, UnevaluatedCallInfo};
pub struct CommandArgs {
pub context: EvaluationContext,
pub call_info: UnevaluatedCallInfo,
pub input: crate::Value,
}

View File

@ -1,4 +1,5 @@
use crate::{Block, BlockId, Command, DeclId, Span, Type, VarId};
use super::Command;
use crate::{ast::Block, BlockId, DeclId, Span, Type, VarId};
use core::panic;
use std::{collections::HashMap, ops::Range, slice::Iter};

View File

@ -0,0 +1,106 @@
use super::EngineState;
use std::{cell::RefCell, collections::HashMap, rc::Rc};
use crate::{ShellError, Value, VarId};
pub struct EvaluationContext {
pub engine_state: Rc<RefCell<EngineState>>,
pub stack: Stack,
}
impl EvaluationContext {
pub fn get_var(&self, var_id: VarId) -> Result<Value, ShellError> {
self.stack.get_var(var_id)
}
pub fn enter_scope(&self) -> EvaluationContext {
Self {
engine_state: self.engine_state.clone(),
stack: self.stack.clone().enter_scope(),
}
}
pub fn add_var(&self, var_id: VarId, value: Value) {
self.stack.add_var(var_id, value);
}
pub fn add_env_var(&self, var: String, value: String) {
self.stack.add_env_var(var, value);
}
pub fn print_stack(&self) {
self.stack.print_stack();
}
}
#[derive(Debug)]
pub struct StackFrame {
pub vars: HashMap<VarId, Value>,
pub env_vars: HashMap<String, String>,
pub parent: Option<Stack>,
}
#[derive(Clone, Debug)]
pub struct Stack(Rc<RefCell<StackFrame>>);
impl Default for Stack {
fn default() -> Self {
Self::new()
}
}
impl Stack {
pub fn new() -> Stack {
Stack(Rc::new(RefCell::new(StackFrame {
vars: HashMap::new(),
env_vars: HashMap::new(),
parent: None,
})))
}
pub fn get_var(&self, var_id: VarId) -> Result<Value, ShellError> {
let this = self.0.borrow();
match this.vars.get(&var_id) {
Some(v) => Ok(v.clone()),
_ => {
if let Some(parent) = &this.parent {
parent.get_var(var_id)
} else {
Err(ShellError::InternalError("variable not found".into()))
}
}
}
}
pub fn add_var(&self, var_id: VarId, value: Value) {
let mut this = self.0.borrow_mut();
this.vars.insert(var_id, value);
}
pub fn add_env_var(&self, var: String, value: String) {
let mut this = self.0.borrow_mut();
this.env_vars.insert(var, value);
}
pub fn enter_scope(self) -> Stack {
Stack(Rc::new(RefCell::new(StackFrame {
vars: HashMap::new(),
env_vars: HashMap::new(),
parent: Some(self),
})))
}
pub fn print_stack(&self) {
println!("===frame===");
println!("vars:");
for (var, val) in &self.0.borrow().vars {
println!(" {}: {:?}", var, val);
}
println!("env vars:");
for (var, val) in &self.0.borrow().env_vars {
println!(" {}: {:?}", var, val);
}
if let Some(parent) = &self.0.borrow().parent {
parent.print_stack()
}
}
}

View File

@ -0,0 +1,11 @@
mod call_info;
mod command;
mod command_args;
mod engine_state;
mod evaluation_context;
pub use call_info::*;
pub use command::*;
pub use command_args::*;
pub use engine_state::*;
pub use evaluation_context::*;

View File

@ -1,35 +1,19 @@
mod block;
mod call;
mod command;
mod engine_state;
pub mod ast;
pub mod engine;
mod example;
mod expr;
mod expression;
mod id;
mod operator;
mod pipeline;
mod shell_error;
mod signature;
mod span;
mod statement;
mod syntax_shape;
mod ty;
mod value;
pub use block::*;
pub use call::*;
pub use command::*;
pub use engine_state::*;
pub use example::*;
pub use expr::*;
pub use expression::*;
pub use id::*;
pub use operator::*;
pub use pipeline::*;
pub use shell_error::*;
pub use signature::*;
pub use span::*;
pub use statement::*;
pub use syntax_shape::*;
pub use ty::*;
pub use value::*;

View File

@ -1,5 +1,5 @@
use crate::engine::Command;
use crate::BlockId;
use crate::Command;
use crate::SyntaxShape;
use crate::VarId;
@ -314,6 +314,10 @@ impl Command for Predeclaration {
fn usage(&self) -> &str {
&self.signature.usage
}
fn run(&self, _args: crate::engine::CommandArgs) -> Result<crate::Value, crate::ShellError> {
panic!("Internal error: can't run a predeclaration without a body")
}
}
struct BlockCommand {
@ -333,4 +337,12 @@ impl Command for BlockCommand {
fn usage(&self) -> &str {
&self.signature.usage
}
fn run(&self, _args: crate::engine::CommandArgs) -> Result<crate::Value, crate::ShellError> {
panic!("Internal error: can't run custom command with 'run', use block_id");
}
fn get_custom_command(&self) -> Option<BlockId> {
Some(self.block_id)
}
}