79 lines
1.9 KiB
Rust
79 lines
1.9 KiB
Rust
use anyhow::Result;
|
|
use clap::{Parser, Subcommand};
|
|
use std::fs;
|
|
|
|
use henceforth::*;
|
|
|
|
#[derive(Debug, Parser)]
|
|
#[clap(author, version, about, long_about = None)]
|
|
struct Cli {
|
|
#[clap(subcommand)]
|
|
commands: Commands,
|
|
}
|
|
|
|
#[derive(Debug, Subcommand)]
|
|
enum Commands {
|
|
#[clap(about = "Lexes source code and outputs tokens")]
|
|
Lex {
|
|
#[clap(value_parser)]
|
|
src: String,
|
|
},
|
|
#[clap(about = "Parses source code and outputs AST")]
|
|
Parse {
|
|
#[clap(value_parser)]
|
|
src: String,
|
|
},
|
|
#[clap(about = "Compiles assembly from source code")]
|
|
Compile {
|
|
#[clap(value_parser)]
|
|
src: String,
|
|
#[clap(value_parser)]
|
|
out: Option<String>,
|
|
#[clap(short, long, action)]
|
|
optimize: Option<bool>,
|
|
#[clap(long, action)]
|
|
dump: bool,
|
|
},
|
|
}
|
|
|
|
fn main() -> Result<()> {
|
|
let args = Cli::parse();
|
|
match args.commands {
|
|
Commands::Lex { src } => {
|
|
let source = fs::read_to_string(src)?;
|
|
let tokens = lexer::lex(&source)?;
|
|
println!("{:#?}", tokens);
|
|
|
|
Ok(())
|
|
}
|
|
Commands::Parse { src } => {
|
|
let source = fs::read_to_string(src)?;
|
|
let tokens = lexer::lex(&source)?;
|
|
let body = parser::parse(tokens)?;
|
|
println!("{:#?}", body);
|
|
|
|
Ok(())
|
|
}
|
|
Commands::Compile {
|
|
src,
|
|
out,
|
|
optimize,
|
|
dump,
|
|
} => {
|
|
let source = fs::read_to_string(&src)?;
|
|
let tokens = lexer::lex(&source)?;
|
|
let ast = parser::parse(tokens)?;
|
|
let assembly = format!("{}\n", compiler::compile(ast, optimize.unwrap_or(true))?);
|
|
|
|
if dump {
|
|
print!("{}", assembly);
|
|
}
|
|
if let Some(x) = out {
|
|
fs::write(x, &assembly)?;
|
|
}
|
|
|
|
Ok(())
|
|
}
|
|
}
|
|
}
|