From bf7f44e776b89fb8f0d6d1adfeab87a742f7f833 Mon Sep 17 00:00:00 2001 From: MCorange Date: Sat, 21 Dec 2024 23:08:29 +0200 Subject: [PATCH] Dehardcode main function, impemented basic cli --- src/cli.rs | 36 ++++++++++++++++++++++++++++++++++++ src/main.rs | 40 ++++++++++++++++++++++++++++++++++------ 2 files changed, 70 insertions(+), 6 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index b28b04f..3624277 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -1,3 +1,39 @@ +use clap::{error::ErrorKind, CommandFactory}; + +use crate::logger::Level; +#[derive(Debug, clap::Parser)] +pub struct CliArgs { + /// Output more info, will get overwritten if -q|--quiet is specified + #[arg(long, short)] + verbose: bool, + /// Output nothing, except errors, will overwrite -v|--verbose + #[arg(long, short)] + quiet: bool, + /// Output file + #[arg(long, short, default_value="a.out")] + pub output: String, + /// All input files + #[clap(num_args = 1..)] + pub input: Vec +} +impl CliArgs { + pub fn set_log_level(&self) { + if self.quiet { + unsafe { + crate::logger::LEVEL = Level::Error; + } + } else if self.verbose { + unsafe { + crate::logger::LEVEL = Level::Debug; + } + } + } + pub fn validate(&self) { + if self.input.len() < 1 { + CliArgs::command().error(ErrorKind::TooFewValues, "at least one value is required for '' but none was supplied").exit(); + } + } +} diff --git a/src/main.rs b/src/main.rs index 077467a..1b5d639 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,11 +1,39 @@ +use std::{path::PathBuf, process::ExitCode}; + +use clap::Parser; +// Importing logger here too cause the logger macros dont work outside the mclanc lib +mod logger; -fn main() -> anyhow::Result<()> { - let data = std::fs::read_to_string("test.mcl").unwrap(); - let tokens = mclangc::tokeniser::tokenise(&data, "test.mcl")?; - let prog = mclangc::parser::parse_program(tokens)?; - mclangc::validator::validate_code(&prog); - Ok(()) +fn main() -> ExitCode { + let cli = mclangc::cli::CliArgs::parse(); + cli.set_log_level(); + cli.validate(); + for file in &cli.input { + let fp = PathBuf::from(file); + if !fp.exists() { + error!("File {fp:?} doesnt exits, exiting"); + return ExitCode::FAILURE; + } + + let data = std::fs::read_to_string(fp).unwrap(); + info!("Tokenising {file}"); + let Ok(tokens) = mclangc::tokeniser::tokenise(&data, &file) else { + error!("Failed to tokenise file, exiting"); + return ExitCode::FAILURE; + }; + info!("Parsing {file}"); + let Ok(prog) = mclangc::parser::parse_program(tokens) else { + error!("Failed to parse file, exiting"); + return ExitCode::FAILURE; + }; + info!("Validating {file}"); + let Ok(validated) = mclangc::validator::validate_code(&prog) else { + error!("Failed to validate file, exiting"); + return ExitCode::FAILURE; + }; + } + ExitCode::SUCCESS }