Brainfuck compiler
// Brain86 | |
// This program compiles well-formed brainfuck code to x86 assembler. | |
// Requires rust nightly, nasm, and ld | |
// | |
// An interesting sample program: | |
// https://raw.githubusercontent.com/JustAPerson/brainrust/master/tests/mandelbrot.bf | |
// | |
// $ rustc brain86.rs | |
// $ cat mandelbrot.bf | ./brain86 > mandelbrot.s | |
// $ nasm -f elf64 mandelbrot.s | |
// $ ld mandelbrot.o -o mandelbrot | |
// $ ./mandelbrot | |
#![feature(io)] | |
use std::io::Read; | |
fn main() { | |
let mut labels = Vec::new(); | |
let mut label_counter = 0; | |
println!("section .bss"); | |
println!(" stack: resb 30000"); | |
println!("section .text"); | |
println!(" global _start"); | |
println!("_start:"); | |
println!(" xor esi, esi"); // esi will be the stack pointer | |
for char in std::io::stdin().chars() { | |
match char.unwrap() { | |
'+' => { | |
println!(" add byte [stack+esi], 1"); | |
}, | |
'-' => { | |
println!(" sub byte [stack+esi], 1"); | |
}, | |
'>' => { println!(" add esi, 1"); }, | |
'<' => { println!(" sub esi, 1"); }, | |
'[' => { | |
let label = format!("loop{}", label_counter); | |
label_counter += 1; | |
labels.push(label.clone()); | |
println!(".{}_start:", &label); | |
println!(" cmp byte [stack+esi], 0"); | |
println!(" jz .{}_end", &label); | |
}, | |
']' => { | |
let label = labels.pop().unwrap(); | |
println!(" jmp .{}_start", &label); | |
println!(".{}_end:", &label); | |
}, | |
'.' => { | |
println!(" mov edx, 1"); | |
println!(" lea ecx, [stack+esi]"); | |
println!(" mov ebx, 1"); // stdout | |
println!(" mov eax, 4"); // sys_write | |
println!(" int 0x80"); | |
}, | |
',' => { | |
println!(" mov edx, 1"); | |
println!(" lea ecx, [stack+esi]"); | |
println!(" mov ebx, 0"); // stdin | |
println!(" mov eax, 3"); // sys_read | |
println!(" int 0x80"); | |
}, | |
_ => { }, | |
} | |
} | |
println!(" mov ebx, 0"); // exit code = 0 | |
println!(" mov eax, 1"); // sys_exit | |
println!(" int 0x80"); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment