mirror of
https://github.com/ziglang/zig.git
synced 2024-11-27 07:32:44 +00:00
stage1: Reject undefined values when taking union ptr
The code rightfully assumes the union_val object to be fully initialized. Closes #7019
This commit is contained in:
parent
252924ae33
commit
129ccad434
@ -22713,6 +22713,16 @@ static IrInstGen *ir_analyze_container_field_ptr(IrAnalyze *ira, Buf *field_name
|
||||
if (type_is_invalid(union_val->type))
|
||||
return ira->codegen->invalid_inst_gen;
|
||||
|
||||
// Reject undefined values unless we're intializing the union:
|
||||
// a undefined union means also the tag is undefined, accessing
|
||||
// its payload slot is UB.
|
||||
const UndefAllowed allow_undef = initializing ? UndefOk : UndefBad;
|
||||
if ((err = ir_resolve_const_val(ira->codegen, ira->new_irb.exec,
|
||||
source_instr->source_node, union_val, allow_undef)))
|
||||
{
|
||||
return ira->codegen->invalid_inst_gen;
|
||||
}
|
||||
|
||||
if (initializing) {
|
||||
ZigValue *payload_val = ira->codegen->pass1_arena->create<ZigValue>();
|
||||
payload_val->special = ConstValSpecialUndef;
|
||||
@ -22737,6 +22747,7 @@ static IrInstGen *ir_analyze_container_field_ptr(IrAnalyze *ira, Buf *field_name
|
||||
}
|
||||
|
||||
ZigValue *payload_val = union_val->data.x_union.payload;
|
||||
assert(payload_val);
|
||||
|
||||
IrInstGen *result;
|
||||
if (ptr_val->data.x_ptr.mut == ConstPtrMutInfer) {
|
||||
|
@ -11,6 +11,21 @@ pub fn addCases(cases: *tests.CompileErrorContext) void {
|
||||
"tmp.zig:1:50: error: use of undefined value here causes undefined behavior",
|
||||
});
|
||||
|
||||
cases.add("wrong initializer for union payload of type 'type'",
|
||||
\\const U = union(enum) {
|
||||
\\ A: type,
|
||||
\\};
|
||||
\\const S = struct {
|
||||
\\ u: U,
|
||||
\\};
|
||||
\\export fn entry() void {
|
||||
\\ comptime var v: S = undefined;
|
||||
\\ v.u.A = U{ .A = i32 };
|
||||
\\}
|
||||
, &[_][]const u8{
|
||||
"tmp.zig:9:8: error: use of undefined value here causes undefined behavior",
|
||||
});
|
||||
|
||||
cases.add("union with too small explicit signed tag type",
|
||||
\\const U = union(enum(i2)) {
|
||||
\\ A: u8,
|
||||
|
Loading…
Reference in New Issue
Block a user