├── .gitignore ├── .vscode └── launch.json ├── Cargo.toml ├── LICENSE ├── README.md ├── src ├── expr │ ├── interpreter.rs │ ├── mod.rs │ ├── serde.rs │ └── symbols │ │ ├── arithmetic.rs │ │ ├── bindings.rs │ │ ├── branching.rs │ │ ├── collections.rs │ │ ├── comparators.rs │ │ ├── functions.rs │ │ ├── lambda.rs │ │ ├── logic.rs │ │ ├── misc.rs │ │ ├── mod.rs │ │ ├── num_types.rs │ │ ├── stream.rs │ │ └── utils.rs ├── integrated │ ├── lisp.rs │ └── mod.rs ├── lexer │ ├── lisp.rs │ └── mod.rs ├── lib.rs ├── parser │ ├── lisp.rs │ └── mod.rs └── types │ ├── custom_types │ ├── any.rs │ ├── bytes.rs │ ├── id.rs │ ├── map.rs │ ├── mod.rs │ ├── owned_map.rs │ ├── pos.rs │ └── shared_map.rs │ ├── macros.rs │ ├── mod.rs │ ├── owned_value.rs │ └── referred.rs └── tests └── tests.rs /.gitignore: -------------------------------------------------------------------------------- 1 | # Generated by Cargo 2 | # will have compiled files and executables 3 | /target/ 4 | 5 | # Remove Cargo.lock from gitignore if creating an executable, leave it for libraries 6 | # More information here http://doc.crates.io/guide.html#cargotoml-vs-cargolock 7 | Cargo.lock 8 | 9 | # These are backup files generated by rustfmt 10 | **/*.rs.bk 11 | 12 | .idea 13 | Dovahkiin.iml -------------------------------------------------------------------------------- /.vscode/launch.json: -------------------------------------------------------------------------------- 1 | { 2 | // Use IntelliSense to learn about possible attributes. 3 | // Hover to view descriptions of existing attributes. 4 | // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 5 | "version": "0.2.0", 6 | "configurations": [ 7 | { 8 | "type": "lldb", 9 | "request": "launch", 10 | "name": "Debug", 11 | "program": "${workspaceFolder}/", 12 | "args": [], 13 | "cwd": "${workspaceFolder}" 14 | } 15 | ] 16 | } -------------------------------------------------------------------------------- /Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "dovahkiin" 3 | version = "0.1.0" 4 | authors = ["Hao Shi "] 5 | edition = "2021" 6 | 7 | [lib] 8 | name = "dovahkiin" 9 | 10 | [[test]] 11 | name = "tests" 12 | 13 | [dependencies] 14 | serde = "*" 15 | serde_derive = "*" 16 | byteorder = "1" 17 | bifrost = { git = "https://github.com/shisoft/bifrost", branch = "develop" } 18 | bifrost_plugins = { git = "https://github.com/shisoft/bifrost", branch = "develop" } 19 | bifrost_hasher = { git = "https://github.com/shisoft/bifrost", branch = "develop" } 20 | lazy_static = "*" 21 | log = "*" 22 | ahash = "0.8.11" 23 | smallvec = {version = "1.15.0", features = ["serde"]} 24 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | GNU LESSER GENERAL PUBLIC LICENSE 2 | Version 3, 29 June 2007 3 | 4 | Copyright (C) 2007 Free Software Foundation, Inc. 5 | Everyone is permitted to copy and distribute verbatim copies 6 | of this license document, but changing it is not allowed. 7 | 8 | 9 | This version of the GNU Lesser General Public License incorporates 10 | the terms and conditions of version 3 of the GNU General Public 11 | License, supplemented by the additional permissions listed below. 12 | 13 | 0. Additional Definitions. 14 | 15 | As used herein, "this License" refers to version 3 of the GNU Lesser 16 | General Public License, and the "GNU GPL" refers to version 3 of the GNU 17 | General Public License. 18 | 19 | "The Library" refers to a covered work governed by this License, 20 | other than an Application or a Combined Work as defined below. 21 | 22 | An "Application" is any work that makes use of an interface provided 23 | by the Library, but which is not otherwise based on the Library. 24 | Defining a subclass of a class defined by the Library is deemed a mode 25 | of using an interface provided by the Library. 26 | 27 | A "Combined Work" is a work produced by combining or linking an 28 | Application with the Library. The particular version of the Library 29 | with which the Combined Work was made is also called the "Linked 30 | Version". 31 | 32 | The "Minimal Corresponding Source" for a Combined Work means the 33 | Corresponding Source for the Combined Work, excluding any source code 34 | for portions of the Combined Work that, considered in isolation, are 35 | based on the Application, and not on the Linked Version. 36 | 37 | The "Corresponding Application Code" for a Combined Work means the 38 | object code and/or source code for the Application, including any data 39 | and utility programs needed for reproducing the Combined Work from the 40 | Application, but excluding the System Libraries of the Combined Work. 41 | 42 | 1. Exception to Section 3 of the GNU GPL. 43 | 44 | You may convey a covered work under sections 3 and 4 of this License 45 | without being bound by section 3 of the GNU GPL. 46 | 47 | 2. Conveying Modified Versions. 48 | 49 | If you modify a copy of the Library, and, in your modifications, a 50 | facility refers to a function or data to be supplied by an Application 51 | that uses the facility (other than as an argument passed when the 52 | facility is invoked), then you may convey a copy of the modified 53 | version: 54 | 55 | a) under this License, provided that you make a good faith effort to 56 | ensure that, in the event an Application does not supply the 57 | function or data, the facility still operates, and performs 58 | whatever part of its purpose remains meaningful, or 59 | 60 | b) under the GNU GPL, with none of the additional permissions of 61 | this License applicable to that copy. 62 | 63 | 3. Object Code Incorporating Material from Library Header Files. 64 | 65 | The object code form of an Application may incorporate material from 66 | a header file that is part of the Library. You may convey such object 67 | code under terms of your choice, provided that, if the incorporated 68 | material is not limited to numerical parameters, data structure 69 | layouts and accessors, or small macros, inline functions and templates 70 | (ten or fewer lines in length), you do both of the following: 71 | 72 | a) Give prominent notice with each copy of the object code that the 73 | Library is used in it and that the Library and its use are 74 | covered by this License. 75 | 76 | b) Accompany the object code with a copy of the GNU GPL and this license 77 | document. 78 | 79 | 4. Combined Works. 80 | 81 | You may convey a Combined Work under terms of your choice that, 82 | taken together, effectively do not restrict modification of the 83 | portions of the Library contained in the Combined Work and reverse 84 | engineering for debugging such modifications, if you also do each of 85 | the following: 86 | 87 | a) Give prominent notice with each copy of the Combined Work that 88 | the Library is used in it and that the Library and its use are 89 | covered by this License. 90 | 91 | b) Accompany the Combined Work with a copy of the GNU GPL and this license 92 | document. 93 | 94 | c) For a Combined Work that displays copyright notices during 95 | execution, include the copyright notice for the Library among 96 | these notices, as well as a reference directing the user to the 97 | copies of the GNU GPL and this license document. 98 | 99 | d) Do one of the following: 100 | 101 | 0) Convey the Minimal Corresponding Source under the terms of this 102 | License, and the Corresponding Application Code in a form 103 | suitable for, and under terms that permit, the user to 104 | recombine or relink the Application with a modified version of 105 | the Linked Version to produce a modified Combined Work, in the 106 | manner specified by section 6 of the GNU GPL for conveying 107 | Corresponding Source. 108 | 109 | 1) Use a suitable shared library mechanism for linking with the 110 | Library. A suitable mechanism is one that (a) uses at run time 111 | a copy of the Library already present on the user's computer 112 | system, and (b) will operate properly with a modified version 113 | of the Library that is interface-compatible with the Linked 114 | Version. 115 | 116 | e) Provide Installation Information, but only if you would otherwise 117 | be required to provide such information under section 6 of the 118 | GNU GPL, and only to the extent that such information is 119 | necessary to install and execute a modified version of the 120 | Combined Work produced by recombining or relinking the 121 | Application with a modified version of the Linked Version. (If 122 | you use option 4d0, the Installation Information must accompany 123 | the Minimal Corresponding Source and Corresponding Application 124 | Code. If you use option 4d1, you must provide the Installation 125 | Information in the manner specified by section 6 of the GNU GPL 126 | for conveying Corresponding Source.) 127 | 128 | 5. Combined Libraries. 129 | 130 | You may place library facilities that are a work based on the 131 | Library side by side in a single library together with other library 132 | facilities that are not Applications and are not covered by this 133 | License, and convey such a combined library under terms of your 134 | choice, if you do both of the following: 135 | 136 | a) Accompany the combined library with a copy of the same work based 137 | on the Library, uncombined with any other library facilities, 138 | conveyed under the terms of this License. 139 | 140 | b) Give prominent notice with the combined library that part of it 141 | is a work based on the Library, and explaining where to find the 142 | accompanying uncombined form of the same work. 143 | 144 | 6. Revised Versions of the GNU Lesser General Public License. 145 | 146 | The Free Software Foundation may publish revised and/or new versions 147 | of the GNU Lesser General Public License from time to time. Such new 148 | versions will be similar in spirit to the present version, but may 149 | differ in detail to address new problems or concerns. 150 | 151 | Each version is given a distinguishing version number. If the 152 | Library as you received it specifies that a certain numbered version 153 | of the GNU Lesser General Public License "or any later version" 154 | applies to it, you have the option of following the terms and 155 | conditions either of that published version or of any later version 156 | published by the Free Software Foundation. If the Library as you 157 | received it does not specify a version number of the GNU Lesser 158 | General Public License, you may choose any version of the GNU Lesser 159 | General Public License ever published by the Free Software Foundation. 160 | 161 | If the Library as you received it specifies that a proxy can decide 162 | whether future versions of the GNU Lesser General Public License shall 163 | apply, that proxy's public statement of acceptance of any version is 164 | permanent authorization for you to choose that version for the 165 | Library. 166 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Dovahkiin 2 | Functional expressions interpreter and compiler infrastructure 3 | 4 | Serializable and runnable code to power Morpheus query language. It only have interpreter for s-expressions right now, will provide a compiler to LLVM IR in the future. 5 | -------------------------------------------------------------------------------- /src/expr/interpreter.rs: -------------------------------------------------------------------------------- 1 | use bifrost_hasher::hash_str; 2 | 3 | use crate::expr::symbols::misc; 4 | use crate::expr::SExpr; 5 | use crate::types::SharedValue; 6 | use std::collections::{BTreeMap, LinkedList}; 7 | use std::mem; 8 | use std::ops::{Deref, DerefMut}; 9 | use std::rc::Rc; 10 | 11 | use super::symbols::bindings::bind; 12 | use super::symbols::bindings::bind_by_name; 13 | 14 | pub const DEFAULT_GLOBAL_VAL: SharedValue = SharedValue::NA; 15 | 16 | #[derive(Debug)] 17 | pub struct Environment<'a> { 18 | pub bindings: BTreeMap>>>, 19 | pub global_val: &'a SharedValue<'a> 20 | } 21 | 22 | impl<'a> Environment<'a> { 23 | pub fn new() -> Self { 24 | Environment { 25 | bindings: BTreeMap::new(), 26 | global_val: &DEFAULT_GLOBAL_VAL 27 | } 28 | } 29 | pub fn get_mut_bindings(&mut self) -> &mut BTreeMap>>> { 30 | &mut self.bindings 31 | } 32 | } 33 | 34 | pub fn eval_all<'a>( 35 | exprs: Vec>, 36 | env: &mut Environment<'a>, 37 | ) -> Result>, String> { 38 | let mut result = Vec::with_capacity(exprs.len()); 39 | for expr in exprs { 40 | result.push(expr.eval(env)?); 41 | } 42 | Ok(result) 43 | } 44 | 45 | pub fn do_eval<'a>(exprs: Vec>, env: &mut Environment<'a>) -> Result, String> { 46 | misc::do_(exprs, env) 47 | } 48 | 49 | #[derive(Debug)] 50 | pub struct Interpreter<'a> { 51 | env: Environment<'a>, 52 | } 53 | 54 | impl<'a> Interpreter<'a> { 55 | pub fn new() -> Self { 56 | Interpreter { 57 | env: Environment::new(), 58 | } 59 | } 60 | pub fn eval(&mut self, exprs: Vec>) -> Result, String> { 61 | do_eval(exprs, &mut self.env) 62 | } 63 | pub fn bind<'b>(&mut self, name: &'b str, expr: SExpr<'a>) { 64 | bind_by_name(&mut self.env, name, expr) 65 | } 66 | pub fn bind_by_id(&mut self, id: u64, expr: SExpr<'a>) { 67 | bind(&mut self.env, id, expr) 68 | } 69 | pub fn get_env(&mut self) -> &mut Environment<'a> { 70 | &mut self.env 71 | } 72 | pub fn clear(&mut self) { 73 | self.env.bindings.clear(); 74 | } 75 | pub fn unbind<'b>(&mut self, name: &'b str) -> Option> { 76 | self.env 77 | .bindings 78 | .remove(&hash_str(name)) 79 | .and_then(|mut list| { 80 | list.pop_front() 81 | .map(|rc| Rc::>::into_inner(rc).unwrap()) 82 | }) 83 | } 84 | pub fn set_global_val(&mut self, val: &'a SharedValue<'a>) { 85 | self.env.global_val = val; 86 | } 87 | pub fn guarded_set_global_val<'b, 'c>(&'a mut self, val: &'b SharedValue<'c>) -> GlobalValGuard<'a> { 88 | unsafe { 89 | self.unsafe_set_global_val(val); 90 | } 91 | GlobalValGuard { 92 | inter: self 93 | } 94 | } 95 | pub unsafe fn unsafe_set_global_val<'b, 'c>(&mut self, val: &'b SharedValue<'c>) { 96 | self.env.global_val = mem::transmute(val); 97 | } 98 | pub fn unset_global_val(&mut self) -> &'a SharedValue<'a> { 99 | mem::replace(&mut self.env.global_val, &DEFAULT_GLOBAL_VAL) 100 | } 101 | } 102 | 103 | pub struct GlobalValGuard<'a> { 104 | inter: & 'a mut Interpreter<'a>, 105 | } 106 | 107 | impl <'a> Drop for GlobalValGuard<'a> { 108 | fn drop(&mut self) { 109 | self.inter.unset_global_val(); 110 | } 111 | } 112 | 113 | impl <'a> Deref for GlobalValGuard<'a> { 114 | type Target = Interpreter<'a>; 115 | 116 | fn deref(&self) -> &Self::Target { 117 | self.inter 118 | } 119 | } 120 | 121 | impl <'a> DerefMut for GlobalValGuard<'a> { 122 | fn deref_mut(&mut self) -> &mut Self::Target { 123 | self.inter 124 | } 125 | } -------------------------------------------------------------------------------- /src/expr/mod.rs: -------------------------------------------------------------------------------- 1 | use crate::parser::lisp::ParserExpr; 2 | use crate::types::referred::OwnedValueRef; 3 | use crate::types::{OwnedValue, SharedValue}; 4 | use bifrost_hasher::hash_str; 5 | use std::borrow::Borrow; 6 | use std::rc::Rc; 7 | 8 | use self::interpreter::Environment; 9 | 10 | #[macro_use] 11 | pub mod symbols; 12 | pub mod interpreter; 13 | pub mod serde; 14 | 15 | #[derive(Debug, Clone, PartialEq, Eq)] 16 | pub enum Value<'a> { 17 | Owned(OwnedValue), 18 | Shared(SharedValue<'a>), 19 | Ref(OwnedValueRef), 20 | } 21 | 22 | impl<'a> Value<'a> { 23 | pub const fn null() -> Self { 24 | Self::Owned(OwnedValue::Null) 25 | } 26 | pub fn shared(&'a self) -> SharedValue<'a> { 27 | match self { 28 | Value::Owned(v) => v.shared(), 29 | Value::Shared(v) => v.clone(), 30 | Value::Ref(v) => v.shared(), 31 | } 32 | } 33 | pub fn owned(val: OwnedValue) -> Self { 34 | Value::Owned(val) 35 | } 36 | pub fn into_owned(self) -> OwnedValue { 37 | match self { 38 | Value::Owned(v) => v, 39 | Value::Shared(v) => v.owned(), 40 | Value::Ref(v) => (&*v).clone(), 41 | } 42 | } 43 | pub fn into_ref(self) -> OwnedValueRef { 44 | match self { 45 | Value::Owned(v) => OwnedValueRef::new(v), 46 | Value::Shared(v) => OwnedValueRef::new(v.owned()), 47 | Value::Ref(v) => v, 48 | } 49 | } 50 | } 51 | 52 | #[derive(Debug, Clone, PartialEq, Eq)] 53 | pub enum SExpr<'a> { 54 | Symbol(String), 55 | ISymbol(u64, String), 56 | Keyword(u64, String), 57 | Value(Value<'a>), 58 | List(Vec>), 59 | Vec(Vec>), 60 | META(Box), 61 | LAMBDA(Vec>, Vec>), 62 | } 63 | 64 | impl<'a> SExpr<'a> { 65 | pub fn eval(self, env: &mut Environment<'a>) -> Result, String> { 66 | match self { 67 | SExpr::List(exprs) => { 68 | if exprs.len() == 0 { 69 | Ok(SExpr::Value(Value::null())) 70 | } else { 71 | let mut iter = exprs.into_iter(); 72 | let func = iter.next().unwrap().eval(env)?; 73 | Ok(symbols::functions::eval_function( 74 | &func, 75 | iter.collect(), 76 | env, 77 | )?) 78 | } 79 | } 80 | SExpr::ISymbol(symbol_id, sym_name) => { 81 | let env_bind_ref; 82 | let bindings = env.get_mut_bindings(); 83 | env_bind_ref = if let Some(binding_list) = bindings.get(&symbol_id) { 84 | binding_list.front().cloned() 85 | } else { 86 | None 87 | }; 88 | if let Some(binding) = env_bind_ref { 89 | let bind_expr: &SExpr = binding.borrow(); 90 | Ok(bind_expr.clone()) 91 | } else { 92 | let param = crate::types::Value::get_by_id(env.global_val, symbol_id); 93 | if param != &SharedValue::Null { 94 | Ok(SExpr::from_shared_value(param.clone())) 95 | } else { 96 | Ok(SExpr::ISymbol(symbol_id, sym_name)) 97 | } 98 | } 99 | } 100 | _ => Ok(self), 101 | } 102 | } 103 | pub fn from_owned_value(val: OwnedValue) -> Self { 104 | Self::Value(Value::Owned(val)) 105 | } 106 | pub fn from_shared_value(val: SharedValue<'a>) -> Self { 107 | Self::Value(Value::Shared(val)) 108 | } 109 | pub fn shared_val(&'a self) -> Option> { 110 | if let SExpr::Value(v) = self { 111 | Some(v.shared()) 112 | } else { 113 | None 114 | } 115 | } 116 | pub fn owned_val(self) -> Option { 117 | if let SExpr::Value(v) = self { 118 | match v { 119 | Value::Owned(v) => Some(v), 120 | Value::Shared(v) => Some(v.owned()), 121 | Value::Ref(v) => Some((&*v).clone()), 122 | } 123 | } else { 124 | None 125 | } 126 | } 127 | pub fn shared(&'a self) -> Self { 128 | match self { 129 | SExpr::Value(Value::Owned(ref owned)) => SExpr::Value(Value::Shared(owned.shared())), 130 | SExpr::Value(Value::Ref(ref owned)) => SExpr::Value(Value::Shared(owned.shared())), 131 | _ => self.clone(), 132 | } 133 | } 134 | pub fn is_empty(&self) -> bool { 135 | match self { 136 | &SExpr::List(ref l) => l.is_empty(), 137 | &SExpr::Vec(ref v) => v.is_empty(), 138 | _ => false, 139 | } 140 | } 141 | } 142 | 143 | impl ParserExpr for SExpr<'_> { 144 | fn list(data: Vec) -> Self { 145 | Self::List(data) 146 | } 147 | 148 | fn vec(data: Vec) -> Self { 149 | Self::Vec(data) 150 | } 151 | 152 | fn symbol(name: String) -> Self { 153 | Self::ISymbol(hash_str(&name), name) 154 | } 155 | 156 | fn owned_val(val: OwnedValue) -> Self { 157 | Self::from_owned_value(val) 158 | } 159 | 160 | fn keyword(name: String) -> Self { 161 | Self::Keyword(hash_str(&name), name) 162 | } 163 | 164 | fn into_val(self) -> Result { 165 | match self { 166 | SExpr::Symbol(s) => Ok(OwnedValue::String(s)), 167 | SExpr::ISymbol(_, s) => Ok(OwnedValue::String(s)), 168 | SExpr::Value(v) => Ok(v.into_owned()), 169 | SExpr::List(l) => array_from_exprs(l), 170 | SExpr::Vec(l) => array_from_exprs(l), 171 | SExpr::Keyword(_, s) => Ok(OwnedValue::String(s)), 172 | SExpr::META(m) => Err(format!("Cannot have meta as value {:?}", m)), 173 | SExpr::LAMBDA(i, o) => Err(format!("Cannot have lambda as value {:?} -> {:?}", i, o)), 174 | } 175 | } 176 | } 177 | 178 | fn array_from_exprs(l: Vec) -> Result { 179 | let mut res = vec![]; 180 | for ele in l.into_iter().map(SExpr::into_val) { 181 | let val = ele?; 182 | res.push(val); 183 | } 184 | return Ok(OwnedValue::Array(res)); 185 | } 186 | -------------------------------------------------------------------------------- /src/expr/serde.rs: -------------------------------------------------------------------------------- 1 | use crate::types::OwnedValue; 2 | use bifrost_hasher::hash_str; 3 | 4 | use crate::expr::Value; 5 | 6 | use super::{symbols::ParserExpr, SExpr}; 7 | 8 | #[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq)] 9 | pub enum Expr { 10 | NA, 11 | Symbol(u64, String), 12 | Value(OwnedValue), 13 | List(Vec), 14 | Vec(Vec), 15 | Keyword(u64, String), 16 | META(Box), 17 | LAMBDA(Vec, Vec), 18 | } 19 | 20 | fn sexpr_list_to_expr_list(list: Vec) -> Vec { 21 | list.into_iter().map(|e| Expr::from_sexpr(e)).collect() 22 | } 23 | 24 | fn expr_list_to_sexpr_list<'a>(list: Vec) -> Vec> { 25 | list.into_iter().map(|e| e.to_sexpr()).collect() 26 | } 27 | 28 | impl Expr { 29 | pub fn from_sexpr<'a>(sexpr: SExpr<'a>) -> Self { 30 | match sexpr { 31 | SExpr::Symbol(s) => Self::Symbol(hash_str(&s), s), 32 | SExpr::ISymbol(i, s) => Self::Symbol(i, s), 33 | SExpr::Keyword(id, name) => Self::Keyword(id, name), 34 | SExpr::Value(v) => Self::Value(match v { 35 | Value::Owned(o) => o, 36 | Value::Shared(s) => s.owned(), 37 | Value::Ref(r) => (&*r).clone(), 38 | }), 39 | SExpr::List(l) => Self::List(sexpr_list_to_expr_list(l)), 40 | SExpr::Vec(v) => Self::Vec(sexpr_list_to_expr_list(v)), 41 | SExpr::META(v) => Self::META(Box::new(Self::from_sexpr(*v))), 42 | SExpr::LAMBDA(p, b) => { 43 | Self::LAMBDA(sexpr_list_to_expr_list(p), sexpr_list_to_expr_list(b)) 44 | } 45 | } 46 | } 47 | 48 | pub fn to_sexpr<'a>(self) -> SExpr<'a> { 49 | match self { 50 | Expr::Symbol(i, s) => SExpr::ISymbol(i, s), 51 | Expr::Keyword(id, name) => SExpr::Keyword(id, name), 52 | Expr::Value(v) => SExpr::Value(Value::Owned(v)), 53 | Expr::List(l) => SExpr::List(expr_list_to_sexpr_list(l)), 54 | Expr::Vec(v) => SExpr::Vec(expr_list_to_sexpr_list(v)), 55 | Expr::META(v) => SExpr::META(Box::new(v.to_sexpr())), 56 | Expr::LAMBDA(p, b) => { 57 | SExpr::LAMBDA(expr_list_to_sexpr_list(p), expr_list_to_sexpr_list(b)) 58 | } 59 | Expr::NA => unreachable!(), 60 | } 61 | } 62 | pub fn is_empty(&self) -> bool { 63 | match self { 64 | &Expr::List(ref l) => l.is_empty(), 65 | &Expr::Vec(ref v) => v.is_empty(), 66 | _ => false, 67 | } 68 | } 69 | 70 | pub fn nothing() -> Self { 71 | Self::List(vec![]) 72 | } 73 | 74 | pub fn with_symbol_id_only<'a>(name: &'a str) -> Self { 75 | Self::Symbol(hash_str(name), String::new()) 76 | } 77 | } 78 | 79 | impl ParserExpr for Expr { 80 | fn list(data: Vec) -> Self { 81 | Self::List(data) 82 | } 83 | 84 | fn vec(data: Vec) -> Self { 85 | Self::Vec(data) 86 | } 87 | 88 | fn symbol(name: String) -> Self { 89 | Self::Symbol(hash_str(&name), name) 90 | } 91 | 92 | fn keyword(name: String) -> Self { 93 | Self::Keyword(hash_str(&name), name) 94 | } 95 | 96 | fn owned_val(val: OwnedValue) -> Self { 97 | Self::Value(val) 98 | } 99 | 100 | fn into_val(self) -> Result { 101 | match self { 102 | Expr::Symbol(_, s) => Ok(OwnedValue::String(s)), 103 | Expr::Value(v) => Ok(v), 104 | Expr::List(l) => array_from_exprs(l), 105 | Expr::Vec(l) => array_from_exprs(l), 106 | Expr::Keyword(_, s) => Ok(OwnedValue::String(s)), 107 | Expr::META(m) => Err(format!("Cannot have meta as value {:?}", m)), 108 | Expr::LAMBDA(i, o) => Err(format!("Cannot have lambda as value {:?} -> {:?}", i, o)), 109 | Expr::NA => Ok(OwnedValue::NA) 110 | } 111 | } 112 | } 113 | 114 | fn array_from_exprs(l: Vec) -> Result { 115 | let mut res = vec![]; 116 | for ele in l.into_iter().map(Expr::into_val) { 117 | let val = ele?; 118 | res.push(val); 119 | } 120 | return Ok(OwnedValue::Array(res)); 121 | } 122 | -------------------------------------------------------------------------------- /src/expr/symbols/arithmetic.rs: -------------------------------------------------------------------------------- 1 | use super::*; 2 | 3 | macro_rules! reduce { 4 | ($type: ident, $values: ident, $exp: expr) => {{ 5 | if let Some((Some(first), elements)) = 6 | $values.split_first().map(|(f, es)| (f.shared_val(), es)) 7 | { 8 | if let SharedValue::$type(n) = first { 9 | let mut result = *n; 10 | for val in elements { 11 | let val = val.shared_val(); 12 | if let Some(SharedValue::$type(n)) = val { 13 | result = $exp(result, n); 14 | } else { 15 | return Err(format!( 16 | "Type not match, expect {} found {:?}", 17 | stringify!($type), 18 | val 19 | )); 20 | } 21 | } 22 | Ok(SExpr::from_owned_value(OwnedValue::$type(result))) 23 | } else { 24 | Err(format!( 25 | "Type not match on the first value, expect {} found {:?}", 26 | stringify!($type), 27 | first 28 | )) 29 | } 30 | } else { 31 | Err("Cannot do reduce on values".to_string()) 32 | } 33 | }}; 34 | } 35 | 36 | macro_rules! add_ { 37 | ($type: ident, $values: ident) => {{ 38 | return reduce!($type, $values, |result, n| { result + n }); 39 | }}; 40 | } 41 | 42 | macro_rules! subtract_ { 43 | ($type: ident, $values: ident) => {{ 44 | return reduce!($type, $values, |result, n| { result - n }); 45 | }}; 46 | } 47 | 48 | macro_rules! multiply_ { 49 | ($type: ident, $values: ident) => {{ 50 | return reduce!($type, $values, |result, n| { result * n }); 51 | }}; 52 | } 53 | 54 | macro_rules! divide_ { 55 | ($type: ident, $values: ident) => {{ 56 | return reduce!($type, $values, |result, n| { result / n }); 57 | }}; 58 | } 59 | 60 | pub fn add(values: Vec) -> Result { 61 | match values.get(0).unwrap().shared_val() { 62 | Some(SharedValue::U8(_)) => add_!(U8, values), 63 | Some(SharedValue::U16(_)) => add_!(U16, values), 64 | Some(SharedValue::U32(_)) => add_!(U32, values), 65 | Some(SharedValue::U64(_)) => add_!(U64, values), 66 | Some(SharedValue::I8(_)) => add_!(I8, values), 67 | Some(SharedValue::I16(_)) => add_!(I16, values), 68 | Some(SharedValue::I32(_)) => add_!(I32, values), 69 | Some(SharedValue::I64(_)) => add_!(I64, values), 70 | Some(SharedValue::F32(_)) => add_!(F32, values), 71 | Some(SharedValue::F64(_)) => add_!(F64, values), 72 | _ => Err(format!("Type cannot be added {:?}", values)), 73 | } 74 | } 75 | 76 | pub fn subtract(values: Vec) -> Result { 77 | match values.get(0).unwrap().shared_val() { 78 | Some(SharedValue::U8(_)) => subtract_!(U8, values), 79 | Some(SharedValue::U16(_)) => subtract_!(U16, values), 80 | Some(SharedValue::U32(_)) => subtract_!(U32, values), 81 | Some(SharedValue::U64(_)) => subtract_!(U64, values), 82 | Some(SharedValue::I8(_)) => subtract_!(I8, values), 83 | Some(SharedValue::I16(_)) => subtract_!(I16, values), 84 | Some(SharedValue::I32(_)) => subtract_!(I32, values), 85 | Some(SharedValue::I64(_)) => subtract_!(I64, values), 86 | Some(SharedValue::F32(_)) => subtract_!(F32, values), 87 | Some(SharedValue::F64(_)) => subtract_!(F64, values), 88 | _ => Err(format!("Type cannot be subtracted: {:?}", values)), 89 | } 90 | } 91 | 92 | pub fn multiply(values: Vec) -> Result { 93 | match values.get(0).unwrap().shared_val() { 94 | Some(SharedValue::U8(_)) => multiply_!(U8, values), 95 | Some(SharedValue::U16(_)) => multiply_!(U16, values), 96 | Some(SharedValue::U32(_)) => multiply_!(U32, values), 97 | Some(SharedValue::U64(_)) => multiply_!(U64, values), 98 | Some(SharedValue::I8(_)) => multiply_!(I8, values), 99 | Some(SharedValue::I16(_)) => multiply_!(I16, values), 100 | Some(SharedValue::I32(_)) => multiply_!(I32, values), 101 | Some(SharedValue::I64(_)) => multiply_!(I64, values), 102 | Some(SharedValue::F32(_)) => multiply_!(F32, values), 103 | Some(SharedValue::F64(_)) => multiply_!(F64, values), 104 | _ => Err(format!("Type cannot be multiplied: {:?}", values)), 105 | } 106 | } 107 | 108 | pub fn divide(values: Vec) -> Result { 109 | match values.get(0).unwrap().shared_val() { 110 | Some(SharedValue::U8(_)) => divide_!(U8, values), 111 | Some(SharedValue::U16(_)) => divide_!(U16, values), 112 | Some(SharedValue::U32(_)) => divide_!(U32, values), 113 | Some(SharedValue::U64(_)) => divide_!(U64, values), 114 | Some(SharedValue::I8(_)) => divide_!(I8, values), 115 | Some(SharedValue::I16(_)) => divide_!(I16, values), 116 | Some(SharedValue::I32(_)) => divide_!(I32, values), 117 | Some(SharedValue::I64(_)) => divide_!(I64, values), 118 | Some(SharedValue::F32(_)) => divide_!(F32, values), 119 | Some(SharedValue::F64(_)) => divide_!(F64, values), 120 | _ => Err(format!("Type cannot be divided: {:?}", values)), 121 | } 122 | } 123 | 124 | pub fn inc(value: SExpr) -> Result { 125 | let value = match value.shared_val() { 126 | Some(SharedValue::U8(v)) => SExpr::from_owned_value(OwnedValue::U8(v + 1)), 127 | Some(SharedValue::U16(v)) => SExpr::from_owned_value(OwnedValue::U16(v + 1)), 128 | Some(SharedValue::U32(v)) => SExpr::from_owned_value(OwnedValue::U32(v + 1)), 129 | Some(SharedValue::U64(v)) => SExpr::from_owned_value(OwnedValue::U64(v + 1)), 130 | Some(SharedValue::I8(v)) => SExpr::from_owned_value(OwnedValue::I8(v + 1)), 131 | Some(SharedValue::I16(v)) => SExpr::from_owned_value(OwnedValue::I16(v + 1)), 132 | Some(SharedValue::I32(v)) => SExpr::from_owned_value(OwnedValue::I32(v + 1)), 133 | Some(SharedValue::I64(v)) => SExpr::from_owned_value(OwnedValue::I64(v + 1)), 134 | _ => return Err(format!("Type cannot be increased: {:?}", value)), 135 | }; 136 | Ok(value) 137 | } 138 | -------------------------------------------------------------------------------- /src/expr/symbols/bindings.rs: -------------------------------------------------------------------------------- 1 | use crate::expr::interpreter::Environment; 2 | 3 | use super::super::Value; 4 | use super::*; 5 | use std::collections::LinkedList; 6 | 7 | pub fn bind_by_name<'a, 'b>(env: &mut Environment<'a>, name: &'b str, val: SExpr<'a>) { 8 | bind(env, hash_str(name), val) 9 | } 10 | 11 | pub fn bind<'a>(env: &mut Environment<'a>, id: u64, val: SExpr<'a>) { 12 | let binding_map = &mut env.bindings; 13 | let bind_val = if let SExpr::Value(v) = val { 14 | SExpr::Value(Value::Ref(v.into_ref())) // Get to ref so cloning won't cost much 15 | } else { 16 | val 17 | }; 18 | binding_map 19 | .entry(id) 20 | .or_insert_with(|| LinkedList::new()) 21 | .push_front(Rc::new(bind_val)); 22 | } 23 | 24 | pub fn unbind<'a>(env: &mut Environment<'a>, id: u64) { 25 | let binding_map = &mut env.bindings; 26 | binding_map 27 | .entry(id) 28 | .or_insert_with(|| LinkedList::new()) 29 | .pop_front(); 30 | } 31 | 32 | pub fn let_binding<'a>( 33 | env: &mut Environment<'a>, 34 | exprs: Vec>, 35 | ) -> Result, String> { 36 | if exprs.len() < 2 { 37 | return Err(format!( 38 | "Too few parameters for let. Required at least 2 but found {}", 39 | exprs.len() 40 | )); 41 | } 42 | let mut exprs = exprs.into_iter(); 43 | let mut binded_ids = Vec::new(); 44 | { 45 | let form_expr = exprs.next().unwrap(); 46 | let form = if let SExpr::Vec(vec) = form_expr { 47 | vec 48 | } else { 49 | return Err(format!("Let need a vector as form, found {:?}", form_expr)); 50 | }; 51 | if form.len() % 2 == 1 { 52 | return Err(format!( 53 | "Let form require even number of parameters, but found {}", 54 | form.len() 55 | )); 56 | } 57 | let mut form_iter = form.into_iter(); 58 | while let Some(symbol) = form_iter.next() { 59 | let symbol_id = match symbol { 60 | SExpr::Symbol(ref sym_str) => hash_str(sym_str), 61 | SExpr::ISymbol(id, _) => id, 62 | _ => return Err(format!("Cannot bind to {:?}, need symbol", symbol)), 63 | }; 64 | if let Some(expr) = form_iter.next() { 65 | let val = expr.eval(env)?; 66 | bind(env, symbol_id, val); 67 | binded_ids.push(symbol_id); 68 | } else { 69 | return Err(format!("cannot bind to {:?}, no value", symbol)); 70 | } 71 | } 72 | } 73 | let mut body_result = SExpr::Value(Value::null()); 74 | for body_line in exprs { 75 | body_result = body_line.eval(env)?; 76 | } 77 | for binded_id in binded_ids { 78 | unbind(env, binded_id); 79 | } 80 | return Ok(body_result); 81 | } 82 | 83 | pub fn define<'a>(env: &mut Environment<'a>, exprs: Vec>) -> Result, String> { 84 | let mut exprs = exprs.into_iter(); 85 | let name = exprs.next().unwrap(); 86 | let val = exprs.next().unwrap().eval(env)?; 87 | if let SExpr::Symbol(name) = name { 88 | bind_by_name(env, &name, val); 89 | } else if let SExpr::ISymbol(id, _) = name { 90 | bind(env, id, val) 91 | } else { 92 | return Err(format!("Cannot bind to {:?}", name)); 93 | } 94 | return Ok(SExpr::Value(Value::null())); 95 | } 96 | -------------------------------------------------------------------------------- /src/expr/symbols/branching.rs: -------------------------------------------------------------------------------- 1 | use super::utils::is_true; 2 | use super::*; 3 | 4 | pub fn if_<'a>(env: &mut Environment<'a>, exprs: Vec>) -> Result, String> { 5 | let mut iter = exprs.into_iter(); 6 | let tester = iter.next().unwrap(); 7 | let then_expr = iter.next().unwrap(); 8 | let else_expr = iter.next(); 9 | if is_true(&tester.eval(env)?) { 10 | return then_expr.eval(env); 11 | } else if let Some(else_expr) = else_expr { 12 | return else_expr.eval(env); 13 | } else { 14 | return Ok(SExpr::Value(Value::null())); 15 | } 16 | } 17 | 18 | pub fn if_not<'a>(env: &mut Environment<'a>, exprs: Vec>) -> Result, String> { 19 | let mut iter = exprs.into_iter(); 20 | let tester = iter.next().unwrap(); 21 | let then_expr = iter.next().unwrap(); 22 | let else_expr = iter.next(); 23 | if !is_true(&tester.eval(env)?) { 24 | return then_expr.eval(env); 25 | } else if let Some(else_expr) = else_expr { 26 | return else_expr.eval(env); 27 | } else { 28 | return Ok(SExpr::Value(Value::null())); 29 | } 30 | } 31 | 32 | pub fn when<'a>(env: &mut Environment<'a>, exprs: Vec>) -> Result, String> { 33 | let mut iter = exprs.into_iter(); 34 | let tester = iter.next().unwrap(); 35 | let then_expr = iter.next().unwrap(); 36 | if is_true(&tester.eval(env)?) { 37 | return then_expr.eval(env); 38 | } else { 39 | return Ok(SExpr::Value(Value::null())); 40 | } 41 | } 42 | 43 | pub fn when_not<'a>(env: &mut Environment<'a>, exprs: Vec>) -> Result, String> { 44 | let mut iter = exprs.into_iter(); 45 | let tester = iter.next().unwrap(); 46 | let then_expr = iter.next().unwrap(); 47 | if !is_true(&tester.eval(env)?) { 48 | return then_expr.eval(env); 49 | } else { 50 | return Ok(SExpr::Value(Value::null())); 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /src/expr/symbols/collections.rs: -------------------------------------------------------------------------------- 1 | use std::collections::BTreeMap; 2 | 3 | use crate::types::{custom_types::map::GenericMap, Map, OwnedMap}; 4 | 5 | use super::*; 6 | use ahash::{HashMap, HashMapExt}; 7 | 8 | pub fn size_(vals: &Vec) -> Result { 9 | let mut result: u64 = 0; 10 | for val in vals { 11 | result += match &val { 12 | &SExpr::Vec(ref v) => v.len(), 13 | &SExpr::Value(val) => { 14 | let v = val.shared(); 15 | match v { 16 | SharedValue::Array(ref a) => a.len(), 17 | SharedValue::String(ref s) => s.len(), 18 | SharedValue::Map(ref m) => m.len(), 19 | _ => return Err(format!("Cannot measure size for value {:?}", val)), 20 | } 21 | } 22 | _ => return Err(format!("Cannot measure size for {:?}", val)), 23 | } as u64; 24 | } 25 | return Ok(result); 26 | } 27 | 28 | pub fn size(vals: Vec) -> Result { 29 | Ok(SExpr::from_owned_value(OwnedValue::U64(size_(&vals)?))) 30 | } 31 | 32 | pub fn concat(lists: Vec) -> Result { 33 | let total_size = size_(&lists)?; 34 | let mut result = Vec::with_capacity(total_size as usize); 35 | let mut vec_lists = Vec::new(); 36 | for list in lists { 37 | vec_lists.push(if let SExpr::Vec(v) = stream::to_vec(list)? { 38 | v 39 | } else { 40 | return Err("Unexpected error on concat".to_string()); 41 | }); 42 | } 43 | for mut vec in vec_lists { 44 | result.append(&mut vec); 45 | } 46 | return Ok(SExpr::Vec(result)); 47 | } 48 | 49 | pub fn map(mut exprs: Vec) -> Result { 50 | if exprs.len() == 1 { 51 | match exprs.into_iter().next().unwrap() { 52 | SExpr::Vec(l) | SExpr::List(l) => exprs = l, 53 | v => { 54 | return Err(format!( 55 | "Single patameter only support list and seq, found {:?}", 56 | v 57 | )) 58 | } 59 | } 60 | } else if exprs.len() & 2 == 0 { 61 | return Err(format!( 62 | "Map require even number of parameters. Found {}", 63 | exprs.len() 64 | )); 65 | } 66 | let mut exprs = exprs.into_iter(); 67 | let mut pairs = Vec::with_capacity(8); 68 | while let (Some(k), Some(v)) = (exprs.next(), exprs.next()) { 69 | match (k, v) { 70 | (SExpr::Value(k_val), SExpr::Value(v)) => { 71 | let k_norm = k_val.shared(); 72 | let k_str_opt = k_norm.string(); 73 | match (k_str_opt, v) { 74 | (Some(k_str), Value::Shared(v)) => { 75 | // TODO: Try not own elements 76 | pairs.push((k_str.to_owned(), v.owned())); 77 | } 78 | (Some(k_str), Value::Owned(v)) => { 79 | pairs.push((k_str.to_owned(), v)); 80 | } 81 | (Some(k_str), Value::Ref(v)) => { 82 | pairs.push((k_str.to_owned(), (&*v).to_owned())); 83 | } 84 | (None, _) => { 85 | return Err(format!("Only string key is allowed, got {:?}", k_val)) 86 | } 87 | } 88 | } 89 | (SExpr::Keyword(_, kw), SExpr::Value(v)) => { 90 | match v { 91 | Value::Shared(v) => { 92 | // TODO: Try not own elements 93 | pairs.push((kw.to_owned(), v.owned())); 94 | } 95 | Value::Owned(v) => { 96 | pairs.push((kw.to_owned(), v)); 97 | } 98 | Value::Ref(v) => { 99 | pairs.push((kw.to_owned(), (&*v).to_owned())); 100 | } 101 | } 102 | } 103 | _ => { 104 | return Err(format!("Wrong hashmap key value data type. Key should be a string or keyword and value should be a value")); 105 | } 106 | } 107 | } 108 | return Ok(SExpr::from_owned_value(OwnedValue::Map( 109 | OwnedMap::from_pairs(pairs.into_iter()), 110 | ))); 111 | } 112 | 113 | pub fn merge<'a>(exprs: Vec>) -> Result, String> { 114 | let mut value_map = GenericMap::new(); 115 | let mut field_names = Vec::new(); 116 | for expr in exprs { 117 | if let SExpr::Value(val) = expr { 118 | match val { 119 | Value::Shared(SharedValue::Map(m)) => { 120 | let map = &m.map; 121 | let mut fields = m.fields.clone(); 122 | for (k, v) in map.iter() { 123 | value_map.insert(*k, v.owned()); 124 | } 125 | field_names.append(&mut fields); 126 | } 127 | Value::Owned(OwnedValue::Map(m)) => { 128 | let map = m.map; 129 | let mut fields = m.fields; 130 | for (k, v) in map.into_iter() { 131 | value_map.insert(k, v); 132 | } 133 | field_names.append(&mut fields); 134 | } 135 | _ => return Err(format!("Only map value can be merged. Found {:?}", val)), 136 | } 137 | } 138 | } 139 | field_names.dedup(); 140 | Ok(SExpr::from_owned_value(OwnedValue::Map(OwnedMap { 141 | map: value_map, 142 | fields: field_names, 143 | }))) 144 | } 145 | 146 | pub fn conj(exprs: Vec) -> Result { 147 | let mut exprs = exprs.into_iter(); 148 | let list = stream::to_vec(exprs.next().unwrap()); 149 | if let Ok(SExpr::Vec(mut vec)) = list { 150 | for item in exprs { 151 | vec.push(item); 152 | } 153 | return Ok(SExpr::Vec(vec)); 154 | } else { 155 | return Err(format!("Cannot concat. {:?}", list)); 156 | } 157 | } 158 | -------------------------------------------------------------------------------- /src/expr/symbols/comparators.rs: -------------------------------------------------------------------------------- 1 | use log::trace; 2 | 3 | use super::*; 4 | 5 | pub fn equals(mut exprs: Vec) -> Result { 6 | let last_expr = exprs.pop().unwrap(); 7 | let last = last_expr.shared_val(); 8 | for expr in exprs { 9 | let expr = expr.shared_val(); 10 | trace!("Comparing {:?} with {:?}", expr, last); 11 | if expr != last { 12 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(false))); 13 | } 14 | } 15 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(true))); 16 | } 17 | 18 | pub fn not_equals(mut exprs: Vec) -> Result { 19 | return Ok(SExpr::from_owned_value(OwnedValue::Bool({ 20 | let l = exprs.pop(); 21 | let r = exprs.pop(); 22 | l.as_ref().map(|e| e.shared_val()) == r.as_ref().map(|e| e.shared_val()) 23 | }))); 24 | } 25 | 26 | macro_rules! reduce { 27 | ($type: ident, $values: ident, $exp: expr) => {{ 28 | if let Some((first, elements)) = $values.split_first() { 29 | if let Some(SharedValue::$type(first)) = first.shared_val() { 30 | let mut last = first; 31 | for val in elements { 32 | if let Some(SharedValue::$type(n)) = val.shared_val() { 33 | if $exp(last, n) { 34 | last = n; 35 | } else { 36 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(false))); 37 | } 38 | } else { 39 | return Err(format!( 40 | "Type not match, expect {} found {:?}", 41 | stringify!($type), 42 | val 43 | )); 44 | } 45 | } 46 | Ok(SExpr::from_owned_value(OwnedValue::Bool(true))) 47 | } else { 48 | Err(format!( 49 | "Type not match on the first value, expect {} found {:?}", 50 | stringify!($type), 51 | first 52 | )) 53 | } 54 | } else { 55 | Err("Cannot do reduce on values".to_string()) 56 | } 57 | }}; 58 | } 59 | 60 | macro_rules! lt_ { 61 | ($type: ident, $values: ident) => {{ 62 | reduce!($type, $values, |last, n| { last < n }) 63 | }}; 64 | } 65 | 66 | macro_rules! lte_ { 67 | ($type: ident, $values: ident) => {{ 68 | reduce!($type, $values, |last, n| { last <= n }) 69 | }}; 70 | } 71 | 72 | macro_rules! gt_ { 73 | ($type: ident, $values: ident) => {{ 74 | reduce!($type, $values, |last, n| { last > n }) 75 | }}; 76 | } 77 | 78 | macro_rules! gte_ { 79 | ($type: ident, $values: ident) => {{ 80 | reduce!($type, $values, |last, n| { last >= n }) 81 | }}; 82 | } 83 | 84 | pub fn lt(values: Vec) -> Result { 85 | match values.get(0).unwrap().shared_val() { 86 | Some(SharedValue::U8(_)) => lt_!(U8, values), 87 | Some(SharedValue::U16(_)) => lt_!(U16, values), 88 | Some(SharedValue::U32(_)) => lt_!(U32, values), 89 | Some(SharedValue::U64(_)) => lt_!(U64, values), 90 | Some(SharedValue::I8(_)) => lt_!(I8, values), 91 | Some(SharedValue::I16(_)) => lt_!(I16, values), 92 | Some(SharedValue::I32(_)) => lt_!(I32, values), 93 | Some(SharedValue::I64(_)) => lt_!(I64, values), 94 | Some(SharedValue::F32(_)) => lt_!(F32, values), 95 | Some(SharedValue::F64(_)) => lt_!(F64, values), 96 | _ => Err(format!("Type cannot be compared: {:?}", values)), 97 | } 98 | } 99 | 100 | pub fn lte(values: Vec) -> Result { 101 | match values.get(0).unwrap().shared_val() { 102 | Some(SharedValue::U8(_)) => lte_!(U8, values), 103 | Some(SharedValue::U16(_)) => lte_!(U16, values), 104 | Some(SharedValue::U32(_)) => lte_!(U32, values), 105 | Some(SharedValue::U64(_)) => lte_!(U64, values), 106 | Some(SharedValue::I8(_)) => lte_!(I8, values), 107 | Some(SharedValue::I16(_)) => lte_!(I16, values), 108 | Some(SharedValue::I32(_)) => lte_!(I32, values), 109 | Some(SharedValue::I64(_)) => lte_!(I64, values), 110 | Some(SharedValue::F32(_)) => lte_!(F32, values), 111 | Some(SharedValue::F64(_)) => lte_!(F64, values), 112 | _ => Err(format!("Type cannot be compared: {:?}", values)), 113 | } 114 | } 115 | 116 | pub fn gt(values: Vec) -> Result { 117 | match values.get(0).unwrap().shared_val() { 118 | Some(SharedValue::U8(_)) => gt_!(U8, values), 119 | Some(SharedValue::U16(_)) => gt_!(U16, values), 120 | Some(SharedValue::U32(_)) => gt_!(U32, values), 121 | Some(SharedValue::U64(_)) => gt_!(U64, values), 122 | Some(SharedValue::I8(_)) => gt_!(I8, values), 123 | Some(SharedValue::I16(_)) => gt_!(I16, values), 124 | Some(SharedValue::I32(_)) => gt_!(I32, values), 125 | Some(SharedValue::I64(_)) => gt_!(I64, values), 126 | Some(SharedValue::F32(_)) => gt_!(F32, values), 127 | Some(SharedValue::F64(_)) => gt_!(F64, values), 128 | _ => Err(format!("Type cannot be compared: {:?}", values)), 129 | } 130 | } 131 | 132 | pub fn gte(values: Vec) -> Result { 133 | match values.get(0).unwrap().shared_val() { 134 | Some(SharedValue::U8(_)) => gte_!(U8, values), 135 | Some(SharedValue::U16(_)) => gte_!(U16, values), 136 | Some(SharedValue::U32(_)) => gte_!(U32, values), 137 | Some(SharedValue::U64(_)) => gte_!(U64, values), 138 | Some(SharedValue::I8(_)) => gte_!(I8, values), 139 | Some(SharedValue::I16(_)) => gte_!(I16, values), 140 | Some(SharedValue::I32(_)) => gte_!(I32, values), 141 | Some(SharedValue::I64(_)) => gte_!(I64, values), 142 | Some(SharedValue::F32(_)) => gte_!(F32, values), 143 | Some(SharedValue::F64(_)) => gte_!(F64, values), 144 | _ => Err(format!("Type cannot be compared: {:?}", values)), 145 | } 146 | } 147 | -------------------------------------------------------------------------------- /src/expr/symbols/functions.rs: -------------------------------------------------------------------------------- 1 | use crate::expr::interpreter::Environment; 2 | use crate::types::Map; 3 | 4 | use super::bindings::{bind, bind_by_name}; 5 | use super::lambda::{eval_lambda, lambda_placeholder}; 6 | use super::*; 7 | 8 | pub fn eval_function<'a>( 9 | func_expr: &SExpr<'a>, 10 | params: Vec>, 11 | env: &mut Environment<'a>, 12 | ) -> Result, String> { 13 | match func_expr { 14 | &SExpr::ISymbol(symbol_id, ref name) => { 15 | let env_bind; 16 | let bindings = env.get_mut_bindings(); 17 | env_bind = if let Some(binding_list) = bindings.get(&symbol_id) { 18 | binding_list.front().cloned() 19 | } else { 20 | None 21 | }; 22 | if let Some(env_bind) = env_bind { 23 | return eval_lambda(env_bind, params, env); 24 | } else { 25 | // internal functions 26 | let symbols = ISYMBOL_MAP.map.borrow(); 27 | match symbols.get(&symbol_id) { 28 | Some(symbol) => { 29 | // if the symbol is not a macro, parameters will all be evaled here. Or passthrough those expressions. 30 | let exprs = if symbol.is_macro() { 31 | params 32 | } else { 33 | let mut evaled_params = Vec::with_capacity(params.len()); 34 | for param in params { 35 | evaled_params.push(param.eval(env)?); 36 | } 37 | evaled_params 38 | }; 39 | return symbol.eval(exprs, env); 40 | } 41 | _ => { 42 | return Err(format!( 43 | "Cannot find symbol \'{}\', id: {}", 44 | name, symbol_id 45 | )) 46 | } 47 | } 48 | } 49 | } 50 | &SExpr::Symbol(ref symbol_name) => { 51 | let symbol_id = hash_str(symbol_name); 52 | let symbol_name = symbol_name.clone(); 53 | return eval_function(&SExpr::ISymbol(symbol_id, symbol_name), params, env); 54 | } 55 | &SExpr::LAMBDA(_, _) => return eval_lambda(Rc::new(func_expr.clone()), params, env), 56 | &SExpr::Value(ref v) => return eval_value(v, params), 57 | _ => {} 58 | } 59 | return Err(format!("{:?} is not a function", func_expr)); 60 | } 61 | 62 | fn eval_value<'a>(v: &Value<'a>, params: Vec>) -> Result, String> { 63 | match &v { 64 | &Value::Shared(sv) => eval_shared_value(sv, params), 65 | &Value::Ref(ov) => eval_owned_value(&**ov, params), 66 | &Value::Owned(ov) => eval_owned_value(ov, params), 67 | } 68 | } 69 | 70 | fn eval_shared_value<'a>( 71 | sv: &SharedValue<'a>, 72 | params: Vec>, 73 | ) -> Result, String> { 74 | match sv { 75 | SharedValue::String(str_key) => { 76 | // same as clojure (:key map) 77 | if params.len() > 1 { 78 | return Err(format!( 79 | "get from map can only take one parameter, found {}", 80 | params.len() 81 | )); 82 | } 83 | if let Some(Some(SharedValue::Map(ref m))) = params.get(0).map(|expr| expr.shared_val()) 84 | { 85 | return Ok(SExpr::from_owned_value(m.get(str_key).owned())); 86 | } else { 87 | return Err(format!( 88 | "When use string value as function, \ 89 | only one map parameter is accepted, found {:?}", 90 | params 91 | )); 92 | } 93 | } 94 | SharedValue::U64(index) => { 95 | // get element by index from vec or by key_id form map 96 | if params.len() > 1 { 97 | return Err(format!( 98 | "get by index/id can only take one parameter, found {}", 99 | params.len() 100 | )); 101 | } 102 | match params.get(0).map(|expr| expr.shared_val()) { 103 | Some(Some(SharedValue::Map(ref m))) => { 104 | let val = m.get_by_key_id(**index).clone(); 105 | return Ok(SExpr::from_owned_value(val.owned())); 106 | } 107 | Some(Some(SharedValue::Array(ref arr))) => { 108 | return Ok(SExpr::from_owned_value( 109 | arr.get(**index as usize) 110 | .cloned() 111 | .unwrap_or(SharedValue::Null) 112 | .owned(), 113 | )) 114 | } 115 | _ => return Err(format!("Data type not accepted for {:?}", params)), 116 | } 117 | } 118 | SharedValue::Map(ref m) => { 119 | if params.len() > 1 { 120 | return Err(format!( 121 | "get map can only take one parameter, found {}", 122 | params.len() 123 | )); 124 | } 125 | match params.get(0).map(|v| v.shared_val()) { 126 | Some(Some(SharedValue::String(str_key))) => { 127 | return Ok(SExpr::from_shared_value(m.get(str_key).clone())) 128 | } 129 | Some(Some(SharedValue::U64(key_id))) => { 130 | return Ok(SExpr::from_shared_value(m.get_by_key_id(*key_id).clone())) 131 | } 132 | _ => { 133 | return Err(format!( 134 | "Key format not accepted, expect one string or u64\ 135 | Found {:?}", 136 | params 137 | )); 138 | } 139 | } 140 | } 141 | SharedValue::Array(ref array) => { 142 | if params.len() > 1 { 143 | return Err(format!( 144 | "get map can only take one parameter, found {}", 145 | params.len() 146 | )); 147 | } 148 | match params.get(0).map(|v| v.shared_val()) { 149 | Some(Some(SharedValue::U64(key_id))) => { 150 | return Ok(SExpr::from_shared_value( 151 | array 152 | .get(*key_id as usize) 153 | .cloned() 154 | .unwrap_or(SharedValue::Null), 155 | )) 156 | } 157 | _ => { 158 | return Err(format!( 159 | "Index format not accepted, expect u64\ 160 | Found {:?}", 161 | params 162 | )); 163 | } 164 | } 165 | } 166 | _ => { 167 | return Err(format!("value {:?} cannot be used as a function", sv)); 168 | } 169 | } 170 | } 171 | 172 | fn eval_owned_value<'a>(ov: &OwnedValue, params: Vec>) -> Result, String> { 173 | match ov { 174 | OwnedValue::String(str_key) => { 175 | // same as clojure (:key map) 176 | if params.len() > 1 { 177 | return Err(format!( 178 | "get from map can only take one parameter, found {}", 179 | params.len() 180 | )); 181 | } 182 | if let Some(Some(SharedValue::Map(ref m))) = params.get(0).map(|expr| expr.shared_val()) 183 | { 184 | return Ok(SExpr::from_owned_value(m.get(str_key).owned())); 185 | } else { 186 | return Err(format!( 187 | "When use string value as function, \ 188 | only one map parameter is accepted, found {:?}", 189 | params 190 | )); 191 | } 192 | } 193 | OwnedValue::U64(index) => { 194 | // get element by index from vec or by key_id form map 195 | if params.len() > 1 { 196 | return Err(format!( 197 | "get by index/id can only take one parameter, found {}", 198 | params.len() 199 | )); 200 | } 201 | match params.get(0).map(|expr| expr.shared_val()) { 202 | Some(Some(SharedValue::Map(ref m))) => { 203 | let val = m.get_by_key_id(*index).clone(); 204 | return Ok(SExpr::from_owned_value(val.owned())); 205 | } 206 | Some(Some(SharedValue::Array(ref arr))) => { 207 | return Ok(SExpr::from_owned_value( 208 | arr.get(*index as usize) 209 | .cloned() 210 | .unwrap_or(SharedValue::Null) 211 | .owned(), 212 | )) 213 | } 214 | _ => return Err(format!("Data type not accepted for {:?}", params)), 215 | } 216 | } 217 | OwnedValue::Map(ref m) => { 218 | if params.len() > 1 { 219 | return Err(format!( 220 | "get map can only take one parameter, found {}", 221 | params.len() 222 | )); 223 | } 224 | match params.get(0).map(|v| v.shared_val()) { 225 | Some(Some(SharedValue::String(str_key))) => { 226 | return Ok(SExpr::from_owned_value(m.get(str_key).clone())) 227 | } 228 | Some(Some(SharedValue::U64(key_id))) => { 229 | return Ok(SExpr::from_owned_value(m.get_by_key_id(*key_id).clone())) 230 | } 231 | _ => { 232 | return Err(format!( 233 | "Key format not accepted, expect one string or u64\ 234 | Found {:?}", 235 | params 236 | )); 237 | } 238 | } 239 | } 240 | OwnedValue::Array(ref array) => { 241 | if params.len() > 1 { 242 | return Err(format!( 243 | "get map can only take one parameter, found {}", 244 | params.len() 245 | )); 246 | } 247 | match params.get(0).map(|v| v.shared_val()) { 248 | Some(Some(SharedValue::U64(key_id))) => { 249 | return Ok(SExpr::from_owned_value( 250 | array 251 | .get(*key_id as usize) 252 | .cloned() 253 | .unwrap_or(OwnedValue::Null), 254 | )) 255 | } 256 | _ => { 257 | return Err(format!( 258 | "Index format not accepted, expect u64\ 259 | Found {:?}", 260 | params 261 | )); 262 | } 263 | } 264 | } 265 | _ => { 266 | return Err(format!("value {:?} cannot be used as a function", ov)); 267 | } 268 | } 269 | } 270 | 271 | pub fn defn<'a>(env: &mut Environment<'a>, exprs: Vec>) -> Result, String> { 272 | let mut exprs = exprs.into_iter(); 273 | let name = exprs.next().unwrap(); 274 | let lambda = lambda_placeholder(exprs)?; 275 | if let SExpr::Symbol(name) = name { 276 | bind_by_name(env, &name, lambda); 277 | } else if let SExpr::ISymbol(id, _) = name { 278 | bind(env, id, lambda); 279 | } else { 280 | return Err(format!( 281 | "Function name should be a symbol, found {:?}", 282 | name 283 | )); 284 | } 285 | return Ok(SExpr::Value(Value::null())); 286 | } 287 | -------------------------------------------------------------------------------- /src/expr/symbols/lambda.rs: -------------------------------------------------------------------------------- 1 | use super::bindings::*; 2 | use super::*; 3 | pub fn lambda_placeholder<'a>( 4 | mut exprs: impl Iterator>, 5 | ) -> Result, String> { 6 | let params = exprs.next().unwrap(); 7 | let params_list = if let SExpr::Vec(symbols) = params { 8 | let mut list = Vec::new(); 9 | for symbol in symbols { 10 | list.push(match symbol { 11 | SExpr::Symbol(name) => SExpr::ISymbol(hash_str(&name), name), 12 | SExpr::ISymbol(id, name) => SExpr::ISymbol(id, name), 13 | _ => { 14 | return Err(format!( 15 | "lambda can only bind to symbols, found {:?}", 16 | symbol 17 | )) 18 | } 19 | }); 20 | } 21 | list 22 | } else { 23 | return Err(format!("lambda form should be vector, found {:?}", params)); 24 | }; 25 | Ok(SExpr::LAMBDA(params_list, exprs.collect())) 26 | } 27 | 28 | pub fn eval_lambda<'a>( 29 | lambda_expr: Rc>, 30 | params: Vec>, 31 | env: &mut Environment<'a>, 32 | ) -> Result, String> { 33 | if let SExpr::LAMBDA(ref params_list, ref body) = &*lambda_expr { 34 | { 35 | // bind parameters 36 | let mut param_pos = 0; 37 | for param in params { 38 | let lambda_param = params_list.get(param_pos).unwrap(); 39 | if let &SExpr::ISymbol(id, _) = lambda_param { 40 | bind(env, id, param); 41 | } else { 42 | return Err(format!( 43 | "Expect ISymbol for lambda form, found {:?}", 44 | lambda_param 45 | )); 46 | } 47 | param_pos += 1; 48 | } 49 | } 50 | let mut last_result = SExpr::Value(Value::null()); 51 | for body_line in body { 52 | // eval function body by cloning expression 53 | last_result = body_line.clone().eval(env)?; 54 | } 55 | for lambda_param in params_list { 56 | // unbind parameters 57 | if let &SExpr::ISymbol(id, _) = lambda_param { 58 | unbind(env, id); 59 | } 60 | } 61 | Ok(last_result) 62 | } else { 63 | return Err(format!("Expect lambda expression, found {:?}", lambda_expr)); 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /src/expr/symbols/logic.rs: -------------------------------------------------------------------------------- 1 | use super::utils::is_true; 2 | use super::*; 3 | 4 | pub fn or<'a>(exprs: Vec>, env: &mut Environment<'a>) -> Result, String> { 5 | for expr in exprs { 6 | if is_true(&expr.eval(env)?) { 7 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(true))); 8 | } 9 | } 10 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(false))); 11 | } 12 | 13 | pub fn and<'a>(exprs: Vec>, env: &mut Environment<'a>) -> Result, String> { 14 | for expr in exprs { 15 | if !is_true(&expr.eval(env)?) { 16 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(false))); 17 | } 18 | } 19 | return Ok(SExpr::from_owned_value(OwnedValue::Bool(true))); 20 | } 21 | 22 | pub fn cond<'a>(exprs: Vec>, env: &mut Environment<'a>) -> Result, String> { 23 | if exprs.len() % 2 == 1 { 24 | return Err(format!( 25 | "cond need even number of parameters, found {}", 26 | exprs.len() 27 | )); 28 | } 29 | let mut exprs = exprs.into_iter(); 30 | while let (Some(condition), Some(expr)) = (exprs.next(), exprs.next()) { 31 | if is_true(&condition.eval(env)?) { 32 | return expr.eval(env); 33 | } 34 | } 35 | return Ok(SExpr::Value(Value::null())); 36 | } 37 | -------------------------------------------------------------------------------- /src/expr/symbols/misc.rs: -------------------------------------------------------------------------------- 1 | use super::*; 2 | 3 | pub fn do_<'a>(exprs: Vec>, env: &mut Environment<'a>) -> Result, String> { 4 | let mut result = SExpr::Value(Value::null()); 5 | for expr in exprs { 6 | result = expr.eval(env)?; 7 | } 8 | return Ok(result); 9 | } 10 | -------------------------------------------------------------------------------- /src/expr/symbols/mod.rs: -------------------------------------------------------------------------------- 1 | use bifrost_hasher::hash_str; 2 | use bifrost_plugins::hash_ident; 3 | use std::cell::RefCell; 4 | use std::collections::HashMap; 5 | use std::fmt::Debug; 6 | 7 | use super::interpreter::Environment; 8 | pub use super::*; 9 | 10 | mod arithmetic; 11 | pub mod bindings; 12 | mod branching; 13 | mod collections; 14 | mod comparators; 15 | pub mod functions; 16 | mod lambda; 17 | mod logic; 18 | pub mod misc; 19 | mod num_types; 20 | mod stream; 21 | pub mod utils; 22 | 23 | pub trait Symbol: Sync + Debug { 24 | fn eval<'a>( 25 | &self, 26 | exprs: Vec>, 27 | env: &mut Environment<'a>, 28 | ) -> Result, String>; 29 | fn is_macro(&self) -> bool; 30 | } 31 | 32 | pub struct ISymbolMap { 33 | pub map: RefCell>>, 34 | } 35 | 36 | unsafe impl Sync for ISymbolMap {} 37 | impl ISymbolMap { 38 | pub fn new(map: HashMap>) -> ISymbolMap { 39 | ISymbolMap { 40 | map: RefCell::new(map), 41 | } 42 | } 43 | pub fn insert<'a, S>(&self, symbol_name: &'a str, symbol_impl: S) -> Result<(), ()> 44 | where 45 | S: Symbol + 'static, 46 | { 47 | match self.map.try_borrow_mut() { 48 | Ok(ref mut m) => { 49 | m.insert(hash_str(symbol_name), Box::new(symbol_impl)); 50 | Ok(()) 51 | } 52 | Err(_) => Err(()), 53 | } 54 | } 55 | } 56 | 57 | macro_rules! defsymbols { 58 | ($($sym: expr => $name: ident, $is_macro: expr, $eval: expr);*) => { 59 | $( 60 | #[derive(Debug)] 61 | pub struct $name; 62 | impl Symbol for $name { 63 | fn eval<'a>(&self, exprs: Vec>, env: &mut Environment<'a>) -> Result, String> where Self: Sized { 64 | $eval(exprs, env) 65 | } 66 | fn is_macro(&self) -> bool { 67 | return $is_macro; 68 | } 69 | } 70 | )* 71 | lazy_static! { 72 | pub static ref ISYMBOL_MAP: ISymbolMap = { 73 | let mut symbol_map: HashMap> = HashMap::new(); 74 | $( 75 | symbol_map.insert(hash_ident!($sym), Box::new($name)); 76 | )* 77 | ISymbolMap::new(symbol_map) 78 | }; 79 | } 80 | 81 | #[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)] 82 | pub enum SysSymbol { 83 | $( 84 | $name = hash_ident!($sym), 85 | )* 86 | } 87 | impl SysSymbol { 88 | pub fn from_id(id: u64) -> Option { 89 | match id { 90 | $( 91 | hash_ident!($sym) => Some(Self::$name), 92 | )* 93 | _ => None 94 | } 95 | } 96 | } 97 | }; 98 | } 99 | 100 | pub fn new_symbol<'a, S>(symbol_name: &'a str, symbol_impl: S) -> Result<(), ()> 101 | where 102 | S: Symbol + 'static, 103 | { 104 | ISYMBOL_MAP.insert(symbol_name, symbol_impl) 105 | } 106 | 107 | fn check_num_params(num: usize, params: &Vec) -> Result<(), String> { 108 | if num != params.len() { 109 | Err(format!( 110 | "Parameter number not match. Except {} but found {}", 111 | num, 112 | params.len() 113 | )) 114 | } else { 115 | Ok(()) 116 | } 117 | } 118 | 119 | fn check_params_not_empty(params: &Vec) -> Result<(), String> { 120 | if params.len() == 0 { 121 | Err(format!( 122 | "Parameter number not match. Expected some but found empty" 123 | )) 124 | } else { 125 | Ok(()) 126 | } 127 | } 128 | 129 | fn check_params_not_least_than(num: usize, params: &Vec) -> Result<(), String> { 130 | if params.len() < num { 131 | Err(format!( 132 | "Parameter number not match, Expected at least {} but found {}", 133 | num, 134 | params.len() 135 | )) 136 | } else { 137 | Ok(()) 138 | } 139 | } 140 | 141 | fn check_params_not_greater_than(num: usize, params: &Vec) -> Result<(), String> { 142 | if params.len() > num { 143 | Err(format!( 144 | "Parameter number not match, Expected at most {} but found {}", 145 | num, 146 | params.len() 147 | )) 148 | } else { 149 | Ok(()) 150 | } 151 | } 152 | 153 | fn split_pair(mut exprs: Vec) -> (SExpr, SExpr) { 154 | let e2 = exprs.pop().unwrap(); 155 | let e1 = exprs.pop().unwrap(); 156 | (e1, e2) 157 | } 158 | 159 | defsymbols! { 160 | "if" => If, true, |exprs, env| { 161 | check_params_not_least_than(2, &exprs)?; 162 | check_params_not_greater_than(3, &exprs)?; 163 | branching::if_(env, exprs) 164 | }; 165 | "if-not" => IfNot, true, |exprs, env| { 166 | check_params_not_least_than(2, &exprs)?; 167 | check_params_not_greater_than(3, &exprs)?; 168 | branching::if_not(env, exprs) 169 | }; 170 | "when" => When, true, |exprs, env| { 171 | check_num_params(2, &exprs)?; 172 | branching::when(env,exprs) 173 | }; 174 | "when-not" => WhenNot, true, |exprs, env| { 175 | check_num_params(2, &exprs)?; 176 | branching::when_not(env,exprs) 177 | }; 178 | "=" => Equals, false, |exprs, _env| { 179 | check_params_not_least_than(2, &exprs)?; 180 | comparators::equals(exprs) 181 | }; 182 | "!=" => NotEquals, false, |exprs, _env| { 183 | check_num_params(2, &exprs)?; 184 | comparators::not_equals(exprs) 185 | }; 186 | ">" => GreaterThan, false, |exprs, _env| { 187 | check_params_not_least_than(2, &exprs)?; 188 | comparators::gt(exprs) 189 | }; 190 | ">=" => GreaterThanEquals, false, |exprs, _env| { 191 | check_params_not_least_than(2, &exprs)?; 192 | comparators::gte(exprs) 193 | }; 194 | "<" => LessThan, false, |exprs, _env| { 195 | check_params_not_least_than(2, &exprs)?; 196 | comparators::lt(exprs) 197 | }; 198 | "<=" => LessThanEquals, false, |exprs, _env| { 199 | check_params_not_least_than(2, &exprs)?; 200 | comparators::lte(exprs) 201 | }; 202 | "+" => Add, false, |exprs, _env| { 203 | check_params_not_empty(&exprs)?; 204 | arithmetic::add(exprs) 205 | }; 206 | "-" => Subtract, false, |exprs, _env| { 207 | check_params_not_empty(&exprs)?; 208 | arithmetic::subtract(exprs) 209 | }; 210 | "*" => Multiply, false, |exprs, _env| { 211 | check_params_not_empty(&exprs)?; 212 | arithmetic::multiply(exprs) 213 | }; 214 | "/" => Divide, false, |exprs, _env| { 215 | check_params_not_empty(&exprs)?; 216 | arithmetic::divide(exprs) 217 | }; 218 | "let" => Let, true, |exprs, env| { 219 | bindings::let_binding(env, exprs) 220 | }; 221 | "lambda" => Lambda, true, |exprs, _env| { 222 | check_params_not_least_than(2, &exprs)?; 223 | lambda::lambda_placeholder(exprs.into_iter()) 224 | }; 225 | "defunc" => DefineFunc, true, |exprs, env| { 226 | check_params_not_least_than(3, &exprs)?; 227 | functions::defn(env, exprs) 228 | }; 229 | "def" => Define, true, |exprs, env| { 230 | check_num_params(2, &exprs)?; 231 | bindings::define(env, exprs) 232 | }; 233 | "map" => Map, false, |exprs, env| { 234 | check_num_params(2, &exprs)?; 235 | let (func, data) = split_pair(exprs); 236 | stream::map(func, data, env) 237 | }; 238 | "filter" => Filter, false, |exprs, env| { 239 | check_num_params(2, &exprs)?; 240 | let (func, data) = split_pair(exprs); 241 | stream::filter(func, data, env) 242 | }; 243 | "do" => Do, false, |exprs, env| { 244 | misc::do_(exprs, env) 245 | }; 246 | "to_vec" => ToVec, false, |mut exprs, _env| { 247 | check_num_params(1, &exprs)?; 248 | stream::to_vec(exprs.pop().unwrap()) 249 | }; 250 | "to_array" => ToArray, false, |mut exprs, _env| { 251 | check_num_params(1, &exprs)?; 252 | stream::to_array(exprs.pop().unwrap()) 253 | }; 254 | "inc" => Inc, false, |mut exprs, _env| { 255 | check_num_params(1, &exprs)?; 256 | arithmetic::inc(exprs.pop().unwrap()) 257 | }; 258 | "concat" => Concat, false, |exprs, _env| { 259 | collections::concat(exprs) 260 | }; 261 | "size" => Size, false, |exprs, _env| { 262 | collections::size(exprs) 263 | }; 264 | "into-map" => IntoMap, false, |exprs, _env| { 265 | collections::map(exprs) 266 | }; 267 | "merge" => MergeHashMap, false, |exprs, _env| { 268 | collections::merge(exprs) 269 | }; 270 | "conj" => Conjuction, false, |exprs, _env| { 271 | collections::conj(exprs) 272 | }; 273 | "or" => Or, true, |exprs, env| { 274 | logic::or(exprs, env) 275 | }; 276 | "and" => And, true, |exprs, env| { 277 | logic::and(exprs, env) 278 | }; 279 | "cond" => Conditional, true, |exprs, env| { 280 | logic::cond(exprs, env) 281 | }; 282 | "u8" => U8, false, |mut exprs, _env| { 283 | check_num_params(1, &exprs)?; 284 | num_types::u8(exprs.pop().unwrap()) 285 | }; 286 | "u16" => U16, false, |mut exprs, _env| { 287 | check_num_params(1, &exprs)?; 288 | num_types::u16(exprs.pop().unwrap()) 289 | }; 290 | "u32" => U32, false, |mut exprs, _env| { 291 | check_num_params(1, &exprs)?; 292 | num_types::u32(exprs.pop().unwrap()) 293 | }; 294 | "u64" => U64, false, |mut exprs, _env| { 295 | check_num_params(1, &exprs)?; 296 | num_types::u64(exprs.pop().unwrap()) 297 | }; 298 | "i8" => I8, false, |mut exprs, _env| { 299 | check_num_params(1, &exprs)?; 300 | num_types::i8(exprs.pop().unwrap()) 301 | }; 302 | "i16" => I16, false, |mut exprs, _env| { 303 | check_num_params(1, &exprs)?; 304 | num_types::i16(exprs.pop().unwrap()) 305 | }; 306 | "i32" => I32, false, |mut exprs, _env| { 307 | check_num_params(1, &exprs)?; 308 | num_types::i32(exprs.pop().unwrap()) 309 | }; 310 | "i64" => I64, false, |mut exprs, _env| { 311 | check_num_params(1, &exprs)?; 312 | num_types::i64(exprs.pop().unwrap()) 313 | }; 314 | "f32" => F32, false, |mut exprs, _env| { 315 | check_num_params(1, &exprs)?; 316 | num_types::f32(exprs.pop().unwrap()) 317 | }; 318 | "f64" => F64, false, |mut exprs, _env| { 319 | check_num_params(1, &exprs)?; 320 | num_types::f64(exprs.pop().unwrap()) 321 | } 322 | } 323 | -------------------------------------------------------------------------------- /src/expr/symbols/num_types.rs: -------------------------------------------------------------------------------- 1 | use super::*; 2 | 3 | pub fn u64(value: SExpr) -> Result { 4 | match value.shared_val() { 5 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 6 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 7 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 8 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 9 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 10 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 11 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 12 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 13 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 14 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U64(*num as u64))), 15 | _ => Err("The value cannot be convert into u64".to_string()), 16 | } 17 | } 18 | 19 | pub fn u32(value: SExpr) -> Result { 20 | match value.shared_val() { 21 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 22 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 23 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 24 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 25 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 26 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 27 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 28 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 29 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 30 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U32(*num as u32))), 31 | _ => Err("The value cannot be convert into u32".to_string()), 32 | } 33 | } 34 | 35 | pub fn u16(value: SExpr) -> Result { 36 | match value.shared_val() { 37 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 38 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 39 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 40 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 41 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 42 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 43 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 44 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 45 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 46 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U16(*num as u16))), 47 | _ => Err("The value cannot be convert into u16".to_string()), 48 | } 49 | } 50 | 51 | pub fn u8(value: SExpr) -> Result { 52 | match value.shared_val() { 53 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 54 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 55 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 56 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 57 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 58 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 59 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 60 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 61 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 62 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::U8(*num as u8))), 63 | _ => Err("The value cannot be convert into u8".to_string()), 64 | } 65 | } 66 | 67 | pub fn i64(value: SExpr) -> Result { 68 | match value.shared_val() { 69 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 70 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 71 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 72 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 73 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 74 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 75 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 76 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 77 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 78 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I64(*num as i64))), 79 | _ => Err("The value cannot be convert into i64".to_string()), 80 | } 81 | } 82 | 83 | pub fn i32(value: SExpr) -> Result { 84 | match value.shared_val() { 85 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 86 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 87 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 88 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 89 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 90 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 91 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 92 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 93 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 94 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I32(*num as i32))), 95 | _ => Err("The value cannot be convert into i32".to_string()), 96 | } 97 | } 98 | 99 | pub fn i16(value: SExpr) -> Result { 100 | match value.shared_val() { 101 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 102 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 103 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 104 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 105 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 106 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 107 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 108 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 109 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 110 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I16(*num as i16))), 111 | _ => Err("The value cannot be convert into i16".to_string()), 112 | } 113 | } 114 | 115 | pub fn i8(value: SExpr) -> Result { 116 | match value.shared_val() { 117 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 118 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 119 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 120 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 121 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 122 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 123 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 124 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 125 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 126 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::I8(*num as i8))), 127 | _ => Err("The value cannot be convert into i8".to_string()), 128 | } 129 | } 130 | 131 | pub fn f32(value: SExpr) -> Result { 132 | match value.shared_val() { 133 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 134 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 135 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 136 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 137 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 138 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 139 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 140 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 141 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 142 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::F32(*num as f32))), 143 | _ => Err("The value cannot be convert into f32".to_string()), 144 | } 145 | } 146 | 147 | pub fn f64(value: SExpr) -> Result { 148 | match value.shared_val() { 149 | Some(SharedValue::U8(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 150 | Some(SharedValue::U16(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 151 | Some(SharedValue::U32(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 152 | Some(SharedValue::U64(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 153 | Some(SharedValue::I8(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 154 | Some(SharedValue::I16(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 155 | Some(SharedValue::I32(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 156 | Some(SharedValue::I64(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 157 | Some(SharedValue::F32(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 158 | Some(SharedValue::F64(num)) => Ok(SExpr::from_owned_value(OwnedValue::F64(*num as f64))), 159 | _ => Err("The value cannot be convert into f64".to_string()), 160 | } 161 | } 162 | -------------------------------------------------------------------------------- /src/expr/symbols/stream.rs: -------------------------------------------------------------------------------- 1 | use super::functions::eval_function; 2 | use super::utils::is_true; 3 | use super::*; 4 | 5 | pub fn to_array<'a>(expr: SExpr<'a>) -> Result, String> { 6 | match expr { 7 | SExpr::Vec(vec) => { 8 | let mut array = Vec::new(); 9 | for expr in vec { 10 | if let SExpr::Value(val) = expr { 11 | array.push(val.into_owned()) 12 | } else { 13 | return Err(format!("Data {:?} cannot be value", expr)); 14 | } 15 | } 16 | return Ok(SExpr::from_owned_value(OwnedValue::Array(array))); 17 | } 18 | SExpr::Value(Value::Shared(SharedValue::Array(_))) 19 | | SExpr::Value(Value::Owned(OwnedValue::Array(_))) => return Ok(expr), 20 | _ => { 21 | return Err(format!( 22 | "Only Vector can convert into array, found {:?}", 23 | expr 24 | )) 25 | } 26 | } 27 | } 28 | 29 | pub fn to_vec(expr: SExpr) -> Result { 30 | match expr { 31 | SExpr::Value(Value::Owned(OwnedValue::Array(array))) => { 32 | return Ok(SExpr::Vec( 33 | array 34 | .into_iter() 35 | .map(|val| SExpr::Value(Value::Owned(val))) 36 | .collect(), 37 | )); 38 | } 39 | SExpr::Value(Value::Shared(SharedValue::Array(array))) => { 40 | return Ok(SExpr::Vec( 41 | array 42 | .into_iter() 43 | .map(|val| SExpr::Value(Value::Shared(val))) 44 | .collect(), 45 | )); 46 | } 47 | SExpr::Vec(_) => Ok(expr), 48 | _ => { 49 | return Err(format!( 50 | "Only array value can convert into vector, found {:?}", 51 | expr 52 | )) 53 | } 54 | } 55 | } 56 | 57 | pub fn map<'a>( 58 | func: SExpr<'a>, 59 | data: SExpr<'a>, 60 | env: &mut Environment<'a>, 61 | ) -> Result, String> { 62 | match data { 63 | SExpr::Value(Value::Owned(OwnedValue::Array(_))) 64 | | SExpr::Value(Value::Shared(SharedValue::Array(_))) => { 65 | return map(func, to_vec(data)?, env) 66 | } 67 | SExpr::Vec(expr_list) => { 68 | let mut result = Vec::with_capacity(expr_list.len()); 69 | for expr in expr_list { 70 | result.push(eval_function(&func, vec![expr.eval(env)?], env)?) 71 | } 72 | return Ok(SExpr::Vec(result)); 73 | } 74 | _ => return Err(format!("Cannot map function on {:?}", data)), 75 | } 76 | } 77 | 78 | pub fn filter<'a>( 79 | func: SExpr<'a>, 80 | data: SExpr<'a>, 81 | env: &mut Environment<'a>, 82 | ) -> Result, String> { 83 | match data { 84 | SExpr::Value(Value::Owned(OwnedValue::Array(_))) 85 | | SExpr::Value(Value::Shared(SharedValue::Array(_))) => { 86 | return filter(func, to_vec(data)?, env) 87 | } 88 | SExpr::Vec(expr_list) => { 89 | let mut result = Vec::with_capacity(expr_list.len()); 90 | for expr in expr_list { 91 | let val = expr.eval(env)?; 92 | if is_true(&eval_function(&func, vec![val.clone()], env)?) { 93 | result.push(val) 94 | } 95 | } 96 | return Ok(SExpr::Vec(result)); 97 | } 98 | _ => return Err(format!("Cannot map function on {:?}", data)), 99 | } 100 | } 101 | -------------------------------------------------------------------------------- /src/expr/symbols/utils.rs: -------------------------------------------------------------------------------- 1 | use super::*; 2 | 3 | pub fn is_true(expr: &SExpr) -> bool { 4 | match expr.shared_val() { 5 | Some(SharedValue::Bool(false)) | Some(SharedValue::Null) => false, 6 | _ => true, // anything else than false and null value will be considered as yes 7 | } 8 | } 9 | -------------------------------------------------------------------------------- /src/integrated/lisp.rs: -------------------------------------------------------------------------------- 1 | use crate::expr::interpreter::Interpreter; 2 | use crate::expr::SExpr; 3 | use crate::lexer::lisp as lisp_lexer; 4 | use crate::parser::lisp as lisp_parser; 5 | 6 | use crate::expr::serde::Expr; 7 | 8 | pub fn parse_to_sexpr<'a, 'b>(code: &'b str) -> Result>, String> { 9 | let tokens = lisp_lexer::tokenize_str(code)?; 10 | lisp_parser::SExprParser::parse_to_expr(tokens) 11 | } 12 | 13 | pub fn parse_to_serde_expr<'b>(code: &'b str) -> Result, String> { 14 | let tokens = lisp_lexer::tokenize_str(code)?; 15 | lisp_parser::SerdeExprParser::parse_to_expr(tokens) 16 | } 17 | 18 | pub fn get_interpreter<'a>() -> Interpreter<'a> { 19 | Interpreter::new() 20 | } 21 | 22 | pub fn eval<'a>( 23 | interpreter: &mut Interpreter<'a>, 24 | exprs: Vec>, 25 | ) -> Result, String> { 26 | interpreter.eval(exprs) 27 | } 28 | 29 | pub fn eval_string<'a, 'b>( 30 | interpreter: &mut Interpreter<'a>, 31 | code: &'b str, 32 | ) -> Result, String> { 33 | eval(interpreter, parse_to_sexpr(code)?) 34 | } 35 | -------------------------------------------------------------------------------- /src/integrated/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod lisp; 2 | -------------------------------------------------------------------------------- /src/lexer/lisp.rs: -------------------------------------------------------------------------------- 1 | use std::collections::HashSet; 2 | 3 | #[derive(Debug)] 4 | pub enum Token { 5 | LeftParentheses, 6 | RightParentheses, 7 | Symbol(String), 8 | IntNumber(String, String), 9 | FloatNumber(String, String), 10 | String(String), 11 | LeftSquareBracket, 12 | RightSquareBracket, 13 | LeftCurlyBracket, 14 | RightCurlyBracket, 15 | Keyword(String), // Quote 16 | } 17 | 18 | impl ToString for Token { 19 | fn to_string(&self) -> String { 20 | match self { 21 | &Token::LeftParentheses => String::from("("), 22 | &Token::RightParentheses => String::from(")"), 23 | &Token::Symbol(ref s) => s.clone(), 24 | &Token::IntNumber(ref n, ref u) => format!("{}{}", n, u), 25 | &Token::FloatNumber(ref n, ref u) => format!("{}{}", n, u), 26 | &Token::String(ref s) => format!("\"{}\"", s), 27 | &Token::LeftSquareBracket => String::from("["), 28 | &Token::RightSquareBracket => String::from("]"), 29 | &Token::LeftCurlyBracket => String::from("{"), 30 | &Token::RightCurlyBracket => String::from("}"), 31 | &Token::Keyword(ref s) => format!(":{}", s), 32 | } 33 | } 34 | } 35 | 36 | pub struct CharIter { 37 | chars: Vec, 38 | current_pos: usize, 39 | } 40 | 41 | impl CharIter { 42 | pub fn new(data: Vec) -> CharIter { 43 | CharIter { 44 | chars: data, 45 | current_pos: 0, 46 | } 47 | } 48 | pub fn next(&mut self) -> Option { 49 | self.current_pos += 1; 50 | self.chars.get(self.current_pos).cloned() 51 | } 52 | pub fn peek_next(&self) -> Option { 53 | self.chars.get(self.current_pos + 1).cloned() 54 | } 55 | 56 | pub fn current(&mut self) -> Option { 57 | self.chars.get(self.current_pos).cloned() 58 | } 59 | } 60 | 61 | lazy_static! { 62 | static ref INT_NUM_TYPES: HashSet = 63 | vec!["u8", "u16", "u32", "u64", "i8", "i16", "i32", "i64"] 64 | .into_iter() 65 | .map(|str| str.to_string()) 66 | .collect(); 67 | static ref FLOAT_NUM_TYPES: HashSet = vec!["f32", "f64"] 68 | .into_iter() 69 | .map(|str| str.to_string()) 70 | .collect(); 71 | } 72 | 73 | macro_rules! defpattern { 74 | ($name: ident: $($pattern: pat)*) => {macro_rules! $name { 75 | () => {$($pattern)*} 76 | }}; 77 | } 78 | 79 | defpattern!(NUMBER_PATTERN: '0'..='9'); 80 | // defpattern!(WHITESPACE_PATTERN: ' '|'\t'|'\r'|'\n'); // unreliable 81 | 82 | fn readout_whitespaces(iter: &mut CharIter) { 83 | while let Some(c) = iter.next() { 84 | match c { 85 | ' ' | '\t' | '\r' | '\n' | ',' => {} 86 | _ => { 87 | break; 88 | } 89 | } 90 | } 91 | } 92 | 93 | fn read_number(first: char, iter: &mut CharIter) -> Result { 94 | let mut digit_chars = vec![first]; 95 | let mut unit_chars = Vec::new(); 96 | let mut is_float_number = false; 97 | while let Some(c) = iter.next() { 98 | match c { 99 | NUMBER_PATTERN!() => { 100 | match (unit_chars.first(), unit_chars.get(1), c) { 101 | // terminal states 102 | (Some(&'u'), None, '8') | // u8 103 | (Some(&'u'), Some(&'1'), '6') | // u16 104 | (Some(&'u'), Some(&'3'), '2') | // u32 105 | (Some(&'u'), Some(&'6'), '4') | // u64 106 | (Some(&'i'), None, '8') | // i8 107 | (Some(&'i'), Some(&'1'), '6') | // i16 108 | (Some(&'i'), Some(&'3'), '2') | // i32 109 | (Some(&'i'), Some(&'6'), '4') | // i64 110 | (Some(&'f'), Some(&'3'), '2') | // f32 111 | (Some(&'f'), Some(&'6'), '4') // f64 112 | => { 113 | unit_chars.push(c); 114 | break; 115 | } 116 | // mid states 117 | (Some(&'u'), None, '1') | // u16 118 | (Some(&'u'), None, '3') | // u32 119 | (Some(&'u'), None, '6') | // u64 120 | (Some(&'i'), None, '1') | // i16 121 | (Some(&'i'), None, '3') | // i32 122 | (Some(&'i'), None, '6') | // i64 123 | (Some(&'f'), None, '3') | // f32 124 | (Some(&'f'), None, '6') // f64 125 | => { 126 | unit_chars.push(c); 127 | }, 128 | (None, _, _) => { 129 | digit_chars.push(c); 130 | } 131 | _ => { 132 | return Err(format!("Unexpected token '{}' for number unit", c)) 133 | } 134 | } 135 | } 136 | '.' => { 137 | if !is_float_number { 138 | is_float_number = true; 139 | digit_chars.push(c); 140 | } else { 141 | return Err("There is a floating point in the number already".to_string()); 142 | } 143 | } 144 | 'u' | 'i' | 'f' => { 145 | unit_chars.push(c); 146 | } 147 | ' ' | '\t' | '\r' | '\n' | ',' => { 148 | break; 149 | } 150 | _ => return Err(format!("Unexpected token '{}' for number", c)), 151 | } 152 | } 153 | let digit_part: String = digit_chars.into_iter().collect(); 154 | let unit_part: String = unit_chars.into_iter().collect(); 155 | iter.next(); 156 | if is_float_number { 157 | if !FLOAT_NUM_TYPES.contains(&unit_part) { 158 | return Err(format!( 159 | "Invalid float number '{}{}'", 160 | digit_part, unit_part 161 | )); 162 | } 163 | return Ok(Token::FloatNumber(digit_part, unit_part)); 164 | } else { 165 | if !INT_NUM_TYPES.contains(&unit_part) { 166 | return Err(format!( 167 | "Invalid integer number '{}{}'", 168 | digit_part, unit_part 169 | )); 170 | } 171 | return Ok(Token::IntNumber(digit_part, unit_part)); 172 | } 173 | } 174 | 175 | fn read_escaped_char(iter: &mut CharIter) -> Result { 176 | while let Some(c) = iter.next() { 177 | match c { 178 | 'u' | 'U' => { 179 | // read 6 digit hex number as unicode 180 | let mut hex_chars: Vec = Vec::new(); 181 | for _ in 0..6 { 182 | if let Some(c) = iter.next() { 183 | let c = c.to_ascii_lowercase(); 184 | match c { 185 | NUMBER_PATTERN!() | 'a'..='f' => { 186 | hex_chars.push(c); 187 | } 188 | _ => break, 189 | } 190 | } else { 191 | break; 192 | } 193 | } 194 | let unicode_hex: String = hex_chars.into_iter().collect(); 195 | let unicode = u32::from_str_radix(&unicode_hex, 16).map_err(|_| { 196 | format!("Cannot parse hex for escape character 0x{}", unicode_hex) 197 | })?; 198 | return ::std::char::from_u32(unicode) 199 | .ok_or(format!("Cannot escape character \\u{}", unicode_hex)); 200 | } 201 | 't' => return Ok('\t'), 202 | 'n' => return Ok('\n'), 203 | 'r' => return Ok('\r'), 204 | '\'' => return Ok('\''), 205 | '"' => return Ok('"'), 206 | '\\' => return Ok('\''), 207 | _ => return Err(format!("Unknown escape character '{}'", c)), 208 | } 209 | } 210 | return Err("Unexpected EOF".to_string()); 211 | } 212 | 213 | fn read_string(iter: &mut CharIter) -> Result { 214 | let mut chars = Vec::new(); 215 | while let Some(c) = iter.next() { 216 | match c { 217 | '\\' => { 218 | // escaping 219 | chars.push(read_escaped_char(iter)?); 220 | } 221 | '"' => { 222 | break; 223 | } 224 | _ => { 225 | chars.push(c); 226 | } 227 | } 228 | } 229 | return Ok(Token::String(chars.into_iter().collect())); 230 | } 231 | 232 | fn read_ident_str(chars: &mut Vec, iter: &mut CharIter) { 233 | while let Some(c) = iter.next() { 234 | match c { 235 | ' ' | '\t' | '\r' | '\n' | '(' | ')' | '[' | ']' | '{' | '}' | '\'' | ',' => { 236 | break; 237 | } 238 | _ => { 239 | chars.push(c); 240 | } 241 | } 242 | } 243 | } 244 | 245 | fn read_symbol(first: char, iter: &mut CharIter) -> Result { 246 | let mut chars = vec![first]; 247 | read_ident_str(&mut chars, iter); 248 | return Ok(Token::Symbol(chars.into_iter().collect())); 249 | } 250 | 251 | fn read_keyword(iter: &mut CharIter) -> Result { 252 | let mut chars = vec![]; // Emit the colon part 253 | read_ident_str(&mut chars, iter); 254 | return Ok(Token::Keyword(chars.into_iter().collect())); 255 | } 256 | 257 | pub fn tokenize_chars_iter(iter: &mut CharIter) -> Result, String> { 258 | let mut tokens = Vec::new(); 259 | while let Some(c) = iter.current() { 260 | match c { 261 | ' ' | '\t' | '\r' | '\n' | ',' => { 262 | // whitespaces 263 | // will do nothing 264 | readout_whitespaces(iter); 265 | } 266 | '(' => { 267 | tokens.push(Token::LeftParentheses); 268 | iter.next(); 269 | } 270 | ')' => { 271 | tokens.push(Token::RightParentheses); 272 | iter.next(); 273 | } 274 | '[' => { 275 | tokens.push(Token::LeftSquareBracket); 276 | iter.next(); 277 | } 278 | ']' => { 279 | tokens.push(Token::RightSquareBracket); 280 | iter.next(); 281 | } 282 | '{' => { 283 | tokens.push(Token::LeftCurlyBracket); 284 | iter.next(); 285 | } 286 | '}' => { 287 | tokens.push(Token::RightCurlyBracket); 288 | iter.next(); 289 | } 290 | NUMBER_PATTERN!() => { 291 | tokens.push(read_number(c, iter)?); 292 | } 293 | // match negative number need next char to be a digit 294 | '-' if match iter.peek_next() { 295 | Some(NUMBER_PATTERN!()) => true, 296 | _ => false, 297 | } => 298 | { 299 | tokens.push(read_number(c, iter)?); 300 | } 301 | // '\'' => { // quote 302 | // tokens.push(Token::Quote); 303 | // iter.next(); 304 | // }, 305 | '"' => { 306 | // string 307 | tokens.push(read_string(iter)?); 308 | } 309 | ':' => tokens.push(read_keyword(iter)?), 310 | _ => { 311 | // symbol with utf8 chars including emojis 312 | tokens.push(read_symbol(c, iter)?); 313 | } 314 | } 315 | } 316 | return Ok(tokens); 317 | } 318 | 319 | pub fn tokenize_str<'a>(str: &'a str) -> Result, String> { 320 | let mut iter = CharIter::new(str.chars().collect()); 321 | tokenize_chars_iter(&mut iter) 322 | } 323 | -------------------------------------------------------------------------------- /src/lexer/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod lisp; 2 | -------------------------------------------------------------------------------- /src/lib.rs: -------------------------------------------------------------------------------- 1 | #![feature(exact_size_is_empty)] 2 | #![crate_type = "lib"] 3 | 4 | extern crate log; 5 | extern crate serde; 6 | #[macro_use] 7 | extern crate serde_derive; 8 | extern crate bifrost; 9 | extern crate bifrost_hasher; 10 | extern crate byteorder; 11 | #[macro_use] 12 | extern crate lazy_static; 13 | 14 | #[macro_use] 15 | pub mod types; 16 | pub mod expr; 17 | pub mod integrated; 18 | pub mod lexer; 19 | pub mod parser; 20 | 21 | pub use ahash; 22 | -------------------------------------------------------------------------------- /src/parser/lisp.rs: -------------------------------------------------------------------------------- 1 | use ahash::{HashMap, HashMapExt}; 2 | 3 | use crate::types::{Map, OwnedValue as Value}; 4 | use crate::{lexer::lisp::Token, types::OwnedMap}; 5 | use std::{marker::PhantomData, mem, vec::IntoIter}; 6 | 7 | use crate::expr::{serde::Expr, SExpr}; 8 | 9 | pub trait ParserExpr: Sized { 10 | fn list(data: Vec) -> Self; 11 | fn vec(data: Vec) -> Self; 12 | fn symbol(name: String) -> Self; 13 | fn keyword(name: String) -> Self; 14 | fn owned_val(val: Value) -> Self; 15 | fn into_val(self) -> Result; 16 | } 17 | 18 | pub struct Parser { 19 | _p: PhantomData, 20 | } 21 | 22 | pub type SExprParser<'a> = Parser>; 23 | pub type SerdeExprParser = Parser; 24 | 25 | impl Parser { 26 | fn parse_list<'a>(iter: &mut IntoIter) -> Result { 27 | let mut contents = Vec::new(); 28 | while let Some(token) = iter.next() { 29 | match token { 30 | Token::RightParentheses => { 31 | return Ok(E::list(contents)); 32 | } 33 | _ => { 34 | contents.push(Self::parse_token(token, iter)?); 35 | } 36 | } 37 | } 38 | Err(String::from("Unexpected EOF, expect ')'")) 39 | } 40 | 41 | fn parse_vec<'a>(iter: &mut IntoIter) -> Result { 42 | let mut contents = Vec::new(); 43 | while let Some(token) = iter.next() { 44 | match token { 45 | Token::RightSquareBracket => { 46 | return Ok(E::vec(contents)); 47 | } 48 | _ => { 49 | contents.push(Self::parse_token(token, iter)?); 50 | } 51 | } 52 | } 53 | Err(String::from("Unexpected EOF, expect ']'")) 54 | } 55 | 56 | fn parse_map<'a>(iter: &mut IntoIter) -> Result { 57 | let mut contents: Vec<(String, Value)> = Vec::with_capacity(4); 58 | let mut visited = 0; 59 | let mut last_key = String::from(""); 60 | while let Some(token) = iter.next() { 61 | match token { 62 | Token::RightCurlyBracket => { 63 | // return Ok(E::map(contents)); 64 | let owned_map = OwnedMap::from_pairs(contents.into_iter()); 65 | return Ok(E::owned_val(Value::Map(owned_map))); 66 | } 67 | _ => { 68 | if visited & 1 == 0 { 69 | // parse key 70 | match token { 71 | Token::Symbol(k) | Token::String(k) | Token::Keyword(k) => { 72 | last_key = k; 73 | } 74 | _ => { 75 | return Err(format!( 76 | "Expecting map key with string but get {:?}", 77 | token 78 | )) 79 | } 80 | } 81 | } else { 82 | let key = mem::replace(&mut last_key, String::from("")); 83 | let val = Self::parse_token(token, iter)?; 84 | let owned_val = val.into_val()?; 85 | contents.push((key, owned_val)); 86 | } 87 | visited += 1; 88 | } 89 | } 90 | } 91 | Err(String::from("Unexpected EOF, expect ']'")) 92 | } 93 | 94 | fn parse_symbol<'a>(name: String) -> E { 95 | E::symbol(name) 96 | } 97 | 98 | fn parse_keyword<'a>(name: String) -> E { 99 | E::keyword(name) 100 | } 101 | 102 | fn parse_int<'a>(num_str: String, unit: String) -> Result { 103 | match unit.as_ref() { 104 | "u8" => num_str.parse::().map(Value::U8), 105 | "u16" => num_str.parse::().map(Value::U16), 106 | "u32" => num_str.parse::().map(Value::U32), 107 | "u64" => num_str.parse::().map(Value::U64), 108 | "i8" => num_str.parse::().map(Value::I8), 109 | "i16" => num_str.parse::().map(Value::I16), 110 | "i32" => num_str.parse::().map(Value::I32), 111 | "i64" => num_str.parse::().map(Value::I64), 112 | _ => return Err(format!("Unknown int number type {}", unit)), 113 | } 114 | .map_err(|e| { 115 | format!( 116 | "Cannot parse int {} with unit {}, reason: {:?}", 117 | num_str, unit, e 118 | ) 119 | }) 120 | .map(E::owned_val) 121 | } 122 | 123 | fn parse_float<'a>(num_str: String, unit: String) -> Result { 124 | match unit.as_ref() { 125 | "f32" => num_str.parse::().map(Value::F32), 126 | "f64" => num_str.parse::().map(Value::F64), 127 | _ => return Err(format!("Unknown float number type {}", unit)), 128 | } 129 | .map_err(|e| { 130 | format!( 131 | "Cannot parse float {} with unit {}, reason: {:?}", 132 | num_str, unit, e 133 | ) 134 | }) 135 | .map(E::owned_val) 136 | } 137 | 138 | fn parse_string<'a>(str: String) -> E { 139 | E::owned_val(Value::String(str)) 140 | } 141 | 142 | fn parse_token<'a>(token: Token, iter: &mut IntoIter) -> Result { 143 | match token { 144 | Token::LeftParentheses => Ok(Self::parse_list(iter)?), // list 145 | Token::Symbol(name) => Ok(Self::parse_symbol(name)), 146 | Token::IntNumber(num, unit) => Ok(Self::parse_int(num, unit)?), 147 | Token::FloatNumber(num, unit) => Ok(Self::parse_float(num, unit)?), 148 | Token::String(str) => Ok(Self::parse_string(str)), 149 | Token::LeftSquareBracket => Ok(Self::parse_vec(iter)?), 150 | Token::LeftCurlyBracket => Ok(Self::parse_map(iter)?), 151 | Token::Keyword(str) => Ok(Self::parse_keyword(str)), 152 | _ => Err(format!("Unexpected start token {}", token.to_string())), 153 | } 154 | } 155 | 156 | pub fn parse_to_expr<'a>(tokens: Vec) -> Result, String> { 157 | let mut exprs: Vec = Vec::new(); 158 | let mut iter = tokens.into_iter(); 159 | while let Some(token) = iter.next() { 160 | exprs.push(Self::parse_token(token, &mut iter)?) 161 | } 162 | Ok(exprs) 163 | } 164 | } 165 | -------------------------------------------------------------------------------- /src/parser/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod lisp; 2 | -------------------------------------------------------------------------------- /src/types/custom_types/any.rs: -------------------------------------------------------------------------------- 1 | use bifrost::utils::serde::{deserialize, serialize}; 2 | use serde; 3 | 4 | #[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq, Hash)] 5 | pub struct Any { 6 | pub data: Vec, 7 | } 8 | impl Any { 9 | pub fn to<'a, T>(&'a self) -> T 10 | where 11 | T: serde::Deserialize<'a>, 12 | { 13 | deserialize(&self.data).unwrap() 14 | } 15 | pub fn from(data: &T) -> Any 16 | where 17 | T: serde::Serialize, 18 | { 19 | Any { 20 | data: serialize(data), 21 | } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /src/types/custom_types/bytes.rs: -------------------------------------------------------------------------------- 1 | use std::ops::Deref; 2 | use std::ops::DerefMut; 3 | 4 | use bifrost::utils::serde::{deserialize, serialize}; 5 | #[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq, Hash, PartialOrd, Ord)] 6 | pub struct Bytes { 7 | pub data: Vec, 8 | } 9 | 10 | #[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq, Hash, PartialOrd, Ord)] 11 | pub struct SmallBytes { 12 | pub data: Vec, 13 | } 14 | 15 | impl Deref for Bytes { 16 | type Target = Vec; 17 | 18 | fn deref(&self) -> &'_ ::Target { 19 | &self.data 20 | } 21 | } 22 | 23 | impl DerefMut for Bytes { 24 | fn deref_mut(&mut self) -> &'_ mut ::Target { 25 | &mut self.data 26 | } 27 | } 28 | 29 | impl Deref for SmallBytes { 30 | type Target = Vec; 31 | 32 | fn deref(&self) -> &'_ ::Target { 33 | &self.data 34 | } 35 | } 36 | 37 | impl DerefMut for SmallBytes { 38 | fn deref_mut(&mut self) -> &'_ mut ::Target { 39 | &mut self.data 40 | } 41 | } 42 | 43 | impl Bytes { 44 | pub fn from_vec(vec: Vec) -> Bytes { 45 | Bytes { data: vec } 46 | } 47 | pub fn to<'a, T>(&'a self) -> T 48 | where 49 | T: serde::Deserialize<'a>, 50 | { 51 | deserialize(&self.data).unwrap() 52 | } 53 | pub fn from(data: &T) -> Self 54 | where 55 | T: serde::Serialize, 56 | { 57 | Self { 58 | data: serialize(data), 59 | } 60 | } 61 | } 62 | 63 | impl SmallBytes { 64 | pub fn from_vec(vec: Vec) -> SmallBytes { 65 | SmallBytes { data: vec } 66 | } 67 | } 68 | 69 | impl From> for SmallBytes { 70 | fn from(vec: Vec) -> Self { 71 | Self { data: vec } 72 | } 73 | } 74 | 75 | impl From> for Bytes { 76 | fn from(vec: Vec) -> Self { 77 | Self { data: vec } 78 | } 79 | } 80 | 81 | impl AsRef<[u8]> for Bytes { 82 | fn as_ref(&self) -> &[u8] { 83 | self.data.as_slice() 84 | } 85 | } 86 | 87 | impl AsRef<[u8]> for SmallBytes { 88 | fn as_ref(&self) -> &[u8] { 89 | self.data.as_slice() 90 | } 91 | } 92 | -------------------------------------------------------------------------------- /src/types/custom_types/id.rs: -------------------------------------------------------------------------------- 1 | use bifrost::utils::serde::serialize; 2 | use bifrost_hasher::{hash_bytes, hash_bytes_secondary}; 3 | use byteorder::{BigEndian, ReadBytesExt, WriteBytesExt}; 4 | use serde; 5 | use std::io::{Cursor, Error}; 6 | 7 | #[derive(Debug, Clone, Copy, Serialize, Deserialize, Hash, Ord, PartialOrd, PartialEq, Eq)] 8 | pub struct Id { 9 | pub higher: u64, 10 | pub lower: u64, 11 | } 12 | 13 | impl Id { 14 | pub const fn new(higher: u64, lower: u64) -> Id { 15 | Id { higher, lower } 16 | } 17 | pub fn from_obj(obj: &T) -> Id 18 | where 19 | T: serde::Serialize, 20 | { 21 | let vec = serialize(obj); 22 | let bin = vec.as_slice(); 23 | Id { 24 | higher: hash_bytes(&bin), 25 | lower: hash_bytes_secondary(&bin), 26 | } 27 | } 28 | pub fn is_greater_than(&self, other: &Id) -> bool { 29 | self.higher >= other.higher && self.lower > other.lower 30 | } 31 | pub const fn unit_id() -> Id { 32 | Id { 33 | higher: 0, 34 | lower: 0, 35 | } 36 | } 37 | pub const fn max_id() -> Id { 38 | Id { 39 | higher: !0, 40 | lower: !0, 41 | } 42 | } 43 | pub fn is_unit_id(&self) -> bool { 44 | self.higher == 0 && self.lower == 0 45 | } 46 | pub fn to_binary(&self) -> [u8; 16] { 47 | let mut slice = [0u8; 16]; 48 | { 49 | let mut cursor = Cursor::new(&mut slice[..]); 50 | cursor.write_u64::(self.higher).unwrap(); 51 | cursor.write_u64::(self.lower).unwrap(); 52 | } 53 | return slice; 54 | } 55 | pub fn from_binary(cursor: &mut Cursor) -> Result 56 | where 57 | Cursor: ReadBytesExt, 58 | { 59 | Ok(Id::new( 60 | cursor.read_u64::()?, 61 | cursor.read_u64::()?, 62 | )) 63 | } 64 | pub fn into_option(self) -> Option { 65 | if self.is_unit_id() { 66 | None 67 | } else { 68 | Some(self) 69 | } 70 | } 71 | } 72 | 73 | impl Default for Id { 74 | fn default() -> Id { 75 | Self::unit_id() 76 | } 77 | } 78 | 79 | #[cfg(test)] 80 | mod test { 81 | use crate::types::custom_types::id::Id; 82 | use std::cmp::Ordering; 83 | use std::collections::BTreeMap; 84 | use std::collections::HashMap; 85 | 86 | #[test] 87 | fn compare() { 88 | let id_1 = Id::new(1, 2); 89 | let id_2 = Id::new(2, 2); 90 | let id_3 = Id::new(1, 2); 91 | let id_4 = Id::new(1, 3); 92 | assert_eq!(id_1.cmp(&id_2), Ordering::Less); 93 | assert!(id_1 < id_2); 94 | assert_eq!(id_1, id_3); 95 | assert!(id_4 > id_1); 96 | } 97 | 98 | #[test] 99 | fn with_btree() { 100 | let mut map = BTreeMap::new(); 101 | let id_1 = Id::new(1, 2); 102 | let id_2 = Id::new(2, 2); 103 | let id_3 = Id::new(1, 3); 104 | let id_4 = Id::new(1, 5); 105 | let id_5 = Id::new(3, 5); 106 | 107 | assert!(map.insert(id_1, 1).is_none()); 108 | assert!(map.insert(id_2, 2).is_none()); 109 | assert!(map.insert(id_3, 3).is_none()); 110 | assert!(map.insert(id_4, 4).is_none()); 111 | assert!(map.insert(id_5, 5).is_none()); 112 | 113 | assert_eq!(map.get(&id_1), Some(&1)); 114 | assert_eq!(map.get(&id_2), Some(&2)); 115 | assert_eq!(map.get(&id_3), Some(&3)); 116 | assert_eq!(map.get(&id_4), Some(&4)); 117 | assert_eq!(map.get(&id_5), Some(&5)); 118 | } 119 | 120 | #[test] 121 | fn with_hashmap() { 122 | let mut map = HashMap::new(); 123 | let id_1 = Id::new(1, 2); 124 | let id_2 = Id::new(2, 2); 125 | let id_3 = Id::new(1, 3); 126 | let id_4 = Id::new(1, 5); 127 | let id_5 = Id::new(3, 5); 128 | 129 | assert!(map.insert(id_1, 1).is_none()); 130 | assert!(map.insert(id_2, 2).is_none()); 131 | assert!(map.insert(id_3, 3).is_none()); 132 | assert!(map.insert(id_4, 4).is_none()); 133 | assert!(map.insert(id_5, 5).is_none()); 134 | 135 | assert_eq!(map.get(&id_1), Some(&1)); 136 | assert_eq!(map.get(&id_2), Some(&2)); 137 | assert_eq!(map.get(&id_3), Some(&3)); 138 | assert_eq!(map.get(&id_4), Some(&4)); 139 | assert_eq!(map.get(&id_5), Some(&5)); 140 | } 141 | } 142 | -------------------------------------------------------------------------------- /src/types/custom_types/map.rs: -------------------------------------------------------------------------------- 1 | use crate::types::{key_hash, OwnedMap, SharedMap, Value}; 2 | use ahash::HashMap; 3 | use serde::Serialize; 4 | use std::{collections::BTreeMap, slice::Iter}; 5 | use std::iter::FromIterator; 6 | use std::ops::{Index, IndexMut}; 7 | 8 | pub trait Map { 9 | type Value: Value; 10 | fn new() -> Self; 11 | fn from_pairs>(map: P) -> Self; 12 | fn insert<'a>(&mut self, key: &'a str, value: Self::Value) -> Option; 13 | fn insert_key_id(&mut self, key: u64, value: Self::Value) -> Option; 14 | fn get_by_key_id(&self, key: u64) -> &Self::Value; 15 | fn get_mut_by_key_id(&mut self, key: u64) -> &mut Self::Value; 16 | fn get<'a>(&self, key: &'a str) -> &Self::Value; 17 | fn get_mut<'a>(&mut self, key: &'a str) -> &mut Self::Value; 18 | fn strs_to_ids<'a>(keys: &[&'a str]) -> Vec { 19 | keys.iter().map(|str| key_hash(str)).collect() 20 | } 21 | fn get_in_by_ids<'a, I: Iterator + ExactSizeIterator>( 22 | &self, 23 | key_ids: I, 24 | ) -> &Self::Value; 25 | fn get_in(&self, keys: &[&'static str]) -> &Self::Value; 26 | fn get_in_mut_by_key_ids(&mut self, keys_ids: Iter) -> Option<&mut Self::Value>; 27 | fn get_in_mut(&mut self, keys: &[&'static str]) -> Option<&mut Self::Value>; 28 | fn update_in_by_key_ids(&mut self, keys: Iter, update: U) -> Option<()> 29 | where 30 | U: FnOnce(&mut Self::Value); 31 | fn update_in(&mut self, keys: &[&'static str], update: U) -> Option<()> 32 | where 33 | U: FnOnce(&mut Self::Value); 34 | fn set_in_by_key_ids(&mut self, keys: Iter, value: Self::Value) -> Option<()>; 35 | fn set_in(&mut self, keys: &[&'static str], value: Self::Value) -> Option<()>; 36 | fn into_string_map(self) -> HashMap; 37 | fn len(&self) -> usize; 38 | fn shared<'a>(&'a self) -> SharedMap<'a>; 39 | fn owned(&self) -> OwnedMap; 40 | } 41 | 42 | const SMALL_MAP_CAPACITY: usize = 16; 43 | 44 | #[derive(Clone, Serialize, Deserialize, Eq, PartialEq, Debug)] 45 | pub struct SmallMap { 46 | pairs: Vec<(K, V)>, 47 | } 48 | 49 | #[derive(Clone, Serialize, Deserialize, Debug)] 50 | pub enum GenericMap { 51 | Small(SmallMap), 52 | Large(BTreeMap), 53 | } 54 | 55 | impl GenericMap { 56 | pub fn new() -> Self { 57 | GenericMap::Small(SmallMap::new()) 58 | } 59 | 60 | pub fn insert(&mut self, key: K, value: V) -> Option { 61 | self.check_upgrade(); 62 | match self { 63 | GenericMap::Small(small) => small.insert(key, value), 64 | GenericMap::Large(large) => large.insert(key, value), 65 | } 66 | } 67 | 68 | pub fn get(&self, key: &K) -> Option<&V> { 69 | match self { 70 | GenericMap::Small(small) => small.get(key), 71 | GenericMap::Large(large) => large.get(key), 72 | } 73 | } 74 | 75 | pub fn get_mut(&mut self, key: &K) -> Option<&mut V> { 76 | match self { 77 | GenericMap::Small(small) => small.get_mut(key), 78 | GenericMap::Large(large) => large.get_mut(key), 79 | } 80 | } 81 | 82 | pub fn len(&self) -> usize { 83 | match self { 84 | GenericMap::Small(small) => small.len(), 85 | GenericMap::Large(large) => large.len(), 86 | } 87 | } 88 | 89 | pub fn is_empty(&self) -> bool { 90 | match self { 91 | GenericMap::Small(small) => small.is_empty(), 92 | GenericMap::Large(large) => large.is_empty(), 93 | } 94 | } 95 | 96 | pub fn remove(&mut self, key: &K) -> Option { 97 | match self { 98 | GenericMap::Small(small) => small.remove(key), 99 | GenericMap::Large(large) => large.remove(key), 100 | } 101 | } 102 | 103 | pub fn iter<'a>(&'a self) -> Box + 'a> { 104 | match self { 105 | GenericMap::Small(small) => Box::new(small.pairs.iter().map(|(k, v)| (k, v))), 106 | GenericMap::Large(large) => Box::new(large.iter()), 107 | } 108 | } 109 | 110 | pub fn into_iter(self) -> Box> 111 | where 112 | K: 'static, 113 | V: 'static, 114 | { 115 | match self { 116 | GenericMap::Small(small) => Box::new(small.pairs.into_iter()), 117 | GenericMap::Large(large) => Box::new(large.into_iter()), 118 | } 119 | } 120 | 121 | fn check_upgrade(&mut self) { 122 | match self { 123 | GenericMap::Small(small) => { 124 | if small.len() + 1 >= SMALL_MAP_CAPACITY { 125 | let mut large = BTreeMap::new(); 126 | for (k, v) in small.pairs.drain(..small.len()) { 127 | large.insert(k, v); 128 | } 129 | *self = GenericMap::Large(large); 130 | } 131 | } 132 | GenericMap::Large(_) => {} 133 | } 134 | } 135 | 136 | // Gets a mutable reference to the value corresponding to the key or inserts a default value 137 | pub fn get_or_insert(&mut self, key: K, default: V) -> &mut V 138 | where K: Clone 139 | { 140 | self.check_upgrade(); 141 | let has_key = match self { 142 | GenericMap::Small(small) => small.get(&key).is_some(), 143 | GenericMap::Large(large) => large.contains_key(&key), 144 | }; 145 | 146 | if !has_key { 147 | self.insert(key.clone(), default); 148 | } 149 | 150 | match self { 151 | GenericMap::Small(small) => { 152 | for (k, v) in &mut small.pairs { 153 | if k == &key { 154 | return v; 155 | } 156 | } 157 | unreachable!("Key not found after insertion") 158 | } 159 | GenericMap::Large(large) => large.get_mut(&key).unwrap(), 160 | } 161 | } 162 | 163 | // Gets a mutable reference to the value corresponding to the key or 164 | // inserts a value computed from the default function 165 | pub fn get_or_insert_with V>(&mut self, key: K, default: F) -> &mut V 166 | where K: Clone 167 | { 168 | self.check_upgrade(); 169 | let has_key = match self { 170 | GenericMap::Small(small) => small.get(&key).is_some(), 171 | GenericMap::Large(large) => large.contains_key(&key), 172 | }; 173 | 174 | if !has_key { 175 | let value = default(); 176 | self.insert(key.clone(), value); 177 | } 178 | 179 | match self { 180 | GenericMap::Small(small) => { 181 | for (k, v) in &mut small.pairs { 182 | if k == &key { 183 | return v; 184 | } 185 | } 186 | unreachable!("Key not found after insertion") 187 | } 188 | GenericMap::Large(large) => large.get_mut(&key).unwrap(), 189 | } 190 | } 191 | } 192 | 193 | impl SmallMap { 194 | pub fn new() -> Self { 195 | SmallMap { 196 | pairs: Vec::with_capacity(SMALL_MAP_CAPACITY), 197 | } 198 | } 199 | 200 | pub fn insert(&mut self, key: K, value: V) -> Option { 201 | for (k, v) in self.pairs.iter_mut() { 202 | if k == &key { 203 | return Some(std::mem::replace(v, value)); 204 | } 205 | } 206 | self.pairs.push((key, value)); 207 | None 208 | } 209 | 210 | pub fn get(&self, key: &K) -> Option<&V> { 211 | for (k, v) in self.pairs.iter() { 212 | if k == key { 213 | return Some(v); 214 | } 215 | } 216 | None 217 | } 218 | 219 | pub fn get_mut(&mut self, key: &K) -> Option<&mut V> { 220 | for (k, v) in self.pairs.iter_mut() { 221 | if k == key { 222 | return Some(v); 223 | } 224 | } 225 | None 226 | } 227 | 228 | pub fn len(&self) -> usize { 229 | self.pairs.len() 230 | } 231 | 232 | pub fn is_empty(&self) -> bool { 233 | self.pairs.is_empty() 234 | } 235 | 236 | pub fn remove(&mut self, key: &K) -> Option { 237 | for (i, (k, _v)) in self.pairs.iter().enumerate() { 238 | if k == key { 239 | return Some(self.pairs.remove(i).1); 240 | } 241 | } 242 | None 243 | } 244 | } 245 | 246 | impl FromIterator<(K, V)> for GenericMap { 247 | fn from_iter>(iter: I) -> Self { 248 | let mut map = GenericMap::new(); 249 | for (k, v) in iter { 250 | map.insert(k, v); 251 | } 252 | map 253 | } 254 | } 255 | 256 | impl Index<&K> for GenericMap { 257 | type Output = V; 258 | 259 | fn index(&self, key: &K) -> &Self::Output { 260 | match self.get(key) { 261 | Some(val) => val, 262 | None => panic!("Key not found in GenericMap"), 263 | } 264 | } 265 | } 266 | 267 | impl IndexMut<&K> for GenericMap { 268 | fn index_mut(&mut self, key: &K) -> &mut Self::Output { 269 | match self.get_mut(key) { 270 | Some(val) => val, 271 | None => panic!("Key not found in GenericMap"), 272 | } 273 | } 274 | } 275 | 276 | impl Eq for GenericMap {} 277 | impl PartialEq for GenericMap { 278 | fn eq(&self, other: &Self) -> bool { 279 | self.iter().all(|(k, v)| other.get(k) == Some(v)) 280 | } 281 | } 282 | -------------------------------------------------------------------------------- /src/types/custom_types/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod any; 2 | pub mod bytes; 3 | pub mod id; 4 | pub mod map; 5 | pub mod owned_map; 6 | pub mod pos; 7 | pub mod shared_map; 8 | -------------------------------------------------------------------------------- /src/types/custom_types/owned_map.rs: -------------------------------------------------------------------------------- 1 | use crate::types::SharedMap; 2 | 3 | use super::map::{GenericMap, Map}; 4 | use super::{super::*, shared_map::key_hash}; 5 | use ahash::{HashMap, HashMapExt}; 6 | use std::collections::BTreeMap; 7 | use std::fmt; 8 | use std::iter::Iterator; 9 | use std::slice::Iter; 10 | 11 | #[derive(Clone, Serialize, Deserialize)] 12 | pub struct OwnedMap { 13 | pub map: GenericMap, 14 | pub fields: Vec, 15 | } 16 | 17 | impl Map for OwnedMap { 18 | type Value = OwnedValue; 19 | 20 | fn new() -> Self { 21 | Self { 22 | map: GenericMap::new(), 23 | fields: Vec::new(), 24 | } 25 | } 26 | fn from_pairs

