Actually added the nasm/ld steps in the binary itself

master
Wynd 2024-10-27 11:05:10 +02:00
parent 5d7231ae8c
commit 7c683ec2fe
3 changed files with 62 additions and 12 deletions

3
.gitignore vendored
View File

@ -2,3 +2,6 @@
# asm gen testing # asm gen testing
/asm /asm
# output
/out

View File

@ -6,21 +6,17 @@ pub fn generate(tokens: Vec<Token>) -> String {
let mut output = String::new(); let mut output = String::new();
// reserving mem // reserving mem
// global start label
// create the pointer for our data
output.push_str( output.push_str(
"section .bss\n\ "section .bss\n\
data: resb 65536\n", data: resb 65536\n\
); global _start\n\
// global start label
output.push_str(
"global _start\n\
section .text\n\ section .text\n\
_start:\n", _start:\n\
mov rdx, data\n",
); );
// create the pointer for our data
output.push_str("mov rdx, data\n");
let mut loops = 0; let mut loops = 0;
let mut stack: VecDeque<usize> = VecDeque::new(); let mut stack: VecDeque<usize> = VecDeque::new();
for token in tokens { for token in tokens {

View File

@ -1,4 +1,5 @@
use std::{fs, io::Write, path::PathBuf}; use core::panic;
use std::{env, fs, io::Write, path::PathBuf, process};
use crate::{asm_gen, tokenizer}; use crate::{asm_gen, tokenizer};
@ -6,7 +7,57 @@ pub fn compile(program: Vec<u8>, name: String) {
let tokens = tokenizer::tokenize(program); let tokens = tokenizer::tokenize(program);
let asm = asm_gen::generate(tokens); let asm = asm_gen::generate(tokens);
let path: PathBuf = [".", &format!("./{name}.asm")].iter().collect(); let out_path: PathBuf = [".", "out"].iter().collect();
fs::DirBuilder::new()
.recursive(true)
.create(out_path)
.unwrap();
let path: PathBuf = [".", "out", &format!("{name}.asm")].iter().collect();
let mut file = fs::File::create(path).unwrap(); let mut file = fs::File::create(path).unwrap();
file.write_all(asm.as_bytes()).unwrap(); file.write_all(asm.as_bytes()).unwrap();
if !is_program_in_path("nasm") {
panic!("No nasm binary found in PATH");
}
process::Command::new("nasm")
.args(["-felf64", &format!("./out/{name}.asm")])
.output()
.expect("failed compile step");
if !is_program_in_path("ld") {
panic!("No ld binary found in PATH");
}
process::Command::new("ld")
.args([
"-s",
"-o",
&format!("./out/{name}"),
&format!("./out/{name}.o"),
])
.output()
.expect("failed linking step");
process::Command::new("rm")
.args([
"-r",
&format!("./out/{name}.asm"),
&format!("./out/{name}.o"),
])
.output()
.expect("failed removing artifcats step");
}
fn is_program_in_path(program: &str) -> bool {
if let Ok(path) = env::var("PATH") {
for p in path.split(":") {
let p_str = format!("{}/{}", p, program);
if fs::metadata(p_str).is_ok() {
return true;
}
}
}
false
} }