zig

fork of https://codeberg.org/ziglang/zig
Log | Files | Refs | README | LICENSE

commit 7eb5acdc800b6683e4f3ce9312f707e568bb641e (tree)
parent 217a5090ffed74f071a5c33798e3de029a2ee3fa
Author: Andrew Kelley <andrew@ziglang.org>
Date:   Sun, 24 Nov 2019 18:57:07 -0500

fix casting `[N:x]T` to `[N]T` memcpying too many bytes

Diffstat:
Msrc/ir.cpp | 14+++++++++++++-
1 file changed, 13 insertions(+), 1 deletion(-)

diff --git a/src/ir.cpp b/src/ir.cpp @@ -16333,7 +16333,19 @@ static IrInstruction *ir_resolve_result_raw(IrAnalyze *ira, IrInstruction *suspe if (!type_has_bits(value_type)) { parent_ptr_align = 0; } - ZigType *ptr_type = get_pointer_to_type_extra(ira->codegen, value_type, + // If we're casting from a sentinel-terminated array to a non-sentinel-terminated array, + // we actually need the result location pointer to *not* have a sentinel. Otherwise the generated + // memcpy will write an extra byte to the destination, and THAT'S NO GOOD. + ZigType *ptr_elem_type; + if (value_type->id == ZigTypeIdArray && value_type->data.array.sentinel != nullptr && + dest_type->id == ZigTypeIdArray && dest_type->data.array.sentinel == nullptr) + { + ptr_elem_type = get_array_type(ira->codegen, value_type->data.array.child_type, + value_type->data.array.len, nullptr); + } else { + ptr_elem_type = value_type; + } + ZigType *ptr_type = get_pointer_to_type_extra(ira->codegen, ptr_elem_type, parent_ptr_type->data.pointer.is_const, parent_ptr_type->data.pointer.is_volatile, PtrLenSingle, parent_ptr_align, 0, 0, parent_ptr_type->data.pointer.allow_zero);