Implement borrowing in codegen

This commit is contained in:
Sofia 2025-07-21 09:54:55 +03:00
parent c8d6566489
commit 09cec9c110

View File

@ -488,7 +488,7 @@ impl mir::Statement {
.unwrap() .unwrap()
.maybe_location(&mut scope.block, location); .maybe_location(&mut scope.block, location);
let store = scope scope
.block .block
.build( .build(
format!("{}.store", name), format!("{}.store", name),
@ -513,12 +513,12 @@ impl mir::Statement {
DebugMetadata::LocalVar(DebugLocalVariable { DebugMetadata::LocalVar(DebugLocalVariable {
name: name.clone(), name: name.clone(),
location, location,
ty: TypeKind::Ptr(Box::new(ty.clone())).get_debug_type(debug, scope), ty: ty.clone().get_debug_type(debug, scope),
always_preserve: true, always_preserve: true,
flags: DwarfFlags, flags: DwarfFlags,
}), }),
); );
store.add_record( alloca.add_record(
&mut scope.block, &mut scope.block,
InstructionDebugRecordData { InstructionDebugRecordData {
variable: var, variable: var,
@ -934,8 +934,62 @@ impl mir::Expression {
TypeKind::CustomType(name.clone()), TypeKind::CustomType(name.clone()),
)) ))
} }
mir::ExprKind::Borrow(named_variable_ref) => todo!(), mir::ExprKind::Borrow(varref) => {
mir::ExprKind::Deref(named_variable_ref) => todo!(), varref.0.known().expect("variable type unknown");
let v = scope
.stack_values
.get(&varref.1)
.expect("Variable reference not found?!");
Some(v.clone())
}
mir::ExprKind::Deref(varref) => {
varref.0.known().expect("variable type unknown");
let v = scope
.stack_values
.get(&varref.1)
.expect("Variable reference not found?!");
let TypeKind::Ptr(ptr_inner) = &v.1 else {
panic!();
};
let var_ptr_instr = scope
.block
.build(
format!("{}.deref", varref.1),
Instr::Load(
v.0.instr(),
ptr_inner.get_type(scope.type_values, scope.types),
),
)
.unwrap();
Some({
if state.should_load {
if let TypeKind::Ptr(inner) = *ptr_inner.clone() {
StackValue(
v.0.derive(
scope
.block
.build(
format!("{}.deref.inner", varref.1),
Instr::Load(
var_ptr_instr,
inner.get_type(scope.type_values, scope.types),
),
)
.unwrap(),
),
*inner.clone(),
)
} else {
panic!("Variable was not a pointer?!?")
}
} else {
StackValue(v.0.derive(var_ptr_instr), *ptr_inner.clone())
}
})
}
}; };
if let Some(value) = &value { if let Some(value) = &value {
value.instr().maybe_location(&mut scope.block, location); value.instr().maybe_location(&mut scope.block, location);
@ -1159,18 +1213,20 @@ impl TypeKind {
), ),
size_bits: self.size_of(), size_bits: self.size_of(),
}), }),
TypeKind::Ptr(inner) => DebugTypeData::Pointer(DebugPointerType { TypeKind::Ptr(inner) | TypeKind::Borrow(inner) => {
name, DebugTypeData::Pointer(DebugPointerType {
pointee: inner.get_debug_type_hard( name,
scope, pointee: inner.get_debug_type_hard(
debug_info, scope,
debug_types, debug_info,
type_values, debug_types,
types, type_values,
tokens, types,
), tokens,
size_bits: self.size_of(), ),
}), size_bits: self.size_of(),
})
}
TypeKind::Array(elem_ty, len) => { TypeKind::Array(elem_ty, len) => {
let elem_ty = elem_ty.clone().get_debug_type_hard( let elem_ty = elem_ty.clone().get_debug_type_hard(
scope, scope,