Add SIGN to IntegerType

This commit is contained in:
Sofia 2025-06-28 18:56:24 +03:00
parent 02d8b37424
commit 740aee1382
3 changed files with 24 additions and 72 deletions

View File

@ -11,20 +11,20 @@ pub fn main() {
let module = context.module("testmodule"); let module = context.module("testmodule");
let int_32 = context.integer_type::<32>(); let int_32 = context.integer_type::<32, true>();
let secondary = module.add_function(int_32.function_type(&[]), "secondary"); let secondary = module.add_function(int_32.function_type(&[]), "secondary");
let s_entry = secondary.block("entry"); let s_entry = secondary.block("entry");
s_entry.ret(&int_32.from_const(54, 1)).unwrap(); s_entry.ret(&int_32.from_const(54)).unwrap();
let function = module.add_function(int_32.function_type(&[]), "main"); let function = module.add_function(int_32.function_type(&[]), "main");
let entry = function.block("entry"); let entry = function.block("entry");
let v1 = int_32.from_const(100, 1); let v1 = int_32.from_const(100);
let v2 = entry.call(&secondary, vec![], "call").unwrap(); let v2 = entry.call(&secondary, vec![], "call").unwrap();
let lhs_cmp = entry.add(&v1, &v2, "add").unwrap(); let lhs_cmp = entry.add(&v1, &v2, "add").unwrap();
let rhs_cmp = int_32.from_const(200, 1); let rhs_cmp = int_32.from_const(200);
let cond_res = entry let cond_res = entry
.integer_compare(&lhs_cmp, &rhs_cmp, &Comparison::LessThan, "cmp") .integer_compare(&lhs_cmp, &rhs_cmp, &Comparison::LessThan, "cmp")
@ -32,8 +32,8 @@ pub fn main() {
let (lhs, rhs) = entry.conditional_br(&cond_res, "lhs", "rhs").unwrap(); let (lhs, rhs) = entry.conditional_br(&cond_res, "lhs", "rhs").unwrap();
lhs.ret(&int_32.from_const(123, 1)).unwrap(); lhs.ret(&int_32.from_const(123)).unwrap();
rhs.ret(&int_32.from_const(456, 1)).unwrap(); rhs.ret(&int_32.from_const(456)).unwrap();
match module.print_to_string() { match module.print_to_string() {
Ok(v) => println!("{}", v), Ok(v) => println!("{}", v),

View File

@ -42,7 +42,9 @@ impl Context {
} }
} }
pub fn integer_type<'a, const T: u32>(&'a self) -> IntegerType<'a, T> { pub fn integer_type<'a, const WIDTH: u32, const SIGN: bool>(
&'a self,
) -> IntegerType<'a, WIDTH, SIGN> {
IntegerType::in_context(&self) IntegerType::in_context(&self)
} }

View File

