mod.rs 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522
  1. /* This file is part of DarkFi (https://dark.fi)
  2. *
  3. * Copyright (C) 2020-2026 Dyne.org foundation
  4. *
  5. * This program is free software: you can redistribute it and/or modify
  6. * it under the terms of the GNU Affero General Public License as
  7. * published by the Free Software Foundation, either version 3 of the
  8. * License, or (at your option) any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU Affero General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU Affero General Public License
  16. * along with this program. If not, see <https://www.gnu.org/licenses/>.
  17. */
  18. use crate::{
  19. error::{Error, Result},
  20. //prop::{Property, PropertySubType, PropertyType, PropertySExprValue},
  21. };
  22. use darkfi_serial::{
  23. async_trait, Decodable, Encodable, FutAsyncWriteExt, ReadExt, SerialDecodable, SerialEncodable,
  24. };
  25. use std::io::{Read, Write};
  26. mod compile;
  27. pub use compile::Compiler;
  28. pub type MachineGlobals = Vec<(String, SExprVal)>;
  29. #[derive(Debug, Clone)]
  30. pub struct NativeFnCallback(fn(&mut MachineGlobals) -> Result<SExprVal>);
  31. impl PartialEq for NativeFnCallback {
  32. fn eq(&self, _: &Self) -> bool {
  33. false
  34. }
  35. }
  36. pub fn const_f32(x: f32) -> SExprCode {
  37. vec![Op::ConstFloat32(x)]
  38. }
  39. pub fn load_var<S: Into<String>>(var: S) -> SExprCode {
  40. vec![Op::LoadVar(var.into())]
  41. }
  42. #[derive(Clone, Debug, PartialEq, SerialEncodable, SerialDecodable)]
  43. pub enum SExprVal {
  44. Null,
  45. Bool(bool),
  46. Uint32(u32),
  47. Float32(f32),
  48. Str(String),
  49. }
  50. impl SExprVal {
  51. #[allow(dead_code)]
  52. fn is_null(&self) -> bool {
  53. match self {
  54. Self::Null => true,
  55. _ => false,
  56. }
  57. }
  58. #[allow(dead_code)]
  59. fn is_bool(&self) -> bool {
  60. match self {
  61. Self::Bool(_) => true,
  62. _ => false,
  63. }
  64. }
  65. fn is_u32(&self) -> bool {
  66. match self {
  67. Self::Uint32(_) => true,
  68. _ => false,
  69. }
  70. }
  71. #[allow(dead_code)]
  72. fn is_f32(&self) -> bool {
  73. match self {
  74. Self::Float32(_) => true,
  75. _ => false,
  76. }
  77. }
  78. #[allow(dead_code)]
  79. fn is_str(&self) -> bool {
  80. match self {
  81. Self::Str(_) => true,
  82. _ => false,
  83. }
  84. }
  85. #[allow(dead_code)]
  86. fn as_bool(&self) -> Result<bool> {
  87. match self {
  88. Self::Bool(v) => Ok(*v),
  89. _ => Err(Error::PropertyWrongType),
  90. }
  91. }
  92. pub fn as_u32(&self) -> Result<u32> {
  93. match self {
  94. Self::Uint32(v) => Ok(*v),
  95. _ => Err(Error::PropertyWrongType),
  96. }
  97. }
  98. pub fn as_f32(&self) -> Result<f32> {
  99. match self {
  100. Self::Float32(v) => Ok(*v),
  101. _ => Err(Error::PropertyWrongType),
  102. }
  103. }
  104. #[allow(dead_code)]
  105. fn as_str(&self) -> Result<String> {
  106. match self {
  107. Self::Str(v) => Ok(v.clone()),
  108. _ => Err(Error::PropertyWrongType),
  109. }
  110. }
  111. pub fn coerce_f32(&self) -> Result<f32> {
  112. match self {
  113. Self::Uint32(v) => Ok(*v as f32),
  114. Self::Float32(v) => Ok(*v),
  115. _ => Err(Error::PropertyWrongType),
  116. }
  117. }
  118. }
  119. #[derive(Debug, PartialEq)]
  120. pub struct SExprMachine<'a> {
  121. pub globals: Vec<(String, SExprVal)>,
  122. pub stmts: &'a SExprCode,
  123. }
  124. // Each item is a statement
  125. pub type SExprCode = Vec<Op>;
  126. #[derive(Clone, Debug, PartialEq)]
  127. pub enum Op {
  128. Null,
  129. Add((Box<Op>, Box<Op>)),
  130. Sub((Box<Op>, Box<Op>)),
  131. Mul((Box<Op>, Box<Op>)),
  132. Div((Box<Op>, Box<Op>)),
  133. ConstBool(bool),
  134. ConstUint32(u32),
  135. ConstFloat32(f32),
  136. ConstStr(String),
  137. LoadVar(String),
  138. StoreVar((String, Box<Op>)),
  139. Min((Box<Op>, Box<Op>)),
  140. Max((Box<Op>, Box<Op>)),
  141. IsEqual((Box<Op>, Box<Op>)),
  142. LessThan((Box<Op>, Box<Op>)),
  143. Float32ToUint32(Box<Op>),
  144. IfElse((Box<Op>, SExprCode, SExprCode)),
  145. NativeFn(NativeFnCallback),
  146. }
  147. impl<'a> SExprMachine<'a> {
  148. pub fn call(&mut self) -> Result<SExprVal> {
  149. if self.stmts.is_empty() {
  150. return Ok(SExprVal::Null)
  151. }
  152. for i in 0..(self.stmts.len() - 1) {
  153. self.eval(&self.stmts[i])?;
  154. }
  155. self.eval(self.stmts.last().unwrap())
  156. }
  157. fn eval(&mut self, op: &Op) -> Result<SExprVal> {
  158. match op {
  159. Op::Null => Ok(SExprVal::Null),
  160. Op::Add((lhs, rhs)) => self.add(lhs, rhs),
  161. Op::Sub((lhs, rhs)) => self.sub(lhs, rhs),
  162. Op::Mul((lhs, rhs)) => self.mul(lhs, rhs),
  163. Op::Div((lhs, rhs)) => self.div(lhs, rhs),
  164. Op::ConstBool(val) => Ok(SExprVal::Bool(*val)),
  165. Op::ConstUint32(val) => Ok(SExprVal::Uint32(*val)),
  166. Op::ConstFloat32(val) => Ok(SExprVal::Float32(*val)),
  167. Op::ConstStr(val) => Ok(SExprVal::Str(val.clone())),
  168. Op::LoadVar(var) => self.load_var(var),
  169. Op::StoreVar((var, val)) => self.store_var(var, val),
  170. Op::Min((lhs, rhs)) => self.min(lhs, rhs),
  171. Op::Max((lhs, rhs)) => self.max(lhs, rhs),
  172. Op::IsEqual((lhs, rhs)) => self.is_equal(lhs, rhs),
  173. Op::LessThan((lhs, rhs)) => self.less_than(lhs, rhs),
  174. Op::Float32ToUint32(val) => self.float32_to_uint32(val),
  175. Op::IfElse((cond, if_val, else_val)) => self.if_else(cond, if_val, else_val),
  176. Op::NativeFn(f) => (f.0)(&mut self.globals),
  177. }
  178. }
  179. fn add(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  180. let lhs = self.eval(lhs)?;
  181. let rhs = self.eval(rhs)?;
  182. if lhs.is_u32() && rhs.is_u32() {
  183. return Ok(SExprVal::Uint32(lhs.as_u32().unwrap() + rhs.as_u32().unwrap()))
  184. }
  185. let lhs = lhs.coerce_f32()?;
  186. let rhs = rhs.coerce_f32()?;
  187. Ok(SExprVal::Float32(lhs + rhs))
  188. }
  189. fn sub(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  190. let lhs = self.eval(lhs)?;
  191. let rhs = self.eval(rhs)?;
  192. if lhs.is_u32() && rhs.is_u32() {
  193. return Ok(SExprVal::Uint32(lhs.as_u32().unwrap() - rhs.as_u32().unwrap()))
  194. }
  195. let lhs = lhs.coerce_f32()?;
  196. let rhs = rhs.coerce_f32()?;
  197. Ok(SExprVal::Float32(lhs - rhs))
  198. }
  199. fn mul(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  200. let lhs = self.eval(lhs)?;
  201. let rhs = self.eval(rhs)?;
  202. if lhs.is_u32() && rhs.is_u32() {
  203. return Ok(SExprVal::Uint32(lhs.as_u32().unwrap() * rhs.as_u32().unwrap()))
  204. }
  205. let lhs = lhs.coerce_f32()?;
  206. let rhs = rhs.coerce_f32()?;
  207. Ok(SExprVal::Float32(lhs * rhs))
  208. }
  209. fn div(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  210. let lhs = self.eval(lhs)?;
  211. let rhs = self.eval(rhs)?;
  212. // Always coerce
  213. let lhs = lhs.coerce_f32()?;
  214. let rhs = rhs.coerce_f32()?;
  215. Ok(SExprVal::Float32(lhs / rhs))
  216. }
  217. fn load_var(&self, var: &str) -> Result<SExprVal> {
  218. for (name, val) in &self.globals {
  219. if name == var {
  220. return Ok(val.clone())
  221. }
  222. }
  223. Err(Error::SExprGlobalNotFound)
  224. }
  225. fn store_var(&mut self, var: &str, val: &Op) -> Result<SExprVal> {
  226. let val = self.eval(val)?;
  227. self.globals.push((var.to_string(), val));
  228. Ok(SExprVal::Null)
  229. }
  230. fn min(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  231. let lhs = self.eval(lhs)?;
  232. let rhs = self.eval(rhs)?;
  233. if lhs.is_u32() && rhs.is_u32() {
  234. let lhs = lhs.as_u32().unwrap();
  235. let rhs = rhs.as_u32().unwrap();
  236. let min = if lhs < rhs { lhs } else { rhs };
  237. return Ok(SExprVal::Uint32(min))
  238. }
  239. let lhs = lhs.coerce_f32()?;
  240. let rhs = rhs.coerce_f32()?;
  241. let min = if lhs < rhs { lhs } else { rhs };
  242. Ok(SExprVal::Float32(min))
  243. }
  244. fn max(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  245. let lhs = self.eval(lhs)?;
  246. let rhs = self.eval(rhs)?;
  247. if lhs.is_u32() && rhs.is_u32() {
  248. let lhs = lhs.as_u32().unwrap();
  249. let rhs = rhs.as_u32().unwrap();
  250. let max = if lhs > rhs { lhs } else { rhs };
  251. return Ok(SExprVal::Uint32(max))
  252. }
  253. let lhs = lhs.coerce_f32()?;
  254. let rhs = rhs.coerce_f32()?;
  255. let max = if lhs > rhs { lhs } else { rhs };
  256. Ok(SExprVal::Float32(max))
  257. }
  258. fn is_equal(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  259. let lhs = self.eval(lhs)?;
  260. let rhs = self.eval(rhs)?;
  261. if lhs.is_u32() && rhs.is_u32() {
  262. return Ok(SExprVal::Bool(lhs.as_u32().unwrap() == rhs.as_u32().unwrap()))
  263. }
  264. let lhs = lhs.coerce_f32()?;
  265. let rhs = rhs.coerce_f32()?;
  266. let is_equal = (lhs - rhs).abs() < f32::EPSILON;
  267. Ok(SExprVal::Bool(is_equal))
  268. }
  269. fn less_than(&mut self, lhs: &Op, rhs: &Op) -> Result<SExprVal> {
  270. let lhs = self.eval(lhs)?;
  271. let rhs = self.eval(rhs)?;
  272. if lhs.is_u32() && rhs.is_u32() {
  273. return Ok(SExprVal::Bool(lhs.as_u32().unwrap() < rhs.as_u32().unwrap()))
  274. }
  275. let lhs = lhs.coerce_f32()?;
  276. let rhs = rhs.coerce_f32()?;
  277. Ok(SExprVal::Bool(lhs < rhs))
  278. }
  279. fn float32_to_uint32(&mut self, val: &Op) -> Result<SExprVal> {
  280. let val = self.eval(val)?;
  281. if val.is_u32() {
  282. return Ok(SExprVal::Uint32(val.as_u32()?))
  283. }
  284. Ok(SExprVal::Uint32(val.as_f32()? as u32))
  285. }
  286. fn if_else(&mut self, cond: &Op, if_val: &SExprCode, else_val: &SExprCode) -> Result<SExprVal> {
  287. let cond = self.eval(cond)?;
  288. let cond = cond.as_bool()?;
  289. if cond {
  290. let mut machine = SExprMachine { globals: self.globals.clone(), stmts: if_val };
  291. machine.call()
  292. } else {
  293. let mut machine = SExprMachine { globals: self.globals.clone(), stmts: else_val };
  294. machine.call()
  295. }
  296. }
  297. }
  298. impl Encodable for Op {
  299. fn encode<S: Write>(&self, s: &mut S) -> std::result::Result<usize, std::io::Error> {
  300. let mut len = 0;
  301. match self {
  302. Self::Null => {
  303. len += 0u8.encode(s)?;
  304. }
  305. Self::Add((lhs, rhs)) => {
  306. len += 1u8.encode(s)?;
  307. len += lhs.encode(s)?;
  308. len += rhs.encode(s)?;
  309. }
  310. Self::Sub((lhs, rhs)) => {
  311. len += 2u8.encode(s)?;
  312. len += lhs.encode(s)?;
  313. len += rhs.encode(s)?;
  314. }
  315. Self::Mul((lhs, rhs)) => {
  316. len += 3u8.encode(s)?;
  317. len += lhs.encode(s)?;
  318. len += rhs.encode(s)?;
  319. }
  320. Self::Div((lhs, rhs)) => {
  321. len += 4u8.encode(s)?;
  322. len += lhs.encode(s)?;
  323. len += rhs.encode(s)?;
  324. }
  325. Self::ConstBool(val) => {
  326. len += 5u8.encode(s)?;
  327. len += val.encode(s)?;
  328. }
  329. Self::ConstUint32(val) => {
  330. len += 6u8.encode(s)?;
  331. len += val.encode(s)?;
  332. }
  333. Self::ConstFloat32(val) => {
  334. len += 7u8.encode(s)?;
  335. len += val.encode(s)?;
  336. }
  337. Self::ConstStr(val) => {
  338. len += 8u8.encode(s)?;
  339. len += val.encode(s)?;
  340. }
  341. Self::LoadVar(var) => {
  342. len += 9u8.encode(s)?;
  343. len += var.encode(s)?;
  344. }
  345. Self::StoreVar((var, val)) => {
  346. len += 10u8.encode(s)?;
  347. len += var.encode(s)?;
  348. len += val.encode(s)?;
  349. }
  350. Self::Min((lhs, rhs)) => {
  351. len += 11u8.encode(s)?;
  352. len += lhs.encode(s)?;
  353. len += rhs.encode(s)?;
  354. }
  355. Self::Max((lhs, rhs)) => {
  356. len += 12u8.encode(s)?;
  357. len += lhs.encode(s)?;
  358. len += rhs.encode(s)?;
  359. }
  360. Self::IsEqual((lhs, rhs)) => {
  361. len += 13u8.encode(s)?;
  362. len += lhs.encode(s)?;
  363. len += rhs.encode(s)?;
  364. }
  365. Self::LessThan((lhs, rhs)) => {
  366. len += 14u8.encode(s)?;
  367. len += lhs.encode(s)?;
  368. len += rhs.encode(s)?;
  369. }
  370. Self::Float32ToUint32(val) => {
  371. len += 15u8.encode(s)?;
  372. len += val.encode(s)?;
  373. }
  374. Self::IfElse((cond, if_val, else_val)) => {
  375. len += 16u8.encode(s)?;
  376. len += cond.encode(s)?;
  377. len += if_val.encode(s)?;
  378. len += else_val.encode(s)?;
  379. }
  380. Self::NativeFn(_) => {
  381. len += 17u8.encode(s)?;
  382. }
  383. }
  384. Ok(len)
  385. }
  386. }
  387. impl Decodable for Op {
  388. fn decode<D: Read>(d: &mut D) -> std::result::Result<Self, std::io::Error> {
  389. let op_type = d.read_u8()?;
  390. let self_ = match op_type {
  391. 0 => Self::Null,
  392. 1 => Self::Add((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  393. 2 => Self::Sub((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  394. 3 => Self::Mul((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  395. 4 => Self::Div((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  396. 5 => Self::ConstBool(d.read_bool()?),
  397. 6 => Self::ConstUint32(d.read_u32()?),
  398. 7 => Self::ConstFloat32(d.read_f32()?),
  399. 8 => Self::ConstStr(String::decode(d)?),
  400. 9 => Self::LoadVar(String::decode(d)?),
  401. 10 => Self::StoreVar((String::decode(d)?, Box::new(Self::decode(d)?))),
  402. 11 => Self::Min((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  403. 12 => Self::Max((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  404. 13 => Self::IsEqual((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  405. 14 => Self::LessThan((Box::new(Self::decode(d)?), Box::new(Self::decode(d)?))),
  406. 15 => Self::Float32ToUint32(Box::new(Self::decode(d)?)),
  407. 16 => Self::IfElse((
  408. Box::new(Self::decode(d)?),
  409. Decodable::decode(d)?,
  410. Decodable::decode(d)?,
  411. )),
  412. 17 => Self::NativeFn(NativeFnCallback(|_| Ok(SExprVal::Null))),
  413. _ => return Err(std::io::Error::new(std::io::ErrorKind::Other, "Invalid Op type")),
  414. };
  415. Ok(self_)
  416. }
  417. }
  418. #[cfg(test)]
  419. mod tests {
  420. use super::*;
  421. use darkfi_serial::{deserialize, serialize};
  422. #[test]
  423. fn seval() {
  424. let mut machine = SExprMachine {
  425. globals: vec![
  426. ("sw".to_string(), SExprVal::Uint32(110u32)),
  427. ("sh".to_string(), SExprVal::Uint32(4u32)),
  428. ],
  429. stmts: &vec![Op::Add((
  430. Box::new(Op::ConstUint32(5)),
  431. Box::new(Op::Div((
  432. Box::new(Op::LoadVar("sw".to_string())),
  433. Box::new(Op::ConstUint32(2)),
  434. ))),
  435. ))],
  436. };
  437. assert_eq!(machine.call().unwrap(), SExprVal::Float32(60.));
  438. }
  439. #[test]
  440. fn encdec_code() {
  441. let code = Op::Add((
  442. Box::new(Op::ConstUint32(5)),
  443. Box::new(Op::Div((
  444. Box::new(Op::LoadVar("sw".to_string())),
  445. Box::new(Op::ConstUint32(2)),
  446. ))),
  447. ));
  448. let code_s = serialize(&code);
  449. let code2 = deserialize::<Op>(&code_s).unwrap();
  450. assert_eq!(code, code2);
  451. }
  452. #[test]
  453. fn if_store() {
  454. let code = vec![
  455. Op::StoreVar((
  456. "s".to_string(),
  457. Box::new(Op::IfElse((
  458. Box::new(Op::ConstBool(false)),
  459. vec![Op::ConstUint32(4)],
  460. vec![Op::ConstUint32(110)],
  461. ))),
  462. )),
  463. Op::LoadVar("s".to_string()),
  464. ];
  465. let mut machine = SExprMachine { globals: vec![], stmts: &code };
  466. assert_eq!(machine.call().unwrap(), SExprVal::Uint32(110));
  467. }
  468. }