| ... | @@ -81,8 +81,10 @@ pub const abbrev_base_type = 4; | ... | @@ -81,8 +81,10 @@ pub const abbrev_base_type = 4; |
| 81 | pub const abbrev_ptr_type = 5; | 81 | pub const abbrev_ptr_type = 5; |
| 82 | pub const abbrev_struct_type = 6; | 82 | pub const abbrev_struct_type = 6; |
| 83 | pub const abbrev_struct_member = 7; | 83 | pub const abbrev_struct_member = 7; |
| 84 | pub const abbrev_pad1 = 8; | 84 | pub const abbrev_enum_type = 8; |
| 85 | pub const abbrev_parameter = 9; | 85 | pub const abbrev_enum_variant = 9; |
| | 86 | pub const abbrev_pad1 = 10; |
| | 87 | pub const abbrev_parameter = 11; |
| 86 | | 88 | |
| 87 | /// The reloc offset for the virtual address of a function in its Line Number Program. | 89 | /// The reloc offset for the virtual address of a function in its Line Number Program. |
| 88 | /// Size is a virtual address integer. | 90 | /// Size is a virtual address integer. |
| ... | @@ -879,6 +881,11 @@ fn addDbgInfoType( | ... | @@ -879,6 +881,11 @@ fn addDbgInfoType( |
| 879 | } | 881 | } |
| 880 | }, | 882 | }, |
| 881 | .Struct => blk: { | 883 | .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 | } |
| 882 | // try dbg_info_buffer.ensureUnusedCapacity(23); | 889 | // try dbg_info_buffer.ensureUnusedCapacity(23); |
| 883 | // DW.AT.structure_type | 890 | // DW.AT.structure_type |
| 884 | try dbg_info_buffer.append(abbrev_struct_type); | 891 | try dbg_info_buffer.append(abbrev_struct_type); |
| ... | @@ -918,6 +925,46 @@ fn addDbgInfoType( | ... | @@ -918,6 +925,46 @@ fn addDbgInfoType( |
| 918 | // DW.AT.structure_type delimit children | 925 | // DW.AT.structure_type delimit children |
| 919 | try dbg_info_buffer.append(0); | 926 | try dbg_info_buffer.append(0); |
| 920 | }, | 927 | }, |
| | 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 | }, |
| 921 | else => { | 968 | else => { |
| 922 | log.debug("TODO implement .debug_info for type '{}'", .{ty.fmtDebug()}); | 969 | log.debug("TODO implement .debug_info for type '{}'", .{ty.fmtDebug()}); |
| 923 | try dbg_info_buffer.append(abbrev_pad1); | 970 | try dbg_info_buffer.append(abbrev_pad1); |
| ... | @@ -1006,6 +1053,24 @@ pub fn writeDbgAbbrev(self: *Dwarf, file: *File) !void { | ... | @@ -1006,6 +1053,24 @@ pub fn writeDbgAbbrev(self: *Dwarf, file: *File) !void { |
| 1006 | DW.FORM.sdata, | 1053 | DW.FORM.sdata, |
| 1007 | 0, | 1054 | 0, |
| 1008 | 0, // table sentinel | 1055 | 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 |
| 1009 | abbrev_pad1, | 1074 | abbrev_pad1, |
| 1010 | DW.TAG.unspecified_type, | 1075 | DW.TAG.unspecified_type, |
| 1011 | DW.CHILDREN.no, // header | 1076 | DW.CHILDREN.no, // header |