interp.rs 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330
  1. use crate::ast::*;
  2. use rand::Rng;
  3. use std::collections::HashMap;
  4. use std::fmt;
  5. macro_rules! bail {
  6. ($fmt:expr) => { return Err(Error { message: format!($fmt), }) };
  7. ($fmt:expr, $($e:expr),*) => { return Err(Error { message: format!($fmt, $($e),*), }) }
  8. }
  9. #[derive(Debug, Clone)]
  10. pub enum Value {
  11. Lit(Literal),
  12. Tup(Vec<Value>),
  13. Builtin(&'static BuiltinFunc),
  14. Nil,
  15. }
  16. impl Value {
  17. fn as_num(&self) -> Result<i64, Error> {
  18. match self {
  19. Value::Lit(Literal::Num(n)) => Ok(*n),
  20. _ => self.with_str(|s| bail!("Expected number, got {}", s)),
  21. }
  22. }
  23. fn as_str(&self) -> Result<&str, Error> {
  24. match self {
  25. Value::Lit(Literal::Str(s)) => Ok(s),
  26. _ => self.with_str(|s| bail!("Expected string, got {}", s)),
  27. }
  28. }
  29. fn with_str<U>(&self, f: impl FnOnce(&str) -> U) -> U {
  30. match self {
  31. Value::Nil => f(""),
  32. Value::Lit(Literal::Str(s)) => f(s),
  33. Value::Lit(Literal::Atom(s)) => f(&format!("{:?}", s)),
  34. Value::Lit(Literal::Num(n)) => f(&format!("{}", n)),
  35. Value::Tup(values) => {
  36. let mut buf = String::new();
  37. buf.push('<');
  38. for (i, val) in values.iter().enumerate() {
  39. if i > 0 {
  40. buf.push_str(", ");
  41. }
  42. buf.push_str(&val.to_string());
  43. }
  44. buf.push('>');
  45. f(&buf)
  46. }
  47. Value::Builtin(func) => f(&format!("#<builtin {}>", func.name)),
  48. }
  49. }
  50. }
  51. impl fmt::Display for Value {
  52. fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
  53. self.with_str(|s| write!(f, "{}", s))
  54. }
  55. }
  56. pub struct BuiltinFunc {
  57. name: &'static str,
  58. callback: &'static dyn Fn(&mut State, &Expr) -> Result<Value, Error>,
  59. }
  60. #[derive(Debug)]
  61. pub struct Error {
  62. message: String,
  63. }
  64. impl From<lalrpop_util::ParseError<usize, crate::lexer::Token<'_>, crate::lexer::LexerError>>
  65. for Error
  66. {
  67. fn from(
  68. err: lalrpop_util::ParseError<usize, crate::lexer::Token<'_>, crate::lexer::LexerError>,
  69. ) -> Error {
  70. Error {
  71. message: format!("{:?}", err),
  72. }
  73. }
  74. }
  75. impl fmt::Display for Error {
  76. fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
  77. write!(fmt, "{}", self.message)
  78. }
  79. }
  80. impl std::error::Error for Error {}
  81. const BUILTINS: &[BuiltinFunc] = &[
  82. BuiltinFunc {
  83. name: "rep",
  84. callback: &|state: &mut State, expr: &Expr| -> Result<Value, Error> {
  85. let args = match expr {
  86. Expr::Tup(tup) => tup,
  87. _ => bail!("`rep`: expected tuple"),
  88. };
  89. if args.len() != 2 {
  90. bail!("`rep`: expected two arguments, got {}", args.len())
  91. }
  92. let num = state.eval(&args[0])?.as_num()?;
  93. let rep = (0..num).map(|_| args[1].clone()).collect();
  94. state.eval(&Expr::Cat(rep))
  95. },
  96. },
  97. BuiltinFunc {
  98. name: "length",
  99. callback: &|_state: &mut State, expr: &Expr| -> Result<Value, Error> {
  100. let args = match expr {
  101. Expr::Tup(tup) => tup,
  102. _ => bail!("`length`: expected tuple"),
  103. };
  104. Ok(Value::Lit(Literal::Num(args.len() as i64)))
  105. },
  106. },
  107. BuiltinFunc {
  108. name: "to-upper",
  109. callback: &|state: &mut State, expr: &Expr| -> Result<Value, Error> {
  110. let s = state.eval(expr)?;
  111. Ok(Value::Lit(Literal::Str(s.as_str()?.to_uppercase())))
  112. },
  113. },
  114. BuiltinFunc {
  115. name: "to-lower",
  116. callback: &|state: &mut State, expr: &Expr| -> Result<Value, Error> {
  117. let s = state.eval(expr)?;
  118. Ok(Value::Lit(Literal::Str(s.as_str()?.to_lowercase())))
  119. },
  120. },
  121. ];
  122. impl fmt::Debug for BuiltinFunc {
  123. fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
  124. writeln!(fmt, "BuiltinFunc {{ name: {:?}, ... }}", self.name)
  125. }
  126. }
  127. enum NamedItem {
  128. Expr(Expr),
  129. Value(Value),
  130. Builtin(&'static BuiltinFunc),
  131. }
  132. pub struct State {
  133. ast: ASTArena,
  134. scope: HashMap<Name, NamedItem>,
  135. rand: rand::rngs::ThreadRng,
  136. parser: crate::grammar::StmtsParser,
  137. }
  138. impl Default for State {
  139. fn default() -> State {
  140. Self::new()
  141. }
  142. }
  143. impl State {
  144. pub fn new() -> State {
  145. let mut s = State {
  146. scope: HashMap::new(),
  147. rand: rand::thread_rng(),
  148. parser: crate::grammar::StmtsParser::new(),
  149. ast: ASTArena::new(),
  150. };
  151. for builtin in BUILTINS {
  152. let sym = s.ast.add_string(builtin.name);
  153. s.scope.insert(sym, NamedItem::Builtin(builtin));
  154. }
  155. s
  156. }
  157. pub fn run(&mut self, src: &str) -> Result<(), Error> {
  158. let lexed = crate::lexer::tokens(src);
  159. let stmts = self.parser.parse(&mut self.ast, lexed)?;
  160. for stmt in stmts {
  161. self.execute(&stmt)?;
  162. }
  163. Ok(())
  164. }
  165. pub fn run_repl(&mut self, src: &str) -> Result<(), Error> {
  166. let lexed = crate::lexer::tokens(src);
  167. let stmts = match self.parser.parse(&mut self.ast, lexed) {
  168. Ok(stmts) => stmts,
  169. Err(err) => {
  170. let with_puts = format!("puts {}", src);
  171. let lexed = crate::lexer::tokens(&with_puts);
  172. if let Ok(stmts) = self.parser.parse(&mut self.ast, lexed) {
  173. stmts
  174. } else {
  175. return Err(err.into());
  176. }
  177. }
  178. };
  179. for stmt in stmts {
  180. self.execute(&stmt)?;
  181. }
  182. Ok(())
  183. }
  184. pub fn autocomplete(&self, fragment: &str, at_beginning: bool) -> Vec<String> {
  185. let mut possibilities = Vec::new();
  186. for name in self.scope.keys() {
  187. if self.ast[*name].starts_with(fragment) {
  188. possibilities.push(self.ast[*name].to_string());
  189. }
  190. }
  191. if at_beginning && "puts".starts_with(fragment) {
  192. possibilities.push("puts ".to_owned());
  193. }
  194. possibilities
  195. }
  196. pub fn execute(&mut self, stmt: &Stmt) -> Result<(), Error> {
  197. match stmt {
  198. Stmt::Puts(expr) => {
  199. let val = self.eval(expr)?;
  200. println!("{}", val.to_string());
  201. }
  202. Stmt::Fix(name) => {
  203. let expr = match self.scope.get(name) {
  204. None => bail!("no such thing: {:?}", name),
  205. Some(NamedItem::Expr(e)) => e.clone(),
  206. // if it's not an expr, then our work here is done
  207. _ => return Ok(()),
  208. };
  209. let val = self.eval(&expr)?;
  210. self.scope.insert(*name, NamedItem::Value(val));
  211. }
  212. Stmt::Assn(fixed, name, expr) => {
  213. if *fixed {
  214. let val = self.eval(expr)?;
  215. self.scope.insert(*name, NamedItem::Value(val));
  216. } else {
  217. self.scope.insert(*name, NamedItem::Expr(expr.clone()));
  218. }
  219. }
  220. Stmt::LitAssn(fixed, name, strs) => {
  221. if *fixed {
  222. let choice = &strs[self.rand.gen_range(0..strs.len())];
  223. self.scope.insert(
  224. *name,
  225. NamedItem::Value(Value::Lit(Literal::Str(choice.clone()))),
  226. );
  227. return Ok(());
  228. }
  229. let choices = strs
  230. .iter()
  231. .map(|s| Choice {
  232. weight: None,
  233. value: Expr::Lit(Literal::Str(s.clone())),
  234. })
  235. .collect();
  236. self.scope
  237. .insert(*name, NamedItem::Expr(Expr::Chc(choices)));
  238. }
  239. }
  240. Ok(())
  241. }
  242. fn eval(&mut self, expr: &Expr) -> Result<Value, Error> {
  243. match expr {
  244. Expr::Lit(l) => Ok(Value::Lit(l.clone())),
  245. Expr::Nil => Ok(Value::Nil),
  246. Expr::Var(v) => {
  247. let e = match self.scope.get(v) {
  248. Some(NamedItem::Expr(e)) => e.clone(),
  249. Some(NamedItem::Value(v)) => return Ok(v.clone()),
  250. Some(NamedItem::Builtin(b)) => return Ok(Value::Builtin(b)),
  251. None => bail!("no such thing: {:?}", v),
  252. };
  253. self.eval(&e)
  254. }
  255. Expr::Cat(cat) => {
  256. if cat.len() == 1 {
  257. self.eval(&cat[0])
  258. } else {
  259. let mut buf = String::new();
  260. for expr in cat {
  261. let val = self.eval(expr)?;
  262. buf.push_str(&val.to_string());
  263. }
  264. Ok(Value::Lit(Literal::Str(buf)))
  265. }
  266. }
  267. Expr::Chc(choices) => {
  268. if choices.len() == 1 {
  269. self.eval(&choices[0].value)
  270. } else {
  271. self.choose(choices)
  272. }
  273. }
  274. Expr::Tup(values) => Ok(Value::Tup(
  275. values
  276. .iter()
  277. .map(|v| self.eval(v))
  278. .collect::<Result<Vec<Value>, Error>>()?,
  279. )),
  280. Expr::Ap(fun, arg) => match self.eval(fun)? {
  281. Value::Builtin(builtin) => (builtin.callback)(self, arg),
  282. _ => bail!("bad function: {:?}", fun),
  283. },
  284. Expr::Range(from, to) => {
  285. let from = self.eval(from)?.as_num()?;
  286. let to = self.eval(to)?.as_num()?;
  287. Ok(Value::Lit(Literal::Num(self.rand.gen_range(from..=to))))
  288. }
  289. _ => bail!("unimplemented: {:?}", expr),
  290. }
  291. }
  292. fn choose(&mut self, choices: &[Choice]) -> Result<Value, Error> {
  293. let max = choices.iter().map(Choice::weight).sum();
  294. let mut choice = self.rand.gen_range(0..max);
  295. for ch in choices {
  296. if choice < ch.weight() {
  297. return self.eval(&ch.value);
  298. }
  299. choice -= ch.weight();
  300. }
  301. bail!("unreachable")
  302. }
  303. }