mirror of
https://github.com/Ed94/Odin.git
synced 2026-08-06 15:48:51 +00:00
Fix LLVM code gen bug
This commit is contained in:
@@ -426,7 +426,7 @@ typeid_base_without_enum :: typeid_core;
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
@(default_calling_convention = "c")
|
@(default_calling_convention = "none")
|
||||||
foreign {
|
foreign {
|
||||||
@(link_name="llvm.assume")
|
@(link_name="llvm.assume")
|
||||||
assume :: proc(cond: bool) ---;
|
assume :: proc(cond: bool) ---;
|
||||||
|
|||||||
+2
-2
@@ -58,7 +58,7 @@ ExprKind check_expr_base (CheckerContext *c, Operand *operand, As
|
|||||||
void check_expr_with_type_hint (CheckerContext *c, Operand *o, Ast *e, Type *t);
|
void check_expr_with_type_hint (CheckerContext *c, Operand *o, Ast *e, Type *t);
|
||||||
Type * check_type (CheckerContext *c, Ast *expression);
|
Type * check_type (CheckerContext *c, Ast *expression);
|
||||||
Type * check_type_expr (CheckerContext *c, Ast *expression, Type *named_type);
|
Type * check_type_expr (CheckerContext *c, Ast *expression, Type *named_type);
|
||||||
Type * make_optional_ok_type (Type *value);
|
Type * make_optional_ok_type (Type *value, bool typed=true);
|
||||||
void check_type_decl (CheckerContext *c, Entity *e, Ast *type_expr, Type *def);
|
void check_type_decl (CheckerContext *c, Entity *e, Ast *type_expr, Type *def);
|
||||||
Entity * check_selector (CheckerContext *c, Operand *operand, Ast *node, Type *type_hint);
|
Entity * check_selector (CheckerContext *c, Operand *operand, Ast *node, Type *type_hint);
|
||||||
Entity * check_ident (CheckerContext *c, Operand *o, Ast *n, Type *named_type, Type *type_hint, bool allow_import_name);
|
Entity * check_ident (CheckerContext *c, Operand *o, Ast *n, Type *named_type, Type *type_hint, bool allow_import_name);
|
||||||
@@ -5532,7 +5532,7 @@ bool check_builtin_procedure(CheckerContext *c, Operand *operand, Ast *call, i32
|
|||||||
check_assignment(c, &y, elem, builtin_name);
|
check_assignment(c, &y, elem, builtin_name);
|
||||||
|
|
||||||
operand->mode = Addressing_Value;
|
operand->mode = Addressing_Value;
|
||||||
operand->type = make_optional_ok_type(elem);
|
operand->type = make_optional_ok_type(elem, /*typed*/false);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|||||||
+1
-2
@@ -2683,10 +2683,9 @@ i64 check_array_count(CheckerContext *ctx, Operand *o, Ast *e) {
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
Type *make_optional_ok_type(Type *value) {
|
Type *make_optional_ok_type(Type *value, bool typed) {
|
||||||
// LEAK TODO(bill): probably don't reallocate everything here and reuse the same one for the same type if possible
|
// LEAK TODO(bill): probably don't reallocate everything here and reuse the same one for the same type if possible
|
||||||
gbAllocator a = heap_allocator();
|
gbAllocator a = heap_allocator();
|
||||||
bool typed = true;
|
|
||||||
Type *t = alloc_type_tuple();
|
Type *t = alloc_type_tuple();
|
||||||
array_init(&t->Tuple.variables, a, 0, 2);
|
array_init(&t->Tuple.variables, a, 0, 2);
|
||||||
array_add (&t->Tuple.variables, alloc_entity_field(nullptr, blank_token, value, false, 0));
|
array_add (&t->Tuple.variables, alloc_entity_field(nullptr, blank_token, value, false, 0));
|
||||||
|
|||||||
+17
-7
@@ -976,9 +976,14 @@ irValue *ir_value_param(irProcedure *parent, Entity *e, Type *abi_type, i32 inde
|
|||||||
if (e != nullptr && abi_type != e->type) {
|
if (e != nullptr && abi_type != e->type) {
|
||||||
if (is_type_pointer(abi_type)) {
|
if (is_type_pointer(abi_type)) {
|
||||||
GB_ASSERT(e->kind == Entity_Variable);
|
GB_ASSERT(e->kind == Entity_Variable);
|
||||||
v->Param.kind = irParamPass_Pointer;
|
Type *av = type_deref(abi_type);
|
||||||
if (e->flags&EntityFlag_Value) {
|
if (are_types_identical(abi_type, e->type)) {
|
||||||
v->Param.kind = irParamPass_ConstRef;
|
v->Param.kind = irParamPass_Pointer;
|
||||||
|
if (e->flags&EntityFlag_Value) {
|
||||||
|
v->Param.kind = irParamPass_ConstRef;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
v->Param.kind = irParamPass_BitCast;
|
||||||
}
|
}
|
||||||
} else if (is_type_integer(abi_type)) {
|
} else if (is_type_integer(abi_type)) {
|
||||||
v->Param.kind = irParamPass_Integer;
|
v->Param.kind = irParamPass_Integer;
|
||||||
@@ -3241,10 +3246,15 @@ irValue *ir_emit_call(irProcedure *p, irValue *value, Array<irValue *> const &ar
|
|||||||
array_add(&processed_args, args[i]);
|
array_add(&processed_args, args[i]);
|
||||||
} else if (!are_types_identical(original_type, new_type)) {
|
} else if (!are_types_identical(original_type, new_type)) {
|
||||||
if (is_type_pointer(new_type) && !is_type_pointer(original_type)) {
|
if (is_type_pointer(new_type) && !is_type_pointer(original_type)) {
|
||||||
if (e->flags&EntityFlag_ImplicitReference) {
|
Type *av = type_deref(new_type);
|
||||||
array_add(&processed_args, ir_address_from_load_or_generate_local(p, args[i]));
|
if (are_types_identical(av, original_type)) {
|
||||||
} else if (!is_type_pointer(arg_type)) {
|
if (e->flags&EntityFlag_ImplicitReference) {
|
||||||
array_add(&processed_args, ir_copy_value_to_ptr(p, args[i], original_type, 16));
|
array_add(&processed_args, ir_address_from_load_or_generate_local(p, args[i]));
|
||||||
|
} else if (!is_type_pointer(arg_type)) {
|
||||||
|
array_add(&processed_args, ir_copy_value_to_ptr(p, args[i], original_type, 16));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
array_add(&processed_args, ir_emit_transmute(p, args[i], new_type));
|
||||||
}
|
}
|
||||||
} else if (is_type_integer(new_type) || is_type_float(new_type)) {
|
} else if (is_type_integer(new_type) || is_type_float(new_type)) {
|
||||||
array_add(&processed_args, ir_emit_transmute(p, args[i], new_type));
|
array_add(&processed_args, ir_emit_transmute(p, args[i], new_type));
|
||||||
|
|||||||
+19
-8
@@ -2270,12 +2270,17 @@ lbProcedure *lb_create_dummy_procedure(lbModule *m, String link_name, Type *type
|
|||||||
lbValue lb_value_param(lbProcedure *p, Entity *e, Type *abi_type, i32 index, lbParamPasskind *kind_) {
|
lbValue lb_value_param(lbProcedure *p, Entity *e, Type *abi_type, i32 index, lbParamPasskind *kind_) {
|
||||||
lbParamPasskind kind = lbParamPass_Value;
|
lbParamPasskind kind = lbParamPass_Value;
|
||||||
|
|
||||||
if (e != nullptr && abi_type != e->type) {
|
if (e != nullptr && !are_types_identical(abi_type, e->type)) {
|
||||||
if (is_type_pointer(abi_type)) {
|
if (is_type_pointer(abi_type)) {
|
||||||
GB_ASSERT(e->kind == Entity_Variable);
|
GB_ASSERT(e->kind == Entity_Variable);
|
||||||
kind = lbParamPass_Pointer;
|
Type *av = type_deref(abi_type);
|
||||||
if (e->flags&EntityFlag_Value) {
|
if (are_types_identical(av, e->type)) {
|
||||||
kind = lbParamPass_ConstRef;
|
kind = lbParamPass_Pointer;
|
||||||
|
if (e->flags&EntityFlag_Value) {
|
||||||
|
kind = lbParamPass_ConstRef;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
kind = lbParamPass_BitCast;
|
||||||
}
|
}
|
||||||
} else if (is_type_integer(abi_type)) {
|
} else if (is_type_integer(abi_type)) {
|
||||||
kind = lbParamPass_Integer;
|
kind = lbParamPass_Integer;
|
||||||
@@ -2364,6 +2369,7 @@ lbValue lb_add_param(lbProcedure *p, Entity *e, Ast *expr, Type *abi_type, i32 i
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
GB_PANIC("Unreachable");
|
GB_PANIC("Unreachable");
|
||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
@@ -7035,10 +7041,15 @@ lbValue lb_emit_call(lbProcedure *p, lbValue value, Array<lbValue> const &args,
|
|||||||
array_add(&processed_args, args[i]);
|
array_add(&processed_args, args[i]);
|
||||||
} else if (!are_types_identical(original_type, new_type)) {
|
} else if (!are_types_identical(original_type, new_type)) {
|
||||||
if (is_type_pointer(new_type) && !is_type_pointer(original_type)) {
|
if (is_type_pointer(new_type) && !is_type_pointer(original_type)) {
|
||||||
if (e->flags&EntityFlag_ImplicitReference) {
|
Type *av = type_deref(new_type);
|
||||||
array_add(&processed_args, lb_address_from_load_or_generate_local(p, args[i]));
|
if (are_types_identical(av, arg_type)) {
|
||||||
} else if (!is_type_pointer(arg_type)) {
|
if (e->flags&EntityFlag_ImplicitReference) {
|
||||||
array_add(&processed_args, lb_copy_value_to_ptr(p, args[i], original_type, 16));
|
array_add(&processed_args, lb_address_from_load_or_generate_local(p, args[i]));
|
||||||
|
} else if (!is_type_pointer(arg_type)) {
|
||||||
|
array_add(&processed_args, lb_copy_value_to_ptr(p, args[i], original_type, 16));
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
array_add(&processed_args, lb_emit_transmute(p, args[i], new_type));
|
||||||
}
|
}
|
||||||
} else if (new_type == t_llvm_bool) {
|
} else if (new_type == t_llvm_bool) {
|
||||||
array_add(&processed_args, lb_emit_conv(p, args[i], new_type));
|
array_add(&processed_args, lb_emit_conv(p, args[i], new_type));
|
||||||
|
|||||||
Reference in New Issue
Block a user