@@ -83,7 +83,7 @@ static void render_const_val_global(CodeGen *g, ZigValue *const_val, const char
83
83
static LLVMValueRef gen_const_val (CodeGen *g, ZigValue *const_val, const char *name);
84
84
static void generate_error_name_table (CodeGen *g);
85
85
static bool value_is_all_undef (CodeGen *g, ZigValue *const_val);
86
- static void gen_undef_init (CodeGen *g, uint32_t ptr_align_bytes , ZigType *value_type, LLVMValueRef ptr);
86
+ static void gen_undef_init (CodeGen *g, ZigType *ptr_type , ZigType *value_type, LLVMValueRef ptr);
87
87
static LLVMValueRef build_alloca (CodeGen *g, ZigType *type_entry, const char *name, uint32_t alignment);
88
88
static LLVMValueRef gen_await_early_return (CodeGen *g, IrInstGen *source_instr,
89
89
LLVMValueRef target_frame_ptr, ZigType *result_type, ZigType *ptr_result_type,
@@ -3351,7 +3351,7 @@ static LLVMValueRef ir_render_ptr_of_array_to_slice(CodeGen *g, IrExecutableGen
3351
3351
gen_store_untyped (g, slice_start_ptr, ptr_field_ptr, 0 , false );
3352
3352
} else if (ir_want_runtime_safety (g, &instruction->base )) {
3353
3353
LLVMValueRef ptr_field_ptr = LLVMBuildStructGEP (g->builder , result_loc, ptr_index, " " );
3354
- gen_undef_init (g, slice_ptr_type-> abi_align , slice_ptr_type, ptr_field_ptr);
3354
+ gen_undef_init (g, slice_ptr_type, slice_ptr_type, ptr_field_ptr);
3355
3355
}
3356
3356
3357
3357
LLVMValueRef len_field_ptr = LLVMBuildStructGEP (g->builder , result_loc, len_index, " " );
@@ -3816,22 +3816,35 @@ static void gen_valgrind_undef(CodeGen *g, LLVMValueRef dest_ptr, LLVMValueRef b
3816
3816
gen_valgrind_client_request (g, zero, req, ptr_as_usize, byte_count, zero, zero, zero);
3817
3817
}
3818
3818
3819
- static void gen_undef_init (CodeGen *g, uint32_t ptr_align_bytes , ZigType *value_type, LLVMValueRef ptr) {
3819
+ static void gen_undef_init (CodeGen *g, ZigType *ptr_type , ZigType *value_type, LLVMValueRef ptr) {
3820
3820
assert (type_has_bits (g, value_type));
3821
+
3822
+ uint64_t ptr_align_bytes = get_ptr_align (g, ptr_type);
3823
+ assert (ptr_align_bytes > 0 );
3821
3824
uint64_t size_bytes = LLVMStoreSizeOfType (g->target_data_ref , get_llvm_type (g, value_type));
3822
3825
assert (size_bytes > 0 );
3823
- assert (ptr_align_bytes > 0 );
3824
- // memset uninitialized memory to 0xaa
3825
- LLVMTypeRef ptr_u8 = LLVMPointerType (LLVMInt8Type (), 0 );
3826
- LLVMValueRef fill_char = LLVMConstInt (LLVMInt8Type (), 0xaa , false );
3827
- LLVMValueRef dest_ptr = LLVMBuildBitCast (g->builder , ptr, ptr_u8, " " );
3828
- ZigType *usize = g->builtin_types .entry_usize ;
3829
- LLVMValueRef byte_count = LLVMConstInt (usize->llvm_type , size_bytes, false );
3830
- ZigLLVMBuildMemSet (g->builder , dest_ptr, fill_char, byte_count, ptr_align_bytes, false );
3831
- // then tell valgrind that the memory is undefined even though we just memset it
3832
- if (g->valgrind_enabled ) {
3833
- gen_valgrind_undef (g, dest_ptr, byte_count);
3826
+
3827
+ if (ptr_type->data .pointer .host_int_bytes == 0 ) {
3828
+ // memset uninitialized memory to 0xaa
3829
+ LLVMTypeRef ptr_u8 = LLVMPointerType (LLVMInt8Type (), 0 );
3830
+ LLVMValueRef fill_char = LLVMConstInt (LLVMInt8Type (), 0xaa , false );
3831
+ LLVMValueRef dest_ptr = LLVMBuildBitCast (g->builder , ptr, ptr_u8, " " );
3832
+ ZigType *usize = g->builtin_types .entry_usize ;
3833
+ LLVMValueRef byte_count = LLVMConstInt (usize->llvm_type , size_bytes, false );
3834
+ ZigLLVMBuildMemSet (g->builder , dest_ptr, fill_char, byte_count, ptr_align_bytes, false );
3835
+ // then tell valgrind that the memory is undefined even though we just memset it
3836
+ if (g->valgrind_enabled ) {
3837
+ gen_valgrind_undef (g, dest_ptr, byte_count);
3838
+ }
3839
+ return ;
3834
3840
}
3841
+
3842
+ // This is a pointer into a packed struct, we can't use memset here.
3843
+ // The jury is still out on what pattern should be written here so clear the
3844
+ // old value and call it a day. Generating a 0xAA...AA mask for this n-bit
3845
+ // value is left as an exercise for the (bored) reader.
3846
+ LLVMValueRef zero = LLVMConstNull (get_llvm_type (g, value_type));
3847
+ gen_assign_raw (g, ptr, ptr_type, zero);
3835
3848
}
3836
3849
3837
3850
static LLVMValueRef ir_render_store_ptr (CodeGen *g, IrExecutableGen *executable, IrInstGenStorePtr *instruction) {
@@ -3860,7 +3873,7 @@ static LLVMValueRef ir_render_store_ptr(CodeGen *g, IrExecutableGen *executable,
3860
3873
LLVMValueRef value = ir_llvm_value (g, instruction->value );
3861
3874
gen_assign_raw (g, ptr, ptr_type, value);
3862
3875
} else if (ir_want_runtime_safety (g, &instruction->base )) {
3863
- gen_undef_init (g, get_ptr_align (g, ptr_type) , instruction->value ->value ->type ,
3876
+ gen_undef_init (g, ptr_type, instruction->value ->value ->type ,
3864
3877
ir_llvm_value (g, instruction->ptr ));
3865
3878
}
3866
3879
return nullptr ;
@@ -5885,7 +5898,7 @@ static LLVMValueRef ir_render_slice(CodeGen *g, IrExecutableGen *executable, IrI
5885
5898
if (slice_start_ptr != nullptr ) {
5886
5899
gen_store_untyped (g, slice_start_ptr, ptr_field_ptr, 0 , false );
5887
5900
} else if (want_runtime_safety) {
5888
- gen_undef_init (g, slice_ptr_type-> abi_align , slice_ptr_type, ptr_field_ptr);
5901
+ gen_undef_init (g, slice_ptr_type, slice_ptr_type, ptr_field_ptr);
5889
5902
} else {
5890
5903
gen_store_untyped (g, LLVMGetUndef (get_llvm_type (g, slice_ptr_type)), ptr_field_ptr, 0 , false );
5891
5904
}
0 commit comments