Skip to content

Commit

Permalink
Introduced alloc, load, and store instruction in asts, lots of failur…
Browse files Browse the repository at this point in the history
…es :sob
  • Loading branch information
hyouteki committed Aug 16, 2024
1 parent ca9b5ce commit 84617b4
Show file tree
Hide file tree
Showing 8 changed files with 131 additions and 60 deletions.
2 changes: 1 addition & 1 deletion editor_plugins/irl-mode.el
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
table))

(defvar irl-keywords
'("function" "arg" "goto" "label" "if" "param" "ret" "call"))
'("function" "arg" "goto" "label" "if" "param" "ret" "call" "alloc" "load" "store"))

(defvar irl-operators
'("=" "\\+" "-" "\\*" "/" "<=" "==" "!=" "<" ">" ">="))
Expand Down
Binary file modified eg/fib
Binary file not shown.
32 changes: 16 additions & 16 deletions eg/fib.fasm
Original file line number Diff line number Diff line change
Expand Up @@ -4,51 +4,51 @@ segment gnustack
segment executable
fib:
sub rsp, 20
mov [rsp+16], edi
mov [rsp+12], edi
jmp fib_label_1
fib_label_1:
mov r15d, 0
mov [rsp+0], r15d
mov r15d, 1
mov [rsp+12], r15d
mov r15d, 1
mov [rsp+4], r15d
mov r15d, 1
mov [rsp+8], r15d
jmp fib_label_begin
fib_label_begin:
mov r15d, [rsp+4]
cmp r15d, [rsp+16]
mov r15d, [rsp+8]
cmp r15d, [rsp+12]
mov r15d, 0
mov r14d, 1
cmove r15d, r14d
cmp r15d, 1
je fib_label_end
jmp fib_label_4
fib_label_end:
mov eax, [rsp+12]
mov eax, [rsp+4]
add rsp, 20
ret
fib_label_4:
mov r15d, [rsp+12]
mov [rsp+8], r15d
mov r15d, [rsp+4]
mov [rsp+16], r15d
mov r15d, [rsp+0]
add r15d, [rsp+12]
mov [rsp+12], r15d
mov r15d, [rsp+8]
add r15d, [rsp+4]
mov [rsp+4], r15d
mov r15d, [rsp+16]
mov [rsp+0], r15d
mov r15d, [rsp+4]
mov r15d, [rsp+8]
add r15d, 1
mov [rsp+4], r15d
mov [rsp+8], r15d
jmp fib_label_begin
main:
sub rsp, 8
jmp main_label_1
main_label_1:
mov edi, 6
call fib
mov [rsp+4], eax
mov edi, [rsp+4]
call print
mov [rsp+0], eax
mov edi, [rsp+0]
call print
mov [rsp+4], eax
mov eax, 60
mov edi, 0
add rsp, 8
Expand Down
7 changes: 7 additions & 0 deletions eg/memory_test.irl
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
function main, 0
r1 = alloc 4
store r1, 42
r2 = load r1
param r2
tmp = call print, 1
ret 0
125 changes: 83 additions & 42 deletions src/fe/ast.rs
Original file line number Diff line number Diff line change
Expand Up @@ -230,6 +230,62 @@ impl UnaryAstNode {
}
}

#[derive(Clone)]
pub struct AllocAstNode {
pub size: Box<AstNode>,
pub loc: Loc,
}

impl PartialEq for AllocAstNode {
fn eq(&self, other: &Self) -> bool {
self.size == other.size
}
}

impl AllocAstNode {
fn print(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
write!(f, "alloc {}", self.size)
}
}

#[derive(Clone)]
pub struct LoadAstNode {
pub ptr: String,
pub loc: Loc,
}

impl PartialEq for LoadAstNode {
fn eq(&self, other: &Self) -> bool {
self.ptr == other.ptr
}
}

impl LoadAstNode {
fn print(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
write!(f, "load {}", self.ptr)
}
}

#[derive(Clone)]
pub struct StoreAstNode {
pub ptr: String,
pub op: Box<AstNode>,
pub loc: Loc,
}

impl PartialEq for StoreAstNode {
fn eq(&self, other: &Self) -> bool {
self.ptr == other.ptr && self.op == other.op
}
}

impl StoreAstNode {
fn print(&self, f: &mut std::fmt::Formatter, indent_sz: usize) -> std::fmt::Result {
print_indent(f, indent_sz);
write!(f, "store {}, {}", self.ptr, self.op)
}
}

#[derive(Clone)]
pub struct FunctionAstNode {
pub name: String,
Expand Down Expand Up @@ -387,6 +443,9 @@ pub enum AstNode {
Arith(ArithAstNode),
Relop(RelopAstNode),
Unary(UnaryAstNode),
Alloc(AllocAstNode),
Load(LoadAstNode),
Store(StoreAstNode),
Function(FunctionAstNode),
Assignment(AssignmentAstNode),
Goto(GotoAstNode),
Expand All @@ -410,6 +469,9 @@ impl AstNode {
AstNode::Label(node) => node.print(f, indent_sz),
AstNode::If(node) => node.print(f, indent_sz),
AstNode::Ret(node) => node.print(f, indent_sz),
AstNode::Alloc(node) => node.print(f),
AstNode::Load(node) => node.print(f),
AstNode::Store(node) => node.print(f, indent_sz),
}
}
pub fn is_terminator(&self) -> bool {
Expand All @@ -422,66 +484,39 @@ impl AstNode {
}
pub fn dependencies(&self) -> Vec<String> {
match self {
AstNode::Iden(_) => vec![],
AstNode::Iden(iden_node) => vec![iden_node.name.clone()],
AstNode::Num(_) => vec![],
AstNode::Call(node) => {
let mut res: Vec<String> = Vec::new();
for param in node.params.iter() {
if let AstNode::Iden(iden) = param {
res.push(iden.name.clone());
}
res.append(&mut param.dependencies());
}
res
},
AstNode::Arith(node) => {
let mut res: Vec<String> = Vec::new();
if let AstNode::Iden(ref iden) = *node.lhs {
res.push(iden.name.clone());
}
if let AstNode::Iden(ref iden) = *node.rhs {
res.push(iden.name.clone());
}
res.append(&mut node.lhs.dependencies());
res.append(&mut node.rhs.dependencies());
res
},
AstNode::Relop(node) => {
let mut res: Vec<String> = Vec::new();
if let AstNode::Iden(ref iden) = *node.lhs {
res.push(iden.name.clone());
}
if let AstNode::Iden(ref iden) = *node.rhs {
res.push(iden.name.clone());
}
res
},
AstNode::Unary(node) => {
let mut res: Vec<String> = Vec::new();
if let AstNode::Iden(ref iden) = *node.var {
res.push(iden.name.clone());
}
res.append(&mut node.lhs.dependencies());
res.append(&mut node.rhs.dependencies());
res
},
AstNode::Unary(node) => node.var.dependencies(),
AstNode::Function(_) => vec![],
AstNode::Assignment(node) => {
let mut res: Vec<String> = Vec::new();
if let AstNode::Iden(ref iden) = *node.var {
res.push(iden.name.clone());
}
res
},
AstNode::Assignment(node) => node.var.dependencies(),
AstNode::Goto(_) => vec![],
AstNode::Label(_) => vec![],
AstNode::If(node) => {
let mut res: Vec<String> = Vec::new();
if let AstNode::Iden(ref iden) = *node.condition {
res.push(iden.name.clone());
}
res
},
AstNode::Ret(node) => {
let mut res: Vec<String> = Vec::new();
if let AstNode::Iden(ref iden) = *node.var {
res.push(iden.name.clone());
}
AstNode::If(node) => node.condition.dependencies(),
AstNode::Ret(node) => node.var.dependencies(),
AstNode::Alloc(node) => node.size.dependencies(),
AstNode::Load(node) => vec![node.ptr.clone()],
AstNode::Store(node) => {
let mut res: Vec<String> = vec![node.ptr.clone()];
res.append(&mut node.op.dependencies());
res
},
}
Expand All @@ -500,6 +535,9 @@ impl AstNode {
AstNode::Label(_) => None,
AstNode::If(_) => None,
AstNode::Ret(_) => None,
AstNode::Alloc(_) => None,
AstNode::Load(_) => None,
AstNode::Store(node) => Some(node.ptr.clone()),
}
}
pub fn evaluate(&self) -> Value {
Expand Down Expand Up @@ -542,6 +580,9 @@ impl AstNode {
AstNode::Label(_) => Value::Nac,
AstNode::If(_) => Value::Nac,
AstNode::Ret(node) => node.var.evaluate(),
AstNode::Alloc(_) => Value::Nac,
AstNode::Load(_) => Value::Nac,
AstNode::Store(_) => Value::Nac,
}
}
pub fn reduced_version(&self, state: &HashMap<String, Value>) -> AstNode {
Expand Down
5 changes: 4 additions & 1 deletion src/fe/lexer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,10 @@ impl Lexer {
(String::from("if"), TokenKind::If),
(String::from("param"), TokenKind::Param),
(String::from("call"), TokenKind::Call),
(String::from("ret"), TokenKind::Ret)
(String::from("ret"), TokenKind::Ret),
(String::from("alloc"), TokenKind::Alloc),
(String::from("load"), TokenKind::Load),
(String::from("store"), TokenKind::Store)
].iter().cloned().collect();

for i in 0..content.len() {
Expand Down
14 changes: 14 additions & 0 deletions src/fe/parser.rs
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,20 @@ fn parse_assignment(tokens: &Vec<Token>, ix: &mut usize) -> AstNode {
assert_n_eat(tokens, TokenKind::Eol, ix);
return AstNode::Call(CallAstNode{id: id, name: name, params: vec![], loc: loc});
}
if tokens[*ix].kind == TokenKind::Alloc {
assert_n_eat(tokens, TokenKind::Alloc, ix);
let size: AstNode = eat_operand(tokens, ix);
assert_n_eat(tokens, TokenKind::Eol, ix);
return AstNode::Assignment(AssignmentAstNode{name: id, var: Box::new(
AstNode::Alloc(AllocAstNode{size: Box::new(size), loc: var_loc})), loc});
}
if tokens[*ix].kind == TokenKind::Load {
assert_n_eat(tokens, TokenKind::Load, ix);
let ptr: String = eat_iden(tokens, ix);
assert_n_eat(tokens, TokenKind::Eol, ix);
return AstNode::Assignment(AssignmentAstNode{name: id, var: Box::new(
AstNode::Load(LoadAstNode{ptr: ptr, loc: var_loc})), loc});
}
let lhs: AstNode = eat_operand(tokens, ix);
if tokens[*ix].is_arith() {
let op: ArithOp = ArithOp::new(&tokens[*ix]);
Expand Down
6 changes: 6 additions & 0 deletions src/fe/token.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,9 @@ pub enum TokenKind {
Minus,
Mul,
Comment,
Alloc,
Load,
Store,
Div,
Goto,
Label,
Expand Down Expand Up @@ -45,6 +48,9 @@ impl std::fmt::Display for TokenKind {
TokenKind::Mul => "*",
TokenKind::Div => "/",
TokenKind::Comment => "//",
TokenKind::Alloc => "alloc",
TokenKind::Load => "load",
TokenKind::Store => "store",
TokenKind::Goto => "goto",
TokenKind::Label => "label",
TokenKind::If => "if",
Expand Down

0 comments on commit 84617b4

Please sign in to comment.