1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128
use std::io::{self, BufRead, Write};
use crate::{lexer::Lexer, parser::Parser, token::Kind};
use super::{bytecode::compiler::Compiler, vm::VM};
const PROMPT: &str = "-> ";
pub fn start() {
let mut buf = String::new();
let mut stdin = io::stdin().lock(); // We get `Stdin` here.
let debug_lexer = false;
let debug_parser = false;
let show_error = true;
loop {
io::stdout().lock().write_all(PROMPT.as_bytes()).unwrap();
io::stdout().flush().unwrap();
match stdin.read_line(&mut buf) {
Ok(_) => {
let lexer = Lexer::new(buf.clone());
let mut cloned_lexer = lexer.clone();
if debug_lexer {
loop {
let cur_token = cloned_lexer.next_token();
println!("Debug Output (Lexer) >> {:?}", cur_token);
if cur_token.kind == Kind::EOF {
break;
}
}
}
let mut parser = Parser::new(lexer);
let program = parser.parse();
if debug_parser {
println!("Debug Output (Parser) >> {:?}", program);
}
if let Ok(program) = program {
let comp_rst = Compiler::create();
if comp_rst.is_err() {
println!(
"Error while compiler creation {:?}",
comp_rst
);
continue;
}
let mut compiler = comp_rst.unwrap();
let comp = compiler.compile(program);
if comp.is_err() {
println!("Error while compiler creation {:?}", comp);
continue;
}
let bytecode_rst = compiler.bytecode();
match bytecode_rst {
Ok(_) => (),
Err(err) => {
println!("Error while taking bytecode {:?}", err);
continue;
}
}
let mut vm =
unsafe { VM::new(bytecode_rst.unwrap_unchecked()) };
buf.clear();
println!("Intitial state:{}", vm);
println!("Commands:");
println!("\tpressing enter: excute next cycle.");
println!("\t exit: terminate");
loop {
match stdin.read_line(&mut buf) {
Ok(_) => {
// HACK: clear screen
println!("\n\n\n\n\n\n\n\n\n");
println!("\n\n\n\n\n\n\n\n\n");
println!("\n\n\n\n\n\n\n\n\n");
println!("\n\n\n\n\n\n\n\n\n");
if buf == "exit" {
break;
}
if !vm.is_runable() {
break;
}
if let Err(e) = vm.run_single() {
eprintln!("{:?}", e);
}
println!("{}", vm);
}
Err(err) => {
println!("Error occured during reading stdin");
println!("{:?}", err);
}
}
}
println!("VM Terminated.");
println!("Please give new input.");
} else if show_error {
println!("!!!> ERROR OCCURED <!!!");
for errs in program.err().unwrap() {
println!(">> ERROR DETAIL ");
for err in errs {
println!("Pos>> {:?}", err.as_ref().position());
println!("Detail>> {} ", err.as_ref().detail());
}
}
}
buf.clear();
}
Err(err) => {
println!("Error occured during reading stdin");
println!("{:?}", err);
return;
}
}
}
}