diff options
| author | kcbanner <kcbanner@gmail.com> | 2023-09-23 14:33:31 -0400 |
|---|---|---|
| committer | kcbanner <kcbanner@gmail.com> | 2023-09-23 14:34:01 -0400 |
| commit | 9f4649b197b720dbc168ced25eee0805d3b678b1 (patch) | |
| tree | edc09234b4d8385fce36a306bb36c55cfadd823c /src/codegen.zig | |
| parent | 4e9f5f25c8226144eff8d9c1df79cfcffbae5492 (diff) | |
| download | zig-9f4649b197b720dbc168ced25eee0805d3b678b1.tar.gz zig-9f4649b197b720dbc168ced25eee0805d3b678b1.zip | |
codegen/sema: handle unions with unknown tags in more places
Diffstat (limited to 'src/codegen.zig')
| -rw-r--r-- | src/codegen.zig | 29 |
1 files changed, 19 insertions, 10 deletions
diff --git a/src/codegen.zig b/src/codegen.zig index 13aefaa8e5..738281cf55 100644 --- a/src/codegen.zig +++ b/src/codegen.zig @@ -583,24 +583,33 @@ pub fn generateSymbol( } const union_obj = mod.typeToUnion(typed_value.ty).?; - const field_index = typed_value.ty.unionTagFieldIndex(un.tag.toValue(), mod).?; + if (un.tag != .none) { + const field_index = typed_value.ty.unionTagFieldIndex(un.tag.toValue(), mod).?; + const field_ty = union_obj.field_types.get(ip)[field_index].toType(); + if (!field_ty.hasRuntimeBits(mod)) { + try code.appendNTimes(0xaa, math.cast(usize, layout.payload_size) orelse return error.Overflow); + } else { + switch (try generateSymbol(bin_file, src_loc, .{ + .ty = field_ty, + .val = un.val.toValue(), + }, code, debug_output, reloc_info)) { + .ok => {}, + .fail => |em| return Result{ .fail = em }, + } - const field_ty = union_obj.field_types.get(ip)[field_index].toType(); - if (!field_ty.hasRuntimeBits(mod)) { - try code.appendNTimes(0xaa, math.cast(usize, layout.payload_size) orelse return error.Overflow); + const padding = math.cast(usize, layout.payload_size - field_ty.abiSize(mod)) orelse return error.Overflow; + if (padding > 0) { + try code.appendNTimes(0, padding); + } + } } else { switch (try generateSymbol(bin_file, src_loc, .{ - .ty = field_ty, + .ty = ip.typeOf(un.val).toType(), .val = un.val.toValue(), }, code, debug_output, reloc_info)) { .ok => {}, .fail => |em| return Result{ .fail = em }, } - - const padding = math.cast(usize, layout.payload_size - field_ty.abiSize(mod)) orelse return error.Overflow; - if (padding > 0) { - try code.appendNTimes(0, padding); - } } if (layout.tag_size > 0 and layout.tag_align.compare(.lt, layout.payload_align)) { |