(map: P) -> Self 27 | where P: IntoIterator 28 | { 29 | let mut target_map = GenericMap::new(); 30 | let mut fields = Vec::new(); 31 | for (key, value) in map { 32 | if target_map.insert(key_hash(&key), value).is_none() { 33 | fields.push(key); 34 | } 35 | } 36 | Self { 37 | map: target_map, 38 | fields, 39 | } 40 | } 41 | fn insert<'a>(&mut self, key: &'a str, value: Self::Value) -> Option { 42 | self.fields.push(key.to_string()); 43 | self.insert_key_id(key_hash(key), value) 44 | } 45 | fn insert_key_id(&mut self, key: u64, value: Self::Value) -> Option { 46 | self.map.insert(key, value) 47 | } 48 | 49 | fn get_by_key_id(&self, key: u64) -> &Self::Value { 50 | self.map.get(&key).unwrap_or(&NULL_OWNED_VALUE) 51 | } 52 | fn get_mut_by_key_id<'a>(&'a mut self, key: u64) -> &'a mut Self::Value { 53 | self.map.get_or_insert(key, OwnedValue::Null) 54 | } 55 | fn get<'a>(&self, key: &'a str) -> &Self::Value { 56 | self.get_by_key_id(key_hash(key)) 57 | } 58 | fn get_mut<'a>(&mut self, key: &'a str) -> &mut Self::Value { 59 | self.get_mut_by_key_id(key_hash(key)) 60 | } 61 | fn get_in_by_ids<'a, I: Iterator + ExactSizeIterator>( 62 | &self, 63 | mut key_ids: I, 64 | ) -> &Self::Value { 65 | let current_key = key_ids.next().cloned(); 66 | if let Some(key) = current_key { 67 | let value = self.get_by_key_id(key); 68 | if key_ids.is_empty() { 69 | return value; 70 | } else { 71 | match value { 72 | &Self::Value::Map(ref map) => return map.get_in_by_ids(key_ids), 73 | _ => {} 74 | } 75 | } 76 | } 77 | return &NULL_OWNED_VALUE; 78 | } 79 | fn get_in(&self, keys: &[&'static str]) -> &Self::Value { 80 | self.get_in_by_ids(Self::strs_to_ids(keys).iter()) 81 | } 82 | fn get_in_mut_by_key_ids(&mut self, mut keys_ids: Iter) -> Option<&mut Self::Value> { 83 | let current_key = keys_ids.next().cloned(); 84 | if let Some(key) = current_key { 85 | let value = self.get_mut_by_key_id(key); 86 | match value { 87 | &mut Self::Value::Null => return None, 88 | _ => { 89 | if keys_ids.is_empty() { 90 | return Some(value); 91 | } else { 92 | match value { 93 | &mut Self::Value::Map(ref mut map) => { 94 | return map.get_in_mut_by_key_ids(keys_ids) 95 | } 96 | _ => return None, 97 | } 98 | } 99 | } 100 | } 101 | } else { 102 | return None; 103 | } 104 | } 105 | fn get_in_mut(&mut self, keys: &[&'static str]) -> Option<&mut Self::Value> { 106 | self.get_in_mut_by_key_ids(Self::strs_to_ids(keys).iter()) 107 | } 108 | fn update_in_by_key_ids(&mut self, keys: Iter, update: U) -> Option<()> 109 | where 110 | U: FnOnce(&mut Self::Value), 111 | { 112 | let value = self.get_in_mut_by_key_ids(keys); 113 | if let Some(value) = value { 114 | update(value); 115 | Some(()) 116 | } else { 117 | None 118 | } 119 | } 120 | fn update_in(&mut self, keys: &[&'static str], update: U) -> Option<()> 121 | where 122 | U: FnOnce(&mut Self::Value), 123 | { 124 | self.update_in_by_key_ids(Self::strs_to_ids(keys).iter(), update) 125 | } 126 | fn set_in_by_key_ids(&mut self, keys: Iter, value: Self::Value) -> Option<()> { 127 | let val = self.get_in_mut_by_key_ids(keys); 128 | if let Some(val) = val { 129 | *val = value; 130 | Some(()) 131 | } else { 132 | None 133 | } 134 | } 135 | fn set_in(&mut self, keys: &[&'static str], value: Self::Value) -> Option<()> { 136 | self.set_in_by_key_ids(Self::strs_to_ids(keys).iter(), value) 137 | } 138 | fn into_string_map(self) -> HashMap { 139 | let mut result = HashMap::new(); 140 | for (i, field_name) in self.fields.into_iter().enumerate() { 141 | if i < self.map.len() { 142 | let field_id = key_hash(&field_name); 143 | if let Some(value) = self.map.get(&field_id) { 144 | result.insert(field_name, value.clone()); 145 | } 146 | } 147 | } 148 | result 149 | } 150 | fn len(&self) -> usize { 151 | self.map.len() 152 | } 153 | fn shared<'a>(&'a self) -> SharedMap<'a> { 154 | SharedMap { 155 | fields: self.fields.clone(), 156 | map: self.map.iter().map(|(k, v)| (*k, v.shared())).collect(), 157 | } 158 | } 159 | 160 | fn owned(&self) -> OwnedMap { 161 | self.clone() 162 | } 163 | } 164 | 165 | impl OwnedMap { 166 | pub fn insert_value<'a, V>(&mut self, key: &'a str, value: V) -> Option 167 | where 168 | V: ToValue, 169 | { 170 | self.insert(key, value.value()) 171 | } 172 | pub fn insert_key_id_value(&mut self, key: u64, value: V) -> Option 173 | where 174 | V: ToValue, 175 | { 176 | self.insert_key_id(key, value.value()) 177 | } 178 | } 179 | 180 | impl fmt::Debug for OwnedMap { 181 | fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { 182 | write!(f, "( ")?; 183 | for name in &self.fields { 184 | let id = key_hash(name); 185 | if let Some(value) = self.map.get(&id) { 186 | write!(f, "{}: {:?} ", name, value)?; 187 | } 188 | } 189 | write!(f, ") ") 190 | } 191 | } 192 | 193 | impl PartialEq for OwnedMap { 194 | fn eq(&self, other: &Self) -> bool { 195 | self.map == other.map 196 | } 197 | } 198 | 199 | impl PartialOrd for OwnedMap { 200 | fn partial_cmp(&self, _: &Self) -> Option { 201 | unreachable!("Cannot compare maps") 202 | } 203 | } 204 | -------------------------------------------------------------------------------- /src/types/custom_types/pos.rs: -------------------------------------------------------------------------------- 1 | #[derive(Debug, Clone, Copy, Serialize, Deserialize, PartialOrd)] 2 | pub struct Pos2d32 { 3 | pub x: f32, 4 | pub y: f32, 5 | } 6 | 7 | #[derive(Debug, Clone, Copy, Serialize, Deserialize, PartialOrd)] 8 | pub struct Pos2d64 { 9 | pub x: f64, 10 | pub y: f64, 11 | } 12 | 13 | #[derive(Debug, Clone, Copy, Serialize, Deserialize, PartialOrd)] 14 | pub struct Pos3d32 { 15 | pub x: f32, 16 | pub y: f32, 17 | pub z: f32, 18 | } 19 | 20 | #[derive(Debug, Clone, Copy, Serialize, Deserialize, PartialOrd)] 21 | pub struct Pos3d64 { 22 | pub x: f64, 23 | pub y: f64, 24 | pub z: f64, 25 | } 26 | 27 | impl PartialEq for Pos2d32 { 28 | fn eq(&self, other: &Pos2d32) -> bool { 29 | self.x == other.x && self.y == other.y 30 | } 31 | fn ne(&self, other: &Pos2d32) -> bool { 32 | self.x != other.x || self.y != other.y 33 | } 34 | } 35 | 36 | impl PartialEq for Pos2d64 { 37 | fn eq(&self, other: &Pos2d64) -> bool { 38 | self.x == other.x && self.y == other.y 39 | } 40 | fn ne(&self, other: &Pos2d64) -> bool { 41 | self.x != other.x || self.y != other.y 42 | } 43 | } 44 | 45 | impl PartialEq for Pos3d32 { 46 | fn eq(&self, other: &Pos3d32) -> bool { 47 | self.x == other.x && self.y == other.y && self.z == other.z 48 | } 49 | fn ne(&self, other: &Pos3d32) -> bool { 50 | self.x != other.x || self.y != other.y || self.z != other.z 51 | } 52 | } 53 | 54 | impl PartialEq for Pos3d64 { 55 | fn eq(&self, other: &Pos3d64) -> bool { 56 | self.x == other.x && self.y == other.y && self.z == other.z 57 | } 58 | fn ne(&self, other: &Pos3d64) -> bool { 59 | self.x != other.x || self.y != other.y || self.z != other.z 60 | } 61 | } 62 | 63 | impl Eq for Pos2d32 {} 64 | 65 | impl Eq for Pos2d64 {} 66 | 67 | impl Eq for Pos3d32 {} 68 | 69 | impl Eq for Pos3d64 {} 70 | -------------------------------------------------------------------------------- /src/types/custom_types/shared_map.rs: -------------------------------------------------------------------------------- 1 | use super::super::*; 2 | use super::map::{GenericMap, Map}; 3 | use ahash::{HashMap, HashMapExt}; 4 | use bifrost_hasher::hash_str; 5 | use std::iter::Iterator; 6 | use std::slice::Iter; 7 | 8 | #[derive(Debug, Clone)] 9 | pub struct SharedMap<'v> { 10 | pub map: GenericMap>, 11 | pub fields: Vec, 12 | } 13 | impl<'v> Map for SharedMap<'v> { 14 | type Value = SharedValue<'v>; 15 | 16 | fn new() -> Self { 17 | Self { 18 | map: GenericMap::new(), 19 | fields: Vec::new(), 20 | } 21 | } 22 | fn from_pairs

(map: P) -> Self 23 | where P: IntoIterator 24 | { 25 | let mut target_map: GenericMap> = GenericMap::new(); 26 | let mut fields = Vec::new(); 27 | for (key, value) in map { 28 | target_map.insert(key_hash(&key), value); 29 | fields.push(key); 30 | } 31 | Self { 32 | map: target_map, 33 | fields, 34 | } 35 | } 36 | fn owned(&self) -> OwnedMap { 37 | OwnedMap { 38 | map: self.map.iter().map(|(k, v)| (*k, v.owned())).collect(), 39 | fields: self.fields.clone(), 40 | } 41 | } 42 | fn insert<'a>(&mut self, key: &'a str, value: Self::Value) -> Option { 43 | self.fields.push(key.to_string()); 44 | self.insert_key_id(key_hash(key), value) 45 | } 46 | fn insert_key_id(&mut self, key: u64, value: Self::Value) -> Option { 47 | self.map.insert(key, value) 48 | } 49 | fn get_by_key_id(&self, key: u64) -> &Self::Value { 50 | self.map.get(&key).unwrap_or(&Self::Value::Null) 51 | } 52 | fn get_mut_by_key_id(&mut self, key: u64) -> &mut Self::Value { 53 | self.map.get_or_insert(key, Self::Value::Null) 54 | } 55 | fn get<'a>(&self, key: &'a str) -> &Self::Value { 56 | self.get_by_key_id(key_hash(key)) 57 | } 58 | fn get_mut<'a>(&mut self, key: &'a str) -> &mut Self::Value { 59 | self.get_mut_by_key_id(key_hash(key)) 60 | } 61 | fn strs_to_ids<'a>(keys: &[&'a str]) -> Vec { 62 | keys.iter().map(|str| key_hash(str)).collect() 63 | } 64 | fn get_in_by_ids<'a, I: Iterator + ExactSizeIterator>( 65 | &self, 66 | mut key_ids: I, 67 | ) -> &Self::Value { 68 | let current_key = key_ids.next().cloned(); 69 | if let Some(key) = current_key { 70 | let value = self.get_by_key_id(key); 71 | if key_ids.is_empty() { 72 | return value; 73 | } else { 74 | match value { 75 | &Self::Value::Map(ref map) => return map.get_in_by_ids(key_ids), 76 | _ => {} 77 | } 78 | } 79 | } 80 | return &Self::Value::Null; 81 | } 82 | fn get_in(&self, keys: &[&'static str]) -> &Self::Value { 83 | self.get_in_by_ids(Self::strs_to_ids(keys).iter()) 84 | } 85 | fn get_in_mut_by_key_ids(&mut self, mut keys_ids: Iter) -> Option<&mut Self::Value> { 86 | let current_key = keys_ids.next().cloned(); 87 | if let Some(key) = current_key { 88 | let value = self.get_mut_by_key_id(key); 89 | match value { 90 | &mut Self::Value::Null => return None, 91 | _ => { 92 | if keys_ids.is_empty() { 93 | return Some(value); 94 | } else { 95 | match value { 96 | &mut Self::Value::Map(ref mut map) => { 97 | return map.get_in_mut_by_key_ids(keys_ids) 98 | } 99 | _ => return None, 100 | } 101 | } 102 | } 103 | } 104 | } else { 105 | return None; 106 | } 107 | } 108 | fn get_in_mut(&mut self, keys: &[&'static str]) -> Option<&mut Self::Value> { 109 | self.get_in_mut_by_key_ids(Self::strs_to_ids(keys).iter()) 110 | } 111 | 112 | fn update_in_by_key_ids(&mut self, keys: Iter, update: U) -> Option<()> 113 | where 114 | U: FnOnce(&mut Self::Value), 115 | { 116 | let value = self.get_in_mut_by_key_ids(keys); 117 | if let Some(value) = value { 118 | update(value); 119 | Some(()) 120 | } else { 121 | None 122 | } 123 | } 124 | 125 | fn update_in(&mut self, keys: &[&'static str], update: U) -> Option<()> 126 | where 127 | U: FnOnce(&mut Self::Value), 128 | { 129 | self.update_in_by_key_ids(Self::strs_to_ids(keys).iter(), update) 130 | } 131 | 132 | fn set_in_by_key_ids(&mut self, keys: Iter, value: Self::Value) -> Option<()> { 133 | let val = self.get_in_mut_by_key_ids(keys); 134 | if let Some(val) = val { 135 | *val = value; 136 | Some(()) 137 | } else { 138 | None 139 | } 140 | } 141 | 142 | fn set_in(&mut self, keys: &[&'static str], value: Self::Value) -> Option<()> { 143 | self.set_in_by_key_ids(Self::strs_to_ids(keys).iter(), value) 144 | } 145 | 146 | fn into_string_map(self) -> HashMap { 147 | let mut result = HashMap::new(); 148 | for (i, field_name) in self.fields.into_iter().enumerate() { 149 | if i < self.map.len() { 150 | let field_id = key_hash(&field_name); 151 | if let Some(value) = self.map.get(&field_id) { 152 | result.insert(field_name, value.clone()); 153 | } 154 | } 155 | } 156 | result 157 | } 158 | 159 | fn len(&self) -> usize { 160 | self.map.len() 161 | } 162 | 163 | fn shared<'a>(&'a self) -> SharedMap<'a> { 164 | self.clone() 165 | } 166 | } 167 | 168 | pub fn key_hash<'a>(key: &'a str) -> u64 { 169 | hash_str(key) 170 | } 171 | 172 | pub fn key_hashes(keys: &Vec) -> Vec { 173 | keys.iter().map(|str| hash_str(str)).collect() 174 | } 175 | 176 | impl<'v> Eq for SharedMap<'v> {} 177 | impl<'v> PartialEq for SharedMap<'v> { 178 | fn eq(&self, other: &Self) -> bool { 179 | self.map == other.map 180 | } 181 | } 182 | -------------------------------------------------------------------------------- /src/types/macros.rs: -------------------------------------------------------------------------------- 1 | macro_rules! gen_primitive_types_io { 2 | ( 3 | $($t:ty: $tmod:ident $feat_writer: expr);* 4 | ) => ( 5 | $( 6 | pub mod $tmod { 7 | use std::mem; 8 | 9 | pub type Slice<'a> = &'a [$t]; 10 | pub type ReadRef<'a> = &'a $t; 11 | 12 | pub fn read<'a>(mem_ptr: usize) -> ReadRef<'a> { 13 | debug_assert!(mem_ptr > 0); 14 | unsafe { 15 | &*(mem_ptr as *const $t) 16 | } 17 | } 18 | pub fn read_slice<'a>(mem_ptr: usize, len: usize) -> (Slice<'a>, usize) { 19 | unsafe { 20 | let slice = std::slice::from_raw_parts(mem_ptr as *const _, len); 21 | let size = type_size() * len; 22 | (slice, size) 23 | } 24 | } 25 | pub fn vec_to_read_ref(vec: &Vec<$t>) -> Slice { 26 | vec.as_slice() 27 | } 28 | pub fn write(val: &$t, mem_ptr: usize) { 29 | debug_assert!(mem_ptr > 0); 30 | unsafe { 31 | std::ptr::write(mem_ptr as *mut $t, *val) 32 | } 33 | } 34 | pub const fn fixed_size() -> bool { 35 | true 36 | } 37 | pub const fn type_size() -> usize { 38 | mem::size_of::<$t>() 39 | } 40 | pub const fn type_align() -> usize { 41 | mem::align_of::<$t>() 42 | } 43 | pub fn size_at(_: usize) -> usize { 44 | type_size() 45 | } 46 | pub fn val_size(_: &$t) -> usize { 47 | type_size() 48 | } 49 | pub fn feature(val: &$t) -> [u8; 8] { 50 | $feat_writer(*val) 51 | } 52 | pub fn hash(val: &$t) -> [u8; 8] { 53 | feature(val) 54 | } 55 | } 56 | )* 57 | ); 58 | } 59 | 60 | macro_rules! big_end { 61 | ( 62 | $writer:ident 63 | ) => { 64 | |n| { 65 | use byteorder::WriteBytesExt; 66 | let mut key_slice = [0u8; 8]; 67 | { 68 | let mut cursor = ::std::io::Cursor::new(&mut key_slice[..]); 69 | cursor.$writer::<::byteorder::BigEndian>(n).unwrap(); 70 | }; 71 | key_slice 72 | } 73 | }; 74 | } 75 | 76 | macro_rules! big_end_cast { 77 | () => { 78 | |n| { 79 | let big_end = big_end!(write_i32); 80 | big_end(n as i32) 81 | } 82 | }; 83 | } 84 | 85 | macro_rules! gen_compound_types_io { 86 | ( 87 | $($t:ident, $tmod:ident, $feat: expr, $hash: expr);* 88 | ) => ( 89 | $( 90 | pub mod $tmod { 91 | use crate::types::*; 92 | 93 | pub type Slice<'a> = &'a [$t]; 94 | pub type ReadRef<'a> = &'a $t; 95 | 96 | pub fn read<'a>(mem_ptr: usize) -> ReadRef<'a> { 97 | unsafe { 98 | &*(mem_ptr as *const $t) 99 | } 100 | } 101 | pub fn read_slice<'a>(mem_ptr: usize, len: usize) -> (Slice<'a>, usize) { 102 | unsafe { 103 | let slice = std::slice::from_raw_parts(mem_ptr as *const _, len); 104 | let size = type_size() * len; 105 | (slice, size) 106 | } 107 | } 108 | pub fn vec_to_read_ref(vec: &Vec<$t>) -> Slice { 109 | vec.as_slice() 110 | } 111 | pub fn write(val: &$t, mem_ptr: usize) { 112 | unsafe { 113 | std::ptr::write(mem_ptr as *mut $t, val.to_owned()) 114 | } 115 | } 116 | pub const fn type_size() -> usize { 117 | std::mem::size_of::<$t>() 118 | } 119 | pub const fn type_align() -> usize { 120 | std::mem::align_of::<$t>() 121 | } 122 | pub const fn fixed_size() -> bool { 123 | true 124 | } 125 | pub fn size_at(_: usize) -> usize { 126 | type_size() 127 | } 128 | pub fn val_size(_: &$t) -> usize { 129 | type_size() 130 | } 131 | pub fn feature(val: &$t) -> [u8; 8] { 132 | ($feat)(val) 133 | } 134 | pub fn hash(val: &$t) -> [u8; 8] { 135 | ($hash)(val) 136 | } 137 | } 138 | )* 139 | ); 140 | } 141 | 142 | macro_rules! gen_variable_types_io { 143 | ( 144 | $( 145 | $t:ty, 146 | $rt: ty, 147 | $tmod:ident, 148 | $reader:expr, 149 | $writer: expr, 150 | $size:expr, 151 | $val_size:expr, 152 | $feat: expr, 153 | $hash: expr, 154 | $as_ref: expr, 155 | $alignment: expr 156 | );* 157 | ) => ( 158 | $( 159 | pub mod $tmod { 160 | use crate::types::*; 161 | 162 | pub type Slice<'a> = Vec>; 163 | pub type ReadRef<'a> = &'a $rt; 164 | 165 | pub fn read<'a>(mem_ptr: usize) -> ReadRef<'a> { 166 | ($reader)(mem_ptr) 167 | } 168 | pub fn read_slice<'a>(mut mem_ptr: usize, len: usize) -> (Slice<'a>, usize) { 169 | let origin_ptr = mem_ptr; 170 | let res = (0..len).map(|_| { 171 | let v = read(mem_ptr); 172 | mem_ptr += val_size(v); 173 | v 174 | }) 175 | .collect::>(); 176 | (res, mem_ptr - origin_ptr) 177 | } 178 | pub fn vec_to_read_ref<'a>(vec: &'a Vec<$t>) -> Slice<'a> { 179 | vec.iter().map(|v| ($as_ref)(v)).collect() 180 | } 181 | pub fn write(val: &$t, mem_ptr: usize) { 182 | ($writer)(val, mem_ptr) 183 | } 184 | pub fn type_size() -> usize { 185 | panic!("variable type does not have type size") 186 | } 187 | pub const fn type_align() -> usize { 188 | $alignment 189 | } 190 | pub const fn fixed_size() -> bool { 191 | false 192 | } 193 | pub fn size_at(mem_ptr: usize) -> usize { 194 | ($size)(mem_ptr) 195 | } 196 | pub fn val_size(val: &$rt) -> usize { 197 | ($val_size)(val) 198 | } 199 | pub fn feature(val: &$rt) -> [u8; 8] { 200 | ($feat)(val) 201 | } 202 | pub fn hash(val: &$rt) -> [u8; 8] { 203 | ($hash)(val) 204 | } 205 | } 206 | )* 207 | ); 208 | } 209 | 210 | macro_rules! get_from_val { 211 | ($e:ident, $d:ident) => { 212 | match &$d { 213 | &OwnedValue::$e(v) => Some(v), 214 | _ => None, 215 | } 216 | }; 217 | } 218 | 219 | macro_rules! ref_from_val_fn { 220 | ($e:ident, $fn: ident, $st:ty) => { 221 | pub fn $fn(&self) -> Option<$st> { 222 | ref_from_val!($e, self) 223 | } 224 | }; 225 | } 226 | 227 | macro_rules! ref_from_val { 228 | ($e:ident, $d:ident) => { 229 | match $d { 230 | &SharedValue::$e(v) => Some(v), 231 | _ => None, 232 | } 233 | }; 234 | } 235 | 236 | macro_rules! get_from_val_fn { 237 | ($e:ident, $fn: ident, $t:ty) => { 238 | #[allow(non_snake_case)] 239 | pub fn $fn(&self) -> Option<&$t> { 240 | get_from_val!($e, self) 241 | } 242 | }; 243 | } 244 | 245 | macro_rules! define_types { 246 | ( 247 | $( 248 | [ $( $name:expr ),* ], $t:ty, $e:ident, $io:ident, $fn: ident 249 | );* 250 | ) => ( 251 | 252 | #[derive(Copy, Clone, Eq, PartialEq, Debug, Serialize, Deserialize)] 253 | pub enum Type { 254 | Null, 255 | Map, // No matter which id we pick for 'Map' because w/r planners will ignore it when sub_fields is not 'None', 256 | $( 257 | $e, 258 | )* 259 | NA 260 | } 261 | 262 | impl Type { 263 | pub const fn id(self) -> u8 { 264 | self as u8 265 | } 266 | pub fn from_id(id: u8) -> Self { 267 | match id { 268 | $( 269 | type_id::$fn => Type::$e, 270 | )* 271 | _ => Type::NA 272 | } 273 | } 274 | pub fn size(&self) -> Option { 275 | match self { 276 | $( 277 | Type::$e => if $io::fixed_size() { 278 | Some($io::type_size()) 279 | } else { 280 | None 281 | }, 282 | )* 283 | _ => None 284 | } 285 | } 286 | } 287 | 288 | mod type_id { 289 | $( 290 | pub const $fn: u8 = super::Type::$e.id(); 291 | )* 292 | } 293 | 294 | $( 295 | impl ToValue for $t { 296 | fn value(self) -> OwnedValue { 297 | OwnedValue::$e(self) 298 | } 299 | } 300 | impl ToValue for Vec<$t> { 301 | fn value(self) -> OwnedValue { 302 | OwnedValue::PrimArray(OwnedPrimArray::$e(self)) 303 | } 304 | } 305 | )* 306 | 307 | #[derive(Debug, Clone, Serialize, Deserialize, PartialEq, PartialOrd)] 308 | pub enum OwnedPrimArray { 309 | $( 310 | $e(Vec<$t>), 311 | )* 312 | } 313 | 314 | impl OwnedPrimArray { 315 | pub fn size(&self) -> usize { 316 | match &self { 317 | $( 318 | &OwnedPrimArray::$e(vec) => { 319 | return vec.iter().map(|v| $io::val_size(v)).sum() 320 | } 321 | ),* 322 | } 323 | } 324 | pub fn len(&self) -> usize { 325 | match self { 326 | $( 327 | OwnedPrimArray::$e(vec) => { 328 | return vec.len() 329 | } 330 | ),* 331 | } 332 | } 333 | pub fn features(&self) -> Vec<[u8; 8]> { 334 | let mut res = vec![]; 335 | match &self { 336 | $( 337 | &OwnedPrimArray::$e(vec) => { 338 | for v in vec { 339 | res.push($io::feature(v)); 340 | } 341 | } 342 | ),* 343 | } 344 | res 345 | } 346 | pub fn data_size(&self) -> u8 { 347 | match &self { 348 | $( 349 | &OwnedPrimArray::$e(vec) => $io::val_size(&vec[0]) as u8 350 | ),* 351 | } 352 | } 353 | pub fn hashes(&self) -> Vec<[u8; 8]> { 354 | let mut res = vec![]; 355 | match &self { 356 | $( 357 | &OwnedPrimArray::$e(vec) => { 358 | for v in vec { 359 | res.push($io::hash(v)); 360 | } 361 | } 362 | ),* 363 | } 364 | res 365 | } 366 | $( 367 | pub fn $fn(&self) -> Option<&Vec<$t>> { 368 | match self { 369 | OwnedPrimArray::$e(ref vec) => Some(vec), 370 | _ => None 371 | } 372 | } 373 | )* 374 | } 375 | 376 | 377 | #[derive(Debug, Clone, Serialize, Deserialize, PartialEq, PartialOrd)] 378 | pub enum OwnedValue { 379 | $( 380 | $e($t), 381 | )* 382 | Map(OwnedMap), 383 | Array(Vec), 384 | PrimArray(OwnedPrimArray), 385 | Null, 386 | NA 387 | } 388 | 389 | impl OwnedValue { 390 | $( 391 | get_from_val_fn!($e, $fn, $t); 392 | )* 393 | pub fn shared<'a>(&'a self) -> SharedValue<'a> { 394 | match self { 395 | $( 396 | OwnedValue::$e(ref v) => { 397 | SharedValue::$e(v) 398 | } 399 | ),*, 400 | OwnedValue::Array(ref array) => SharedValue::Array(array.iter().map(|v| v.shared()).collect()), 401 | $( 402 | OwnedValue::PrimArray(OwnedPrimArray::$e(ref vec)) => SharedValue::PrimArray(SharedPrimArray::$e($io::vec_to_read_ref(vec))), 403 | )* 404 | OwnedValue::Map(ref map) => SharedValue::Map(map.shared()), 405 | OwnedValue::Null => SharedValue::Null, 406 | OwnedValue::NA => SharedValue::NA, 407 | } 408 | } 409 | #[allow(non_snake_case)] 410 | pub fn Map(&self) -> Option<&OwnedMap> { 411 | match self { 412 | &OwnedValue::Map(ref m) => Some(m), 413 | _ => None 414 | } 415 | } 416 | pub fn get_int(&self) -> Option { 417 | match self { 418 | Self::I8(v) => Some(*v as _), 419 | Self::I16(v) => Some(*v as _), 420 | Self::I32(v) => Some(*v as _), 421 | Self::I64(v) => Some(*v as _), 422 | 423 | Self::U8(v) => Some(*v as _), 424 | Self::U16(v) => Some(*v as _), 425 | Self::U32(v) => Some(*v as _), 426 | Self::U64(v) => Some(*v as _), 427 | 428 | _ => None 429 | } 430 | } 431 | pub fn get_uint(&self) -> Option { 432 | match self { 433 | Self::U8(v) => Some(*v as _), 434 | Self::U16(v) => Some(*v as _), 435 | Self::U32(v) => Some(*v as _), 436 | Self::U64(v) => Some(*v as _), 437 | 438 | _ => None 439 | } 440 | } 441 | pub fn base_size(&self) -> usize { 442 | get_vsize(self.base_type(), self) 443 | } 444 | pub fn cloned_iter_value(&self) -> Option> { 445 | match self { 446 | OwnedValue::Array(ref array) => Some(array.clone().into_iter()), 447 | $(OwnedValue::PrimArray(OwnedPrimArray::$e(ref vec)) => { 448 | let packed_iter = vec.iter().map(|v| v.clone().value()); 449 | let packed_vec: Vec<_> = packed_iter.collect(); 450 | Some(packed_vec.into_iter()) 451 | },)* 452 | _ => None 453 | } 454 | } 455 | pub fn iter_value(&self) -> Option { 456 | if let OwnedValue::Array(ref array) = self { 457 | Some(ValueIter::new(array)) 458 | } else { None } 459 | } 460 | pub fn len(&self) -> Option { 461 | match self { 462 | OwnedValue::Array(ref array) => Some(array.len()), 463 | OwnedValue::Map(ref map) => Some(map.len()), 464 | $(OwnedValue::PrimArray(OwnedPrimArray::$e(ref vec)) => Some(vec.len()),)* 465 | _ => None 466 | } 467 | } 468 | pub fn feature(&self) -> [u8; 8] { 469 | match &self { 470 | $( 471 | &OwnedValue::$e(v) => $io::feature(&v) 472 | ),*, 473 | &OwnedValue::Map(_) | &OwnedValue::Array(_) | &OwnedValue::PrimArray(_) => unreachable!(), 474 | _ => [0u8; 8] 475 | } 476 | } 477 | 478 | pub fn features(&self) -> Vec<[u8; 8]> { 479 | match self { 480 | OwnedValue::Array(ref vec) => { 481 | let mut res = vec![]; 482 | for v in vec { 483 | res.push(v.feature()); 484 | } 485 | res 486 | }, 487 | OwnedValue::PrimArray(ref prim_arr) => { 488 | prim_arr.features() 489 | }, 490 | _ => unreachable!() 491 | } 492 | } 493 | 494 | pub fn hash(&self) -> [u8; 8] { 495 | match &self { 496 | $( 497 | &OwnedValue::$e(v) => $io::hash(&v) 498 | ),*, 499 | OwnedValue::Map(_) | OwnedValue::Array(_) | OwnedValue::PrimArray(_) => panic!(), 500 | _ => [0u8; 8] 501 | } 502 | } 503 | 504 | pub fn hashes(&self) -> Vec<[u8; 8]> { 505 | match self { 506 | OwnedValue::Array(ref vec) => { 507 | let mut res = vec![]; 508 | for v in vec { 509 | res.push(v.hash()); 510 | } 511 | res 512 | }, 513 | OwnedValue::PrimArray(ref prim_arr) => { 514 | prim_arr.hashes() 515 | }, 516 | _ => unreachable!() 517 | } 518 | } 519 | pub fn base_type(&self) -> Type { 520 | match self { 521 | $( 522 | &OwnedValue::$e(ref _v) => Type::$e, 523 | )* 524 | $( 525 | OwnedValue::PrimArray(OwnedPrimArray::$e(_)) => Type::$e, 526 | )* 527 | &OwnedValue::Array(ref v) => v[0].base_type(), 528 | &OwnedValue::Map(_) => Type::Map, 529 | &OwnedValue::Null => Type::Null, 530 | &OwnedValue::NA => Type::NA, 531 | } 532 | } 533 | pub fn prim_array(&self) -> Option<&OwnedPrimArray> { 534 | match self { 535 | &OwnedValue::PrimArray(ref pa) => Some(pa), 536 | _ => None 537 | } 538 | } 539 | } 540 | pub fn get_type_id (name: String) -> u8 { 541 | match name.as_ref() { 542 | $( 543 | $($name => Type::$e.id(),)* 544 | )* 545 | _ => 0, 546 | } 547 | } 548 | pub fn get_type (t: Type) -> &'static str { 549 | match t { 550 | $( 551 | Type::$e => [$($name),*][0], 552 | )* 553 | _ => "N/A", 554 | } 555 | } 556 | pub fn get_size (t: Type, mem_ptr: usize) -> usize { 557 | match t { 558 | $( 559 | Type::$e => $io::size_at(mem_ptr), 560 | )* 561 | _ => 0 562 | } 563 | } 564 | pub fn get_owned_val (t: Type, mem_ptr: usize) -> OwnedValue { 565 | match t { 566 | $( 567 | Type::$e => { 568 | let val: $t = $io::read(mem_ptr).to_owned().into(); 569 | OwnedValue::$e(val) 570 | }, 571 | )* 572 | _ => OwnedValue::NA 573 | } 574 | } 575 | pub fn get_shared_val<'a> (t: Type, mem_ptr: usize) -> SharedValue<'a> { 576 | match t { 577 | $( 578 | Type::$e => SharedValue::$e($io::read(mem_ptr)), 579 | )* 580 | _ => SharedValue::NA 581 | } 582 | } 583 | pub fn get_owned_prim_array_val(t: Type, size: usize, mem_ptr: &mut usize) -> Option { 584 | match t { 585 | $( 586 | Type::$e => { 587 | let mut vals: Vec<$t> = Vec::with_capacity(size); 588 | for _ in 0..size { 589 | let read_res = $io::read(*mem_ptr).to_owned(); 590 | vals.push(read_res.into()); 591 | *mem_ptr += get_size(t, *mem_ptr); 592 | } 593 | Some(OwnedPrimArray::$e(vals)) 594 | }, 595 | )* 596 | _ => None 597 | } 598 | } 599 | pub fn get_shared_prim_array_val<'v>(t: Type, len: usize, mem_ptr: &mut usize) -> Option> { 600 | match t { 601 | $( 602 | Type::$e => { 603 | let (slice, size) = $io::read_slice(*mem_ptr, len); 604 | *mem_ptr += size; 605 | Some(SharedPrimArray::$e(slice)) 606 | }, 607 | )* 608 | _ => None, 609 | } 610 | } 611 | pub fn set_val (t: Type, val: &OwnedValue, mut mem_ptr: usize) { 612 | match t { 613 | $( 614 | Type::$e => { 615 | if let &OwnedValue::PrimArray(OwnedPrimArray::$e(vec)) = &val { 616 | for v in vec.iter() { 617 | $io::write(v , mem_ptr); 618 | mem_ptr += $io::val_size(v); 619 | } 620 | } else { 621 | if let Some(val) = get_from_val!($e, val) { 622 | $io::write(val, mem_ptr); 623 | } else { 624 | panic!("value does not match type id {:?}, actual value {:?}", t, val); 625 | } 626 | } 627 | }, 628 | )* 629 | _ => panic!("type {:?} does not supported for set_value", t) 630 | } 631 | } 632 | pub fn size_of_type(t: Type) -> usize { 633 | match t { 634 | $( 635 | Type::$e => { 636 | $io::type_size() 637 | }, 638 | )* 639 | _ => panic!("type {:?} does not supported for size_of", t) 640 | } 641 | } 642 | pub fn align_of_type(t: Type) -> usize { 643 | match t { 644 | $( 645 | Type::$e => { 646 | $io::type_align() 647 | }, 648 | )* 649 | Type::Map => 0, 650 | _ => panic!("type {:?} does not supported for size_of", t) 651 | } 652 | } 653 | pub fn fixed_size(t: Type) -> bool { 654 | match t { 655 | $( 656 | Type::$e => { 657 | $io::fixed_size() 658 | }, 659 | )* 660 | _ => false 661 | } 662 | } 663 | pub fn get_vsize (t: Type, val: &OwnedValue) -> usize { 664 | match t { 665 | $( 666 | Type::$e => { 667 | if let Some(val) = get_from_val!($e, val) { 668 | $io::val_size(val) 669 | } else { 670 | panic!("value does not match type id {:?}, actual value {:?}", t, val); 671 | } 672 | }, 673 | )* 674 | _ => panic!("type {:?} does not supported for get_vsize", t) 675 | } 676 | } 677 | pub fn get_rsize (t: Type, val: &SharedValue) -> usize { 678 | match t { 679 | $( 680 | Type::$e => { 681 | if let Some(val) = ref_from_val!($e, val) { 682 | $io::val_size(val) 683 | } else { 684 | panic!("value does not match type id {:?}, actual value {:?}", t, val); 685 | } 686 | }, 687 | )* 688 | _ => panic!("type {:?} does not supported for get_rsize", t), 689 | } 690 | } 691 | #[derive(Debug, PartialEq, Clone)] 692 | pub enum SharedPrimArray<'a> { 693 | $( 694 | $e($io::Slice<'a>), 695 | )* 696 | } 697 | 698 | impl <'a> SharedPrimArray <'a> { 699 | pub fn size(&self) -> usize { 700 | match self { 701 | $( 702 | SharedPrimArray::$e(vec) => { 703 | return vec.iter().map(|v| $io::val_size(v)).sum() 704 | } 705 | ),* 706 | } 707 | } 708 | pub fn len(&self) -> usize { 709 | match self { 710 | $( 711 | SharedPrimArray::$e(vec) => { 712 | return vec.len() 713 | } 714 | ),* 715 | } 716 | } 717 | pub fn features(&self) -> Vec<[u8; 8]> { 718 | let mut res = vec![]; 719 | match self { 720 | $( 721 | SharedPrimArray::$e(vec) => { 722 | for v in vec.iter() { 723 | res.push($io::feature(v)); 724 | } 725 | } 726 | ),* 727 | } 728 | res 729 | } 730 | pub fn data_size(&self) -> u8 { 731 | match self { 732 | $( 733 | SharedPrimArray::$e(vec) => $io::val_size(&vec[0]) as u8 734 | ),* 735 | } 736 | } 737 | pub fn hashes(&self) -> Vec<[u8; 8]> { 738 | let mut res = vec![]; 739 | match self { 740 | $( 741 | SharedPrimArray::$e(vec) => { 742 | for v in vec.iter() { 743 | res.push($io::hash(v)); 744 | } 745 | } 746 | ),* 747 | } 748 | res 749 | } 750 | $( 751 | pub fn $fn(&self) -> Option<& $io::Slice> { 752 | match self { 753 | SharedPrimArray::$e(ref vec) => Some(vec), 754 | _ => None 755 | } 756 | } 757 | )* 758 | pub fn copy_into_owned(&self) -> OwnedPrimArray { 759 | match self { 760 | $( 761 | SharedPrimArray::$e(ref vec) => { 762 | OwnedPrimArray::$e(vec.iter().map(|v| (*v).to_owned().into()).collect()) 763 | }, 764 | )* 765 | } 766 | } 767 | } 768 | 769 | #[derive(Debug, PartialEq, Clone)] 770 | pub enum SharedValue<'a> { 771 | $( 772 | $e($io::ReadRef<'a>), 773 | )* 774 | Map(SharedMap<'a>), 775 | Array(Vec>), 776 | PrimArray(SharedPrimArray<'a>), 777 | Null, 778 | NA 779 | } 780 | impl <'a> SharedValue <'a> { 781 | $( 782 | ref_from_val_fn!($e, $fn, $io::ReadRef); 783 | )* 784 | 785 | pub fn owned(&self) -> OwnedValue { 786 | match self { 787 | $( 788 | SharedValue::$e(ref v) => { 789 | let v: $t = (*v).to_owned().into(); 790 | OwnedValue::$e(v) 791 | } 792 | ),*, 793 | SharedValue::Array(ref array) => OwnedValue::Array(array.iter().map(|v| v.owned()).collect()), 794 | $( 795 | SharedValue::PrimArray(SharedPrimArray::$e(ref vec)) => OwnedValue::PrimArray(OwnedPrimArray::$e(vec 796 | .iter() 797 | .map(|v| { 798 | (*v).to_owned().into() 799 | }) 800 | .collect())), 801 | )* 802 | SharedValue::Map(ref map) => OwnedValue::Map(map.owned()), 803 | SharedValue::Null => OwnedValue::Null, 804 | SharedValue::NA => OwnedValue::NA, 805 | } 806 | } 807 | 808 | #[allow(non_snake_case)] 809 | pub fn Map(&self) -> Option<&SharedMap> { 810 | match self { 811 | &SharedValue::Map(ref m) => Some(m), 812 | _ => None 813 | } 814 | } 815 | pub fn base_size(&self) -> usize { 816 | get_rsize(self.base_type(), self) 817 | } 818 | pub fn len(&self) -> Option { 819 | match self { 820 | SharedValue::Array(ref array) => Some(array.len()), 821 | SharedValue::Map(ref map) => Some(map.len()), 822 | $(SharedValue::PrimArray(SharedPrimArray::$e(ref vec)) => Some(vec.len()),)* 823 | _ => None 824 | } 825 | } 826 | pub fn feature(&self) -> [u8; 8] { 827 | match self { 828 | $( 829 | SharedValue::$e(ref v) => $io::feature(v) 830 | ),*, 831 | SharedValue::Map(_) | SharedValue::Array(_) | SharedValue::PrimArray(_) => unreachable!(), 832 | _ => [0u8; 8] 833 | } 834 | } 835 | 836 | pub fn features(&self) -> Vec<[u8; 8]> { 837 | match self { 838 | SharedValue::Array(ref vec) => { 839 | let mut res = vec![]; 840 | for v in vec { 841 | res.push(v.feature()); 842 | } 843 | res 844 | }, 845 | SharedValue::PrimArray(ref prim_arr) => { 846 | prim_arr.features() 847 | }, 848 | _ => unreachable!() 849 | } 850 | } 851 | 852 | pub fn hash(&self) -> [u8; 8] { 853 | match self { 854 | $( 855 | &SharedValue::$e(v) => $io::hash(v) 856 | ),*, 857 | SharedValue::Map(_) | SharedValue::Array(_) | SharedValue::PrimArray(_) => panic!(), 858 | _ => [0u8; 8] 859 | } 860 | } 861 | 862 | pub fn hashes(&self) -> Vec<[u8; 8]> { 863 | match self { 864 | SharedValue::Array(ref vec) => { 865 | let mut res = vec![]; 866 | for v in vec { 867 | res.push(v.hash()); 868 | } 869 | res 870 | }, 871 | SharedValue::PrimArray(ref prim_arr) => { 872 | prim_arr.hashes() 873 | }, 874 | _ => unreachable!() 875 | } 876 | } 877 | pub fn base_type(&self) -> Type { 878 | match self { 879 | $( 880 | &SharedValue::$e(ref _v) => Type::$e, 881 | )* 882 | $( 883 | SharedValue::PrimArray(SharedPrimArray::$e(_)) => Type::$e, 884 | )* 885 | &SharedValue::Array(ref v) => v[0].base_type(), 886 | &SharedValue::Map(_) => Type::Map, 887 | &SharedValue::Null => Type::Null, 888 | &SharedValue::NA => Type::NA 889 | } 890 | } 891 | pub fn prim_array(&self) -> Option<&SharedPrimArray> { 892 | match self { 893 | &SharedValue::PrimArray(ref pa) => Some(pa), 894 | _ => None 895 | } 896 | } 897 | pub fn get_int(&self) -> Option { 898 | match self { 899 | Self::I8(v) => Some(**v as _), 900 | Self::I16(v) => Some(**v as _), 901 | Self::I32(v) => Some(**v as _), 902 | Self::I64(v) => Some(**v as _), 903 | 904 | Self::U8(v) => Some(**v as _), 905 | Self::U16(v) => Some(**v as _), 906 | Self::U32(v) => Some(**v as _), 907 | Self::U64(v) => Some(**v as _), 908 | 909 | _ => None 910 | } 911 | } 912 | pub fn get_uint(&self) -> Option { 913 | match self { 914 | Self::U8(v) => Some(**v as _), 915 | Self::U16(v) => Some(**v as _), 916 | Self::U32(v) => Some(**v as _), 917 | Self::U64(v) => Some(**v as _), 918 | 919 | _ => None 920 | } 921 | } 922 | } 923 | 924 | impl <'a> Eq for SharedValue<'a> { 925 | // TODO: elaborate it 926 | } 927 | 928 | pub trait Valued {} 929 | 930 | $( 931 | impl Valued for $t {} 932 | )* 933 | 934 | use std::hash::Hash; 935 | pub trait Value: ToTypped + Sized { 936 | type Map: Map; 937 | type Out: Value; 938 | 939 | fn into>(&self) -> Option; 940 | fn get_in_by_ids(&self, ids: &Vec) -> &Self::Out; 941 | fn get_by_id(&self, id: u64) -> &Self::Out; 942 | fn feature(&self) -> [u8; 8]; 943 | fn features(&self) -> Vec<[u8; 8]>; 944 | fn hash(&self) -> [u8; 8]; 945 | fn hashes(&self) -> Vec<[u8; 8]>; 946 | fn base_type(&self) -> Type; 947 | fn index_of(&self, index: usize) -> &Self::Out; 948 | fn base_size(&self) -> usize; 949 | fn prim_array_data_size(&self) -> Option; 950 | fn uni_array(&self) -> Option>; 951 | fn map(&self) -> Option<&Self::Map>; 952 | } 953 | 954 | pub trait FromValue where Self: Sized { 955 | fn get_from_value(value: &V) -> Option; 956 | } 957 | 958 | $( 959 | impl FromValue for $t { 960 | fn get_from_value(value: &OwnedValue) -> Option<$t> { 961 | OwnedValue::$fn(value).map(|v| v.to_owned()) 962 | } 963 | } 964 | )* 965 | 966 | 967 | pub trait ToTypped: Sized { 968 | fn to_typped>(&self) -> Option; 969 | } 970 | 971 | impl ToTypped for OwnedValue { 972 | fn to_typped>(&self) -> Option { 973 | // OwnedValue::$fn(value).map(|v| v.to_owned()) 974 | T::get_from_value(self) 975 | } 976 | } 977 | 978 | impl Value for OwnedValue { 979 | 980 | type Map = OwnedMap; 981 | type Out = Self; 982 | 983 | fn into>(&self) -> Option { 984 | V::get_from_value(self) 985 | } 986 | 987 | fn feature(&self) -> [u8; 8] { 988 | OwnedValue::feature(self) 989 | } 990 | fn features(&self) -> Vec<[u8; 8]> { 991 | OwnedValue::features(&self) 992 | } 993 | fn hash(&self) -> [u8; 8] { 994 | OwnedValue::hash(self) 995 | } 996 | fn hashes(&self) -> Vec<[u8; 8]> { 997 | OwnedValue::hashes(self) 998 | } 999 | fn base_type(&self) -> Type { 1000 | OwnedValue::base_type(self) 1001 | } 1002 | fn index_of(&self, index: usize) -> &Self { 1003 | &self[index] 1004 | } 1005 | fn base_size(&self) -> usize { 1006 | OwnedValue::base_size(&self) 1007 | } 1008 | fn prim_array_data_size(&self) -> Option { 1009 | match self { 1010 | OwnedValue::PrimArray(arr) => Some(arr.data_size()), 1011 | _ => None, 1012 | } 1013 | } 1014 | fn uni_array(&self) -> Option> { 1015 | match self { 1016 | OwnedValue::Array(arr) => Some(arr.iter().map(|v| v as &Self).collect()), 1017 | _ => None 1018 | } 1019 | } 1020 | fn get_in_by_ids(&self, ids: &Vec) -> &Self { 1021 | if let OwnedValue::Map(map) = &self { 1022 | map.get_in_by_ids(ids.iter()) 1023 | } else { 1024 | &OwnedValue::Null 1025 | } 1026 | } 1027 | fn get_by_id(&self, id: u64) -> &Self { 1028 | if let OwnedValue::Map(map) = &self { 1029 | map.get_by_key_id(id) 1030 | } else { 1031 | &OwnedValue::Null 1032 | } 1033 | } 1034 | fn map(&self) -> Option<&OwnedMap> { 1035 | match self { 1036 | OwnedValue::Map(map) => Some(map), 1037 | _ => None 1038 | } 1039 | } 1040 | } 1041 | 1042 | impl Index for OwnedValue { 1043 | type Output = Self; 1044 | fn index(&self, index: usize) -> &Self::Output { 1045 | match self { 1046 | &Self::Array(ref array) => array.get(index).unwrap_or(&NULL_OWNED_VALUE), 1047 | &Self::Map(ref map) => map.get_by_key_id(index as u64), 1048 | _ => &NULL_OWNED_VALUE, 1049 | } 1050 | } 1051 | } 1052 | 1053 | impl Index for OwnedValue { 1054 | type Output = Self; 1055 | 1056 | fn index(&self, index: u64) -> &Self::Output { 1057 | match self { 1058 | &Self::Map(ref map) => map.get_by_key_id(index), 1059 | &Self::Array(ref array) => array.get(index as usize).unwrap_or(&NULL_OWNED_VALUE), 1060 | _ => &NULL_OWNED_VALUE, 1061 | } 1062 | } 1063 | } 1064 | 1065 | $( 1066 | impl <'a> FromValue> for $t { 1067 | fn get_from_value(value: &SharedValue<'a>) -> Option<$t> { 1068 | SharedValue::$fn(value).map(|v| v.to_owned().into()) 1069 | } 1070 | } 1071 | )* 1072 | 1073 | impl <'a> ToTypped for SharedValue<'a> { 1074 | fn to_typped>(&self) -> Option { 1075 | // OwnedValue::$fn(value).map(|v| v.to_owned()) 1076 | T::get_from_value(self) 1077 | } 1078 | } 1079 | 1080 | impl <'a> Value for SharedValue<'a> { 1081 | 1082 | type Map = SharedMap<'a>; 1083 | type Out = Self; 1084 | 1085 | fn into>(&self) -> Option { 1086 | V::get_from_value(self) 1087 | } 1088 | 1089 | fn feature(&self) -> [u8; 8] { 1090 | SharedValue::feature(self) 1091 | } 1092 | fn features(&self) -> Vec<[u8; 8]> { 1093 | SharedValue::features(&self) 1094 | } 1095 | fn hash(&self) -> [u8; 8] { 1096 | SharedValue::hash(self) 1097 | } 1098 | fn hashes(&self) -> Vec<[u8; 8]> { 1099 | SharedValue::hashes(self) 1100 | } 1101 | fn base_type(&self) -> Type { 1102 | SharedValue::base_type(&self) 1103 | } 1104 | fn index_of(&self, index: usize) -> &Self { 1105 | &self[index] 1106 | } 1107 | fn base_size(&self) -> usize { 1108 | SharedValue::base_size(self) 1109 | } 1110 | fn prim_array_data_size(&self) -> Option { 1111 | match self { 1112 | SharedValue::PrimArray(arr) => Some(arr.data_size()), 1113 | _ => None, 1114 | } 1115 | } 1116 | fn uni_array(&self) -> Option> { 1117 | match self { 1118 | SharedValue::Array(arr) => Some(arr.iter().map(|v| v as &Self).collect()), 1119 | _ => None 1120 | } 1121 | } 1122 | fn get_in_by_ids(&self, ids: &Vec) -> &Self { 1123 | if let SharedValue::Map(map) = &self { 1124 | map.get_in_by_ids(ids.iter()) 1125 | } else { 1126 | &SharedValue::Null 1127 | } 1128 | } 1129 | fn get_by_id(&self, id: u64) -> &Self { 1130 | if let SharedValue::Map(map) = &self { 1131 | map.get_by_key_id(id) 1132 | } else { 1133 | &SharedValue::Null 1134 | } 1135 | } 1136 | fn map(&self) -> Option<&SharedMap<'a>> { 1137 | match self { 1138 | SharedValue::Map(map) => Some(map), 1139 | _ => None 1140 | } 1141 | } 1142 | } 1143 | 1144 | impl <'a> Hash for SharedValue<'a> { 1145 | fn hash(&self, state: &mut H) { 1146 | ::hash(&self.owned(), state) 1147 | } 1148 | } 1149 | 1150 | impl <'a> Index for SharedValue<'a> { 1151 | type Output = Self; 1152 | 1153 | fn index(&self, index: usize) -> &Self::Output { 1154 | match self { 1155 | &Self::Array(ref array) => array.get(index).unwrap_or(&NULL_SHARED_VALUE), 1156 | &Self::Map(ref map) => map.get_by_key_id(index as u64), 1157 | _ => &NULL_SHARED_VALUE, 1158 | } 1159 | } 1160 | } 1161 | 1162 | impl <'a> Index for SharedValue<'a> { 1163 | type Output = Self; 1164 | 1165 | fn index(&self, index: u64) -> &Self::Output { 1166 | match self { 1167 | &Self::Map(ref map) => map.get_by_key_id(index), 1168 | &Self::Array(ref array) => array.get(index as usize).unwrap_or(&NULL_SHARED_VALUE), 1169 | _ => &NULL_SHARED_VALUE, 1170 | } 1171 | } 1172 | } 1173 | 1174 | impl <'a> Default for SharedValue<'a> { 1175 | fn default() -> Self { 1176 | Self::NA 1177 | } 1178 | } 1179 | 1180 | use crate::types::referred::OwnedValueRef; 1181 | $( 1182 | impl FromValue for $t { 1183 | fn get_from_value(value: &OwnedValueRef) -> Option<$t> { 1184 | OwnedValue::$fn(&*value).map(|v| v.to_owned()) 1185 | } 1186 | } 1187 | )* 1188 | impl <'a> ToTypped for OwnedValueRef { 1189 | fn to_typped>(&self) -> Option { 1190 | // OwnedValue::$fn(value).map(|v| v.to_owned()) 1191 | T::get_from_value(self) 1192 | } 1193 | } 1194 | 1195 | impl Value for OwnedValueRef { 1196 | 1197 | type Map = OwnedMap; 1198 | type Out = OwnedValue; 1199 | 1200 | fn into>(&self) -> Option { 1201 | V::get_from_value(&*self) 1202 | } 1203 | 1204 | fn feature(&self) -> [u8; 8] { 1205 | OwnedValue::feature(&*self) 1206 | } 1207 | fn features(&self) -> Vec<[u8; 8]> { 1208 | OwnedValue::features(&**self) 1209 | } 1210 | fn hash(&self) -> [u8; 8] { 1211 | OwnedValue::hash(&*self) 1212 | } 1213 | fn hashes(&self) -> Vec<[u8; 8]> { 1214 | OwnedValue::hashes(&*self) 1215 | } 1216 | fn base_type(&self) -> Type { 1217 | OwnedValue::base_type(&*self) 1218 | } 1219 | fn index_of(&self, index: usize) -> &Self::Out { 1220 | &self[index] 1221 | } 1222 | fn base_size(&self) -> usize { 1223 | OwnedValue::base_size(&*self) 1224 | } 1225 | fn prim_array_data_size(&self) -> Option { 1226 | match &**self { 1227 | OwnedValue::PrimArray(ref arr) => Some(arr.data_size()), 1228 | _ => None, 1229 | } 1230 | } 1231 | fn uni_array(&self) -> Option> { 1232 | match &**self { 1233 | OwnedValue::Array(arr) => Some(arr.iter().map(|v| v as &Self::Out).collect()), 1234 | _ => None 1235 | } 1236 | } 1237 | fn get_in_by_ids(&self, ids: &Vec) -> &Self::Out { 1238 | if let OwnedValue::Map(map) = &**self { 1239 | map.get_in_by_ids(ids.iter()) 1240 | } else { 1241 | &OwnedValue::Null 1242 | } 1243 | } 1244 | fn get_by_id(&self, id: u64) -> &Self::Out { 1245 | if let OwnedValue::Map(map) = &**self { 1246 | map.get_by_key_id(id) 1247 | } else { 1248 | &OwnedValue::Null 1249 | } 1250 | } 1251 | fn map(&self) -> Option<&OwnedMap> { 1252 | match &**self { 1253 | OwnedValue::Map(map) => Some(map), 1254 | _ => None 1255 | } 1256 | } 1257 | } 1258 | 1259 | impl Hash for OwnedValueRef { 1260 | fn hash(&self, state: &mut H) { 1261 | ::hash(&**self, state) 1262 | } 1263 | } 1264 | 1265 | impl PartialEq for OwnedValueRef { 1266 | fn eq(&self, other: &Self) -> bool { 1267 | ::eq(&**self, &**other) 1268 | } 1269 | } 1270 | 1271 | impl Eq for OwnedValueRef {} 1272 | 1273 | ); 1274 | } 1275 | -------------------------------------------------------------------------------- /src/types/mod.rs: -------------------------------------------------------------------------------- 1 | #[macro_use] 2 | mod macros; 3 | pub mod custom_types; 4 | pub mod owned_value; 5 | pub mod referred; 6 | 7 | use ahash; 8 | use serde::Deserialize; 9 | use std::{ops::Index, vec::IntoIter}; 10 | 11 | pub use crate::types::custom_types::any::*; 12 | pub use crate::types::custom_types::bytes::*; 13 | pub use crate::types::custom_types::id::*; 14 | pub use crate::types::custom_types::map::Map; 15 | pub use crate::types::custom_types::owned_map::*; 16 | pub use crate::types::custom_types::pos::*; 17 | pub use crate::types::custom_types::shared_map::*; 18 | pub use crate::types::owned_value::*; 19 | 20 | gen_primitive_types_io!( 21 | bool: bool_io big_end_cast!(); 22 | char: char_io big_end_cast!(); 23 | i8: i8_io big_end_cast!(); 24 | i16: i16_io big_end!(write_i16); 25 | i32: i32_io big_end!(write_i32); 26 | i64: i64_io big_end!(write_i64); 27 | u8: u8_io big_end_cast!(); 28 | u16: u16_io big_end!(write_u16); 29 | u32: u32_io big_end!(write_u32); 30 | u64: u64_io big_end!(write_u64); 31 | f32: f32_io big_end!(write_f32); 32 | f64: f64_io big_end!(write_f64) 33 | ); 34 | 35 | gen_compound_types_io! ( 36 | Pos2d32, pos2d32_io, 37 | { 38 | |_| [0u8; 8] 39 | }, { 40 | |val: &Pos2d32| { 41 | use std::hash::Hasher; 42 | let mut hasher = ahash::AHasher::default(); 43 | hasher.write(&f32_io::feature(&val.x)); 44 | hasher.write(&f32_io::feature(&val.y)); 45 | u64_io::feature(&hasher.finish()) 46 | } 47 | }; 48 | 49 | Pos2d64, pos2d64_io, 50 | { 51 | |_| [0u8; 8] 52 | }, { 53 | |val: &Pos2d64| { 54 | use std::hash::Hasher; 55 | let mut hasher = ahash::AHasher::default(); 56 | hasher.write(&f64_io::feature(&val.x)); 57 | hasher.write(&f64_io::feature(&val.y)); 58 | u64_io::feature(&hasher.finish()) 59 | } 60 | }; 61 | 62 | ////////////////////////////////////////////////////////////// 63 | 64 | Pos3d32, pos3d32_io, 65 | { 66 | |_| [0u8; 8] 67 | }, { 68 | |val: &Pos3d32| { 69 | use std::hash::Hasher; 70 | let mut hasher = ahash::AHasher::default(); 71 | hasher.write(&f32_io::feature(&val.x)); 72 | hasher.write(&f32_io::feature(&val.y)); 73 | hasher.write(&f32_io::feature(&val.z)); 74 | u64_io::feature(&hasher.finish()) 75 | } 76 | }; 77 | 78 | Pos3d64, pos3d64_io, 79 | { 80 | |_| [0u8; 8] 81 | }, { 82 | |val: &Pos3d64| { 83 | use std::hash::Hasher; 84 | let mut hasher = ahash::AHasher::default(); 85 | hasher.write(&f64_io::feature(&val.x)); 86 | hasher.write(&f64_io::feature(&val.y)); 87 | hasher.write(&f64_io::feature(&val.z)); 88 | u64_io::feature(&hasher.finish()) 89 | } 90 | }; 91 | 92 | ////////////////////////////////////////////////////////// 93 | 94 | Id, id_io, 95 | { 96 | |id: &Id| { 97 | let big_end = big_end!(write_u64); 98 | big_end(id.higher ^ id.lower) 99 | } 100 | }, { 101 | |val: &Id| { 102 | use std::hash::Hasher; 103 | let mut hasher = ahash::AHasher::default(); 104 | hasher.write(&u64_io::feature(&val.higher)); 105 | hasher.write(&u64_io::feature(&val.lower)); 106 | u64_io::feature(&hasher.finish()) 107 | } 108 | } 109 | ); 110 | 111 | gen_variable_types_io!( 112 | String, 113 | str, 114 | string_io, 115 | { 116 | |mem_ptr| { 117 | let len = *u32_io::read(mem_ptr) as usize; 118 | let smem_ptr = mem_ptr + u32_io::type_size(); 119 | let slice = unsafe { std::slice::from_raw_parts(smem_ptr as *const u8, len) }; 120 | std::str::from_utf8(slice).unwrap() 121 | } 122 | }, 123 | { 124 | use std::ptr; 125 | |val: &str, mem_ptr| { 126 | let bytes = val.as_bytes(); 127 | let len = bytes.len(); 128 | u32_io::write(&(len as u32), mem_ptr); 129 | let mut smem_ptr = mem_ptr + u32_io::type_size(); 130 | unsafe { 131 | for b in bytes { 132 | ptr::write(smem_ptr as *mut u8, *b); 133 | smem_ptr += 1; 134 | } 135 | } 136 | } 137 | }, 138 | { 139 | |mem_ptr| { 140 | let str_len = *u32_io::read(mem_ptr) as usize; 141 | str_len + u32_io::type_size() 142 | } 143 | }, 144 | |val: &str| { val.as_bytes().len() + u32_io::type_size() }, 145 | |val: &str| { 146 | let bytes = val.as_bytes(); 147 | let mut r = [0u8; 8]; 148 | for i in 0..::std::cmp::min(r.len(), bytes.len()) { 149 | r[i] = bytes[i] 150 | } 151 | r 152 | }, 153 | |val: &str| { u64_io::feature(&::bifrost_hasher::hash_str(val)) }, 154 | |val: &'a String| { val.as_str() }, 155 | { std::mem::align_of::() } 156 | ); 157 | 158 | gen_variable_types_io!( 159 | Bytes, 160 | [u8], 161 | bytes_io, 162 | { 163 | |mem_ptr| { 164 | let len = *u32_io::read(mem_ptr) as usize; 165 | let smem_ptr = mem_ptr + u32_io::type_size(); 166 | unsafe { std::slice::from_raw_parts(smem_ptr as *const u8, len) } 167 | } 168 | }, 169 | { 170 | use std::ptr; 171 | |val: &[u8], mem_ptr| { 172 | let len = val.len(); 173 | u32_io::write(&(len as u32), mem_ptr); 174 | let mut smem_ptr = mem_ptr + u32_io::type_size(); 175 | unsafe { 176 | for b in val { 177 | ptr::write(smem_ptr as *mut u8, *b); 178 | smem_ptr += 1; 179 | } 180 | } 181 | } 182 | }, 183 | |mem_ptr| { *u32_io::read(mem_ptr) as usize + u32_io::type_size() }, 184 | |val: &[u8]| { val.len() + u32_io::type_size() }, 185 | |val: &[u8]| { 186 | let mut r = [0u8; 8]; 187 | for i in 0..::std::cmp::min(r.len(), val.len()) { 188 | r[i] = val[i] 189 | } 190 | r 191 | }, 192 | |val: &[u8]| { 193 | use std::hash::Hasher; 194 | let mut hasher = ahash::AHasher::default(); 195 | hasher.write(val); 196 | u64_io::feature(&hasher.finish()) 197 | }, 198 | |val: &'a Bytes| { val.data.as_slice() }, 199 | { std::mem::align_of::() } 200 | ); 201 | 202 | gen_variable_types_io!( 203 | SmallBytes, 204 | [u8], 205 | small_bytes_io, 206 | { 207 | |mem_ptr| { 208 | let len = *u8_io::read(mem_ptr) as usize; 209 | let smem_ptr = mem_ptr + 1; 210 | unsafe { std::slice::from_raw_parts(smem_ptr as *const u8, len) } 211 | } 212 | }, 213 | { 214 | use std::ptr; 215 | |val: &[u8], mem_ptr| { 216 | let len = val.len() as u8; 217 | u8_io::write(&len, mem_ptr); 218 | let mut smem_ptr = mem_ptr + 1; 219 | unsafe { 220 | for b in val { 221 | ptr::write(smem_ptr as *mut u8, *b); 222 | smem_ptr += 1; 223 | } 224 | } 225 | } 226 | }, 227 | |mem_ptr| { *u8_io::read(mem_ptr) as usize + 1 }, 228 | |val: &[u8]| { val.len() + 1 }, 229 | |val: &[u8]| { 230 | let mut r = [0u8; 8]; 231 | for i in 0..::std::cmp::min(r.len(), val.len()) { 232 | r[i] = val[i] 233 | } 234 | r 235 | }, 236 | |val: &[u8]| { 237 | use std::hash::Hasher; 238 | let mut hasher = ahash::AHasher::default(); 239 | hasher.write(&val); 240 | u64_io::feature(&hasher.finish()) 241 | }, 242 | |val: &'a SmallBytes| { val.data.as_slice() }, 243 | { std::mem::align_of::() } 244 | ); 245 | 246 | define_types!( 247 | ["bool", "bit"], bool ,Bool , bool_io, bool ; 248 | ["char"], char ,Char , char_io, char ; 249 | ["i8"], i8 ,I8 , i8_io, i8 ; 250 | ["i16", "int"], i16 ,I16 , i16_io, i16 ; 251 | ["i32", "long"], i32 ,I32 , i32_io, i32 ; 252 | ["i64", "longlong"], i64 ,I64 , i64_io, i64 ; 253 | ["u8", "byte"], u8 ,U8 , u8_io, u8 ; 254 | ["u16"], u16 ,U16 , u16_io, u16 ; 255 | ["u32"], u32 ,U32 , u32_io, u32 ; 256 | ["u64"], u64 ,U64 , u64_io, u64 ; 257 | ["f32", "float"], f32 ,F32 , f32_io, f32 ; 258 | ["f64", "double"], f64 ,F64 , f64_io, f64 ; 259 | ["pos2d32", "pos2d", "pos", "pos32"], Pos2d32 ,Pos2d32 , pos2d32_io, pos2d32 ; 260 | ["pos2d64", "pos64"], Pos2d64 ,Pos2d64 , pos2d64_io, pos2d64 ; 261 | ["pos3d32", "pos3d"], Pos3d32 ,Pos3d32 , pos3d32_io, pos3d32 ; 262 | ["pos3d64"], Pos3d64 ,Pos3d64 , pos3d64_io, pos3d64 ; 263 | ["id"], Id ,Id , id_io, id ; 264 | ["string", "str"], String ,String , string_io, string ; 265 | ["bytes"], Bytes ,Bytes , bytes_io, bytes ; 266 | ["small_bytes"], SmallBytes ,SmallBytes , small_bytes_io, small_bytes 267 | ); 268 | 269 | #[macro_export] 270 | macro_rules! data_map { 271 | ($($k:ident: $v:expr),*) => {{ 272 | let mut map = $crate::types::OwnedMap::new(); 273 | $(map.insert_value(stringify!($k), $v);)* 274 | map 275 | }}; 276 | } 277 | 278 | #[macro_export] 279 | macro_rules! data_map_value { 280 | ($($k:ident: $v:expr),*) => {{ 281 | $crate::types::OwnedValue::Map(data_map!($($k: $v),*)) 282 | }}; 283 | } 284 | 285 | pub fn type_id_of(t: Type) -> u32 { 286 | return t as u32; 287 | } 288 | 289 | pub static NULL_OWNED_VALUE: OwnedValue = OwnedValue::Null; 290 | pub static NULL_SHARED_VALUE: SharedValue = SharedValue::Null; 291 | pub const ARRAY_LEN_TYPE: Type = Type::U32; //u32 292 | pub const TYPE_CODE_TYPE: Type = Type::U8; //u32 293 | 294 | impl<'a, 'v> Index<&'a str> for SharedValue<'v> { 295 | type Output = Self; 296 | 297 | fn index(&self, index: &'a str) -> &Self::Output { 298 | match self { 299 | &Self::Map(ref map) => map.get(index), 300 | _ => &NULL_SHARED_VALUE, 301 | } 302 | } 303 | } 304 | -------------------------------------------------------------------------------- /src/types/owned_value.rs: -------------------------------------------------------------------------------- 1 | use super::*; 2 | use std::collections::HashMap; 3 | use std::hash::Hash; 4 | use std::iter::Iterator; 5 | use std::ops::{Index, IndexMut}; 6 | use std::vec::IntoIter; 7 | 8 | type Value = OwnedValue; 9 | 10 | pub trait ToValue { 11 | fn value(self) -> Value; 12 | } 13 | 14 | impl<'a> ToValue for &'a str { 15 | fn value(self) -> Value { 16 | Value::String(self.to_string()) 17 | } 18 | } 19 | 20 | impl ToValue for Value { 21 | fn value(self) -> Value { 22 | self 23 | } 24 | } 25 | 26 | impl ToValue for Vec { 27 | fn value(self) -> Value { 28 | return Value::Array(self); 29 | } 30 | } 31 | 32 | impl ToValue for Vec> 33 | where 34 | V: ToValue, 35 | { 36 | fn value(self) -> Value { 37 | return Value::Array(self.into_iter().map(|m| m.value()).collect()); 38 | } 39 | } 40 | 41 | impl ToValue for HashMap 42 | where 43 | V: ToValue, 44 | { 45 | fn value(self) -> Value { 46 | let mut map = OwnedMap::new(); 47 | for (k, v) in self { 48 | map.insert_value(&k, v); 49 | } 50 | return Value::Map(map); 51 | } 52 | } 53 | 54 | impl<'a> Index<&'a str> for OwnedValue { 55 | type Output = Self; 56 | 57 | fn index(&self, index: &'a str) -> &Self::Output { 58 | match self { 59 | &Self::Map(ref map) => map.get(index), 60 | _ => &NULL_OWNED_VALUE, 61 | } 62 | } 63 | } 64 | 65 | static MISSING_ARRAY_ITEM: &'static str = "Cannot get item from array"; 66 | static DATA_TYPE_DONT_SUPPORT_INDEXING: &'static str = "Data type don't support indexing"; 67 | 68 | impl<'a> IndexMut<&'a str> for Value { 69 | fn index_mut<'b>(&'b mut self, index: &'a str) -> &'b mut Self::Output { 70 | match self { 71 | &mut Value::Map(ref mut map) => map.get_mut(index), 72 | _ => panic!("{}", DATA_TYPE_DONT_SUPPORT_INDEXING), 73 | } 74 | } 75 | } 76 | 77 | impl IndexMut for Value { 78 | fn index_mut(&mut self, index: usize) -> &mut Self::Output { 79 | match self { 80 | &mut Value::Array(ref mut array) => array.get_mut(index).expect(MISSING_ARRAY_ITEM), 81 | &mut Value::Map(ref mut map) => map.get_mut_by_key_id(index as u64), 82 | _ => panic!("{}", DATA_TYPE_DONT_SUPPORT_INDEXING), 83 | } 84 | } 85 | } 86 | 87 | impl IndexMut for Value { 88 | fn index_mut<'a>(&'a mut self, index: u64) -> &'a mut Self::Output { 89 | match self { 90 | &mut Value::Map(ref mut map) => map.get_mut_by_key_id(index), 91 | &mut Value::Array(ref mut array) => { 92 | array.get_mut(index as usize).expect(MISSING_ARRAY_ITEM) 93 | } 94 | _ => panic!("{}", DATA_TYPE_DONT_SUPPORT_INDEXING), 95 | } 96 | } 97 | } 98 | 99 | impl IntoIterator for Value { 100 | type Item = Value; 101 | type IntoIter = IntoIter; 102 | 103 | fn into_iter(self) -> ::IntoIter { 104 | if let Value::Array(array) = self { 105 | return array.into_iter(); 106 | } else { 107 | panic!() 108 | } 109 | } 110 | } 111 | 112 | pub struct ValueIter<'a> { 113 | array: &'a Vec, 114 | cursor: usize, 115 | } 116 | 117 | impl<'a> ValueIter<'a> { 118 | pub fn new(array: &'a Vec) -> ValueIter<'a> { 119 | ValueIter { array, cursor: 0 } 120 | } 121 | } 122 | 123 | impl<'a> Iterator for ValueIter<'a> { 124 | type Item = &'a Value; 125 | fn next(&mut self) -> Option<::Item> { 126 | self.iter_next() 127 | } 128 | } 129 | 130 | impl<'a> ValueIter<'a> { 131 | fn iter_next(&mut self) -> Option<::Item> { 132 | let val_opt = self.array.get(self.cursor); 133 | if let Some(ref _val) = val_opt { 134 | self.cursor += 1; 135 | } 136 | return val_opt; 137 | } 138 | } 139 | 140 | impl Eq for Value { 141 | // TODO: elaborate it 142 | } 143 | 144 | impl Hash for Value { 145 | fn hash(&self, state: &mut H) { 146 | state.write(bifrost::utils::serde::serialize(self).as_slice()); 147 | } 148 | } 149 | 150 | impl Default for Value { 151 | fn default() -> Self { 152 | Self::NA 153 | } 154 | } 155 | 156 | pub trait Compound {} 157 | -------------------------------------------------------------------------------- /src/types/referred.rs: -------------------------------------------------------------------------------- 1 | use std::fmt::Debug; 2 | use std::sync::atomic::Ordering::Relaxed; 3 | use std::{ops::Deref, sync::atomic::AtomicUsize}; 4 | 5 | use super::OwnedValue; 6 | 7 | pub type OwnedValueRef = ARef; 8 | 9 | struct ARefInner { 10 | obj: T, 11 | rc: AtomicUsize, 12 | } 13 | 14 | pub struct ARef(*mut ARefInner); 15 | 16 | impl ARef { 17 | pub fn new(obj: T) -> Self { 18 | let inner = ARefInner { 19 | obj, 20 | rc: AtomicUsize::new(1), 21 | }; 22 | Self(Box::into_raw(Box::new(inner))) 23 | } 24 | } 25 | 26 | impl ARef { 27 | pub fn clone_referred(&self) -> T { 28 | let inner = unsafe { &*self.0 }; 29 | inner.obj.clone() 30 | } 31 | } 32 | 33 | impl Debug for ARef { 34 | fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { 35 | f.debug_tuple("ARef").field(&self.0).finish() 36 | } 37 | } 38 | 39 | impl Deref for ARef { 40 | type Target = T; 41 | 42 | fn deref(&self) -> &Self::Target { 43 | let inner = unsafe { &*self.0 }; 44 | &inner.obj 45 | } 46 | } 47 | 48 | impl Clone for ARef { 49 | fn clone(&self) -> Self { 50 | let inner = unsafe { &*self.0 }; 51 | inner.rc.fetch_add(1, Relaxed); 52 | Self(self.0) 53 | } 54 | } 55 | 56 | impl Drop for ARef { 57 | fn drop(&mut self) { 58 | let inner = unsafe { &*self.0 }; 59 | let old_rc = inner.rc.fetch_sub(1, Relaxed); 60 | if old_rc == 1 { 61 | unsafe { 62 | drop(Box::from_raw(self.0)); 63 | } 64 | } 65 | } 66 | } 67 | -------------------------------------------------------------------------------- /tests/tests.rs: -------------------------------------------------------------------------------- 1 | use dovahkiin::expr::{SExpr, Value}; 2 | use dovahkiin::integrated::lisp; 3 | use dovahkiin::types::{Map, OwnedValue, SharedValue}; 4 | 5 | extern crate dovahkiin; 6 | 7 | #[test] 8 | pub fn lisp_integrated_plus_function() { 9 | let mut interpreter = lisp::get_interpreter(); 10 | let str_function = " (+ -1i32 1i32 15i32)"; 11 | assert_eq!( 12 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 13 | SExpr::from_owned_value(OwnedValue::I32(15)) 14 | ); 15 | } 16 | 17 | #[test] 18 | pub fn lisp_integrated_binding() { 19 | let mut interpreter = lisp::get_interpreter(); 20 | let str_function = " (let [x 1u32] (+ 1u32 x))"; 21 | assert_eq!( 22 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 23 | SExpr::from_owned_value(OwnedValue::U32(2)) 24 | ); 25 | } 26 | 27 | #[test] 28 | pub fn lisp_integrated_binding_2() { 29 | let mut interpreter = lisp::get_interpreter(); 30 | let str_function = " (let [x 1u32 y 2u32] (+ x y))"; 31 | assert_eq!( 32 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 33 | SExpr::from_owned_value(OwnedValue::U32(3)) 34 | ); 35 | } 36 | 37 | #[test] 38 | pub fn lisp_integrated_binding_def() { 39 | let mut interpreter = lisp::get_interpreter(); 40 | let str_function = "(def x 1u32) (let [y 2u32] (+ x y))"; 41 | assert_eq!( 42 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 43 | SExpr::from_owned_value(OwnedValue::U32(3)) 44 | ); 45 | } 46 | 47 | #[test] 48 | pub fn lisp_integrated_lambda() { 49 | let mut interpreter = lisp::get_interpreter(); 50 | let str_function = " ((lambda [x] (+ 1u32 x)) 5u32)"; 51 | assert_eq!( 52 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 53 | SExpr::from_owned_value(OwnedValue::U32(6)) 54 | ); 55 | } 56 | 57 | #[test] 58 | pub fn lisp_integrated_lambda_2() { 59 | let mut interpreter = lisp::get_interpreter(); 60 | let str_function = " ((lambda [x y] (* x y)) 5u32 4u32)"; 61 | assert_eq!( 62 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 63 | SExpr::from_owned_value(OwnedValue::U32(20)) 64 | ); 65 | } 66 | 67 | #[test] 68 | pub fn lisp_integrated_functional() { 69 | let mut interpreter = lisp::get_interpreter(); 70 | let str_function = "(map (lambda [x] (+ x 1u32)) [1u32 2u32 3u32 4u32 5u32 6u32])"; 71 | assert_eq!( 72 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 73 | SExpr::Vec(vec![ 74 | SExpr::from_owned_value(OwnedValue::U32(2)), 75 | SExpr::from_owned_value(OwnedValue::U32(3)), 76 | SExpr::from_owned_value(OwnedValue::U32(4)), 77 | SExpr::from_owned_value(OwnedValue::U32(5)), 78 | SExpr::from_owned_value(OwnedValue::U32(6)), 79 | SExpr::from_owned_value(OwnedValue::U32(7)) 80 | ]) 81 | ); 82 | } 83 | 84 | #[test] 85 | pub fn lisp_integrated_functional_symbolic() { 86 | let mut interpreter = lisp::get_interpreter(); 87 | let str_function = " (map inc [1u32 2u32 3u32 4u32 5u32 6u32])"; 88 | assert_eq!( 89 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 90 | SExpr::Vec(vec![ 91 | SExpr::from_owned_value(OwnedValue::U32(2)), 92 | SExpr::from_owned_value(OwnedValue::U32(3)), 93 | SExpr::from_owned_value(OwnedValue::U32(4)), 94 | SExpr::from_owned_value(OwnedValue::U32(5)), 95 | SExpr::from_owned_value(OwnedValue::U32(6)), 96 | SExpr::from_owned_value(OwnedValue::U32(7)) 97 | ]) 98 | ); 99 | } 100 | 101 | #[test] 102 | pub fn lisp_integrated_functional_defunc() { 103 | let mut interpreter = lisp::get_interpreter(); 104 | let str_function = "(defunc dec [x] (- x 1u32))\ 105 | (map dec [1u32 2u32 3u32 4u32 5u32 6u32])"; 106 | assert_eq!( 107 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 108 | SExpr::Vec(vec![ 109 | SExpr::from_owned_value(OwnedValue::U32(0)), 110 | SExpr::from_owned_value(OwnedValue::U32(1)), 111 | SExpr::from_owned_value(OwnedValue::U32(2)), 112 | SExpr::from_owned_value(OwnedValue::U32(3)), 113 | SExpr::from_owned_value(OwnedValue::U32(4)), 114 | SExpr::from_owned_value(OwnedValue::U32(5)) 115 | ]) 116 | ); 117 | } 118 | 119 | #[test] 120 | pub fn lisp_lexer_test_1() { 121 | let mut interpreter = lisp::get_interpreter(); 122 | let str_function = "(+(+ 1u32 2u32) 3u32)"; 123 | assert_eq!( 124 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 125 | SExpr::from_owned_value(OwnedValue::U32(6)) 126 | ); 127 | } 128 | 129 | #[test] 130 | pub fn scoping() { 131 | let mut interpreter = lisp::get_interpreter(); 132 | let str_function = "(def x 1u32)\n 133 | (defunc y [] x)\n 134 | (let [x 2u32] (y))"; 135 | // 2 for dynamic scoping, 1 for lexical scoping. Dovahkiin is dynamic scoping 136 | assert_eq!( 137 | lisp::eval_string(&mut interpreter, str_function) 138 | .unwrap() 139 | .owned_val() 140 | .unwrap(), 141 | OwnedValue::U32(2) 142 | ); 143 | } 144 | 145 | #[test] 146 | pub fn or() { 147 | let mut interpreter = lisp::get_interpreter(); 148 | let str_function = "(let [x 2u64] (or (= x 1u64) (= x 2u64)))"; 149 | assert_eq!( 150 | lisp::eval_string(&mut interpreter, str_function).unwrap(), 151 | SExpr::from_owned_value(OwnedValue::Bool(true)) 152 | ); 153 | } 154 | 155 | #[test] 156 | pub fn keyword() { 157 | let mut interpreter = lisp::get_interpreter(); 158 | let str_exp = "(into-map [:x 123u32, :y 456u64])"; 159 | let map_expr = lisp::eval_string(&mut interpreter, str_exp).unwrap(); 160 | let map_val = map_expr.shared_val().unwrap(); 161 | let map = map_val.Map().unwrap(); 162 | assert_eq!(map.get("x").u32().unwrap(), &123); 163 | assert_eq!(map.get("y").u64().unwrap(), &456); 164 | } 165 | 166 | #[test] 167 | pub fn map() { 168 | let mut interpreter = lisp::get_interpreter(); 169 | let str_exp = "{:x 123u32, :y 456u64}"; 170 | let map_expr = lisp::eval_string(&mut interpreter, str_exp).unwrap(); 171 | let map_val = map_expr.shared_val().unwrap(); 172 | let map = map_val.Map().unwrap(); 173 | assert_eq!(map.get("x").u32().unwrap(), &123); 174 | assert_eq!(map.get("y").u64().unwrap(), &456); 175 | } 176 | 177 | #[test] 178 | pub fn map_vec() { 179 | let mut interpreter = lisp::get_interpreter(); 180 | let str_exp = "{:x 123u32, :y [456u64, 789u64]}"; 181 | let map_expr = lisp::eval_string(&mut interpreter, str_exp).unwrap(); 182 | let map_val = map_expr.shared_val().unwrap(); 183 | let map = map_val.Map().unwrap(); 184 | assert_eq!(map.get("x").u32().unwrap(), &123); 185 | let y = map.get("y"); 186 | match y { 187 | SharedValue::Array(arr) => { 188 | assert_eq!(arr[0].u64().unwrap(), &456); 189 | assert_eq!(arr[1].u64().unwrap(), &789); 190 | } 191 | _ => panic!(), 192 | } 193 | } 194 | --------------------------------------------------------------------------------