Fix array to ptr cast

This commit is contained in:
Sofia 2026-04-14 18:26:33 +03:00
parent d3f0a730fd
commit 45df4fdf5f
5 changed files with 42 additions and 12 deletions

View File

@ -59,15 +59,16 @@ namespace types {
if (!types_equal(array_ty->m_inner, ptr_ty->m_inner))
return {};
return CastDefinition{ casted_ty, target_ty, true,
[](codegen::Builder& builder, std::shared_ptr<Type> target, llvm::Value* value) {
auto ptr_ty = dynamic_cast<types::PointerType*>(target.get());
[](codegen::Builder&, std::shared_ptr<Type>, llvm::Value* value) {
// auto ptr_ty = dynamic_cast<types::PointerType*>(target.get());
std::vector<llvm::Value*> indices {};
indices.push_back(llvm::ConstantInt::get(
builder.builder->getInt32Ty(),
0
));
return builder.builder->CreateGEP(ptr_ty->m_inner->codegen(builder), value, indices, "cast_gep");
// std::vector<llvm::Value*> indices {};
// indices.push_back(llvm::ConstantInt::get(
// builder.builder->getInt32Ty(),
// 0
// ));
// return builder.builder->CreateGEP(ptr_ty->m_inner->codegen(builder), value, indices, "arraydecay");
return value;
} };
}

View File

@ -32,9 +32,10 @@ namespace AST {
};
auto str = llvm::StringRef{ this->m_value.c_str() };
auto global_str = builder.builder->CreateGlobalString(str);
return codegen::StackValue{
builder.builder->CreateGlobalString(str),
builder.builder->CreateLoad(stack_type->codegen(builder), global_str, "literal"),
std::unique_ptr<types::Type>{stack_type},
};
}
@ -105,6 +106,14 @@ namespace AST {
auto expr = this->m_expr->codegen(builder, scope);
auto cast = types::find_cast(scope.casts, expr.ty, this->m_ty);
if (cast) {
if (cast->target_ty->m_kind == types::TypeKind::Pointer && cast->casted_ty->m_kind == types::TypeKind::Array) {
auto allocated = builder.builder->CreateAlloca(cast->casted_ty->codegen(builder));
builder.builder->CreateStore(expr.value, allocated);
return codegen::StackValue{
cast->codegen(builder, cast->target_ty, allocated),
cast->target_ty
};
}
return codegen::StackValue{
cast->codegen(builder, cast->target_ty, expr.value),
cast->target_ty
@ -165,7 +174,6 @@ namespace AST {
// Must be an array otherwise
auto arr_ty = dynamic_cast<types::ArrayType*>(ptr_ty->m_inner.get());
std::cout << arr_ty->m_inner->formatted() << std::endl;
auto gep_value = builder.builder->CreateGEP(arr_ty->m_inner->codegen(builder), value.value, idx_list, "GEP");
if (scope.is_lvalue) {
return codegen::StackValue{

View File

@ -320,7 +320,9 @@ namespace AST {
void InitializationStatement::typecheck(typecheck::State& state, typecheck::Scope& scope) {
if (this->m_expr) {
(*this->m_expr)->typecheck(state, scope, this->m_type);
auto expr_ty = (*this->m_expr)->typecheck(state, scope, this->m_type);
auto check_res = check_type(state, expr_ty, this->m_type);
this->m_expr = handle_res(std::move(*this->m_expr), check_res, state);
}
scope.symbols[this->m_name] = this->m_type;
}

View File

@ -1,5 +1,6 @@
#include <sstream>
#include <iostream>
#include "types.h"
#include "binops.h"
@ -160,6 +161,17 @@ namespace types {
}
bool types_equal(std::shared_ptr<types::Type> type1, std::shared_ptr<types::Type> type2) {
// if (type1->m_kind == TypeKind::Array && type2->m_kind == TypeKind::Pointer) {
// auto ty1 = dynamic_cast<ArrayType*>(type1.get());
// auto ty2 = dynamic_cast<PointerType*>(type2.get());
// return types_equal(ty1->m_inner, ty2->m_inner);
// }
// else if (type1->m_kind == TypeKind::Pointer && type2->m_kind == TypeKind::Array) {
// auto ty1 = dynamic_cast<PointerType*>(type1.get());
// auto ty2 = dynamic_cast<ArrayType*>(type2.get());
// return types_equal(ty1->m_inner, ty2->m_inner);
// }
if (type1->m_kind != type2->m_kind)
return false;
@ -194,6 +206,12 @@ namespace types {
return types_equal(ty1->m_inner, ty2->m_inner);
}
else if (type1->m_kind == TypeKind::Array) {
auto ty1 = dynamic_cast<ArrayType*>(type1.get());
auto ty2 = dynamic_cast<ArrayType*>(type2.get());
return types_equal(ty1->m_inner, ty2->m_inner) && ty1->m_size == ty2->m_size;
}
else {
return false;
}

3
test.c
View File

@ -11,7 +11,8 @@ void modify_value(char* otus) {
}
int main() {
printf("10th fibonacci number is %d!", fibonacci(10));
char text[29] = "10th fibonacci number is %d!";
printf(text, fibonacci(10));
char somelist[5];