parent
36aeb10da9
commit
c8062f7843
@ -1 +1,80 @@
|
||||
fn main() {}
|
||||
use std::{
|
||||
collections::HashMap,
|
||||
io::{Write, stdin, stdout},
|
||||
rc::Rc,
|
||||
};
|
||||
|
||||
use stlc_type_inference::{infer_type, is_ident, parse, parse_string, parse_type};
|
||||
|
||||
macro_rules! repl_err {
|
||||
($err:expr) => {{
|
||||
println!($err);
|
||||
print!("> ");
|
||||
stdout().flush().unwrap();
|
||||
continue;
|
||||
}};
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let mut gamma = Rc::new(HashMap::new());
|
||||
print!("> ");
|
||||
stdout().flush().unwrap();
|
||||
for line in stdin().lines() {
|
||||
let line = line.unwrap();
|
||||
if let Some(tl) = line.strip_prefix(':') {
|
||||
if let Some((cmd, expr)) = tl.split_once(' ') {
|
||||
match cmd {
|
||||
"t" => match parse(expr) {
|
||||
Ok(a) => match infer_type(gamma.clone(), a) {
|
||||
Ok(t) => println!("{t}"),
|
||||
Err(e) => repl_err!("Could not infer type {e:?}"),
|
||||
},
|
||||
Err(e) => repl_err!("Parse error {e:?}"),
|
||||
},
|
||||
"ctx" => {
|
||||
if let Some((ident, typ)) = expr.split_once(':') {
|
||||
let ident: String =
|
||||
ident.chars().filter(|c| !c.is_whitespace()).collect();
|
||||
if !is_ident(&ident) {
|
||||
repl_err!("{ident} is not a valid identifer");
|
||||
}
|
||||
let typ_ast = match parse_string(typ) {
|
||||
Ok(t) => t,
|
||||
Err(e) => repl_err!("Could not parse the type: {e:?}"),
|
||||
};
|
||||
|
||||
let typ = match parse_type(&typ_ast) {
|
||||
Ok(t) => t,
|
||||
Err(e) => repl_err!("type could not be parsed {e:?}"),
|
||||
};
|
||||
|
||||
println!("Added {ident} with type {typ} to the context");
|
||||
Rc::make_mut(&mut gamma).insert(ident, typ);
|
||||
}
|
||||
}
|
||||
c => println!("Unknown command {c}"),
|
||||
}
|
||||
} else {
|
||||
match tl {
|
||||
"t" => println!(":t need an expr as an argument"),
|
||||
"ctx" => println!(":ctx needs an ident and a type as argument"),
|
||||
c => println!("Unknown command {c}"),
|
||||
}
|
||||
}
|
||||
} else {
|
||||
let ast = match parse(&line) {
|
||||
Ok(a) => a,
|
||||
Err(e) => repl_err!("Parse error {e:?}"),
|
||||
};
|
||||
|
||||
let typ = match infer_type(gamma.clone(), ast.clone()) {
|
||||
Ok(t) => t,
|
||||
Err(e) => repl_err!("Could not infer type {e:?}"),
|
||||
};
|
||||
let ast = ast.beta_reduce();
|
||||
println!("{ast} : {typ}")
|
||||
}
|
||||
print!("> ");
|
||||
stdout().flush().unwrap();
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in new issue