Read return and function name from signature
This commit is contained in:
parent
525dab2147
commit
7208fe962e
@ -1,10 +1,5 @@
|
|||||||
// Arithmetic, function calls and imports!
|
// Arithmetic, function calls and imports!
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
let test = 9;
|
return 5;
|
||||||
let simpleAdd = 2 + 2;
|
|
||||||
let simpleMult = 7 * 2;
|
|
||||||
let arithmetic = 3 + 2 * 5 + 1 * 2;
|
|
||||||
|
|
||||||
return arithmetic + simpleMult * arithmetic;
|
|
||||||
}
|
}
|
@ -5,6 +5,8 @@ use llvm_sys::{
|
|||||||
core::*, prelude::*, LLVMBasicBlock, LLVMBuilder, LLVMContext, LLVMModule, LLVMType, LLVMValue,
|
core::*, prelude::*, LLVMBasicBlock, LLVMBuilder, LLVMContext, LLVMModule, LLVMType, LLVMValue,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use crate::ast;
|
||||||
|
|
||||||
fn into_cstring<T: Into<String>>(value: T) -> CString {
|
fn into_cstring<T: Into<String>>(value: T) -> CString {
|
||||||
let string = value.into();
|
let string = value.into();
|
||||||
unsafe { CString::from_vec_with_nul_unchecked((string + "\0").into_bytes()) }
|
unsafe { CString::from_vec_with_nul_unchecked((string + "\0").into_bytes()) }
|
||||||
@ -92,7 +94,7 @@ pub struct IRFunction<'a, 'b> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'b> IRFunction<'a, 'b> {
|
impl<'a, 'b> IRFunction<'a, 'b> {
|
||||||
pub fn new(module: &'b mut IRModule<'a>) -> IRFunction<'a, 'b> {
|
pub fn new(name: &String, module: &'b mut IRModule<'a>) -> IRFunction<'a, 'b> {
|
||||||
unsafe {
|
unsafe {
|
||||||
// TODO, fix later!
|
// TODO, fix later!
|
||||||
|
|
||||||
@ -102,8 +104,7 @@ impl<'a, 'b> IRFunction<'a, 'b> {
|
|||||||
let func_type =
|
let func_type =
|
||||||
LLVMFunctionType(return_type, argts.as_mut_ptr(), argts.len() as u32, 0);
|
LLVMFunctionType(return_type, argts.as_mut_ptr(), argts.len() as u32, 0);
|
||||||
|
|
||||||
let function =
|
let function = LLVMAddFunction(module.module, into_cstring(name).as_ptr(), func_type);
|
||||||
LLVMAddFunction(module.module, into_cstring("testfunc").as_ptr(), func_type);
|
|
||||||
|
|
||||||
IRFunction {
|
IRFunction {
|
||||||
module,
|
module,
|
||||||
@ -156,15 +157,20 @@ pub struct IRValue {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl IRValue {
|
impl IRValue {
|
||||||
pub fn const_i32(value: i32, block: &mut IRBlock) -> Self {
|
pub fn from_literal(literal: &ast::Literal, block: &mut IRBlock) -> Self {
|
||||||
|
use ast::Literal;
|
||||||
|
match literal {
|
||||||
|
Literal::I32(v) => {
|
||||||
let ir_type = IRType::I32;
|
let ir_type = IRType::I32;
|
||||||
unsafe {
|
unsafe {
|
||||||
let ir_value = LLVMConstInt(
|
let ir_value = LLVMConstInt(
|
||||||
ir_type.in_context(block.function.module.context),
|
ir_type.in_context(block.function.module.context),
|
||||||
mem::transmute(3 as i64),
|
mem::transmute(*v as i64),
|
||||||
1,
|
1,
|
||||||
);
|
);
|
||||||
return IRValue { ir_type, ir_value };
|
return IRValue { ir_type, ir_value };
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,10 @@ mod llvm;
|
|||||||
|
|
||||||
use llvm::{IRBlock, IRContext, IRFunction, IRModule, IRValue};
|
use llvm::{IRBlock, IRContext, IRFunction, IRModule, IRValue};
|
||||||
|
|
||||||
use crate::{ast::FunctionDefinition, TopLevelStatement};
|
use crate::{
|
||||||
|
ast::{Block, Expression, ExpressionKind, FunctionDefinition},
|
||||||
|
TopLevelStatement,
|
||||||
|
};
|
||||||
|
|
||||||
#[derive(thiserror::Error, Debug)]
|
#[derive(thiserror::Error, Debug)]
|
||||||
pub enum Error {}
|
pub enum Error {}
|
||||||
@ -34,9 +37,31 @@ impl TopLevelStatement {
|
|||||||
|
|
||||||
impl FunctionDefinition {
|
impl FunctionDefinition {
|
||||||
fn codegen(&self, module: &mut IRModule) {
|
fn codegen(&self, module: &mut IRModule) {
|
||||||
let mut function = IRFunction::new(module);
|
let FunctionDefinition(signature, block, _) = self;
|
||||||
let mut block = IRBlock::new(&mut function);
|
let mut function = IRFunction::new(&signature.name, module);
|
||||||
let value = IRValue::const_i32(3, &mut block);
|
block.codegen(&mut function)
|
||||||
block.add_return(Some(value))
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Block {
|
||||||
|
fn codegen(&self, function: &mut IRFunction) {
|
||||||
|
let mut block = IRBlock::new(function);
|
||||||
|
|
||||||
|
if let Some((_, return_exp)) = &self.1 {
|
||||||
|
let value = return_exp.codegen(&mut block);
|
||||||
|
block.add_return(Some(value))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Expression {
|
||||||
|
fn codegen(&self, block: &mut IRBlock) -> IRValue {
|
||||||
|
let Expression(kind, _) = self;
|
||||||
|
|
||||||
|
use ExpressionKind::*;
|
||||||
|
match kind {
|
||||||
|
Literal(lit) => IRValue::from_literal(lit, block),
|
||||||
|
_ => panic!("expression type not supported"),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user