@ -48,41 +48,48 @@ impl PartialEq<LLVMTypeRef> for &dyn BasicType {
} }
} }
pub struct IntegerType<'ctx, const T: u32> { pub struct IntegerType<'ctx, const WIDTH: u32, const SIGNED: bool> {
context: &'ctx Context, context: &'ctx Context,
type_ref: LLVMTypeRef, type_ref: LLVMTypeRef,
} }
impl<'ctx, const T: u32> BasicType for IntegerType<'ctx, T> { impl<'ctx, const WIDTH: u32, const SIGNED: bool> BasicType for IntegerType<'ctx, WIDTH, SIGNED> {
fn llvm_type(&self) -> LLVMTypeRef { fn llvm_type(&self) -> LLVMTypeRef {
self.type_ref self.type_ref
} }
} }
impl<'ctx, const T: u32> IntegerType<'ctx, T> { impl<'ctx, const WIDTH: u32, const SIGNED: bool> IntegerType<'ctx, WIDTH, SIGNED> {
pub(crate) fn in_context(context: &Context) -> IntegerType<T> { pub(crate) fn in_context(context: &Context) -> IntegerType<WIDTH, SIGNED> {
let type_ref = unsafe { let type_ref = unsafe {
match T { match WIDTH {
128 => LLVMInt128TypeInContext(context.context_ref), 128 => LLVMInt128TypeInContext(context.context_ref),
64 => LLVMInt64TypeInContext(context.context_ref), 64 => LLVMInt64TypeInContext(context.context_ref),
32 => LLVMInt32TypeInContext(context.context_ref), 32 => LLVMInt32TypeInContext(context.context_ref),
16 => LLVMInt16TypeInContext(context.context_ref), 16 => LLVMInt16TypeInContext(context.context_ref),
8 => LLVMInt8TypeInContext(context.context_ref), 8 => LLVMInt8TypeInContext(context.context_ref),
1 => LLVMInt1TypeInContext(context.context_ref), 1 => LLVMInt1TypeInContext(context.context_ref),
_ => LLVMIntTypeInContext(context.context_ref, T), _ => LLVMIntTypeInContext(context.context_ref, WIDTH),
} }
}; };
IntegerType { context, type_ref } IntegerType { context, type_ref }
} }
pub fn from_const(&self, value: u64, sign: i32) -> OpaqueValue { pub fn from_const(&self, value: u64) -> OpaqueValue {
unsafe { unsafe {
OpaqueValue { OpaqueValue {
basic_type: self, basic_type: self,
value_ref: LLVMConstInt(self.type_ref, value, sign), value_ref: LLVMConstInt(self.type_ref, value, Self::sign_to_i32()),
} }
} }
} }
const fn sign_to_i32() -> i32 {
match SIGNED {
true => 1,
false => 0,
}
}
} }
pub struct FunctionType<'ctx, ReturnType: BasicType> { pub struct FunctionType<'ctx, ReturnType: BasicType> {
@ -131,60 +138,3 @@ impl<'ctx> OpaqueValue<'ctx> {
} }
} }
} }
// pub trait IRType {
// const SIGNED: LLVMBool;
// unsafe fn llvm_type(context: &IRContext) -> LLVMTypeRef;
// }
// impl IRType for bool {
// const SIGNED: LLVMBool = 0;
// unsafe fn llvm_type(context: &IRContext) -> LLVMTypeRef {
// unsafe { LLVMInt1TypeInContext(context.context) }
// }
// }
// impl IRType for i32 {
// const SIGNED: LLVMBool = 1;
// unsafe fn llvm_type(context: &IRContext) -> LLVMTypeRef {
// unsafe { LLVMInt32TypeInContext(context.context) }
// }
// }
// impl IRType for u32 {
// const SIGNED: LLVMBool = 0;
// unsafe fn llvm_type(context: &IRContext) -> LLVMTypeRef {
// unsafe { LLVMInt32TypeInContext(context.context) }
// }
// }
// impl IRType for u16 {
// const SIGNED: LLVMBool = 0;
// unsafe fn llvm_type(context: &IRContext) -> LLVMTypeRef {
// unsafe { LLVMInt16TypeInContext(context.context) }
// }
// }
// pub struct IRValue<T: IRType>(PhantomData<T>, pub(crate) OpaqueIRValue);
// impl<T: IRType> IRValue<T> {
// pub(crate) unsafe fn from_runtime(t: LLVMTypeRef, value: LLVMValueRef) -> IRValue<T> {
// IRValue(PhantomData, OpaqueIRValue(t, value))
// }
// }
// impl<T: IRType + Into<i64>> IRValue<T> {
// pub fn from_const(context: &IRContext, value: T) -> Self {
// unsafe {
// let t = T::llvm_type(context);
// let value = LLVMConstInt(t, value.into() as u64, T::SIGNED);
// IRValue(PhantomData, OpaqueIRValue(t, value))
// }
// }
// }
// impl<T: IRType> From<IRValue<T>> for OpaqueIRValue {
// fn from(value: IRValue<T>) -> Self {
// value.1
// }
// }