lisp.rs 31 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779
  1. #![allow(non_snake_case)]
  2. use crate::types::LispCircuit;
  3. use drk::BlsStringConversion;
  4. use bellman::groth16;
  5. use bls12_381::Bls12;
  6. // use fnv::FnvHashMap;
  7. use itertools::Itertools;
  8. use rand::rngs::OsRng;
  9. use std::rc::Rc;
  10. use std::time::Instant;
  11. use std::{cell::RefCell, collections::HashMap};
  12. use types::EnforceAllocation;
  13. #[macro_use]
  14. extern crate clap;
  15. #[macro_use]
  16. extern crate lazy_static;
  17. // extern crate fnv;
  18. extern crate itertools;
  19. extern crate regex;
  20. #[macro_use]
  21. mod types;
  22. use crate::types::MalErr::{ErrMalVal, ErrString};
  23. use crate::types::MalVal::{
  24. Alloc, Bool, Enforce, Func, Hash, List, MalFunc, Nil, Str, Sym, Vector,
  25. };
  26. use crate::types::VerifyKeyParams;
  27. use crate::types::{error, format_error, MalArgs, MalErr, MalRet, MalVal};
  28. mod env;
  29. mod printer;
  30. mod reader;
  31. use crate::env::{env_bind, env_find, env_get, env_new, env_set, env_sets, Env};
  32. #[macro_use]
  33. mod core;
  34. // read
  35. fn read(str: &str) -> MalRet {
  36. reader::read_str(str.to_string())
  37. }
  38. // eval
  39. fn qq_iter(elts: &MalArgs) -> MalVal {
  40. let mut acc = list![];
  41. for elt in elts.iter().rev() {
  42. if let List(v, _) = elt {
  43. if v.len() == 2 {
  44. if let Sym(ref s) = v[0] {
  45. if s == "splice-unquote" {
  46. acc = list![Sym("concat".to_string()), v[1].clone(), acc];
  47. continue;
  48. }
  49. }
  50. }
  51. }
  52. acc = list![Sym("cons".to_string()), quasiquote(&elt), acc];
  53. }
  54. return acc;
  55. }
  56. fn quasiquote(ast: &MalVal) -> MalVal {
  57. match ast {
  58. List(v, _) => {
  59. if v.len() == 2 {
  60. if let Sym(ref s) = v[0] {
  61. if s == "unquote" {
  62. return v[1].clone();
  63. }
  64. }
  65. }
  66. return qq_iter(&v);
  67. }
  68. Vector(v, _) => return list![Sym("vec".to_string()), qq_iter(&v)],
  69. Hash(_, _) | Sym(_) => return list![Sym("quote".to_string()), ast.clone()],
  70. _ => ast.clone(),
  71. }
  72. }
  73. fn is_macro_call(ast: &MalVal, env: &Env) -> Option<(MalVal, MalArgs)> {
  74. match ast {
  75. List(v, _) => match v[0] {
  76. Sym(ref s) => match env_find(env, s) {
  77. Some(e) => match env_get(&e, &v[0]) {
  78. Ok(f @ MalFunc { is_macro: true, .. }) => Some((f, v[1..].to_vec())),
  79. _ => None,
  80. },
  81. _ => None,
  82. },
  83. _ => None,
  84. },
  85. _ => None,
  86. }
  87. }
  88. fn macroexpand(mut ast: MalVal, env: &Env) -> (bool, MalRet) {
  89. let mut was_expanded = false;
  90. while let Some((mf, args)) = is_macro_call(&ast, env) {
  91. // println!("macroexpand 1: {:?}", ast);
  92. ast = match mf.apply(args) {
  93. Err(e) => return (false, Err(e)),
  94. Ok(a) => a,
  95. };
  96. // println!("macroexpand 2: {:?}", ast);
  97. was_expanded = true;
  98. }
  99. (was_expanded, Ok(ast))
  100. }
  101. fn eval_ast(ast: &MalVal, env: &Env) -> MalRet {
  102. match ast {
  103. Sym(_) => Ok(env_get(&env, &ast)?),
  104. List(v, _) => {
  105. let mut lst: MalArgs = vec![];
  106. for a in v.iter() {
  107. lst.push(eval(a.clone(), env.clone())?)
  108. }
  109. Ok(list!(lst))
  110. }
  111. Vector(v, _) => {
  112. let mut lst: MalArgs = vec![];
  113. for a in v.iter() {
  114. lst.push(eval(a.clone(), env.clone())?)
  115. }
  116. Ok(vector!(lst))
  117. }
  118. Hash(hm, _) => {
  119. let mut new_hm: HashMap<String, MalVal> = HashMap::default();
  120. for (k, v) in hm.iter() {
  121. new_hm.insert(k.to_string(), eval(v.clone(), env.clone())?);
  122. }
  123. Ok(Hash(Rc::new(new_hm), Rc::new(Nil)))
  124. }
  125. _ => Ok(ast.clone()),
  126. }
  127. }
  128. fn eval(mut _ast: MalVal, mut env: Env) -> MalRet {
  129. let ret: MalRet;
  130. let start = Instant::now();
  131. 'tco: loop {
  132. // TODO check DEBUG symbol on env
  133. println!("debug eval \t {:?} \t {:?}", _ast, start.elapsed());
  134. ret = match _ast.clone() {
  135. List(l, _) => {
  136. if l.len() == 0 {
  137. return Ok(_ast);
  138. }
  139. match macroexpand(_ast.clone(), &env) {
  140. (true, Ok(new_ast)) => {
  141. _ast = new_ast;
  142. continue 'tco;
  143. }
  144. (_, Err(e)) => return Err(e),
  145. _ => (),
  146. }
  147. if l.len() == 0 {
  148. return Ok(_ast);
  149. }
  150. let a0 = &l[0];
  151. match a0 {
  152. Sym(ref a0sym) if a0sym == "def!" => {
  153. env_set(&env, l[1].clone(), eval(l[2].clone(), env.clone())?)
  154. }
  155. Sym(ref a0sym) if a0sym == "zk*" => {
  156. // println!("zk* {:?}", l[1]);
  157. let (a1, a2) = (l[1].clone(), l[2].clone());
  158. match a1 {
  159. List(ref binds, _) | Vector(ref binds, _) => {
  160. for (b, e) in binds.iter().tuples() {
  161. match b {
  162. Sym(_) => {
  163. let _ = env_set(
  164. &env,
  165. b.clone(),
  166. eval(e.clone(), env.clone())?,
  167. );
  168. }
  169. _ => {
  170. return error("let* with non-Sym binding");
  171. }
  172. }
  173. }
  174. }
  175. _ => {
  176. return error("let* with non-List bindings");
  177. }
  178. };
  179. _ast = a2;
  180. continue 'tco;
  181. }
  182. Sym(ref a0sym) if a0sym == "let*" => {
  183. env = env_new(Some(env.clone()));
  184. let (a1, a2) = (l[1].clone(), l[2].clone());
  185. match a1 {
  186. List(ref binds, _) | Vector(ref binds, _) => {
  187. for (b, e) in binds.iter().tuples() {
  188. match b {
  189. Sym(_) => {
  190. let _ = env_set(
  191. &env,
  192. b.clone(),
  193. eval(e.clone(), env.clone())?,
  194. );
  195. }
  196. _ => {
  197. return error("let* with non-Sym binding");
  198. }
  199. }
  200. }
  201. }
  202. _ => {
  203. return error("let* with non-List bindings");
  204. }
  205. };
  206. _ast = a2;
  207. continue 'tco;
  208. }
  209. Sym(ref a0sym) if a0sym == "quote" => Ok(l[1].clone()),
  210. Sym(ref a0sym) if a0sym == "quasiquoteexpand" => Ok(quasiquote(&l[1])),
  211. Sym(ref a0sym) if a0sym == "quasiquote" => {
  212. _ast = quasiquote(&l[1]);
  213. continue 'tco;
  214. }
  215. Sym(ref a0sym) if a0sym == "defmacro!" => {
  216. let (a1, a2) = (l[1].clone(), l[2].clone());
  217. let r = eval(a2, env.clone())?;
  218. match r {
  219. MalFunc {
  220. eval,
  221. ast,
  222. env,
  223. params,
  224. ..
  225. } => Ok(env_set(
  226. &env,
  227. a1.clone(),
  228. MalFunc {
  229. eval,
  230. ast: ast.clone(),
  231. env: env.clone(),
  232. params: params.clone(),
  233. is_macro: true,
  234. meta: Rc::new(Nil),
  235. },
  236. )?),
  237. _ => error("set_macro on non-function"),
  238. }
  239. }
  240. Sym(ref a0sym) if a0sym == "macroexpand" => {
  241. match macroexpand(l[1].clone(), &env) {
  242. (_, Ok(new_ast)) => Ok(new_ast),
  243. (_, e) => return e,
  244. }
  245. }
  246. Sym(ref a0sym) if a0sym == "try*" => match eval(l[1].clone(), env.clone()) {
  247. Err(ref e) if l.len() >= 3 => {
  248. let exc = match e {
  249. ErrMalVal(mv) => mv.clone(),
  250. ErrString(s) => Str(s.to_string()),
  251. };
  252. match l[2].clone() {
  253. List(c, _) => {
  254. let catch_env = env_bind(
  255. Some(env.clone()),
  256. list!(vec![c[1].clone()]),
  257. vec![exc],
  258. )?;
  259. eval(c[2].clone(), catch_env)
  260. }
  261. _ => error("invalid catch block"),
  262. }
  263. }
  264. res => res,
  265. },
  266. Sym(ref a0sym) if a0sym == "do" => {
  267. match eval_ast(&list!(l[1..l.len() - 1].to_vec()), &env)? {
  268. List(_, _) => {
  269. _ast = l.last().unwrap_or(&Nil).clone();
  270. continue 'tco;
  271. }
  272. _ => error("invalid do form"),
  273. }
  274. }
  275. Sym(ref a0sym) if a0sym == "dotimes" => {
  276. match eval(l[1].clone(), env.clone())? {
  277. MalVal::Int(v) => {
  278. for _i in 0..v {
  279. _ast = eval_ast(&l[2], &env)?;
  280. }
  281. Ok(Nil)
  282. }
  283. _ => error("invalid args for dotimes"),
  284. }
  285. }
  286. Sym(ref a0sym) if a0sym == "if" => {
  287. let cond = eval(l[1].clone(), env.clone())?;
  288. match cond {
  289. Bool(false) | Nil if l.len() >= 4 => {
  290. _ast = l[3].clone();
  291. continue 'tco;
  292. }
  293. Bool(false) | Nil => Ok(Nil),
  294. _ if l.len() >= 3 => {
  295. _ast = l[2].clone();
  296. continue 'tco;
  297. }
  298. _ => Ok(Nil),
  299. }
  300. }
  301. Sym(ref a0sym) if a0sym == "fn*" => {
  302. let (a1, a2) = (l[1].clone(), l[2].clone());
  303. Ok(MalFunc {
  304. eval,
  305. ast: Rc::new(a2),
  306. env,
  307. params: Rc::new(a1),
  308. is_macro: false,
  309. meta: Rc::new(Nil),
  310. })
  311. }
  312. Sym(ref a0sym) if a0sym == "eval" => {
  313. _ast = eval(l[1].clone(), env.clone())?;
  314. while let Some(ref e) = env.clone().outer {
  315. env = e.clone();
  316. }
  317. continue 'tco;
  318. }
  319. Sym(ref a0sym) if a0sym == "setup" => {
  320. let a1 = l[1].clone();
  321. // todo
  322. _ast = eval(a1.clone(), env.clone())?;
  323. // let _pvk = setup(a1.clone(), env.clone())?;
  324. continue 'tco;
  325. }
  326. Sym(ref a0sym) if a0sym == "prove" => {
  327. let a1 = l[1].clone();
  328. eval(a1.clone(), env.clone())?;
  329. // TODO add debug param
  330. prove(a1.clone(), env.clone())
  331. }
  332. Sym(ref a0sym) if a0sym == "kill" => {
  333. error(&format!("KILL at: {:?}", _ast).to_string())
  334. }
  335. Sym(ref a0sym) if a0sym == "alloc-const" => {
  336. let start = Instant::now();
  337. let a1 = l[1].clone();
  338. let mut value = eval(l[2].clone(), env.clone())?;
  339. if let Func(_, _) = value {
  340. value = value.apply(vec![]).unwrap();
  341. }
  342. let result = eval(value.clone(), env.clone())?;
  343. let allocs = get_allocations(&env, "AllocationsConst");
  344. allocs.borrow_mut().insert(a1.pr_str(false), result.clone());
  345. if let Some(e) = &env.outer {
  346. env_set(&e, Sym("AllocationsConst".to_string()), Alloc(allocs))?;
  347. } else {
  348. env_set(&env, Sym("AllocationsConst".to_string()), Alloc(allocs))?;
  349. }
  350. println!("Alloc Const: {:?}", start.elapsed());
  351. Ok(result.clone())
  352. }
  353. Sym(ref a0sym) if a0sym == "alloc-input" => {
  354. let start = Instant::now();
  355. let a1 = l[1].clone();
  356. let mut value = eval(l[2].clone(), env.clone())?;
  357. if let Func(_, _) = value {
  358. value = value.apply(vec![]).unwrap();
  359. }
  360. let result = eval(value.clone(), env.clone())?;
  361. let allocs = get_allocations(&env, "AllocationsInput");
  362. allocs.borrow_mut().insert(a1.pr_str(false), result.clone());
  363. if let Some(e) = &env.outer {
  364. env_set(&e, Sym("AllocationsInput".to_string()), Alloc(allocs))?;
  365. } else {
  366. env_set(&env, Sym("AllocationsInput".to_string()), Alloc(allocs))?;
  367. }
  368. println!("Alloc Input: {:?}", start.elapsed());
  369. Ok(result.clone())
  370. }
  371. Sym(ref a0sym) if a0sym == "alloc" => {
  372. let start = Instant::now();
  373. let a1 = l[1].clone();
  374. let mut value = eval(l[2].clone(), env.clone())?;
  375. if let Func(_, _) = value {
  376. value = value.apply(vec![]).unwrap();
  377. }
  378. let result = eval(value.clone(), env.clone())?;
  379. let allocs = get_allocations(&env, "Allocations");
  380. allocs.borrow_mut().insert(a1.pr_str(false), result.clone());
  381. if let Some(e) = &env.outer {
  382. env_set(&e, Sym("Allocations".to_string()), Alloc(allocs))?;
  383. } else {
  384. env_set(&env, Sym("Allocations".to_string()), Alloc(allocs))?;
  385. }
  386. println!("Alloc:\t{:?}\t{:?}\t{:?}", value, result, start.elapsed());
  387. Ok(result.clone())
  388. }
  389. //Sym(ref a0sym) if a0sym == "verify" => {
  390. Sym(ref a0sym) if a0sym == "enforce" => {
  391. let mut left_vec = vec![];
  392. let mut right_vec = vec![];
  393. let mut out_vec = vec![];
  394. match l[1].clone() {
  395. List(v, _) | Vector(v, _) => {
  396. if v.to_vec().len() > 0 {
  397. // println!("{:?} {:?}", v, v.to_vec().len());
  398. if let List(_, _) = &v.to_vec()[0] {
  399. for ele in v.to_vec().iter() {
  400. if let List(ele_vec, _) = ele {
  401. left_vec.push((
  402. ele_vec[0].pr_str(false),
  403. ele_vec[1].pr_str(false),
  404. ));
  405. }
  406. }
  407. } else {
  408. if v.to_vec().len() == 1 {
  409. let result = eval(v.to_vec()[0].clone(), env.clone())?;
  410. if let List(val, _) = result {
  411. for ele in val.iter() {
  412. // println!("{:?}", ele);
  413. if let Vector(ele_vec, _) = ele {
  414. left_vec.push((
  415. ele_vec[0].pr_str(false),
  416. ele_vec[1].pr_str(false),
  417. ));
  418. }
  419. }
  420. }
  421. } else {
  422. left_vec.push((v[0].pr_str(false), v[1].pr_str(false)));
  423. }
  424. }
  425. }
  426. }
  427. _ => {}
  428. };
  429. match l[2].clone() {
  430. List(v, _) | Vector(v, _) => {
  431. if v.to_vec().len() > 0 {
  432. if let List(_, _) = &v.to_vec()[0] {
  433. for ele in v.to_vec().iter() {
  434. if let List(ele_vec, _) = ele {
  435. right_vec.push((
  436. ele_vec[0].pr_str(false),
  437. ele_vec[1].pr_str(false),
  438. ));
  439. }
  440. }
  441. } else {
  442. if v.to_vec().len() == 1 {
  443. let result = eval(v.to_vec()[0].clone(), env.clone())?;
  444. if let List(val, _) = result {
  445. for ele in val.iter() {
  446. // println!("{:?}", ele);
  447. if let Vector(ele_vec, _) = ele {
  448. right_vec.push((
  449. ele_vec[0].pr_str(false),
  450. ele_vec[1].pr_str(false),
  451. ));
  452. }
  453. }
  454. }
  455. } else {
  456. right_vec
  457. .push((v[0].pr_str(false), v[1].pr_str(false)));
  458. }
  459. }
  460. }
  461. }
  462. _ => {}
  463. };
  464. match l[3].clone() {
  465. List(v, _) | Vector(v, _) => {
  466. if v.to_vec().len() > 0 {
  467. if let List(_, _) = &v.to_vec()[0] {
  468. for ele in v.to_vec().iter() {
  469. if let List(ele_vec, _) = ele {
  470. out_vec.push((
  471. ele_vec[0].pr_str(false),
  472. ele_vec[1].pr_str(false),
  473. ));
  474. }
  475. }
  476. } else {
  477. if v.to_vec().len() == 1 {
  478. let result = eval(v.to_vec()[0].clone(), env.clone())?;
  479. if let List(val, _) = result {
  480. for ele in val.iter() {
  481. // println!("{:?}", ele);
  482. if let Vector(ele_vec, _) = ele {
  483. out_vec.push((
  484. ele_vec[0].pr_str(false),
  485. ele_vec[1].pr_str(false),
  486. ));
  487. }
  488. }
  489. }
  490. } else {
  491. out_vec.push((v[0].pr_str(false), v[1].pr_str(false)));
  492. }
  493. }
  494. }
  495. }
  496. _ => {}
  497. };
  498. let mut enforce_vec = get_enforce_allocs(&env).clone();
  499. let enforce = EnforceAllocation {
  500. idx: enforce_vec.len() + 1,
  501. left: left_vec,
  502. right: right_vec,
  503. output: out_vec,
  504. };
  505. enforce_vec.push(enforce);
  506. if let Some(e) = &env.outer {
  507. env_set(
  508. &e,
  509. Sym("AllocationsEnforce".to_string()),
  510. vector![vec![Enforce(Rc::new(enforce_vec))]],
  511. )?;
  512. } else {
  513. env_set(
  514. &env,
  515. Sym("AllocationsEnforce".to_string()),
  516. vector![vec![Enforce(Rc::new(enforce_vec))]],
  517. )?;
  518. }
  519. Ok(MalVal::Str("enforce-eof".to_string()))
  520. }
  521. _ => match eval_ast(&_ast, &env)? {
  522. List(ref el, _) => {
  523. let ref f = el[0].clone();
  524. let args = el[1..].to_vec();
  525. match f {
  526. Func(_, _) => f.apply(args),
  527. MalFunc {
  528. ast: mast,
  529. env: menv,
  530. params,
  531. ..
  532. } => {
  533. let a = &**mast;
  534. let p = &**params;
  535. env = env_bind(Some(menv.clone()), p.clone(), args)?;
  536. _ast = a.clone();
  537. continue 'tco;
  538. }
  539. _ => {
  540. // println!("{:?}", args);
  541. Ok(vector![el.to_vec()])
  542. //error("call non-function")
  543. }
  544. }
  545. }
  546. _ => error("expected a list"),
  547. },
  548. }
  549. }
  550. _ => eval_ast(&_ast, &env),
  551. };
  552. break;
  553. } // end 'tco loop
  554. // println!("debug eval \t {:?} \t {:?}", ast, start.elapsed());
  555. ret
  556. }
  557. pub fn get_enforce_allocs(env: &Env) -> Vec<EnforceAllocation> {
  558. if let Some(e) = &env.outer {
  559. get_enforce_allocs_nested(&e)
  560. } else {
  561. get_enforce_allocs_nested(&env)
  562. }
  563. }
  564. pub fn get_enforce_allocs_nested(env: &Env) -> Vec<EnforceAllocation> {
  565. match env_find(env, "AllocationsEnforce") {
  566. Some(e) => match env_get(&e, &Sym("AllocationsEnforce".to_string())) {
  567. Ok(f) => {
  568. if let Vector(val, _) = f {
  569. if let Enforce(ret) = &val[0] {
  570. ret.to_vec()
  571. } else {
  572. vec![]
  573. }
  574. } else {
  575. vec![]
  576. }
  577. }
  578. _ => vec![],
  579. },
  580. _ => vec![],
  581. }
  582. }
  583. pub fn get_allocations(env: &Env, key: &str) -> RefCell<HashMap<String, MalVal>> {
  584. if let Some(e) = &env.outer {
  585. get_allocations_nested(&e, key)
  586. } else {
  587. get_allocations_nested(&env, key)
  588. }
  589. }
  590. pub fn get_allocations_nested(env: &Env, key: &str) -> RefCell<HashMap<String, MalVal>> {
  591. let alloc_hm: RefCell<HashMap<String, MalVal>> = RefCell::new(HashMap::default());
  592. match env_find(env, key) {
  593. Some(e) => match env_get(&e, &Sym(key.to_string())) {
  594. Ok(f) => {
  595. if let MalVal::Alloc(allocs) = f {
  596. allocs
  597. } else {
  598. alloc_hm
  599. }
  600. }
  601. _ => alloc_hm,
  602. },
  603. _ => alloc_hm,
  604. }
  605. }
  606. pub fn setup(_ast: MalVal, _env: Env) -> Result<VerifyKeyParams, MalErr> {
  607. let start = Instant::now();
  608. let c = LispCircuit {
  609. params: HashMap::default(),
  610. allocs: HashMap::default(),
  611. alloc_inputs: HashMap::default(),
  612. constraints: Vec::new(),
  613. };
  614. let random_parameters =
  615. groth16::generate_random_parameters::<Bls12, _, _>(c, &mut OsRng).unwrap();
  616. let pvk = groth16::prepare_verifying_key(&random_parameters.vk);
  617. println!("Setup: [{:?}]", start.elapsed());
  618. Ok(VerifyKeyParams {
  619. verifying_key: pvk,
  620. random_params: random_parameters,
  621. })
  622. }
  623. pub fn prove(_ast: MalVal, env: Env) -> MalRet {
  624. let start = Instant::now();
  625. let allocs_input = get_allocations(&env, "AllocationsInput");
  626. let allocs = get_allocations(&env, "Allocations");
  627. let enforce_allocs = get_enforce_allocs(&env);
  628. let allocs_const = get_allocations(&env, "AllocationsConst");
  629. //setup
  630. let params = Some({
  631. let circuit = LispCircuit {
  632. params: allocs_const.borrow().clone(),
  633. allocs: allocs.borrow().clone(),
  634. alloc_inputs: allocs_input.borrow().clone(),
  635. constraints: enforce_allocs.clone(),
  636. };
  637. groth16::generate_random_parameters::<Bls12, _, _>(circuit, &mut OsRng)?
  638. });
  639. let verifying_key = Some(groth16::prepare_verifying_key(&params.as_ref().unwrap().vk));
  640. // prove
  641. let circuit = LispCircuit {
  642. params: allocs_const.borrow().clone(),
  643. allocs: allocs.borrow().clone(),
  644. alloc_inputs: allocs_input.borrow().clone(),
  645. constraints: enforce_allocs.clone(),
  646. };
  647. let proof = groth16::create_random_proof(circuit, params.as_ref().unwrap(), &mut OsRng)?;
  648. let mut vec_input = vec![];
  649. for (_k, val) in allocs_input.borrow_mut().iter() {
  650. match val {
  651. MalVal::Str(v) => {
  652. vec_input.push(bls12_381::Scalar::from_string(&v.to_string()));
  653. }
  654. MalVal::ZKScalar(v) => {
  655. vec_input.push(bls12_381::Scalar::from(*v));
  656. }
  657. _ => {}
  658. };
  659. }
  660. println!("groth16::create_random_proof: {:?}", start.elapsed());
  661. // verification process
  662. let start = Instant::now();
  663. let result = groth16::verify_proof(verifying_key.as_ref().unwrap(), &proof, &vec_input);
  664. println!("groth16::verify_proof: {:?}", start.elapsed());
  665. println!("vec public {:?}", vec_input);
  666. println!("result {:?}", result);
  667. Ok(MalVal::Nil)
  668. }
  669. pub fn verify(_ast: &MalVal) -> MalRet {
  670. let _public_input = vec![bls12_381::Scalar::from(27)];
  671. let start = Instant::now();
  672. println!("Verify: [{:?}]", start.elapsed());
  673. Ok(MalVal::Nil)
  674. }
  675. // print
  676. fn print(ast: &MalVal) -> String {
  677. ast.pr_str(true)
  678. }
  679. fn rep(str: &str, env: &Env) -> Result<String, MalErr> {
  680. let ast = read(str)?;
  681. let exp = eval(ast, env.clone())?;
  682. Ok(print(&exp))
  683. }
  684. fn main() -> Result<(), ()> {
  685. let matches = clap_app!(zklisp =>
  686. (version: "0.1.0")
  687. (author: "Dark Renaissance")
  688. (about: "A Lisp Interpreter for Zero Knowledge Virtual Machine")
  689. (@subcommand load =>
  690. (about: "Load the file into the interpreter")
  691. (@arg FILE: +required "Lisp Contract filename")
  692. )
  693. )
  694. .get_matches();
  695. // CombinedLogger::init(vec![TermLogger::new(
  696. // LevelFilter::Debug,
  697. // Config::default(),
  698. // TerminalMode::Mixed,
  699. // )
  700. // .unwrap()])
  701. // .unwrap();
  702. match matches.subcommand() {
  703. Some(("load", matches)) => {
  704. let file: String = matches.value_of("FILE").unwrap().parse().unwrap();
  705. repl_load(file)?;
  706. }
  707. _ => {
  708. eprintln!("error: Invalid subcommand invoked");
  709. std::process::exit(-1);
  710. }
  711. }
  712. Ok(())
  713. }
  714. fn repl_load(file: String) -> Result<(), ()> {
  715. let start = Instant::now();
  716. let repl_env = env_new(None);
  717. for (k, v) in core::ns() {
  718. env_sets(&repl_env, k, v);
  719. }
  720. let _ = rep("(def! not (fn* (a) (if a false true)))", &repl_env);
  721. let _ = rep(
  722. "(def! load-file (fn* (f) (eval (read-string (str \"(do \" (slurp f) \"\nnil)\")))))",
  723. &repl_env,
  724. );
  725. match rep(&format!("(load-file \"{}\")", file), &repl_env) {
  726. Ok(_) => {
  727. println!("lisp end \t {:?}", start.elapsed());
  728. std::process::exit(0)
  729. }
  730. Err(e) => {
  731. println!("Error: {}", format_error(e));
  732. std::process::exit(1);
  733. }
  734. }
  735. }
  736. #[cfg(test)]
  737. mod tests {
  738. #[test]
  739. fn it_works() {
  740. assert_eq!(2 + 2, 4);
  741. }
  742. }