diff --git a/src/append.rs b/src/append.rs
index 415cf05..8819713 100644
--- a/src/append.rs
+++ b/src/append.rs
@@ -14,7 +14,7 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-/*
+
use crate::func::{FTable, Function, Args, Operation};
use crate::vars::{VTable};
use crate::segment::{Ctr, Ast, circuit, list_idx, list_append, new_ast};
@@ -27,7 +27,7 @@ pub fn get_append() -> Function {
loose_syms: false,
eval_lazy: false,
args: Args::Lazy(-1),
- function: Operation::Internal(
+ function: Operation::Internal(Box::new(
|a: Ast, _b: Rc>, _c: Rc>| -> Ctr {
let ptr = list_idx(a.clone(), 0);
match ptr {
@@ -63,6 +63,6 @@ pub fn get_append() -> Function {
}
}
}
- )
+ ))
};
-}*/
+}
diff --git a/src/config.rs b/src/config.rs
index 1a0a67e..0b45ba2 100644
--- a/src/config.rs
+++ b/src/config.rs
@@ -16,7 +16,7 @@
*/
use crate::vars::{VTable, define};
-use crate::func::{FTable, Args, Function, Operation, InternalOperation, func_declare};
+use crate::func::{FTable, Args, Function, Operation, func_declare};
use crate::segment::{Ast, Ctr};
use crate::lex::lex;
use crate::eval::eval;
@@ -25,13 +25,11 @@ use std::rc::Rc;
use std::cell::RefCell;
use std::fs;
-/*
-fn get_prompt_default() -> InternalOperation {
- |_: Ast, _: Rc>, _: Rc>| -> Ctr {
- print!("λ ");
- return Ctr::None;
- }
-}*/
+
+fn prompt_default_callback(_: Ast, _: Rc>, _: Rc>) -> Ctr {
+ print!("λ ");
+ return Ctr::None;
+}
pub fn configure(filename: String, vars: Rc>, mut funcs: Rc>) {
define(vars.clone(), String::from("CFG_RELISH_POSIX"), Rc::new(Ctr::String(String::from("0"))));
@@ -42,14 +40,14 @@ pub fn configure(filename: String, vars: Rc>, mut funcs: Rc println!("{}", s)
}
- /*
+
func_declare(funcs.clone(), Rc::new(RefCell::new(Function{
name: String::from("CFG_RELISH_PROMPT"),
loose_syms: false,
eval_lazy: false,
args: Args::Lazy(0),
- function: Operation::Internal(get_prompt_default())
- })));*/
+ function: Operation::Internal(Box::new(prompt_default_callback))
+ })));
match fs::read_to_string(filename) {
Err(s) => {
diff --git a/src/func.rs b/src/func.rs
index 7e6ac27..07b3b5a 100644
--- a/src/func.rs
+++ b/src/func.rs
@@ -26,7 +26,7 @@ use crate::eval::eval;
pub type FTable = HashMap>>;
// Standardized function signature for stdlib functions
-pub type InternalOperation = impl Fn(Ast, Rc>, Rc>) -> Ctr;
+//pub type InternalOperation = impl Fn(Ast, Rc>, Rc>) -> Ctr;
pub struct ExternalOperation {
// Un-evaluated abstract syntax tree
// TODO: Intermediate evaluation to simplify branches with no argument in them
@@ -41,7 +41,7 @@ pub struct ExternalOperation {
* or a syntax tree to eval with the arguments
*/
pub enum Operation {
- Internal(InternalOperation),
+ Internal(Box>, Rc>)->Ctr>),
External(ExternalOperation)
}
@@ -160,9 +160,10 @@ pub fn func_call(
}
match &called_func.function {
- Operation::Internal(f) => Ok((f)(n_args, vars, funcs)),
+ Operation::Internal(f) => {
+ return Ok(f(n_args, vars, funcs))
+ },
Operation::External(f) => {
-
for n in 0..f.arg_syms.len() {
let iter_arg = list_idx(n_args.clone(), n as u128);
diff --git a/src/lib.rs b/src/lib.rs
index 8afda30..633a639 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -15,7 +15,6 @@
* along with this program. If not, see .
*/
-#![feature(type_alias_impl_trait)]
mod segment;
mod lex;
@@ -31,16 +30,15 @@ pub mod ast {
pub use crate::segment::{Seg, Ctr, ast_to_string, Type, Ast, new_ast};
pub use crate::lex::lex;
pub use crate::func::{Function, Operation, FTable, Args,
- InternalOperation, ExternalOperation,
- func_declare, func_call};
+ ExternalOperation, func_declare, func_call};
pub use crate::vars::{VTable, define};
pub use crate::eval::eval;
}
pub mod stdlib {
pub use crate::stl::{get_stdlib};
-// pub use crate::str::{get_echo, get_concat};
-// pub use crate::append::{get_append};
+ pub use crate::str::{get_echo, get_concat};
+ pub use crate::append::{get_append};
pub use crate::vars::{get_export};
}
diff --git a/src/stl.rs b/src/stl.rs
index 64450eb..b03eb9d 100644
--- a/src/stl.rs
+++ b/src/stl.rs
@@ -16,8 +16,8 @@
*/
use crate::segment::{Ctr};
-//use crate::str::{get_echo, get_concat};
-//use crate::append::get_append;
+use crate::str::{get_echo, get_concat};
+use crate::append::get_append;
use crate::func::{FTable, func_declare};
use crate::vars::{VTable, get_export};
use std::rc::Rc;
@@ -25,7 +25,7 @@ use std::cell::RefCell;
pub fn get_stdlib(conf: Rc>) -> Result>, String> {
let ft = Rc::new(RefCell::new(FTable::new()));
- /* if let Some(s) = func_declare(ft.clone(), Rc::new(RefCell::new(get_echo()))) {
+ if let Some(s) = func_declare(ft.clone(), Rc::new(RefCell::new(get_echo()))) {
return Err(s)
}
if let Some(s) = func_declare(ft.clone(), Rc::new(RefCell::new(get_append()))) {
@@ -33,7 +33,7 @@ pub fn get_stdlib(conf: Rc>) -> Result>, Stri
}
if let Some(s) = func_declare(ft.clone(), Rc::new(RefCell::new(get_concat()))) {
return Err(s)
- }*/
+ }
let mut cfg_env = true;
match conf.borrow().get(&String::from("CFG_RELISH_ENV")) {
diff --git a/src/str.rs b/src/str.rs
index 19eb6bf..06aab18 100644
--- a/src/str.rs
+++ b/src/str.rs
@@ -14,7 +14,7 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-/*
+
use crate::func::{FTable, Function, Args, Operation};
use crate::vars::{VTable};
use crate::segment::{Ctr, Ast, circuit, ast_as_string};
@@ -29,7 +29,7 @@ pub fn get_echo() -> Function {
loose_syms: false,
eval_lazy: false,
args: Args::Lazy(-1),
- function: Operation::Internal(
+ function: Operation::Internal(Box::new(
|a: Ast, _b: Rc>, _c: Rc>| -> Ctr {
let mut string = String::from("");
if !circuit(a, &mut |arg: &Ctr| {
@@ -50,7 +50,7 @@ pub fn get_echo() -> Function {
}
return Ctr::None;
}
- )
+ ))
};
}
@@ -60,7 +60,7 @@ pub fn get_concat() -> Function {
loose_syms: false,
eval_lazy: false,
args: Args::Lazy(-1),
- function: Operation::Internal(
+ function: Operation::Internal(Box::new(
|a: Ast, _b: Rc>, _c: Rc>| -> Ctr {
let mut string = String::from("");
if !circuit(a, &mut |arg: &Ctr| {
@@ -80,7 +80,6 @@ pub fn get_concat() -> Function {
}
return Ctr::String(string);
}
- )
+ ))
};
}
-*/
diff --git a/src/vars.rs b/src/vars.rs
index cc5d8dd..441d139 100644
--- a/src/vars.rs
+++ b/src/vars.rs
@@ -21,7 +21,7 @@ use std::collections::HashMap;
use std::env;
use crate::segment::{Ctr, Ast, ast_to_string};
use crate::eval::eval;
-use crate::func::{Function, Operation, InternalOperation, Args, FTable};
+use crate::func::{Function, Operation, Args, FTable};
/* Mapping between a string token and a tree of Segments
* The string token can be found in any Ctr::Symbol value
* it is expected that the trees stored are already evaluated
@@ -40,63 +40,76 @@ pub fn define(
}
pub fn get_export(env_cfg: bool) -> Function {
- return Function{
- name: String::from("export"),
- loose_syms: true,
- eval_lazy: true,
- args: Args::Lazy(2),
- function: Operation::Internal(get_export_callback(env_cfg)),
- };
+ // This is the most hilarious way to work around the lifetime of env_cfg
+ // TODO: figure out the RUSTEY way of doing this
+ if env_cfg {
+ return Function{
+ name: String::from("export"),
+ loose_syms: true,
+ eval_lazy: true,
+ args: Args::Lazy(2),
+ function: Operation::Internal(Box::new(|a: Ast, b: Rc>, c: Rc>| -> Ctr {
+ export_callback(true, a, b, c)
+ })),
+ };
+ } else {
+ return Function{
+ name: String::from("export"),
+ loose_syms: true,
+ eval_lazy: true,
+ args: Args::Lazy(2),
+ function: Operation::Internal(Box::new(|a: Ast, b: Rc>, c: Rc>| -> Ctr {
+ export_callback(false, a, b, c)
+ })),
+ };
+ }
}
-fn get_export_callback(env_cfg: bool) -> InternalOperation {
- InternalOperation(|a: Ast, b: Rc>, c: Rc>| -> Ctr {
- let inner = a.borrow_mut();
- match &inner.car {
- Ctr::Symbol(identifier) => {
- match &inner.cdr {
- Ctr::Seg(tree) => {
- match eval(tree.clone(), b.clone(), c.clone(), false) {
- Ok(seg) => {
- match seg {
- Ctr::Seg(val) => {
- let val_tmp = val.borrow().clone();
- define(b, identifier.to_string(), Rc::new(val_tmp.car));
- if env_cfg {
- match val_tmp.car {
- Ctr::Symbol(s) => env::set_var(identifier, s),
- Ctr::String(s) => env::set_var(identifier, s),
- Ctr::Integer(i) => env::set_var(identifier, format!("{}", i)),
- Ctr::Float(f) => env::set_var(identifier, format!("{}", f)),
- Ctr::Bool(b) => env::set_var(identifier, format!("{}", b)),
- Ctr::Seg(c) => env::set_var(identifier, ast_to_string(c)),
- Ctr::None => ()
- }
+fn export_callback(env_cfg: bool, a: Ast, b: Rc>, c: Rc>) -> Ctr{
+ let inner = a.borrow_mut();
+ match &inner.car {
+ Ctr::Symbol(identifier) => {
+ match &inner.cdr {
+ Ctr::Seg(tree) => {
+ match eval(tree.clone(), b.clone(), c.clone(), false) {
+ Ok(seg) => {
+ match seg {
+ Ctr::Seg(val) => {
+ define(b, identifier.to_string(), Rc::new(val.borrow().clone().car));
+ if env_cfg {
+ match val.borrow().clone().car {
+ Ctr::Symbol(s) => env::set_var(identifier, s),
+ Ctr::String(s) => env::set_var(identifier, s),
+ Ctr::Integer(i) => env::set_var(identifier, format!("{}", i)),
+ Ctr::Float(f) => env::set_var(identifier, format!("{}", f)),
+ Ctr::Bool(b) => env::set_var(identifier, format!("{}", b)),
+ Ctr::Seg(c) => env::set_var(identifier, ast_to_string(c)),
+ Ctr::None => ()
}
- },
+ }
+ },
- _ => eprintln!("impossible args to export")
- }
- },
+ _ => eprintln!("impossible args to export")
+ }
+ },
- Err(e) => eprintln!("couldnt eval symbol: {}", e)
- }
- },
+ Err(e) => eprintln!("couldnt eval symbol: {}", e)
+ }
+ },
- Ctr::None => {
- (*b).borrow_mut().remove(identifier);
- if env_cfg {
- // TODO: unset variable
- }
- },
+ Ctr::None => {
+ (*b).borrow_mut().remove(identifier);
+ if env_cfg {
+ // TODO: unset variable
+ }
+ },
- _ => eprintln!("args not in standard form")
- }
- },
+ _ => eprintln!("args not in standard form")
+ }
+ },
- _ => eprintln!("first argument to export must be a symbol")
- }
+ _ => eprintln!("first argument to export must be a symbol")
+ }
- return Ctr::None;
- })
+ return Ctr::None;
}
diff --git a/tests/test_func.rs b/tests/test_func.rs
index 6868fe4..4a522ca 100644
--- a/tests/test_func.rs
+++ b/tests/test_func.rs
@@ -12,7 +12,7 @@ mod func_tests {
loose_syms: false,
eval_lazy: false,
args: Args::Strict(vec![Type::Bool]),
- function: Operation::Internal(
+ function: Operation::Internal(Box::new(
|a: Ast, _b: Rc>, _c: Rc>| -> Ctr {
let inner = a.borrow();
let mut is_bool = false;
@@ -22,7 +22,7 @@ mod func_tests {
Ctr::Bool(is_bool)
}
- )
+ ))
};
let ft = Rc::new(RefCell::new(FTable::new()));
let vt = Rc::new(RefCell::new(VTable::new()));
@@ -174,7 +174,7 @@ mod func_tests {
loose_syms: false,
eval_lazy: false,
args: Args::Strict(vec![Type::Bool]),
- function: Operation::Internal(
+ function: Operation::Internal(Box::new(
|a: Ast, _b: Rc>, _c: Rc>| -> Ctr {
let inner = a.borrow();
if let Ctr::Bool(b) = &inner.car {
@@ -187,7 +187,7 @@ mod func_tests {
Ctr::None
}
}
- )
+ ))
};
match lex("((test_inner true))".to_string()) {