make form_kind part of DW_Form

This commit is contained in:
Nikita Smith
2026-02-10 15:27:27 -08:00
parent 12f8f4e078
commit 6e100ad52f
2 changed files with 181 additions and 178 deletions
+161 -159
View File
@@ -173,7 +173,7 @@ internal DW_SectionKind
dw_section_kind_from_string(String8 string)
{
DW_SectionKind s = DW_Section_Null;
#define X(_K,_L,_M,_W) \
#define X(_K,_L,_M,_W) \
if (str8_match_lit(_L, string, 0)) { s = DW_Section_##_K; } \
if (str8_match_lit(_M, string, 0)) { s = DW_Section_##_K; }
DW_SectionKind_XList
@@ -185,8 +185,7 @@ internal DW_SectionKind
dw_section_dwo_kind_from_string(String8 string)
{
DW_SectionKind s = DW_Section_Null;
#define X(_K,_L,_M,_W) \
if (str8_match_lit(_W, string, 0)) { s = DW_Section_##_K; }
#define X(_K,_L,_M,_W) if (str8_match_lit(_W, string, 0)) { s = DW_Section_##_K; }
DW_SectionKind_XList
#undef X
return s;
@@ -198,28 +197,37 @@ dw_unit_ranges_from_data(Arena *arena, String8 data)
Rng1U64List result = {0};
for (U64 cursor = 0; cursor < data.size; ) {
// read CU size
U64 cu_size = 0;
U64 cu_size_size = str8_deserial_read_dwarf_packed_size(data, cursor, &cu_size);
// was read ok?
if (cu_size_size == 0) {
break;
U64 start = cursor;
// read unit size
U64 size;
U64 size_size = str8_deserial_read_dwarf_packed_size(data, cursor, &size);
if (size_size == 0) { break; }
cursor += size_size;
// is unit size valid?
if (cursor + size > data.size) { break; }
cursor += size;
// push unit range
if (size > 0) {
rng1u64_list_push(arena, &result, rng_1u64(start, cursor));
}
if (cu_size > 0) {
// push unit range
rng1u64_list_push(arena, &result, rng_1u64(cursor, cursor+cu_size+cu_size_size));
}
// advance
cursor += cu_size_size;
cursor += cu_size;
}
return result;
}
internal Rng1U64Array
dw_unit_ranges_from_data_arr(Arena *arena, String8 data)
{
Temp scratch = scratch_begin(&arena, 1);
Rng1U64List list = dw_unit_ranges_from_data(scratch.arena, data);
Rng1U64Array arr = rng1u64_array_from_list(arena, &list);
scratch_end(scratch);
return arr;
}
internal U64
dw_read_list_unit_header_addr(String8 unit_data, DW_ListUnit *lu_out)
{
@@ -731,8 +739,9 @@ dw_read_form(String8 data,
} break;
default: InvalidPath; break;
}
if (form_out) {
form.kind = form_kind;
*form_out = form;
}
if (bytes_read_out) {
@@ -774,7 +783,7 @@ dw_read_tag(Arena *arena,
if (tag_abbrev_id > 0) {
// map abbrev id -> .debug_abbrev offset
U64 abbrev_cursor = dw_abbrev_offset_from_abbrev_id(abbrev_table, tag_abbrev_id);
if (abbrev_cursor >= abbrev_data.size) { Assert(0 && "failed to find abbrev id"); goto exit; }
if (abbrev_cursor >= abbrev_data.size) { log_user_errorf("failed to find abbrev id 0x%I64x for tag 0x%I64x", tag_abbrev_id, tag_info_off); goto exit; }
// read tag abbrev
DW_Abbrev tag_abbrev = {0};
@@ -817,7 +826,6 @@ dw_read_tag(Arena *arena,
attrib_n->v.abbrev_off = attrib_abbrev_off;
attrib_n->v.abbrev_id = attrib_abbrev.id;
attrib_n->v.attrib_kind = attrib_kind;
attrib_n->v.form_kind = form_kind;
attrib_n->v.form = form;
// push node to list
@@ -882,31 +890,31 @@ dw_u64_from_const_value(String8 const_value)
}
internal U64
dw_interp_sec_offset(DW_FormKind form_kind, DW_Form form)
dw_interp_sec_offset(DW_Form form)
{
U64 sec_offset = 0;
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
sec_offset = form.sec_offset;
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return sec_offset;
}
internal String8
dw_interp_exprloc(DW_FormKind form_kind, DW_Form form)
dw_interp_exprloc(DW_Form form)
{
String8 expr = {0};
if (form_kind == DW_Form_ExprLoc) {
if (form.kind == DW_Form_ExprLoc) {
expr = form.exprloc;
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return expr;
}
internal U128
dw_interp_const_u128(DW_FormKind form_kind, DW_Form form)
dw_interp_const_u128(DW_Form form)
{
AssertAlways(form.data.size <= sizeof(U128));
U128 result = {0};
@@ -915,10 +923,10 @@ dw_interp_const_u128(DW_FormKind form_kind, DW_Form form)
}
internal U64
dw_interp_const64(U64 type_byte_size, DW_ATE type_encoding, DW_FormKind form_kind, DW_Form form)
dw_interp_const64(U64 type_byte_size, DW_ATE type_encoding, DW_Form form)
{
U64 result = max_U64;
if (form_kind == DW_Form_Data1 || form_kind == DW_Form_Data2 || form_kind == DW_Form_Data4 || form_kind == DW_Form_Data8 || form_kind == DW_Form_Data16) {
if (form.kind == DW_Form_Data1 || form.kind == DW_Form_Data2 || form.kind == DW_Form_Data4 || form.kind == DW_Form_Data8 || form.kind == DW_Form_Data16) {
if (form.data.size <= sizeof(result)) {
if (!dw_try_u64_from_const_value(type_byte_size, type_encoding, form.data, &result)) {
Assert(!"unable to decode data");
@@ -926,13 +934,13 @@ dw_interp_const64(U64 type_byte_size, DW_ATE type_encoding, DW_FormKind form_kin
} else {
Assert(!"unable to cast U128 to U64");
}
} else if (form_kind == DW_Form_UData) {
} else if (form.kind == DW_Form_UData) {
result = form.udata;
} else if (form_kind == DW_Form_SData) {
} else if (form.kind == DW_Form_SData) {
result = form.sdata;
} else if (form_kind == DW_Form_ImplicitConst) {
} else if (form.kind == DW_Form_ImplicitConst) {
result = form.implicit_const;
} else if (form_kind == DW_Form_Null) {
} else if (form.kind == DW_Form_Null) {
// skip
} else {
AssertAlways(!"unexpected form");
@@ -941,47 +949,47 @@ dw_interp_const64(U64 type_byte_size, DW_ATE type_encoding, DW_FormKind form_kin
}
internal U64
dw_interp_const_u64(DW_FormKind form_kind, DW_Form form)
dw_interp_const_u64(DW_Form form)
{
return dw_interp_const64(sizeof(U64), DW_ATE_Unsigned, form_kind, form);
return dw_interp_const64(sizeof(U64), DW_ATE_Unsigned, form);
}
internal U32
dw_interp_const_u32(DW_FormKind form_kind, DW_Form form)
dw_interp_const_u32(DW_Form form)
{
U64 const64 = dw_interp_const_u64(form_kind, form);
U64 const64 = dw_interp_const_u64(form);
U32 const32 = safe_cast_u32(const64);
return const32;
}
internal S64
dw_interp_const_s64(DW_FormKind form_kind, DW_Form form)
dw_interp_const_s64(DW_Form form)
{
U64 const_u64 = dw_interp_const_u64(form_kind, form);
U64 const_u64 = dw_interp_const_u64(form);
S64 const_s64 = (S64)const_u64;
return const_s64;
}
internal S32
dw_interp_const_s32(DW_FormKind form_kind, DW_Form form)
dw_interp_const_s32(DW_Form form)
{
U32 const_u32 = dw_interp_const_u32(form_kind, form);
U32 const_u32 = dw_interp_const_u32(form);
S32 const_s32 = (S32)const_u32;
return const_s32;
}
internal U64
dw_interp_address(U64 address_size, U64 base_addr, DW_ListUnit *addr_lu, DW_FormKind form_kind, DW_Form form)
dw_interp_address(U64 address_size, U64 base_addr, DW_ListUnit *addr_lu, DW_Form form)
{
U64 address = 0;
if (form_kind == DW_Form_Addr) {
if (form.kind == DW_Form_Addr) {
if (!dw_try_u64_from_const_value(address_size, DW_ATE_Address, form.addr, &address)) {
AssertAlways(!"unable to decode address");
}
} else if (form_kind == DW_Form_Addrx || form_kind == DW_Form_Addrx1 || form_kind == DW_Form_Addrx2 ||
form_kind == DW_Form_Addrx3 || form_kind == DW_Form_Addrx4) {
} else if (form.kind == DW_Form_Addrx || form.kind == DW_Form_Addrx1 || form.kind == DW_Form_Addrx2 ||
form.kind == DW_Form_Addrx3 || form.kind == DW_Form_Addrx4) {
address = dw_addr_from_list_unit(addr_lu, form.xval);
} else if (form_kind == DW_Form_SecOffset) {
} else if (form.kind == DW_Form_SecOffset) {
if (addr_lu->segment_selector_size > 0) {
AssertAlways(!"TODO: support for segmented address space");
}
@@ -990,14 +998,14 @@ dw_interp_address(U64 address_size, U64 base_addr, DW_ListUnit *addr_lu, DW_Form
} else {
Assert(!"out of bounds .debug_addr offset");
}
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return address;
}
internal String8
dw_interp_block(DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form)
dw_interp_block(DW_Input *input, DW_CompUnit *cu, DW_Form form)
{
NotImplemented;
return str8_zero();
@@ -1007,24 +1015,23 @@ internal String8
dw_interp_string(DW_Input *input,
DW_Format unit_format,
DW_ListUnit *str_offsets,
DW_FormKind form_kind,
DW_Form form)
{
String8 string = {0};
if (form_kind == DW_Form_String) {
if (form.kind == DW_Form_String) {
string = form.string;
} else if (form_kind == DW_Form_Strp) {
} else if (form.kind == DW_Form_Strp) {
U64 bytes_read = str8_deserial_read_cstr(input->sec[DW_Section_Str].data, form.sec_offset, &string);
Assert(bytes_read > 0);
} else if (form_kind == DW_Form_LineStrp) {
} else if (form.kind == DW_Form_LineStrp) {
U64 bytes_read = str8_deserial_read_cstr(input->sec[DW_Section_LineStr].data, form.sec_offset, &string);
Assert(bytes_read > 0);
} else if (form_kind == DW_Form_StrpSup) {
} else if (form.kind == DW_Form_StrpSup) {
U64 bytes_read = str8_deserial_read_cstr(input->sec[DW_Section_Str].data, form.strp_sup, &string);
Assert(bytes_read > 0);
} else if (form_kind == DW_Form_Strx || form_kind == DW_Form_Strx1 ||
form_kind == DW_Form_Strx2 || form_kind == DW_Form_Strx3 ||
form_kind == DW_Form_Strx4) {
} else if (form.kind == DW_Form_Strx || form.kind == DW_Form_Strx1 ||
form.kind == DW_Form_Strx2 || form.kind == DW_Form_Strx3 ||
form.kind == DW_Form_Strx4) {
U64 sec_offset = dw_offset_from_list_unit(str_offsets, form.xval);
if (sec_offset < input->sec[DW_Section_Str].data.size) {
U64 bytes_read = str8_deserial_read_cstr(input->sec[DW_Section_Str].data, sec_offset, &string);
@@ -1032,78 +1039,73 @@ dw_interp_string(DW_Input *input,
} else {
AssertAlways(!"unable to translate index to offset");
}
} else if (form_kind == DW_Form_GNU_StrpAlt) {
} else if (form.kind == DW_Form_GNU_StrpAlt) {
NotImplemented;
} else if (form_kind == DW_Form_GNU_StrIndex) {
} else if (form.kind == DW_Form_GNU_StrIndex) {
NotImplemented;
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return string;
}
internal String8
dw_interp_line_ptr(DW_Input *input, DW_FormKind form_kind, DW_Form form)
dw_interp_line_ptr(DW_Input *input, DW_Form form)
{
String8 result = {0};
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
result = str8_skip(input->sec[DW_Section_Line].data, form.sec_offset);
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return result;
}
internal DW_LineFile *
dw_interp_file(DW_LineVMHeader *line_vm, DW_FormKind form_kind, DW_Form form)
dw_interp_file(DW_LineVM *line_vm, DW_Form form)
{
DW_LineFile *result = 0;
U64 file_idx = dw_interp_const_u64(form_kind, form);
if (file_idx < line_vm->file_table.count) {
result = &line_vm->file_table.v[file_idx];
} else {
Assert(!"out of bounds file index");
}
U64 file_idx = dw_interp_const_u64(form);
DW_LineFile *result = dw_line_vm_find_file(line_vm, file_idx);
return result;
}
internal DW_Reference
dw_interp_ref(DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form)
dw_interp_ref(DW_Input *input, DW_CompUnit *cu, DW_Form form)
{
DW_Reference ref = {0};
if (form_kind == DW_Form_Ref1 || form_kind == DW_Form_Ref2 ||
form_kind == DW_Form_Ref4 || form_kind == DW_Form_Ref8 ||
form_kind == DW_Form_RefUData) {
if (form.kind == DW_Form_Ref1 || form.kind == DW_Form_Ref2 ||
form.kind == DW_Form_Ref4 || form.kind == DW_Form_Ref8 ||
form.kind == DW_Form_RefUData) {
ref.cu = cu;
ref.info_off = cu->info_range.min + form.ref;
} else if (form_kind == DW_Form_RefAddr) {
} else if (form.kind == DW_Form_RefAddr) {
NotImplemented;
} else if (form_kind == DW_Form_RefSig8) {
} else if (form.kind == DW_Form_RefSig8) {
NotImplemented;
} else if (form_kind == DW_Form_RefSup4 || form_kind == DW_Form_RefSup8) {
} else if (form.kind == DW_Form_RefSup4 || form.kind == DW_Form_RefSup8) {
NotImplemented;
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return ref;
}
internal DW_LocList
dw_interp_loclist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form)
dw_interp_loclist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Form form)
{
DW_LocList loclist = {0};
if (cu->version < DW_Version_5) {
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
U64 sec_offset = max_U64;
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
sec_offset = form.sec_offset;
} else if (form_kind == DW_Form_Data8 || form_kind == DW_Form_Data4 ||
form_kind == DW_Form_Data2 || form_kind == DW_Form_Data1) {
} else if (form.kind == DW_Form_Data8 || form.kind == DW_Form_Data4 ||
form.kind == DW_Form_Data2 || form.kind == DW_Form_Data1) {
if (!dw_try_u64_from_const_value(form.data.size, DW_ATE_Unsigned, form.data, &sec_offset)) {
Assert(!"unable to extract section offset");
}
} else if (form_kind == DW_Form_Null) {
} else if (form.kind == DW_Form_Null) {
Assert(!"unexpected form");
}
@@ -1157,22 +1159,22 @@ dw_interp_loclist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind fo
cursor += expr_size;
}
}
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
} else {
DW_Version version = DW_Version_Null;
String8 raw_lle = {0};
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
// offset is from beginning of the section
U64 sec_offset = form.sec_offset;
raw_lle = str8_skip(input->sec[DW_Section_LocLists].data, sec_offset);
} else if (form_kind == DW_Form_LocListx) {
} else if (form.kind == DW_Form_LocListx) {
// offset is from beginning of the entries
U64 entries_off = dw_offset_from_list_unit(cu->loclists_lu, form.xval);
raw_lle = str8_skip(cu->loclists_lu->entries, entries_off);
version = cu->loclists_lu->version;
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
@@ -1364,33 +1366,33 @@ dw_interp_loclist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind fo
}
internal B32
dw_interp_flag(DW_FormKind form_kind, DW_Form form)
dw_interp_flag(DW_Form form)
{
B32 flag = 0;
if (form_kind == DW_Form_Flag || form_kind == DW_Form_FlagPresent) {
if (form.kind == DW_Form_Flag || form.kind == DW_Form_FlagPresent) {
flag = form.flag;
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
return flag;
}
internal Rng1U64List
dw_interp_rnglist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form)
dw_interp_rnglist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Form form)
{
Rng1U64List rnglist = {0};
if (cu->version < DW_Version_5) {
// decode section offset
U64 sec_offset = max_U64;
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
sec_offset = form.sec_offset;
} else if (form_kind == DW_Form_Data8 || form_kind == DW_Form_Data4 ||
form_kind == DW_Form_Data2 || form_kind == DW_Form_Data1) {
} else if (form.kind == DW_Form_Data8 || form.kind == DW_Form_Data4 ||
form.kind == DW_Form_Data2 || form.kind == DW_Form_Data1) {
if (!dw_try_u64_from_const_value(form.data.size, DW_ATE_Unsigned, form.data, &sec_offset)) {
Assert(!"unable to extract section offset");
}
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
Assert(!"unexpected form");
}
@@ -1428,15 +1430,15 @@ dw_interp_rnglist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind fo
}
} else {
String8 raw_rle = {0};
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
// offset is from beginning of the section
U64 sec_offset = form.sec_offset;
raw_rle = str8_skip(input->sec[DW_Section_RngLists].data, sec_offset);
} else if (form_kind == DW_Form_RngListx) {
} else if (form.kind == DW_Form_RngListx) {
// offset is from beginning of the entries
U64 sec_offset = dw_offset_from_list_unit(cu->rnglists_lu, form.xval);
raw_rle = str8_skip(cu->rnglists_lu->entries, sec_offset);
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
AssertAlways(!"unexpected form");
}
@@ -1567,47 +1569,47 @@ dw_interp_rnglist(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind fo
}
internal String8
dw_interp_secptr(DW_Input *input, DW_SectionKind section, DW_FormKind form_kind, DW_Form form)
dw_interp_secptr(DW_Input *input, DW_SectionKind section, DW_Form form)
{
String8 secptr = {0};
if (form_kind == DW_Form_SecOffset) {
if (form.kind == DW_Form_SecOffset) {
String8 sect = input->sec[section].data;
Rng1U64 range = rng_1u64(form.sec_offset, sect.size);
secptr = str8_substr(sect, range);
} else if (form_kind != DW_Form_Null) {
} else if (form.kind != DW_Form_Null) {
Assert(!"unexpected form");
}
return secptr;
}
internal String8
dw_interp_addrptr(DW_Input *input, DW_FormKind form_kind, DW_Form form)
dw_interp_addrptr(DW_Input *input, DW_Form form)
{
return dw_interp_secptr(input, DW_Section_Addr, form_kind, form);
return dw_interp_secptr(input, DW_Section_Addr, form);
}
internal String8
dw_interp_str_offsets_ptr(DW_Input *input, DW_FormKind form_kind, DW_Form form)
dw_interp_str_offsets_ptr(DW_Input *input, DW_Form form)
{
return dw_interp_secptr(input, DW_Section_StrOffsets, form_kind, form);
return dw_interp_secptr(input, DW_Section_StrOffsets, form);
}
internal String8
dw_interp_rnglists_ptr(DW_Input *input, DW_FormKind form_kind, DW_Form form)
dw_interp_rnglists_ptr(DW_Input *input, DW_Form form)
{
return dw_interp_secptr(input, DW_Section_RngLists, form_kind, form);
return dw_interp_secptr(input, DW_Section_RngLists, form);
}
internal String8
dw_interp_loclists_ptr(DW_Input *input, DW_FormKind form_kind, DW_Form form)
dw_interp_loclists_ptr(DW_Input *input, DW_Form form)
{
return dw_interp_secptr(input, DW_Section_LocLists, form_kind, form);
return dw_interp_secptr(input, DW_Section_LocLists, form);
}
internal DW_AttribClass
dw_value_class_from_attrib(DW_CompUnit *cu, DW_Attrib *attrib)
{
return dw_pick_attrib_value_class(cu->version, cu->ext, cu->relaxed, attrib->attrib_kind, attrib->form_kind);
return dw_pick_attrib_value_class(cu->version, cu->ext, cu->relaxed, attrib->attrib_kind, attrib->form.kind);
}
internal String8
@@ -1615,7 +1617,7 @@ dw_exprloc_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_ExprLoc || value_class == DW_AttribClass_Block);
return dw_interp_exprloc(attrib->form_kind, attrib->form);
return dw_interp_exprloc(attrib->form);
}
internal U128
@@ -1623,7 +1625,7 @@ dw_const_u128_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Const);
return dw_interp_const_u128(attrib->form_kind, attrib->form);
return dw_interp_const_u128(attrib->form);
}
internal U64
@@ -1631,7 +1633,7 @@ dw_const_u64_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Const);
return dw_interp_const_u64(attrib->form_kind, attrib->form);
return dw_interp_const_u64(attrib->form);
}
internal U32
@@ -1639,7 +1641,7 @@ dw_const_u32_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Const);
return dw_interp_const_u32(attrib->form_kind, attrib->form);
return dw_interp_const_u32(attrib->form);
}
internal S64
@@ -1647,7 +1649,7 @@ dw_const_s64_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Const);
return dw_interp_const_s64(attrib->form_kind, attrib->form);
return dw_interp_const_s64(attrib->form);
}
internal S32
@@ -1655,7 +1657,7 @@ dw_const_s32_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Const);
return dw_interp_const_s32(attrib->form_kind, attrib->form);
return dw_interp_const_s32(attrib->form);
}
internal B32
@@ -1663,7 +1665,7 @@ dw_flag_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Flag);
return dw_interp_flag(attrib->form_kind, attrib->form);
return dw_interp_flag(attrib->form);
}
internal U64
@@ -1673,22 +1675,18 @@ dw_address_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
AssertAlways(value_class == DW_AttribClass_Null ||
value_class == DW_AttribClass_Address ||
value_class == DW_AttribClass_AddrPtr);
DW_FormKind form_kind = attrib->form_kind;
DW_Form form = attrib->form;
DW_Form form = attrib->form;
if (value_class == DW_AttribClass_AddrPtr) {
if (attrib->form_kind == DW_Form_SecOffset) {
if (attrib->form.kind == DW_Form_SecOffset) {
NotImplemented;
} else {
AssertAlways(!"unexpected form");
}
form_kind = DW_Form_Addr;
form.addr = dw_interp_addrptr(input, attrib->form_kind, attrib->form);
form.kind = DW_Form_Addr;
form.addr = dw_interp_addrptr(input, attrib->form);
}
return dw_interp_address(cu->address_size, cu->low_pc, cu->addr_lu, form_kind, form);
return dw_interp_address(cu->address_size, cu->low_pc, cu->addr_lu, form);
}
internal String8
@@ -1696,7 +1694,7 @@ dw_block_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Block);
return dw_interp_block(input, cu, attrib->form_kind, attrib->form);
return dw_interp_block(input, cu, attrib->form);
}
internal String8
@@ -1704,7 +1702,7 @@ dw_string_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_String || value_class == DW_AttribClass_StrOffsetsPtr);
return dw_interp_string(input, cu->format, cu->str_offsets_lu, attrib->form_kind, attrib->form);
return dw_interp_string(input, cu->format, cu->str_offsets_lu, attrib->form);
}
internal String8
@@ -1712,15 +1710,15 @@ dw_line_ptr_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_LinePtr);
return dw_interp_line_ptr(input, attrib->form_kind, attrib->form);
return dw_interp_line_ptr(input, attrib->form);
}
internal DW_LineFile *
dw_file_from_attrib(DW_CompUnit *cu, DW_LineVMHeader *line_vm, DW_Attrib *attrib)
dw_file_from_attrib(DW_CompUnit *cu, DW_LineVM *line_vm, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Const);
return dw_interp_file(line_vm, attrib->form_kind, attrib->form);
return dw_interp_file(line_vm, attrib->form);
}
internal DW_Reference
@@ -1728,7 +1726,7 @@ dw_ref_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
AssertAlways(value_class == DW_AttribClass_Null || value_class == DW_AttribClass_Reference);
return dw_interp_ref(input, cu, attrib->form_kind, attrib->form);
return dw_interp_ref(input, cu, attrib->form);
}
internal DW_LocList
@@ -1738,7 +1736,7 @@ dw_loclist_from_attrib(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Attrib
AssertAlways(value_class == DW_AttribClass_Null ||
value_class == DW_AttribClass_LocList ||
value_class == DW_AttribClass_LocListPtr);
return dw_interp_loclist(arena, input, cu, attrib->form_kind, attrib->form);
return dw_interp_loclist(arena, input, cu, attrib->form);
}
internal Rng1U64List
@@ -1747,7 +1745,7 @@ dw_rnglist_from_attrib(Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Attrib
Rng1U64List rnglist = {0};
DW_AttribClass value_class = dw_value_class_from_attrib(cu, attrib);
if (value_class == DW_AttribClass_RngListPtr || value_class == DW_AttribClass_RngList) {
rnglist = dw_interp_rnglist(arena, input, cu, attrib->form_kind, attrib->form);
rnglist = dw_interp_rnglist(arena, input, cu, attrib->form);
} else if (value_class != DW_AttribClass_Null) {
Assert(!"unexpected value class");
}
@@ -1777,7 +1775,7 @@ dw_attrib_from_tag(DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind k
if (cu && cu->tag_ht) {
DW_Attrib *ao_attrib = dw_attrib_from_tag_(tag, DW_AttribKind_AbstractOrigin);
if (ao_attrib->attrib_kind == DW_AttribKind_AbstractOrigin) {
DW_Reference ref = dw_interp_ref(input, cu, ao_attrib->form_kind, ao_attrib->form);
DW_Reference ref = dw_interp_ref(input, cu, ao_attrib->form);
DW_TagNode *ref_tag = dw_tag_node_from_info_off(ref.cu, ref.info_off);
attrib = dw_attrib_from_tag_(ref_tag->tag, kind);
}
@@ -1868,7 +1866,7 @@ dw_flag_from_tag_attrib_kind(DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_At
}
internal DW_LineFile *
dw_file_from_tag_attrib_kind(DW_Input *input, DW_CompUnit *cu, DW_LineVMHeader *line_vm, DW_Tag tag, DW_AttribKind kind)
dw_file_from_tag_attrib_kind(DW_Input *input, DW_CompUnit *cu, DW_LineVM *line_vm, DW_Tag tag, DW_AttribKind kind)
{
return dw_file_from_attrib(cu, line_vm, dw_attrib_from_tag(input, cu, tag, kind));
}
@@ -1929,11 +1927,11 @@ dw_u64_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind k
U64 type_byte_size = dw_byte_size_from_tag(input, cu, type_tag);
DW_ATE type_encoding = dw_const_u64_from_tag_attrib_kind(input, type_ref.cu, type_tag, DW_AttribKind_Encoding);
if (type_encoding == DW_ATE_Unsigned || type_encoding == DW_ATE_UnsignedChar) {
result = dw_interp_const64(type_byte_size, type_encoding, attrib->form_kind, attrib->form);
result = dw_interp_const64(type_byte_size, type_encoding, attrib->form);
}
scratch_end(scratch);
} else {
result = dw_interp_const_u64(attrib->form_kind, attrib->form);
result = dw_interp_const_u64(attrib->form);
}
} else if (attrib_class == DW_AttribClass_Address) {
result = dw_address_from_attrib(input, cu, attrib);
@@ -1949,7 +1947,7 @@ internal B32
dw_is_attrib_var_ref(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib)
{
B32 is_var_ref = 0;
if (dw_is_form_kind_ref(cu->version, cu->ext, attrib->form_kind)) {
if (dw_is_form_kind_ref(cu->version, cu->ext, attrib->form.kind)) {
Temp scratch = scratch_begin(0,0);
DW_Reference ref = dw_ref_from_attrib(input, cu, attrib);
DW_Tag ref_tag = {0};
@@ -2029,8 +2027,8 @@ dw_cu_from_info_off(Arena *arena, DW_Input *input, DW_ListUnitInput lu_input, U6
dw_read_tag(arena, input, abbrev_table, version, format, address_size, info_range, cu_header_offset + header_size, &cu_tag);
// TODO: handle these unit types
Assert(cu_tag.kind != DW_TagKind_SkeletonUnit);
Assert(cu_tag.kind != DW_TagKind_TypeUnit);
if (cu_tag.kind == DW_TagKind_SkeletonUnit) { log_user_errorf("TODO: Skeleton Unit"); }
if (cu_tag.kind == DW_TagKind_TypeUnit) { log_user_errorf("TODO Type Unit"); }
if (cu_tag.kind != DW_TagKind_CompileUnit && cu_tag.kind != DW_TagKind_PartialUnit) {
// unexpected tag, release memory and exit
@@ -2045,10 +2043,10 @@ dw_cu_from_info_off(Arena *arena, DW_Input *input, DW_ListUnitInput lu_input, U6
DW_Attrib *loclists_base_attrib = dw_attrib_from_tag(0, 0, cu_tag, DW_AttribKind_LocListsBase );
// interp attribs as section offsets
U64 addr_sec_off = dw_interp_sec_offset(addr_base_attrib->form_kind, addr_base_attrib->form );
U64 str_offsets_sec_off = dw_interp_sec_offset(str_offsets_base_attrib->form_kind, str_offsets_base_attrib->form);
U64 rnglists_sec_off = dw_interp_sec_offset(rnglists_base_attrib->form_kind, rnglists_base_attrib->form );
U64 loclists_sec_off = dw_interp_sec_offset(loclists_base_attrib->form_kind, loclists_base_attrib->form );
U64 addr_sec_off = dw_interp_sec_offset(addr_base_attrib->form );
U64 str_offsets_sec_off = dw_interp_sec_offset(str_offsets_base_attrib->form);
U64 rnglists_sec_off = dw_interp_sec_offset(rnglists_base_attrib->form );
U64 loclists_sec_off = dw_interp_sec_offset(loclists_base_attrib->form );
// map section offset to unit index
U64 addr_lu_idx = rng_1u64_array_bsearch(lu_input.addr_ranges, addr_sec_off );
@@ -2064,7 +2062,7 @@ dw_cu_from_info_off(Arena *arena, DW_Input *input, DW_ListUnitInput lu_input, U6
// find compile unit base address
DW_Attrib *low_pc_attrib = dw_attrib_from_tag(0, 0, cu_tag, DW_AttribKind_LowPc);
U64 low_pc = dw_interp_address(address_size, max_U64, addr_lu, low_pc_attrib->form_kind, low_pc_attrib->form);
U64 low_pc = dw_interp_address(address_size, max_U64, addr_lu, low_pc_attrib->form);
// fill out compile unit
cu.relaxed = relaxed;
@@ -2194,7 +2192,7 @@ dw_read_line_vm_header(Arena *arena,
DW_LineVMHeader *header_out)
{
Temp scratch = scratch_begin(&arena, 1);
// read unit length
U64 length = 0;
U64 length_size = str8_deserial_read_dwarf_packed_size(cu_stmt_list, 0, &length);
@@ -2339,7 +2337,7 @@ dw_read_line_vm_header(Arena *arena,
U64 form_size = 0;
if (!dw_read_form(str8_skip(data, cursor), version, format, address_size, form_kind, max_U64, &form, &form_size)) { goto exit; }
cursor += form_size;
dir_table.v[i] = dw_interp_string(input, format, cu_str_offsets, form_kind, form);
dir_table.v[i] = dw_interp_string(input, format, cu_str_offsets, form);
}
}
@@ -2372,12 +2370,12 @@ dw_read_line_vm_header(Arena *arena,
cursor += form_size;
switch (lnct) {
case DW_LNCT_Path: { file->file_name = dw_interp_string(input, format, cu_str_offsets, form_kind, form); } break;
case DW_LNCT_DirectoryIndex: { file->dir_idx = dw_interp_const_u64(form_kind, form); } break;
case DW_LNCT_TimeStamp: { file->modify_time = dw_interp_const_u64(form_kind, form); } break;
case DW_LNCT_Size: { file->file_size = dw_interp_const_u64(form_kind, form); } break;
case DW_LNCT_MD5: { file->md5_digest = dw_interp_const_u128(form_kind, form); } break;
case DW_LNCT_LLVM_Source: { file->source = dw_interp_string(input, format, cu_str_offsets, form_kind, form); } break;
case DW_LNCT_Path: { file->file_name = dw_interp_string(input, format, cu_str_offsets, form); } break;
case DW_LNCT_DirectoryIndex: { file->dir_idx = dw_interp_const_u64(form); } break;
case DW_LNCT_TimeStamp: { file->modify_time = dw_interp_const_u64(form); } break;
case DW_LNCT_Size: { file->file_size = dw_interp_const_u64(form); } break;
case DW_LNCT_MD5: { file->md5_digest = dw_interp_const_u128(form); } break;
case DW_LNCT_LLVM_Source: { file->source = dw_interp_string(input, format, cu_str_offsets, form); } break;
default: {
Assert(!"unexpected LNTC encoding");
} break;
@@ -2424,7 +2422,11 @@ dw_line_vm_init(DW_Input *input, DW_CompUnit *cu)
// read the line table header
DW_LineVMHeader header = {0};
if ( ! dw_read_line_vm_header(arena, input, cu_stmt_list, cu_dir, cu_name, cu->address_size, cu->str_offsets_lu, &header)) { goto exit; }
if (cu_stmt_list.size) {
if ( ! dw_read_line_vm_header(arena, input, cu_stmt_list, cu_dir, cu_name, cu->address_size, cu->str_offsets_lu, &header)) {
goto exit;
}
}
vm = push_array(arena, DW_LineVM, 1);
*vm = (DW_LineVM){
+20 -19
View File
@@ -423,7 +423,8 @@ internal U64 str8_deserial_read_sleb128 (String8 string, U64 off, S64 *
internal U64 str8_deserial_read_uleb128_array(Arena *arena, String8 string, U64 off, U64 count, U64 **arr_out);
internal U64 str8_deserial_read_sleb128_array(Arena *arena, String8 string, U64 off, U64 count, S64 **arr_out);
internal Rng1U64List dw_unit_ranges_from_data(Arena *arena, String8 data);
internal Rng1U64List dw_unit_ranges_from_data(Arena *arena, String8 data);
internal Rng1U64Array dw_unit_ranges_from_data_arr(Arena *arena, String8 data);
// list units
@@ -452,22 +453,22 @@ internal U64 dw_read_tag_cu(Arena *arena, DW_Input *input, DW_CompUnit *cu, U64
// attrib interp
internal U64 dw_interp_sec_offset(DW_FormKind form_kind, DW_Form form);
internal String8 dw_interp_exprloc (DW_FormKind form_kind, DW_Form form);
internal U128 dw_interp_const_u128(DW_FormKind form_kind, DW_Form form);
internal U64 dw_interp_const_u64 (DW_FormKind form_kind, DW_Form form);
internal U32 dw_interp_const_u32 (DW_FormKind form_kind, DW_Form form);
internal S64 dw_interp_const_s64 (DW_FormKind form_kind, DW_Form form);
internal S32 dw_interp_const_s32 (DW_FormKind form_kind, DW_Form form);
internal B32 dw_interp_flag (DW_FormKind form_kind, DW_Form form);
internal U64 dw_interp_address (U64 address_size, U64 base_addr, DW_ListUnit *addr_xlist, DW_FormKind form_kind, DW_Form form);
internal String8 dw_interp_block (DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form);
internal String8 dw_interp_string (DW_Input *input, DW_Format unit_format, DW_ListUnit *str_offsets, DW_FormKind form_kind, DW_Form form);
internal String8 dw_interp_line_ptr (DW_Input *input, DW_FormKind form_kind, DW_Form form);
internal DW_LineFile * dw_interp_file (DW_LineVMHeader *line_vm, DW_FormKind form_kind, DW_Form form);
internal DW_Reference dw_interp_ref (DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form);
internal DW_LocList dw_interp_loclist (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form);
internal Rng1U64List dw_interp_rnglist (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_FormKind form_kind, DW_Form form);
internal U64 dw_interp_sec_offset(DW_Form form);
internal String8 dw_interp_exprloc (DW_Form form);
internal U128 dw_interp_const_u128(DW_Form form);
internal U64 dw_interp_const_u64 (DW_Form form);
internal U32 dw_interp_const_u32 (DW_Form form);
internal S64 dw_interp_const_s64 (DW_Form form);
internal S32 dw_interp_const_s32 (DW_Form form);
internal B32 dw_interp_flag (DW_Form form);
internal U64 dw_interp_address (U64 address_size, U64 base_addr, DW_ListUnit *addr_xlist, DW_Form form);
internal String8 dw_interp_block (DW_Input *input, DW_CompUnit *cu, DW_Form form);
internal String8 dw_interp_string (DW_Input *input, DW_Format unit_format, DW_ListUnit *str_offsets, DW_Form form);
internal String8 dw_interp_line_ptr (DW_Input *input, DW_Form form);
internal DW_LineFile * dw_interp_file (DW_LineVM *line_vm, DW_Form form);
internal DW_Reference dw_interp_ref (DW_Input *input, DW_CompUnit *cu, DW_Form form);
internal DW_LocList dw_interp_loclist (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Form form);
internal Rng1U64List dw_interp_rnglist (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Form form);
internal String8 dw_exprloc_from_attrib (DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
internal U128 dw_const_u128_from_attrib(DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
@@ -480,7 +481,7 @@ internal U64 dw_address_from_attrib (DW_Input *input, DW_CompUnit *c
internal String8 dw_block_from_attrib (DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
internal String8 dw_string_from_attrib (DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
internal String8 dw_line_ptr_from_attrib (DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
internal DW_LineFile * dw_file_from_attrib (DW_CompUnit *cu, DW_LineVMHeader *line_vm, DW_Attrib *attrib);
internal DW_LineFile * dw_file_from_attrib (DW_CompUnit *cu, DW_LineVM *line_vm, DW_Attrib *attrib);
internal DW_Reference dw_ref_from_attrib (DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
internal DW_LocList dw_loclist_from_attrib (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
internal Rng1U64List dw_rnglist_from_attrib (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Attrib *attrib);
@@ -495,7 +496,7 @@ internal String8 dw_block_from_tag_attrib_kind (DW_Input *input, DW_Co
internal String8 dw_string_from_tag_attrib_kind (DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind kind);
internal String8 dw_line_ptr_from_tag_attrib_kind (DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind kind);
internal String8 dw_line_ptr_from_tag_attrib_kind (DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind kind);
internal DW_LineFile * dw_file_from_tag_attrib_kind (DW_Input *input, DW_CompUnit *cu, DW_LineVMHeader *line_vm, DW_Tag tag, DW_AttribKind kind);
internal DW_LineFile * dw_file_from_tag_attrib_kind (DW_Input *input, DW_CompUnit *cu, DW_LineVM *line_vm, DW_Tag tag, DW_AttribKind kind);
internal DW_Reference dw_ref_from_tag_attrib_kind (DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind kind);
internal DW_LocList dw_loclist_from_tag_attrib_kind (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind kind);
internal Rng1U64List dw_rnglist_from_tag_attrib_kind (Arena *arena, DW_Input *input, DW_CompUnit *cu, DW_Tag tag, DW_AttribKind kind);