diff options
| author | gingerBill <bill@gingerbill.org> | 2024-05-16 16:27:09 +0100 |
|---|---|---|
| committer | gingerBill <bill@gingerbill.org> | 2024-05-16 16:27:09 +0100 |
| commit | c9b1c99a4057b7e3f6caee3fb37cf85ca29a7fc9 (patch) | |
| tree | bb00cdb51a5c3120eb2a7cf5aa48e6ece3e7dcb6 /src | |
| parent | 32245e93a106c5cb1ee9b448789f623a4dbef717 (diff) | |
Fix `soa_zip` and `soa_unzip`
Diffstat (limited to 'src')
| -rw-r--r-- | src/check_builtin.cpp | 4 | ||||
| -rw-r--r-- | src/llvm_backend_utility.cpp | 14 | ||||
| -rw-r--r-- | src/types.cpp | 10 |
3 files changed, 23 insertions, 5 deletions
diff --git a/src/check_builtin.cpp b/src/check_builtin.cpp index c7d27cf38..4636d810a 100644 --- a/src/check_builtin.cpp +++ b/src/check_builtin.cpp @@ -3428,8 +3428,8 @@ gb_internal bool check_builtin_procedure(CheckerContext *c, Operand *operand, As auto types = slice_make<Type *>(permanent_allocator(), t->Struct.fields.count-1); for_array(i, types) { Entity *f = t->Struct.fields[i]; - GB_ASSERT(f->type->kind == Type_Pointer); - types[i] = alloc_type_slice(f->type->Pointer.elem); + GB_ASSERT(f->type->kind == Type_MultiPointer); + types[i] = alloc_type_slice(f->type->MultiPointer.elem); } operand->type = alloc_type_tuple_from_field_types(types.data, types.count, false, false); diff --git a/src/llvm_backend_utility.cpp b/src/llvm_backend_utility.cpp index 8b046c784..5ebe0ddd9 100644 --- a/src/llvm_backend_utility.cpp +++ b/src/llvm_backend_utility.cpp @@ -328,6 +328,7 @@ gb_internal lbValue lb_soa_zip(lbProcedure *p, AstCallExpr *ce, TypeAndValue con lbAddr res = lb_add_local_generated(p, tv.type, true); for_array(i, slices) { lbValue src = lb_slice_elem(p, slices[i]); + src = lb_emit_conv(p, src, alloc_type_pointer_to_multi_pointer(src.type)); lbValue dst = lb_emit_struct_ep(p, res.addr, cast(i32)i); lb_emit_store(p, dst, src); } @@ -1559,19 +1560,26 @@ gb_internal lbValue lb_emit_matrix_ev(lbProcedure *p, lbValue s, isize row, isiz return lb_emit_load(p, ptr); } - gb_internal void lb_fill_slice(lbProcedure *p, lbAddr const &slice, lbValue base_elem, lbValue len) { Type *t = lb_addr_type(slice); GB_ASSERT(is_type_slice(t)); lbValue ptr = lb_addr_get_ptr(p, slice); - lb_emit_store(p, lb_emit_struct_ep(p, ptr, 0), base_elem); + lbValue data = lb_emit_struct_ep(p, ptr, 0); + if (are_types_identical(type_deref(base_elem.type, true), type_deref(type_deref(data.type), true))) { + base_elem = lb_emit_conv(p, base_elem, type_deref(data.type)); + } + lb_emit_store(p, data, base_elem); lb_emit_store(p, lb_emit_struct_ep(p, ptr, 1), len); } gb_internal void lb_fill_string(lbProcedure *p, lbAddr const &string, lbValue base_elem, lbValue len) { Type *t = lb_addr_type(string); GB_ASSERT(is_type_string(t)); lbValue ptr = lb_addr_get_ptr(p, string); - lb_emit_store(p, lb_emit_struct_ep(p, ptr, 0), base_elem); + lbValue data = lb_emit_struct_ep(p, ptr, 0); + if (are_types_identical(type_deref(base_elem.type, true), type_deref(type_deref(data.type), true))) { + base_elem = lb_emit_conv(p, base_elem, type_deref(data.type)); + } + lb_emit_store(p, data, base_elem); lb_emit_store(p, lb_emit_struct_ep(p, ptr, 1), len); } diff --git a/src/types.cpp b/src/types.cpp index 47ed86f7a..390ee842a 100644 --- a/src/types.cpp +++ b/src/types.cpp @@ -988,6 +988,16 @@ gb_internal Type *alloc_type_soa_pointer(Type *elem) { return t; } +gb_internal Type *alloc_type_pointer_to_multi_pointer(Type *ptr) { + Type *original_type = ptr; + ptr = base_type(ptr); + if (ptr->kind == Type_Pointer) { + return alloc_type_multi_pointer(ptr->Pointer.elem); + } else if (ptr->kind != Type_MultiPointer) { + GB_PANIC("Invalid type: %s", type_to_string(original_type)); + } + return original_type; +} gb_internal Type *alloc_type_array(Type *elem, i64 count, Type *generic_count = nullptr) { if (generic_count != nullptr) { |