| ... | ... | @@ -3414,17 +3414,34 @@ static LLVMValueRef ir_render_struct_init(CodeGen *g, IrExecutable *executable, |
| 3414 | 3414 | static LLVMValueRef ir_render_union_init(CodeGen *g, IrExecutable *executable, IrInstructionUnionInit *instruction) { |
| 3415 | 3415 | TypeUnionField *type_union_field = instruction->field; |
| 3416 | 3416 | |
| 3417 | | assert(type_has_bits(type_union_field->type_entry)); |
| 3418 | | |
| 3419 | | LLVMValueRef field_ptr = LLVMBuildStructGEP(g->builder, instruction->tmp_ptr, (unsigned)0, ""); |
| 3420 | | LLVMValueRef value = ir_llvm_value(g, instruction->init_value); |
| 3417 | if (!type_has_bits(type_union_field->type_entry)) |
| 3418 | return nullptr; |
| 3421 | 3419 | |
| 3422 | 3420 | uint32_t field_align_bytes = get_abi_alignment(g, type_union_field->type_entry); |
| 3423 | | |
| 3424 | 3421 | TypeTableEntry *ptr_type = get_pointer_to_type_extra(g, type_union_field->type_entry, |
| 3425 | 3422 | false, false, field_align_bytes, |
| 3426 | 3423 | 0, 0); |
| 3427 | 3424 | |
| 3425 | LLVMValueRef uncasted_union_ptr; |
| 3426 | // Even if safety is off in this block, if the union type has the safety field, we have to populate it |
| 3427 | // correctly. Otherwise safety code somewhere other than here could fail. |
| 3428 | TypeTableEntry *union_type = instruction->union_type; |
| 3429 | if (union_type->data.unionation.gen_tag_index != SIZE_MAX) { |
| 3430 | LLVMValueRef tag_field_ptr = LLVMBuildStructGEP(g->builder, instruction->tmp_ptr, |
| 3431 | union_type->data.unionation.gen_tag_index, ""); |
| 3432 | LLVMValueRef tag_value = LLVMConstInt(union_type->data.unionation.tag_type->type_ref, |
| 3433 | type_union_field->value, false); |
| 3434 | gen_store_untyped(g, tag_value, tag_field_ptr, 0, false); |
| 3435 | |
| 3436 | uncasted_union_ptr = LLVMBuildStructGEP(g->builder, instruction->tmp_ptr, |
| 3437 | (unsigned)union_type->data.unionation.gen_union_index, ""); |
| 3438 | } else { |
| 3439 | uncasted_union_ptr = LLVMBuildStructGEP(g->builder, instruction->tmp_ptr, (unsigned)0, ""); |
| 3440 | } |
| 3441 | |
| 3442 | LLVMValueRef field_ptr = LLVMBuildBitCast(g->builder, uncasted_union_ptr, ptr_type->type_ref, ""); |
| 3443 | LLVMValueRef value = ir_llvm_value(g, instruction->init_value); |
| 3444 | |
| 3428 | 3445 | gen_assign_raw(g, field_ptr, ptr_type, value); |
| 3429 | 3446 | |
| 3430 | 3447 | return instruction->tmp_ptr; |