Beginning

This commit is contained in:
vanten-s 2025-09-08 16:47:18 +02:00
parent d9bea76666
commit d81272f085
4 changed files with 106 additions and 135 deletions

View file

@ -1,11 +1,6 @@
use std::{collections::HashMap, ops::AddAssign}; use std::{iter::Sum, ops::{Add, AddAssign}};
use color_eyre::eyre::Error; use crate::ir::{Command, IRepr};
use crate::{
lexer::Keyword,
parser::{LispAtom, SExpression},
};
#[derive(Debug, Clone, Copy, PartialEq, Eq)] #[derive(Debug, Clone, Copy, PartialEq, Eq)]
enum InstructionFrom { enum InstructionFrom {
@ -40,144 +35,124 @@ enum InstructionTo {
RegisterSP, RegisterSP,
RegisterSB, RegisterSB,
IncSP,
DecSP,
} }
#[derive(Debug, Clone, Copy, PartialEq, Eq)] #[derive(Debug, Clone, Copy, PartialEq, Eq)]
struct Command { struct Instruction {
data_from: InstructionFrom, from: InstructionFrom,
data_to: InstructionTo, to: InstructionTo,
data: i8, value: i8,
} }
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
pub struct Scope { pub struct Code {
variables: Vec<String>, instructions: Vec<Instruction>,
stack_position: usize,
} }
#[derive(Debug, Clone, PartialEq, Eq)] impl From<IRepr> for Code {
pub struct EightBitLang { fn from(value: IRepr) -> Self {
instructions: Vec<Command>, value.commands.into_iter().map(|x| Code::from(x)).sum()
labels: Option<HashMap<String, usize>>, }
} }
pub trait GenerateCode { impl From<Command> for Code {
fn to_code(self, codegen_scope: &mut Scope) -> Result<EightBitLang, Self::Error> fn from(value: Command) -> Self {
where use Instruction as I;
Self: Sized; use InstructionFrom as IF;
use InstructionTo as IT;
type Error; match value {
} Command::PopR1 => vec![
I::new(IF::RegisterSP, IT::RamAddressLower, 0x00),
impl GenerateCode for SExpression { I::new(IF::RAM, IT::RegisterA, 0x00),
fn to_code(self, codegen_scope: &mut Scope) -> Result<EightBitLang, Self::Error> { I::new(IF::ROM, IT::DecSP, 0x00),
match self { ],
SExpression::Atom(a) => a.to_code(codegen_scope), Command::PopR2 => vec![
I::new(IF::RegisterSP, IT::RamAddressLower, 0x00),
I::new(IF::RAM, IT::RegisterB, 0x00),
I::new(IF::ROM, IT::DecSP, 0x00),
],
Command::PushInt(val) => vec![
I::new(IF::RegisterSP, IT::RamAddressLower, 0x00),
I::new(IF::ROM, IT::RAM, val as i8),
I::new(IF::ROM, IT::IncSP, 0x00),
],
Command::PushSum => vec![
I::new(IF::RegisterSP, IT::RamAddressLower, 0x00),
I::new(IF::ALU, IT::RAM, 0x00),
I::new(IF::ROM, IT::IncSP, 0x00),
],
_ => todo!(), _ => todo!(),
} }.into()
} }
type Error = Error;
} }
impl GenerateCode for LispAtom { impl AddAssign for Code {
fn to_code(self, codegen_scope: &mut Scope) -> Result<EightBitLang, Self::Error> {
match self {
LispAtom::Keyword(keyword) => keyword.to_code(codegen_scope),
LispAtom::Integer(number) => number.to_code(codegen_scope),
_ => todo!(),
}
}
type Error = Error;
}
impl GenerateCode for isize {
fn to_code(self, codegen_scope: &mut Scope) -> Result<EightBitLang, Self::Error> {
if let Err(_e) = i8::try_from(self) {
return Err(Error::msg("Yo integer too big brah"));
}
return Ok(EightBitLang::push(self as i8, codegen_scope));
}
type Error = Error;
}
impl GenerateCode for Keyword {
fn to_code(self, _codegen_scope: &mut Scope) -> Result<EightBitLang, Self::Error> {
match self {
_ => todo!(),
}
}
type Error = Error;
}
impl AddAssign for EightBitLang {
fn add_assign(&mut self, mut rhs: Self) { fn add_assign(&mut self, mut rhs: Self) {
let mut labels = self.labels.clone().unwrap();
if rhs.labels.is_some() || self.labels.is_some() {
if self.labels.is_none() {
labels = rhs.labels.unwrap();
} else if rhs.labels.is_none() {
} else {
labels = HashMap::new();
for label in rhs.labels.unwrap() {
labels.insert(label.0, label.1 + self.instructions.len());
}
}
self.labels = Some(labels);
}
self.instructions.append(&mut rhs.instructions); self.instructions.append(&mut rhs.instructions);
} }
} }
impl From<Command> for EightBitLang { impl AddAssign<Instruction> for Code {
fn from(value: Command) -> Self { fn add_assign(&mut self, rhs: Instruction) {
self.instructions.push(rhs);
}
}
impl Add for Code {
fn add(mut self, rhs: Self) -> Self::Output {
self += rhs;
self
}
type Output = Self;
}
impl Add<Instruction> for Code {
fn add(mut self, rhs: Instruction) -> Self::Output {
self += rhs;
self
}
type Output = Self;
}
impl From<Vec<Instruction>> for Code {
fn from(value: Vec<Instruction>) -> Self {
Self { Self {
instructions: vec![value], instructions: value,
labels: None,
} }
} }
} }
impl EightBitLang { impl Sum for Code {
fn push(value: i8, codegen_scope: &mut Scope) -> Self { fn sum<I: Iterator<Item = Self>>(iter: I) -> Self {
use InstructionFrom as IF; let mut sum = Self::new();
use InstructionTo as IT;
codegen_scope.stack_position += 1; for i in iter {
sum += i;
}
let mut commands = Vec::new(); sum
commands.push(Command::new(IF::RegisterSP, IT::RegisterA, 0x00)); }
commands.push(Command::new(IF::ROM, IT::RegisterB, 0x01)); }
commands.push(Command::new(IF::ALU, IT::RegisterSP, 0x00));
commands.push(Command::new(IF::RegisterSP, IT::RamAddressLower, 0x00));
commands.push(Command::new(IF::ROM, IT::RAM, value));
impl Code {
fn new() -> Self {
Self { Self {
instructions: commands, instructions: vec![]
labels: None,
} }
} }
} }
impl Command { impl Instruction {
fn new(data_from: InstructionFrom, data_to: InstructionTo, data: i8) -> Self { fn new(from: InstructionFrom, to: InstructionTo, value: i8) -> Self {
Self { Self {
data_from, from,
data_to, to,
data, value,
}
}
}
impl Scope {
pub fn new() -> Self {
Self {
variables: Vec::new(),
stack_position: 0,
} }
} }
} }

