authorgravatar for kubkon@jakubkonka.comJakub Konka <kubkon@jakubkonka.com> 2022-03-22 21:27:10+01:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2022-03-22 23:37:20-04:00
log47f1a43bb73607b7bdfcb50de2c4ac8d2bc796af
tree3fc46290e6d1af3add9c0c4bdcd1c898ad07ffe2
parent8f9c3fd3dfb93a8621a55edef8ebfba87c9a6975

dwarf: lower enums


2 files changed, 67 insertions(+), 3 deletions(-)

src/codegen.zig-1
......@@ -479,7 +479,6 @@ pub fn generateSymbol(
479479 return Result{ .appended = {} };
480480 },
481481 .Enum => {
482 // TODO populate .debug_info for the enum
483482 var int_buffer: Value.Payload.U64 = undefined;
484483 const int_val = typed_value.enumToInt(&int_buffer);
485484
src/link/Dwarf.zig+67-2
......@@ -81,8 +81,10 @@ pub const abbrev_base_type = 4;
8181pub const abbrev_ptr_type = 5;
8282pub const abbrev_struct_type = 6;
8383pub const abbrev_struct_member = 7;
84pub const abbrev_pad1 = 8;
85pub const abbrev_parameter = 9;
84pub const abbrev_enum_type = 8;
85pub const abbrev_enum_variant = 9;
86pub const abbrev_pad1 = 10;
87pub const abbrev_parameter = 11;
8688
8789/// The reloc offset for the virtual address of a function in its Line Number Program.
8890/// Size is a virtual address integer.
......@@ -879,6 +881,11 @@ fn addDbgInfoType(
879881 }
880882 },
881883 .Struct => blk: {
884 if (ty.tag() == .tuple) {
885 log.debug("TODO implement .debug_info for type '{}'", .{ty.fmtDebug()});
886 try dbg_info_buffer.append(abbrev_pad1);
887 break :blk;
888 }
882889 // try dbg_info_buffer.ensureUnusedCapacity(23);
883890 // DW.AT.structure_type
884891 try dbg_info_buffer.append(abbrev_struct_type);
......@@ -918,6 +925,46 @@ fn addDbgInfoType(
918925 // DW.AT.structure_type delimit children
919926 try dbg_info_buffer.append(0);
920927 },
928 .Enum => {
929 // DW.AT.enumeration_type
930 try dbg_info_buffer.append(abbrev_enum_type);
931 // DW.AT.byte_size, DW.FORM.sdata
932 const abi_size = ty.abiSize(target);
933 try leb128.writeULEB128(dbg_info_buffer.writer(), abi_size);
934 // DW.AT.name, DW.FORM.string
935 const enum_name = try ty.nameAllocArena(arena, target);
936 try dbg_info_buffer.ensureUnusedCapacity(enum_name.len + 1);
937 dbg_info_buffer.appendSliceAssumeCapacity(enum_name);
938 dbg_info_buffer.appendAssumeCapacity(0);
939
940 const fields = ty.enumFields();
941 const values: ?Module.EnumFull.ValueMap = switch (ty.tag()) {
942 .enum_full, .enum_nonexhaustive => ty.cast(Type.Payload.EnumFull).?.data.values,
943 .enum_simple => null,
944 .enum_numbered => ty.castTag(.enum_numbered).?.data.values,
945 else => unreachable,
946 };
947 const target_endian = self.target.cpu.arch.endian();
948 for (fields.keys()) |field_name, field_i| {
949 // DW.AT.enumerator
950 try dbg_info_buffer.ensureUnusedCapacity(field_name.len + 2 + @sizeOf(u64));
951 dbg_info_buffer.appendAssumeCapacity(abbrev_enum_variant);
952 // DW.AT.name, DW.FORM.string
953 dbg_info_buffer.appendSliceAssumeCapacity(field_name);
954 dbg_info_buffer.appendAssumeCapacity(0);
955 // DW.AT.const_value, DW.FORM.data8
956 const value: u64 = if (values) |vals| value: {
957 if (vals.count() == 0) break :value @intCast(u64, field_i); // auto-numbered
958 const value = vals.keys()[field_i];
959 var int_buffer: Value.Payload.U64 = undefined;
960 break :value value.enumToInt(ty, &int_buffer).toUnsignedInt(target);
961 } else @intCast(u64, field_i);
962 mem.writeInt(u64, dbg_info_buffer.addManyAsArrayAssumeCapacity(8), value, target_endian);
963 }
964
965 // DW.AT.enumeration_type delimit children
966 try dbg_info_buffer.append(0);
967 },
921968 else => {
922969 log.debug("TODO implement .debug_info for type '{}'", .{ty.fmtDebug()});
923970 try dbg_info_buffer.append(abbrev_pad1);
......@@ -1006,6 +1053,24 @@ pub fn writeDbgAbbrev(self: *Dwarf, file: *File) !void {
10061053 DW.FORM.sdata,
10071054 0,
10081055 0, // table sentinel
1056 abbrev_enum_type,
1057 DW.TAG.enumeration_type,
1058 DW.CHILDREN.yes, // header
1059 DW.AT.byte_size,
1060 DW.FORM.sdata,
1061 DW.AT.name,
1062 DW.FORM.string,
1063 0,
1064 0, // table sentinel
1065 abbrev_enum_variant,
1066 DW.TAG.enumerator,
1067 DW.CHILDREN.no, // header
1068 DW.AT.name,
1069 DW.FORM.string,
1070 DW.AT.const_value,
1071 DW.FORM.data8,
1072 0,
1073 0, // table sentinel
10091074 abbrev_pad1,
10101075 DW.TAG.unspecified_type,
10111076 DW.CHILDREN.no, // header