View file

@ -12,11 +12,11 @@ use crate::{
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
pub struct IRepr { pub struct IRepr {
commands: Vec<Command>, pub commands: Vec<Command>,
} }
#[derive(Debug, Clone, PartialEq, Eq)] #[derive(Debug, Clone, PartialEq, Eq)]
enum Command { pub enum Command {
PushInt(isize), PushInt(isize),
PushSum, PushSum,
PopR1, PopR1,
@ -168,9 +168,6 @@ impl ToIRMacro for Macro {
} }
} }
dbg!(&commands);
dbg!(&ir_scope);
while body != NIL { while body != NIL {
match body { match body {
SExpression::Atom(_a) => todo!(), SExpression::Atom(_a) => todo!(),
@ -181,12 +178,11 @@ impl ToIRMacro for Macro {
} }
} }
dbg!(&commands);
dbg!(&ir_scope);
commands += Command::Leave; commands += Command::Leave;
todo!() ir_scope.stack_position = ir_scope.stack_positions.pop().unwrap();
Ok(commands)
} }
_ => todo!(), _ => todo!(),
} }

View file

@ -8,12 +8,11 @@ mod error;
use color_eyre::eyre::Result; use color_eyre::eyre::Result;
// pub use error::*; // pub use error::*;
use ir::IRepr;
use lexer::TokenString;
use parser::SExpression;
use crate::{ use crate::{
code_gen::{EightBitLang, GenerateCode, Scope}, code_gen::Code,
lexer::TokenString,
parser::SExpression,
ir::generate_code, ir::generate_code,
}; };
@ -23,17 +22,19 @@ fn main() -> Result<()> {
// let code = r#"(mul 2 (add 3 4))"#.to_string(); // let code = r#"(mul 2 (add 3 4))"#.to_string();
// let code = "(add 3 4) (add 1 2)"; let code = "(add 3 4) (add 1 2)";
let code = "(let ((a 3)) (out (add 1 a)) (out (add 2 a)))"; // let code = "(let ((a 3)) (out (add 1 a)) (out (add 2 a)))";
let lexed: TokenString = dbg!((code.parse())?); let lexed: TokenString = code.parse()?;
let parsed: Vec<SExpression> = (lexed.try_into())?; let parsed: Vec<SExpression> = (lexed.try_into())?;
println!("{parsed:?}"); for instruction in parsed.clone() {
println!("{instruction}");
}
let code: IRepr = generate_code(parsed)?; let code = generate_code(parsed)?;
// let code: EightBitLang = code.to_code(&mut Scope::new())?; let code: Code = code.into();
dbg!(code); dbg!(code);
/* /*

View file

@ -65,8 +65,7 @@ impl SExpression {
state.expression[state.index].row, state.expression[state.index].col state.expression[state.index].row, state.expression[state.index].col
))), ))),
}; };
expr
dbg!(expr)
} }
fn parse_expression(state: &mut State) -> Result<Self, Error> { fn parse_expression(state: &mut State) -> Result<Self, Error> {
@ -78,7 +77,7 @@ impl SExpression {
} }
state.index += 1; state.index += 1;
let expression_1 = dbg!(Self::parse_sexpression(state)?); let expression_1 = Self::parse_sexpression(state)?;
state.index += 1; state.index += 1;
// Is pair // Is pair