This series is mainly a change in internal structures for describing functions: - symt_function doesn't support multi range of addresses - while symt_inlinesite does That's the major difference between the two. So the aim of this serie is to decribe function and inline sites with a single structure.
-- v2: dbghelp: Get rid of symt_inlinesite by merging it inside symt_function. dbghelp: Use addr_range for storing symt_function address and size. dbghelp: Store address range as FAM in symt_inlinesite. dbghelp: No longer pass inline site's address upon creation.
From: Eric Pouech eric.pouech@gmail.com
Rather use the first address of the first defined range of address.
Signed-off-by: Eric Pouech eric.pouech@gmail.com --- dlls/dbghelp/dbghelp_private.h | 1 - dlls/dbghelp/dwarf.c | 4 +++- dlls/dbghelp/msc.c | 33 +++++---------------------------- dlls/dbghelp/symbol.c | 5 ++--- 4 files changed, 10 insertions(+), 33 deletions(-)
diff --git a/dlls/dbghelp/dbghelp_private.h b/dlls/dbghelp/dbghelp_private.h index daf15732877..d1ca5d38868 100644 --- a/dlls/dbghelp/dbghelp_private.h +++ b/dlls/dbghelp/dbghelp_private.h @@ -850,7 +850,6 @@ extern struct symt_inlinesite* struct symt_function* func, struct symt* parent, const char* name, - ULONG_PTR addr, struct symt* type) DECLSPEC_HIDDEN; extern void symt_add_func_line(struct module* module, struct symt_function* func, diff --git a/dlls/dbghelp/dwarf.c b/dlls/dbghelp/dwarf.c index f9ffa374dbc..cc31cc7912c 100644 --- a/dlls/dbghelp/dwarf.c +++ b/dlls/dbghelp/dwarf.c @@ -2141,13 +2141,15 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, subpgm->top_func, subpgm->current_block ? &subpgm->current_block->symt : &subpgm->current_func->symt, dwarf2_get_cpp_name(di, name.u.string), - adranges[0].low, &sig_type->symt); + &sig_type->symt); subpgm->current_func = (struct symt_function*)inlined; subpgm->current_block = NULL;
for (i = 0; i < num_adranges; ++i) symt_add_inlinesite_range(subpgm->ctx->module_ctx->module, inlined, adranges[i].low, adranges[i].high); + /* temporary: update address field */ + inlined->func.address = adranges[0].low; free(adranges);
children = dwarf2_get_di_children(di); diff --git a/dlls/dbghelp/msc.c b/dlls/dbghelp/msc.c index 872b0e70b58..39beaf80c12 100644 --- a/dlls/dbghelp/msc.c +++ b/dlls/dbghelp/msc.c @@ -2101,7 +2101,7 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu const union codeview_type* cvt; struct symt_inlinesite* inlined; struct cv_binannot cvba; - BOOL srcok, found = FALSE; + BOOL srcok; unsigned offset, line, srcfile; const struct CV_Checksum_t* chksms;
@@ -2111,42 +2111,17 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu return NULL; }
- /* grasp first code offset in binary annotation to compute inline site start address */ - cvba.annot = annot; - cvba.last_annot = last_annot; - while (codeview_advance_binannot(&cvba)) - if (cvba.opcode == BA_OP_CodeOffset || - cvba.opcode == BA_OP_ChangeCodeOffset || - cvba.opcode == BA_OP_ChangeCodeOffsetAndLineOffset) - { - offset = cvba.arg1; - found = TRUE; - break; - } - else if (cvba.opcode == BA_OP_ChangeCodeLengthAndCodeOffset) - { - offset = cvba.arg2; - found = TRUE; - break; - } - - if (!found) - { - WARN("Couldn't find start address of inlined\n"); - return NULL; - } - switch (cvt->generic.id) { case LF_FUNC_ID: inlined = symt_new_inlinesite(msc_dbg->module, top_func, container, - cvt->func_id_v3.name, top_func->address + offset, + cvt->func_id_v3.name, codeview_get_type(cvt->func_id_v3.type, FALSE)); break; case LF_MFUNC_ID: /* FIXME we just declare a function, not a method */ inlined = symt_new_inlinesite(msc_dbg->module, top_func, container, - cvt->mfunc_id_v3.name, top_func->address + offset, + cvt->mfunc_id_v3.name, codeview_get_type(cvt->mfunc_id_v3.type, FALSE)); break; default: @@ -2228,6 +2203,8 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu if (range->low == range->high) WARN("pending empty range at end of %s inside %s\n", inlined->func.hash_elt.name, top_func->hash_elt.name); + /* temporary: update address field */ + inlined->func.address = ((struct addr_range*)vector_at(&inlined->vranges, 0))->low; } return inlined; } diff --git a/dlls/dbghelp/symbol.c b/dlls/dbghelp/symbol.c index 6e6c35e9b98..082eec2a555 100644 --- a/dlls/dbghelp/symbol.c +++ b/dlls/dbghelp/symbol.c @@ -362,17 +362,16 @@ struct symt_inlinesite* symt_new_inlinesite(struct module* module, struct symt_function* func, struct symt* container, const char* name, - ULONG_PTR addr, struct symt* sig_type) { struct symt_inlinesite* sym;
- TRACE_(dbghelp_symt)("Adding inline site %s @%Ix\n", name, addr); + TRACE_(dbghelp_symt)("Adding inline site %s\n", name); if ((sym = pool_alloc(&module->pool, sizeof(*sym)))) { struct symt** p; assert(container); - init_function_or_inlinesite(&sym->func, module, SymTagInlineSite, container, name, addr, 0, sig_type); + init_function_or_inlinesite(&sym->func, module, SymTagInlineSite, container, name, 0, 0, sig_type); vector_init(&sym->vranges, sizeof(struct addr_range), 2); /* FIXME: number of elts => to be set on input */ /* chain inline sites */ sym->func.next_inlinesite = func->next_inlinesite;
From: Eric Pouech eric.pouech@gmail.com
Signed-off-by: Eric Pouech eric.pouech@gmail.com --- dlls/dbghelp/dbghelp_private.h | 11 +++-- dlls/dbghelp/dwarf.c | 23 +++++----- dlls/dbghelp/msc.c | 79 +++++++++++++++++++++++++--------- dlls/dbghelp/symbol.c | 50 +++------------------ 4 files changed, 81 insertions(+), 82 deletions(-)
diff --git a/dlls/dbghelp/dbghelp_private.h b/dlls/dbghelp/dbghelp_private.h index d1ca5d38868..b574dbc7462 100644 --- a/dlls/dbghelp/dbghelp_private.h +++ b/dlls/dbghelp/dbghelp_private.h @@ -294,7 +294,8 @@ struct symt_function struct symt_inlinesite { struct symt_function func; - struct vector vranges; /* of addr_range: where the inline site is actually defined */ + unsigned num_ranges; + struct addr_range ranges[]; };
struct symt_hierarchy_point @@ -850,7 +851,8 @@ extern struct symt_inlinesite* struct symt_function* func, struct symt* parent, const char* name, - struct symt* type) DECLSPEC_HIDDEN; + struct symt* type, + unsigned num_ranges) DECLSPEC_HIDDEN; extern void symt_add_func_line(struct module* module, struct symt_function* func, unsigned source_idx, int line_num, @@ -880,11 +882,8 @@ extern struct symt_hierarchy_point* enum SymTagEnum point, const struct location* loc, const char* name) DECLSPEC_HIDDEN; -extern BOOL symt_add_inlinesite_range(struct module* module, - struct symt_inlinesite* inlined, - ULONG_PTR low, ULONG_PTR high) DECLSPEC_HIDDEN; extern struct symt_thunk* - symt_new_thunk(struct module* module, + symt_new_thunk(struct module* module, struct symt_compiland* parent, const char* name, THUNK_ORDINAL ord, ULONG_PTR addr, ULONG_PTR size) DECLSPEC_HIDDEN; diff --git a/dlls/dbghelp/dwarf.c b/dlls/dbghelp/dwarf.c index cc31cc7912c..dd8606634ee 100644 --- a/dlls/dbghelp/dwarf.c +++ b/dlls/dbghelp/dwarf.c @@ -2117,12 +2117,11 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, struct vector* children; dwarf2_debug_info_t*child; unsigned int i; - struct addr_range* adranges; - unsigned num_adranges; + unsigned num_ranges;
TRACE("%s\n", dwarf2_debug_di(di));
- if ((adranges = dwarf2_get_ranges(di, &num_adranges)) == NULL) + if (!(num_ranges = dwarf2_get_num_ranges(di))) { WARN("cannot read ranges\n"); return; @@ -2141,16 +2140,17 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, subpgm->top_func, subpgm->current_block ? &subpgm->current_block->symt : &subpgm->current_func->symt, dwarf2_get_cpp_name(di, name.u.string), - &sig_type->symt); + &sig_type->symt, num_ranges); subpgm->current_func = (struct symt_function*)inlined; subpgm->current_block = NULL;
- for (i = 0; i < num_adranges; ++i) - symt_add_inlinesite_range(subpgm->ctx->module_ctx->module, inlined, - adranges[i].low, adranges[i].high); + if (!dwarf2_fill_ranges(di, inlined->ranges, num_ranges)) + { + FIXME("Unexpected situation\n"); + inlined->num_ranges = 0; + } /* temporary: update address field */ - inlined->func.address = adranges[0].low; - free(adranges); + inlined->func.address = inlined->ranges[0].low;
children = dwarf2_get_di_children(di); if (children) for (i = 0; i < vector_length(children); i++) @@ -2616,10 +2616,9 @@ static void dwarf2_set_line_number(struct module* module, ULONG_PTR address, for (inlined = func->next_inlinesite; inlined; inlined = inlined->func.next_inlinesite) { int i; - for (i = 0; i < inlined->vranges.num_elts; ++i) + for (i = 0; i < inlined->num_ranges; ++i) { - struct addr_range* ar = (struct addr_range*)vector_at(&inlined->vranges, i); - if (ar->low <= address && address < ar->high) + if (inlined->ranges[i].low <= address && address < inlined->ranges[i].high) { symt_add_func_line(module, &inlined->func, *psrc, line, address); return; /* only add to lowest matching inline site */ diff --git a/dlls/dbghelp/msc.c b/dlls/dbghelp/msc.c index 39beaf80c12..228b7019d4e 100644 --- a/dlls/dbghelp/msc.c +++ b/dlls/dbghelp/msc.c @@ -2077,18 +2077,48 @@ static BOOL cv_dbgsubsect_find_inlinee(const struct msc_debug_info* msc_dbg, return FALSE; }
-static inline void inline_site_update_last_range(struct symt_inlinesite* inlined, ULONG_PTR hi) +static inline void inline_site_update_last_range(struct symt_inlinesite* inlined, unsigned index, ULONG_PTR hi) { - unsigned num = inlined->vranges.num_elts; - if (num) + if (index && index <= inlined->num_ranges) { - struct addr_range* range = vector_at(&inlined->vranges, num - 1); + struct addr_range* range = &inlined->ranges[index - 1]; /* only change range if it has no span (code start without code end) */ if (range->low == range->high) range->high = hi; } }
+static unsigned inline_site_get_num_ranges(const unsigned char* annot, + const unsigned char* last_annot) +{ + struct cv_binannot cvba; + unsigned num_ranges = 0; + + cvba.annot = annot; + cvba.last_annot = last_annot; + + while (codeview_advance_binannot(&cvba)) + { + switch (cvba.opcode) + { + case BA_OP_CodeOffset: + case BA_OP_ChangeCodeLength: + case BA_OP_ChangeFile: + case BA_OP_ChangeLineOffset: + break; + case BA_OP_ChangeCodeOffset: + case BA_OP_ChangeCodeOffsetAndLineOffset: + case BA_OP_ChangeCodeLengthAndCodeOffset: + num_ranges++; + break; + default: + WARN("Unsupported op %d\n", cvba.opcode); + break; + } + } + return num_ranges; +} + static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debug_info* msc_dbg, const struct cv_module_snarf* cvmod, struct symt_function* top_func, @@ -2102,7 +2132,8 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu struct symt_inlinesite* inlined; struct cv_binannot cvba; BOOL srcok; - unsigned offset, line, srcfile; + unsigned num_ranges; + unsigned offset, index, line, srcfile; const struct CV_Checksum_t* chksms;
if (!cvmod->ipi_ctp || !(cvt = codeview_jump_to_type(cvmod->ipi_ctp, inlinee))) @@ -2110,19 +2141,23 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu FIXME("Couldn't find type %x in IPI stream\n", inlinee); return NULL; } + num_ranges = inline_site_get_num_ranges(annot, last_annot); + if (!num_ranges) return NULL;
switch (cvt->generic.id) { case LF_FUNC_ID: inlined = symt_new_inlinesite(msc_dbg->module, top_func, container, cvt->func_id_v3.name, - codeview_get_type(cvt->func_id_v3.type, FALSE)); + codeview_get_type(cvt->func_id_v3.type, FALSE), + num_ranges); break; case LF_MFUNC_ID: /* FIXME we just declare a function, not a method */ inlined = symt_new_inlinesite(msc_dbg->module, top_func, container, cvt->mfunc_id_v3.name, - codeview_get_type(cvt->mfunc_id_v3.type, FALSE)); + codeview_get_type(cvt->mfunc_id_v3.type, FALSE), + num_ranges); break; default: FIXME("unsupported inlinee kind %x\n", cvt->generic.id); @@ -2144,6 +2179,7 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu
/* rescan all annotations and store ranges & line information */ offset = 0; + index = 0; cvba.annot = annot; cvba.last_annot = last_annot;
@@ -2156,18 +2192,15 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu break; case BA_OP_ChangeCodeOffset: offset += cvba.arg1; - inline_site_update_last_range(inlined, top_func->address + offset); + inline_site_update_last_range(inlined, index, top_func->address + offset); if (srcok) symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->address + offset); - symt_add_inlinesite_range(msc_dbg->module, inlined, top_func->address + offset, top_func->address + offset); + inlined->ranges[index ].low = top_func->address + offset; + inlined->ranges[index++].high = top_func->address + offset; break; case BA_OP_ChangeCodeLength: /* this op doesn't seem widely used... */ - if (inlined->vranges.num_elts) - { - struct addr_range* range = vector_at(&inlined->vranges, inlined->vranges.num_elts - 1); - inline_site_update_last_range(inlined, range->low + cvba.arg1); - } + inline_site_update_last_range(inlined, index, inlined->ranges[index - 1].low + cvba.arg1); break; case BA_OP_ChangeFile: chksms = CV_RECORD_GAP(hdr_files, cvba.arg1); @@ -2180,31 +2213,35 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu case BA_OP_ChangeCodeOffsetAndLineOffset: line += binannot_getsigned(cvba.arg2); offset += cvba.arg1; - inline_site_update_last_range(inlined, top_func->address + offset); + inline_site_update_last_range(inlined, index, top_func->address + offset); if (srcok) symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->address + offset); - symt_add_inlinesite_range(msc_dbg->module, inlined, top_func->address + offset, top_func->address + offset); + inlined->ranges[index ].low = top_func->address + offset; + inlined->ranges[index++].high = top_func->address + offset; break; case BA_OP_ChangeCodeLengthAndCodeOffset: offset += cvba.arg2; - inline_site_update_last_range(inlined, top_func->address + offset); + inline_site_update_last_range(inlined, index, top_func->address + offset); if (srcok) symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->address + offset); - symt_add_inlinesite_range(msc_dbg->module, inlined, top_func->address + offset, top_func->address + offset + cvba.arg1); + inlined->ranges[index ].low = top_func->address + offset; + inlined->ranges[index++].high = top_func->address + offset + cvba.arg1; break; default: WARN("Unsupported op %d\n", cvba.opcode); break; } } - if (inlined->vranges.num_elts) + if (index != num_ranges) /* sanity check */ + FIXME("Internal logic error\n"); + if (inlined->num_ranges) { - struct addr_range* range = vector_at(&inlined->vranges, inlined->vranges.num_elts - 1); + struct addr_range* range = &inlined->ranges[inlined->num_ranges - 1]; if (range->low == range->high) WARN("pending empty range at end of %s inside %s\n", inlined->func.hash_elt.name, top_func->hash_elt.name); /* temporary: update address field */ - inlined->func.address = ((struct addr_range*)vector_at(&inlined->vranges, 0))->low; + inlined->func.address = inlined->ranges[0].low; } return inlined; } diff --git a/dlls/dbghelp/symbol.c b/dlls/dbghelp/symbol.c index 082eec2a555..614bf40f0a3 100644 --- a/dlls/dbghelp/symbol.c +++ b/dlls/dbghelp/symbol.c @@ -362,20 +362,21 @@ struct symt_inlinesite* symt_new_inlinesite(struct module* module, struct symt_function* func, struct symt* container, const char* name, - struct symt* sig_type) + struct symt* sig_type, + unsigned num_ranges) { struct symt_inlinesite* sym;
TRACE_(dbghelp_symt)("Adding inline site %s\n", name); - if ((sym = pool_alloc(&module->pool, sizeof(*sym)))) + if ((sym = pool_alloc(&module->pool, offsetof(struct symt_inlinesite, ranges[num_ranges])))) { struct symt** p; assert(container); init_function_or_inlinesite(&sym->func, module, SymTagInlineSite, container, name, 0, 0, sig_type); - vector_init(&sym->vranges, sizeof(struct addr_range), 2); /* FIXME: number of elts => to be set on input */ /* chain inline sites */ sym->func.next_inlinesite = func->next_inlinesite; func->next_inlinesite = sym; + sym->num_ranges = num_ranges; if (container->tag == SymTagFunction || container->tag == SymTagInlineSite) p = vector_add(&((struct symt_function*)container)->vchildren, &module->pool); else @@ -534,7 +535,7 @@ struct symt_block* symt_open_func_block(struct module* module, assert(num_ranges > 0); assert(!parent_block || parent_block->symt.tag == SymTagBlock);
- block = pool_alloc(&module->pool, sizeof(*block) + num_ranges * sizeof(block->ranges[0])); + block = pool_alloc(&module->pool, offsetof(struct symt_block, ranges[num_ranges])); block->symt.tag = SymTagBlock; block->num_ranges = num_ranges; block->container = parent_block ? &parent_block->symt : &func->symt; @@ -579,42 +580,6 @@ struct symt_hierarchy_point* symt_add_function_point(struct module* module, return sym; }
-/* low and high are absolute addresses */ -BOOL symt_add_inlinesite_range(struct module* module, - struct symt_inlinesite* inlined, - ULONG_PTR low, ULONG_PTR high) -{ - struct addr_range* p; - - p = vector_add(&inlined->vranges, &module->pool); - p->low = low; - p->high = high; - if (TRUE) - { - int i; - - /* see dbghelp_private.h for the assumptions */ - for (i = 0; i < inlined->vranges.num_elts - 1; i++) - { - if (!addr_range_disjoint((struct addr_range*)vector_at(&inlined->vranges, i), p)) - { - FIXME("Added addr_range isn't disjoint from siblings\n"); - } - } - for ( ; inlined->func.symt.tag != SymTagFunction; inlined = (struct symt_inlinesite*)symt_get_upper_inlined(inlined)) - { - for (i = 0; i < inlined->vranges.num_elts; i++) - { - struct addr_range* ar = (struct addr_range*)vector_at(&inlined->vranges, i); - if (!addr_range_disjoint(ar, p) && !addr_range_inside(ar, p)) - WARN("Added addr_range not compatible with parent\n"); - } - } - } - - return TRUE; -} - struct symt_thunk* symt_new_thunk(struct module* module, struct symt_compiland* compiland, const char* name, THUNK_ORDINAL ord, @@ -1244,11 +1209,10 @@ struct symt_inlinesite* symt_find_lowest_inlined(struct symt_function* func, DWO assert(func->symt.tag == SymTagFunction); for (current = func->next_inlinesite; current; current = current->func.next_inlinesite) { - for (i = 0; i < current->vranges.num_elts; ++i) + for (i = 0; i < current->num_ranges; ++i) { - struct addr_range* ar = (struct addr_range*)vector_at(¤t->vranges, i); /* first matching range gives the lowest inline site; see dbghelp_private.h for details */ - if (ar->low <= addr && addr < ar->high) + if (current->ranges[i].low <= addr && addr < current->ranges[i].high) return current; } }
From: Eric Pouech eric.pouech@gmail.com
Signed-off-by: Eric Pouech eric.pouech@gmail.com --- dlls/dbghelp/dbghelp.c | 2 +- dlls/dbghelp/dbghelp_private.h | 8 +++++-- dlls/dbghelp/dwarf.c | 4 ++-- dlls/dbghelp/elf_module.c | 27 ++++++++++++----------- dlls/dbghelp/macho_module.c | 11 +++++----- dlls/dbghelp/msc.c | 40 +++++++++++++++++----------------- dlls/dbghelp/stabs.c | 20 ++++++++--------- dlls/dbghelp/symbol.c | 6 ++--- dlls/dbghelp/type.c | 6 ++--- 9 files changed, 65 insertions(+), 59 deletions(-)
diff --git a/dlls/dbghelp/dbghelp.c b/dlls/dbghelp/dbghelp.c index 3ad8d179c65..3fd40fbb21e 100644 --- a/dlls/dbghelp/dbghelp.c +++ b/dlls/dbghelp/dbghelp.c @@ -694,7 +694,7 @@ BOOL WINAPI SymSetScopeFromIndex(HANDLE hProcess, ULONG64 addr, DWORD index) sym = symt_index2ptr(pair.effective, index); if (!symt_check_tag(sym, SymTagFunction)) return FALSE;
- pair.pcs->localscope_pc = ((struct symt_function*)sym)->address; /* FIXME of FuncDebugStart when it exists? */ + pair.pcs->localscope_pc = ((struct symt_function*)sym)->ranges[0].low; /* FIXME of FuncDebugStart when it exists? */ pair.pcs->localscope_symt = sym;
return TRUE; diff --git a/dlls/dbghelp/dbghelp_private.h b/dlls/dbghelp/dbghelp_private.h index b574dbc7462..a8e862076bc 100644 --- a/dlls/dbghelp/dbghelp_private.h +++ b/dlls/dbghelp/dbghelp_private.h @@ -120,6 +120,11 @@ struct addr_range DWORD64 high; /* absolute address of first byte after the range */ };
+static inline DWORD64 addr_range_size(const struct addr_range* ar) +{ + return ar->high - ar->low; +} + /* tests whether ar2 is inside ar1 */ static inline BOOL addr_range_inside(const struct addr_range* ar1, const struct addr_range* ar2) { @@ -281,13 +286,12 @@ struct symt_function { struct symt symt; /* SymTagFunction (or SymTagInlineSite when embedded in symt_inlinesite) */ struct hash_table_elt hash_elt; /* if global symbol */ - ULONG_PTR address; struct symt* container; /* compiland */ struct symt* type; /* points to function_signature */ - ULONG_PTR size; struct vector vlines; struct vector vchildren; /* locals, params, blocks, start/end, labels, inline sites */ struct symt_inlinesite* next_inlinesite;/* linked list of inline sites in this function */ + struct addr_range ranges[1]; };
/* a symt_inlinesite* can be casted to a symt_function* to access all function bits */ diff --git a/dlls/dbghelp/dwarf.c b/dlls/dbghelp/dwarf.c index dd8606634ee..80be7aa5814 100644 --- a/dlls/dbghelp/dwarf.c +++ b/dlls/dbghelp/dwarf.c @@ -2093,7 +2093,7 @@ static void dwarf2_parse_subprogram_label(dwarf2_subprogram_t* subpgm, if (dwarf2_find_attribute(di, DW_AT_low_pc, &low_pc)) { loc.kind = loc_absolute; - loc.offset = subpgm->ctx->module_ctx->load_offset + low_pc.u.uvalue - subpgm->top_func->address; + loc.offset = subpgm->ctx->module_ctx->load_offset + low_pc.u.uvalue - subpgm->top_func->ranges[0].low; symt_add_function_point(subpgm->ctx->module_ctx->module, subpgm->top_func, SymTagLabel, &loc, name.u.string); } @@ -2150,7 +2150,7 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, inlined->num_ranges = 0; } /* temporary: update address field */ - inlined->func.address = inlined->ranges[0].low; + inlined->func.ranges[0].low = inlined->ranges[0].low;
children = dwarf2_get_di_children(di); if (children) for (i = 0; i < vector_length(children); i++) diff --git a/dlls/dbghelp/elf_module.c b/dlls/dbghelp/elf_module.c index 306fecc1272..bc063bf1466 100644 --- a/dlls/dbghelp/elf_module.c +++ b/dlls/dbghelp/elf_module.c @@ -841,6 +841,7 @@ static void elf_finish_stabs_info(struct module* module, const struct hash_table struct symt_ht* sym; const struct elf_sym* symp; struct elf_module_info* elf_info = module->format_info[DFI_ELF]->u.elf_info; + DWORD64 size;
hash_table_iter_init(&module->ht_symbols, &hti, NULL); while ((ptr = hash_table_iter_up(&hti))) @@ -849,8 +850,8 @@ static void elf_finish_stabs_info(struct module* module, const struct hash_table switch (sym->symt.tag) { case SymTagFunction: - if (((struct symt_function*)sym)->address != elf_info->elf_addr && - ((struct symt_function*)sym)->size) + size = addr_range_size(&((struct symt_function*)sym)->ranges[0]); + if (((struct symt_function*)sym)->ranges[0].low != elf_info->elf_addr && size) { break; } @@ -858,19 +859,19 @@ static void elf_finish_stabs_info(struct module* module, const struct hash_table ((struct symt_function*)sym)->container); if (symp) { - if (((struct symt_function*)sym)->address != elf_info->elf_addr && - ((struct symt_function*)sym)->address != elf_info->elf_addr + symp->st_value) - FIXME("Changing address for %p/%s!%s from %08Ix to %I64x\n", + if (((struct symt_function*)sym)->ranges[0].low != elf_info->elf_addr && + ((struct symt_function*)sym)->ranges[0].low != elf_info->elf_addr + symp->st_value) + FIXME("Changing address for %p/%s!%s from %I64x to %I64x\n", sym, debugstr_w(module->modulename), sym->hash_elt.name, - ((struct symt_function*)sym)->address, + ((struct symt_function*)sym)->ranges[0].low, elf_info->elf_addr + symp->st_value); - if (((struct symt_function*)sym)->size && ((struct symt_function*)sym)->size != symp->st_size) - FIXME("Changing size for %p/%s!%s from %08Ix to %08x\n", + if (size && size != symp->st_size) + FIXME("Changing size for %p/%s!%s from %I64x to %I64x\n", sym, debugstr_w(module->modulename), sym->hash_elt.name, - ((struct symt_function*)sym)->size, (unsigned int)symp->st_size); + size, symp->st_size);
- ((struct symt_function*)sym)->address = elf_info->elf_addr + symp->st_value; - ((struct symt_function*)sym)->size = symp->st_size; + ((struct symt_function*)sym)->ranges[0].low = elf_info->elf_addr + symp->st_value; + ((struct symt_function*)sym)->ranges[0].high = elf_info->elf_addr + symp->st_value + symp->st_size; } else FIXME("Couldn't find %s!%s\n", debugstr_w(module->modulename), sym->hash_elt.name); @@ -889,9 +890,9 @@ static void elf_finish_stabs_info(struct module* module, const struct hash_table { if (((struct symt_data*)sym)->u.var.offset != elf_info->elf_addr && ((struct symt_data*)sym)->u.var.offset != elf_info->elf_addr + symp->st_value) - FIXME("Changing address for %p/%s!%s from %08Ix to %I64x\n", + FIXME("Changing address for %p/%s!%s from %I64x to %I64x\n", sym, debugstr_w(module->modulename), sym->hash_elt.name, - ((struct symt_function*)sym)->address, + ((struct symt_function*)sym)->ranges[0].low, elf_info->elf_addr + symp->st_value); ((struct symt_data*)sym)->u.var.offset = elf_info->elf_addr + symp->st_value; ((struct symt_data*)sym)->kind = elf_is_local_symbol(symp->st_info) ? diff --git a/dlls/dbghelp/macho_module.c b/dlls/dbghelp/macho_module.c index 16fa0f815a9..4852f5beaa4 100644 --- a/dlls/dbghelp/macho_module.c +++ b/dlls/dbghelp/macho_module.c @@ -1063,15 +1063,16 @@ static void macho_finish_stabs(struct module* module, struct hash_table* ht_symt { case SymTagFunction: func = (struct symt_function*)sym; - if (func->address == module->format_info[DFI_MACHO]->u.macho_info->load_addr) + if (func->ranges[0].low == module->format_info[DFI_MACHO]->u.macho_info->load_addr) { - TRACE("Adjusting function %p/%s!%s from 0x%08Ix to 0x%08Ix\n", func, + TRACE("Adjusting function %p/%s!%s from %#I64x to %#Ix\n", func, debugstr_w(module->modulename), sym->hash_elt.name, - func->address, ste->addr); - func->address = ste->addr; + func->ranges[0].low, ste->addr); + func->ranges[0].high += ste->addr - func->ranges[0].low; + func->ranges[0].low = ste->addr; adjusted = TRUE; } - if (func->address == ste->addr) + if (func->ranges[0].low == ste->addr) ste->used = 1; break; case SymTagData: diff --git a/dlls/dbghelp/msc.c b/dlls/dbghelp/msc.c index 228b7019d4e..7bbc5d6bbd7 100644 --- a/dlls/dbghelp/msc.c +++ b/dlls/dbghelp/msc.c @@ -1614,7 +1614,7 @@ static void codeview_snarf_linetab(const struct msc_debug_info* msc_dbg, const B /* unfortunately, we can have several functions in the same block, if there's no * gap between them... find the new function if needed */ - if (!func || addr >= func->address + func->size) + if (!func || addr >= func->ranges[0].high) { func = (struct symt_function*)symt_find_symbol_at(msc_dbg->module, addr); /* FIXME: at least labels support line numbers */ @@ -1927,8 +1927,8 @@ static unsigned codeview_transform_defrange(const struct msc_debug_info* msc_dbg break; case S_DEFRANGE_FRAMEPOINTER_REL_FULL_SCOPE: locinfo->offset = symrange->defrange_frameptr_relfullscope_v3.offFramePointer; - locinfo->start = curr_func->address; - locinfo->rangelen = curr_func->size; + locinfo->start = curr_func->ranges[0].low; + locinfo->rangelen = addr_range_size(&curr_func->ranges[0]); break; case S_DEFRANGE_REGISTER_REL: locinfo->reg = symrange->defrange_registerrel_v3.baseReg; @@ -2192,11 +2192,11 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu break; case BA_OP_ChangeCodeOffset: offset += cvba.arg1; - inline_site_update_last_range(inlined, index, top_func->address + offset); + inline_site_update_last_range(inlined, index, top_func->ranges[0].low + offset); if (srcok) - symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->address + offset); - inlined->ranges[index ].low = top_func->address + offset; - inlined->ranges[index++].high = top_func->address + offset; + symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->ranges[0].low + offset); + inlined->ranges[index ].low = top_func->ranges[0].low + offset; + inlined->ranges[index++].high = top_func->ranges[0].low + offset; break; case BA_OP_ChangeCodeLength: /* this op doesn't seem widely used... */ @@ -2213,19 +2213,19 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu case BA_OP_ChangeCodeOffsetAndLineOffset: line += binannot_getsigned(cvba.arg2); offset += cvba.arg1; - inline_site_update_last_range(inlined, index, top_func->address + offset); + inline_site_update_last_range(inlined, index, top_func->ranges[0].low + offset); if (srcok) - symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->address + offset); - inlined->ranges[index ].low = top_func->address + offset; - inlined->ranges[index++].high = top_func->address + offset; + symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->ranges[0].low + offset); + inlined->ranges[index ].low = top_func->ranges[0].low + offset; + inlined->ranges[index++].high = top_func->ranges[0].low + offset; break; case BA_OP_ChangeCodeLengthAndCodeOffset: offset += cvba.arg2; - inline_site_update_last_range(inlined, index, top_func->address + offset); + inline_site_update_last_range(inlined, index, top_func->ranges[0].low + offset); if (srcok) - symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->address + offset); - inlined->ranges[index ].low = top_func->address + offset; - inlined->ranges[index++].high = top_func->address + offset + cvba.arg1; + symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->ranges[0].low + offset); + inlined->ranges[index ].low = top_func->ranges[0].low + offset; + inlined->ranges[index++].high = top_func->ranges[0].low + offset + cvba.arg1; break; default: WARN("Unsupported op %d\n", cvba.opcode); @@ -2241,7 +2241,7 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu inlined->func.hash_elt.name, top_func->hash_elt.name); /* temporary: update address field */ - inlined->func.address = inlined->ranges[0].low; + inlined->func.ranges[0].low = inlined->ranges[0].low; } return inlined; } @@ -2534,7 +2534,7 @@ static BOOL codeview_snarf(const struct msc_debug_info* msc_dbg, if (curr_func) { loc.kind = loc_absolute; - loc.offset = codeview_get_address(msc_dbg, sym->label_v1.segment, sym->label_v1.offset) - curr_func->address; + loc.offset = codeview_get_address(msc_dbg, sym->label_v1.segment, sym->label_v1.offset) - curr_func->ranges[0].low; symt_add_function_point(msc_dbg->module, curr_func, SymTagLabel, &loc, terminate_string(&sym->label_v1.p_name)); } @@ -2546,7 +2546,7 @@ static BOOL codeview_snarf(const struct msc_debug_info* msc_dbg, if (curr_func) { loc.kind = loc_absolute; - loc.offset = codeview_get_address(msc_dbg, sym->label_v3.segment, sym->label_v3.offset) - curr_func->address; + loc.offset = codeview_get_address(msc_dbg, sym->label_v3.segment, sym->label_v3.offset) - curr_func->ranges[0].low; symt_add_function_point(msc_dbg->module, curr_func, SymTagLabel, &loc, sym->label_v3.name); } @@ -2798,8 +2798,8 @@ static BOOL codeview_is_inside(const struct cv_local_info* locinfo, const struct /* ip must be in local_info range, but not in any of its gaps */ if (ip < locinfo->start || ip >= locinfo->start + locinfo->rangelen) return FALSE; for (i = 0; i < locinfo->ngaps; ++i) - if (func->address + locinfo->gaps[i].gapStartOffset <= ip && - ip < func->address + locinfo->gaps[i].gapStartOffset + locinfo->gaps[i].cbRange) + if (func->ranges[0].low + locinfo->gaps[i].gapStartOffset <= ip && + ip < func->ranges[0].low + locinfo->gaps[i].gapStartOffset + locinfo->gaps[i].cbRange) return FALSE; return TRUE; } diff --git a/dlls/dbghelp/stabs.c b/dlls/dbghelp/stabs.c index 5969780fe35..f21f7e15d0b 100644 --- a/dlls/dbghelp/stabs.c +++ b/dlls/dbghelp/stabs.c @@ -1166,9 +1166,9 @@ static void pending_flush(struct pending_list* pending, struct module* module, break; case PENDING_LINE: if (module->type == DMT_MACHO) - pending->objs[i].u.line.offset -= func->address - pending->objs[i].u.line.load_offset; + pending->objs[i].u.line.offset -= func->ranges[0].low - pending->objs[i].u.line.load_offset; symt_add_func_line(module, func, pending->objs[i].u.line.source_idx, - pending->objs[i].u.line.line_num, func->address + pending->objs[i].u.line.offset); + pending->objs[i].u.line.line_num, func->ranges[0].low + pending->objs[i].u.line.offset); break; default: ERR("Unknown pending object tag %u\n", (unsigned)pending->objs[i].tag); @@ -1199,15 +1199,15 @@ static void stabs_finalize_function(struct module* module, struct symt_function* * Not 100% bullet proof, but better than nothing */ il.SizeOfStruct = sizeof(il); - if (SymGetLineFromAddr64(module->process->handle, func->address, &disp, &il) && + if (SymGetLineFromAddr64(module->process->handle, func->ranges[0].low, &disp, &il) && SymGetLineNext64(module->process->handle, &il)) { loc.kind = loc_absolute; - loc.offset = il.Address - func->address; + loc.offset = il.Address - func->ranges[0].low; symt_add_function_point(module, func, SymTagFuncDebugStart, &loc, NULL); } - if (size) func->size = size; + if (size) func->ranges[0].high = func->ranges[0].low + size; }
static inline void stabbuf_append(char **buf, unsigned *buf_size, const char *str) @@ -1375,7 +1375,7 @@ BOOL stabs_parse(struct module* module, ULONG_PTR load_offset, if (curr_func) { block = symt_open_func_block(module, curr_func, block, 1); - block->ranges[0].low = curr_func->address + n_value; + block->ranges[0].low = curr_func->ranges[0].low + n_value; block->ranges[0].high = 0; /* will be set by N_RBRAC */ pending_flush(&pending_block, module, curr_func, block); } @@ -1383,7 +1383,7 @@ BOOL stabs_parse(struct module* module, ULONG_PTR load_offset, case N_RBRAC: if (curr_func) { - block->ranges[0].high = curr_func->address + n_value; + block->ranges[0].high = curr_func->ranges[0].low + n_value; block = symt_close_func_block(module, curr_func, block); } break; @@ -1493,9 +1493,9 @@ BOOL stabs_parse(struct module* module, ULONG_PTR load_offset, { ULONG_PTR offset = n_value; if (module->type == DMT_MACHO) - offset -= curr_func->address - load_offset; + offset -= curr_func->ranges[0].low - load_offset; symt_add_func_line(module, curr_func, source_idx, - stab_ptr->n_desc, curr_func->address + offset); + stab_ptr->n_desc, curr_func->ranges[0].low + offset); } else pending_add_line(&pending_func, source_idx, stab_ptr->n_desc, n_value, load_offset); @@ -1531,7 +1531,7 @@ BOOL stabs_parse(struct module* module, ULONG_PTR load_offset, */ stabs_finalize_function(module, curr_func, n_value ? - (load_offset + n_value - curr_func->address) : 0); + (load_offset + n_value - curr_func->ranges[0].low) : 0); } func_type = symt_new_function_signature(module, stabs_parse_type(ptr), -1); diff --git a/dlls/dbghelp/symbol.c b/dlls/dbghelp/symbol.c index 614bf40f0a3..e0763d2f842 100644 --- a/dlls/dbghelp/symbol.c +++ b/dlls/dbghelp/symbol.c @@ -326,9 +326,9 @@ static void init_function_or_inlinesite(struct symt_function* sym, sym->symt.tag = tag; sym->hash_elt.name = pool_strdup(&module->pool, name); sym->container = container; - sym->address = addr; + sym->ranges[0].low = addr; + sym->ranges[0].high = addr + size; sym->type = sig_type; - sym->size = size; vector_init(&sym->vlines, sizeof(struct line_info), 64); vector_init(&sym->vchildren, sizeof(struct symt*), 8); } @@ -2685,7 +2685,7 @@ BOOL WINAPI SymFromInlineContext(HANDLE hProcess, DWORD64 addr, ULONG inline_ctx if (inlined) { symt_fill_sym_info(&pair, NULL, &inlined->func.symt, si); - if (disp) *disp = addr - inlined->func.address; + if (disp) *disp = addr - inlined->func.ranges[0].low; return TRUE; } /* fall through */ diff --git a/dlls/dbghelp/type.c b/dlls/dbghelp/type.c index ad2b304eebe..f847656beb7 100644 --- a/dlls/dbghelp/type.c +++ b/dlls/dbghelp/type.c @@ -153,10 +153,10 @@ BOOL symt_get_address(const struct symt* type, ULONG64* addr) *addr = ((const struct symt_block*)type)->ranges[0].low; break; case SymTagFunction: - *addr = ((const struct symt_function*)type)->address; + *addr = ((const struct symt_function*)type)->ranges[0].low; break; case SymTagInlineSite: - *addr = ((const struct symt_inlinesite*)type)->func.address; + *addr = ((const struct symt_inlinesite*)type)->func.ranges[0].low; break; case SymTagPublicSymbol: *addr = ((const struct symt_public*)type)->address; @@ -816,7 +816,7 @@ BOOL symt_get_info(struct module* module, const struct symt* type, X(DWORD64) = ((const struct symt_basic*)type)->size; break; case SymTagFunction: - X(DWORD64) = ((const struct symt_function*)type)->size; + X(DWORD64) = addr_range_size(&((const struct symt_function*)type)->ranges[0]); break; case SymTagBlock: /* When there are several ranges available, we can only return one contiguous chunk of memory.
From: Eric Pouech eric.pouech@gmail.com
Basically: - extending symt_function to enable storage of multiple address ranges - symt_function and sym_inlinesite now share the same fields, so get rid to the later.
Note that only the first range of a top level function is actually stored and used (even if the structure allows for more).
Signed-off-by: Eric Pouech eric.pouech@gmail.com --- dlls/dbghelp/dbghelp.c | 4 +- dlls/dbghelp/dbghelp_private.h | 31 +++++------- dlls/dbghelp/dwarf.c | 14 +++--- dlls/dbghelp/module.c | 2 +- dlls/dbghelp/msc.c | 50 +++++++++--------- dlls/dbghelp/symbol.c | 92 ++++++++++++++++++---------------- dlls/dbghelp/type.c | 24 +++------ 7 files changed, 101 insertions(+), 116 deletions(-)
diff --git a/dlls/dbghelp/dbghelp.c b/dlls/dbghelp/dbghelp.c index 3fd40fbb21e..32ce7e13865 100644 --- a/dlls/dbghelp/dbghelp.c +++ b/dlls/dbghelp/dbghelp.c @@ -706,7 +706,7 @@ BOOL WINAPI SymSetScopeFromIndex(HANDLE hProcess, ULONG64 addr, DWORD index) BOOL WINAPI SymSetScopeFromInlineContext(HANDLE hProcess, ULONG64 addr, DWORD inlinectx) { struct module_pair pair; - struct symt_inlinesite* inlined; + struct symt_function* inlined;
TRACE("(%p %I64x %lx)\n", hProcess, addr, inlinectx);
@@ -718,7 +718,7 @@ BOOL WINAPI SymSetScopeFromInlineContext(HANDLE hProcess, ULONG64 addr, DWORD in if (inlined) { pair.pcs->localscope_pc = addr; - pair.pcs->localscope_symt = &inlined->func.symt; + pair.pcs->localscope_symt = &inlined->symt; return TRUE; } /* fall through */ diff --git a/dlls/dbghelp/dbghelp_private.h b/dlls/dbghelp/dbghelp_private.h index a8e862076bc..09457db0fff 100644 --- a/dlls/dbghelp/dbghelp_private.h +++ b/dlls/dbghelp/dbghelp_private.h @@ -284,20 +284,13 @@ struct symt_data
struct symt_function { - struct symt symt; /* SymTagFunction (or SymTagInlineSite when embedded in symt_inlinesite) */ - struct hash_table_elt hash_elt; /* if global symbol */ - struct symt* container; /* compiland */ + struct symt symt; /* SymTagFunction or SymTagInlineSite */ + struct hash_table_elt hash_elt; /* if global symbol, inline site */ + struct symt* container; /* compiland (for SymTagFunction) or function (for SymTagInlineSite) */ struct symt* type; /* points to function_signature */ struct vector vlines; struct vector vchildren; /* locals, params, blocks, start/end, labels, inline sites */ - struct symt_inlinesite* next_inlinesite;/* linked list of inline sites in this function */ - struct addr_range ranges[1]; -}; - -/* a symt_inlinesite* can be casted to a symt_function* to access all function bits */ -struct symt_inlinesite -{ - struct symt_function func; + struct symt_function* next_inlinesite;/* linked list of inline sites in this function */ unsigned num_ranges; struct addr_range ranges[]; }; @@ -850,7 +843,7 @@ extern struct symt_function* const char* name, ULONG_PTR addr, ULONG_PTR size, struct symt* type) DECLSPEC_HIDDEN; -extern struct symt_inlinesite* +extern struct symt_function* symt_new_inlinesite(struct module* module, struct symt_function* func, struct symt* parent, @@ -945,18 +938,18 @@ extern struct symt_pointer* extern struct symt_typedef* symt_new_typedef(struct module* module, struct symt* ref, const char* name) DECLSPEC_HIDDEN; -extern struct symt_inlinesite* +extern struct symt_function* symt_find_lowest_inlined(struct symt_function* func, DWORD64 addr) DECLSPEC_HIDDEN; extern struct symt* - symt_get_upper_inlined(struct symt_inlinesite* inlined) DECLSPEC_HIDDEN; + symt_get_upper_inlined(struct symt_function* inlined) DECLSPEC_HIDDEN; static inline struct symt_function* - symt_get_function_from_inlined(struct symt_inlinesite* inlined) + symt_get_function_from_inlined(struct symt_function* inlined) { - while (!symt_check_tag(&inlined->func.symt, SymTagFunction)) - inlined = (struct symt_inlinesite*)symt_get_upper_inlined(inlined); - return &inlined->func; + while (!symt_check_tag(&inlined->symt, SymTagFunction)) + inlined = (struct symt_function*)symt_get_upper_inlined(inlined); + return inlined; } -extern struct symt_inlinesite* +extern struct symt_function* symt_find_inlined_site(struct module* module, DWORD64 addr, DWORD inline_ctx) DECLSPEC_HIDDEN; extern DWORD symt_get_inlinesite_depth(HANDLE hProcess, DWORD64 addr) DECLSPEC_HIDDEN; diff --git a/dlls/dbghelp/dwarf.c b/dlls/dbghelp/dwarf.c index 80be7aa5814..9ed63463513 100644 --- a/dlls/dbghelp/dwarf.c +++ b/dlls/dbghelp/dwarf.c @@ -2113,7 +2113,7 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, struct attribute name; struct symt* ret_type; struct symt_function_signature* sig_type; - struct symt_inlinesite* inlined; + struct symt_function* inlined; struct vector* children; dwarf2_debug_info_t*child; unsigned int i; @@ -2149,8 +2149,6 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, FIXME("Unexpected situation\n"); inlined->num_ranges = 0; } - /* temporary: update address field */ - inlined->func.ranges[0].low = inlined->ranges[0].low;
children = dwarf2_get_di_children(di); if (children) for (i = 0; i < vector_length(children); i++) @@ -2182,7 +2180,7 @@ static void dwarf2_parse_inlined_subroutine(dwarf2_subprogram_t* subpgm, } subpgm->current_block = symt_check_tag(subpgm->current_func->container, SymTagBlock) ? (struct symt_block*)subpgm->current_func->container : NULL; - subpgm->current_func = (struct symt_function*)symt_get_upper_inlined((struct symt_inlinesite*)subpgm->current_func); + subpgm->current_func = (struct symt_function*)symt_get_upper_inlined(subpgm->current_func); }
static void dwarf2_parse_subprogram_block(dwarf2_subprogram_t* subpgm, @@ -2601,7 +2599,7 @@ static void dwarf2_set_line_number(struct module* module, ULONG_PTR address, const struct vector* v, unsigned file, unsigned line) { struct symt_function* func; - struct symt_inlinesite* inlined; + struct symt_function* inlined; struct symt_ht* symt; unsigned* psrc;
@@ -2613,14 +2611,14 @@ static void dwarf2_set_line_number(struct module* module, ULONG_PTR address, if (symt_check_tag(&symt->symt, SymTagFunction)) { func = (struct symt_function*)symt; - for (inlined = func->next_inlinesite; inlined; inlined = inlined->func.next_inlinesite) + for (inlined = func->next_inlinesite; inlined; inlined = inlined->next_inlinesite) { int i; for (i = 0; i < inlined->num_ranges; ++i) { if (inlined->ranges[i].low <= address && address < inlined->ranges[i].high) { - symt_add_func_line(module, &inlined->func, *psrc, line, address); + symt_add_func_line(module, inlined, *psrc, line, address); return; /* only add to lowest matching inline site */ } } @@ -3019,7 +3017,7 @@ static BOOL dwarf2_lookup_loclist(const struct module_format* modfmt, const dwar static const dwarf2_cuhead_t* get_cuhead_from_func(const struct symt_function* func) { if (symt_check_tag(&func->symt, SymTagInlineSite)) - func = symt_get_function_from_inlined((struct symt_inlinesite*)func); + func = symt_get_function_from_inlined((struct symt_function*)func); if (symt_check_tag(&func->symt, SymTagFunction) && symt_check_tag(func->container, SymTagCompiland)) { struct symt_compiland* c = (struct symt_compiland*)func->container; diff --git a/dlls/dbghelp/module.c b/dlls/dbghelp/module.c index 6a204349b73..4840a44f5de 100644 --- a/dlls/dbghelp/module.c +++ b/dlls/dbghelp/module.c @@ -1012,7 +1012,7 @@ BOOL module_remove(struct process* pcs, struct module* module) { struct symt* locsym = pcs->localscope_symt; if (symt_check_tag(locsym, SymTagInlineSite)) - locsym = &symt_get_function_from_inlined((struct symt_inlinesite*)locsym)->symt; + locsym = &symt_get_function_from_inlined((struct symt_function*)locsym)->symt; if (symt_check_tag(locsym, SymTagFunction)) { locsym = ((struct symt_function*)locsym)->container; diff --git a/dlls/dbghelp/msc.c b/dlls/dbghelp/msc.c index 7bbc5d6bbd7..85d12063076 100644 --- a/dlls/dbghelp/msc.c +++ b/dlls/dbghelp/msc.c @@ -2077,7 +2077,7 @@ static BOOL cv_dbgsubsect_find_inlinee(const struct msc_debug_info* msc_dbg, return FALSE; }
-static inline void inline_site_update_last_range(struct symt_inlinesite* inlined, unsigned index, ULONG_PTR hi) +static inline void inline_site_update_last_range(struct symt_function* inlined, unsigned index, ULONG_PTR hi) { if (index && index <= inlined->num_ranges) { @@ -2119,17 +2119,17 @@ static unsigned inline_site_get_num_ranges(const unsigned char* annot, return num_ranges; }
-static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debug_info* msc_dbg, - const struct cv_module_snarf* cvmod, - struct symt_function* top_func, - struct symt* container, - cv_itemid_t inlinee, - const unsigned char* annot, - const unsigned char* last_annot) +static struct symt_function* codeview_create_inline_site(const struct msc_debug_info* msc_dbg, + const struct cv_module_snarf* cvmod, + struct symt_function* top_func, + struct symt* container, + cv_itemid_t inlinee, + const unsigned char* annot, + const unsigned char* last_annot) { const struct CV_DebugSSubsectionHeader_t* hdr_files = NULL; const union codeview_type* cvt; - struct symt_inlinesite* inlined; + struct symt_function* inlined; struct cv_binannot cvba; BOOL srcok; unsigned num_ranges; @@ -2194,7 +2194,7 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu offset += cvba.arg1; inline_site_update_last_range(inlined, index, top_func->ranges[0].low + offset); if (srcok) - symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->ranges[0].low + offset); + symt_add_func_line(msc_dbg->module, inlined, srcfile, line, top_func->ranges[0].low + offset); inlined->ranges[index ].low = top_func->ranges[0].low + offset; inlined->ranges[index++].high = top_func->ranges[0].low + offset; break; @@ -2215,7 +2215,7 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu offset += cvba.arg1; inline_site_update_last_range(inlined, index, top_func->ranges[0].low + offset); if (srcok) - symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->ranges[0].low + offset); + symt_add_func_line(msc_dbg->module, inlined, srcfile, line, top_func->ranges[0].low + offset); inlined->ranges[index ].low = top_func->ranges[0].low + offset; inlined->ranges[index++].high = top_func->ranges[0].low + offset; break; @@ -2223,7 +2223,7 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu offset += cvba.arg2; inline_site_update_last_range(inlined, index, top_func->ranges[0].low + offset); if (srcok) - symt_add_func_line(msc_dbg->module, &inlined->func, srcfile, line, top_func->ranges[0].low + offset); + symt_add_func_line(msc_dbg->module, inlined, srcfile, line, top_func->ranges[0].low + offset); inlined->ranges[index ].low = top_func->ranges[0].low + offset; inlined->ranges[index++].high = top_func->ranges[0].low + offset + cvba.arg1; break; @@ -2238,10 +2238,8 @@ static struct symt_inlinesite* codeview_create_inline_site(const struct msc_debu { struct addr_range* range = &inlined->ranges[inlined->num_ranges - 1]; if (range->low == range->high) WARN("pending empty range at end of %s inside %s\n", - inlined->func.hash_elt.name, + inlined->hash_elt.name, top_func->hash_elt.name); - /* temporary: update address field */ - inlined->func.ranges[0].low = inlined->ranges[0].low; } return inlined; } @@ -2657,11 +2655,11 @@ static BOOL codeview_snarf(const struct msc_debug_info* msc_dbg, break; case S_INLINESITE: { - struct symt_inlinesite* inlined = codeview_create_inline_site(msc_dbg, cvmod, top_func, - block ? &block->symt : &curr_func->symt, - sym->inline_site_v3.inlinee, - sym->inline_site_v3.binaryAnnotations, - (const unsigned char*)sym + length); + struct symt_function* inlined = codeview_create_inline_site(msc_dbg, cvmod, top_func, + block ? &block->symt : &curr_func->symt, + sym->inline_site_v3.inlinee, + sym->inline_site_v3.binaryAnnotations, + (const unsigned char*)sym + length); if (inlined) { curr_func = (struct symt_function*)inlined; @@ -2678,11 +2676,11 @@ static BOOL codeview_snarf(const struct msc_debug_info* msc_dbg, break; case S_INLINESITE2: { - struct symt_inlinesite* inlined = codeview_create_inline_site(msc_dbg, cvmod, top_func, - block ? &block->symt : &curr_func->symt, - sym->inline_site2_v3.inlinee, - sym->inline_site2_v3.binaryAnnotations, - (const unsigned char*)sym + length); + struct symt_function* inlined = codeview_create_inline_site(msc_dbg, cvmod, top_func, + block ? &block->symt : &curr_func->symt, + sym->inline_site2_v3.inlinee, + sym->inline_site2_v3.binaryAnnotations, + (const unsigned char*)sym + length); if (inlined) { curr_func = (struct symt_function*)inlined; @@ -2701,7 +2699,7 @@ static BOOL codeview_snarf(const struct msc_debug_info* msc_dbg, case S_INLINESITE_END: block = symt_check_tag(curr_func->container, SymTagBlock) ? (struct symt_block*)curr_func->container : NULL; - curr_func = (struct symt_function*)symt_get_upper_inlined((struct symt_inlinesite*)curr_func); + curr_func = (struct symt_function*)symt_get_upper_inlined(curr_func); break;
/* diff --git a/dlls/dbghelp/symbol.c b/dlls/dbghelp/symbol.c index e0763d2f842..c82b5b3d4ef 100644 --- a/dlls/dbghelp/symbol.c +++ b/dlls/dbghelp/symbol.c @@ -314,23 +314,27 @@ struct symt_data* symt_new_global_variable(struct module* module, return sym; }
-static void init_function_or_inlinesite(struct symt_function* sym, - struct module* module, - DWORD tag, - struct symt* container, - const char* name, - ULONG_PTR addr, ULONG_PTR size, - struct symt* sig_type) +static struct symt_function* init_function_or_inlinesite(struct module* module, + DWORD tag, + struct symt* container, + const char* name, + struct symt* sig_type, + unsigned num_ranges) { + struct symt_function* sym; + assert(!sig_type || sig_type->tag == SymTagFunctionType); - sym->symt.tag = tag; - sym->hash_elt.name = pool_strdup(&module->pool, name); - sym->container = container; - sym->ranges[0].low = addr; - sym->ranges[0].high = addr + size; - sym->type = sig_type; - vector_init(&sym->vlines, sizeof(struct line_info), 64); - vector_init(&sym->vchildren, sizeof(struct symt*), 8); + if ((sym = pool_alloc(&module->pool, offsetof(struct symt_function, ranges[num_ranges])))) + { + sym->symt.tag = tag; + sym->hash_elt.name = pool_strdup(&module->pool, name); + sym->container = container; + sym->type = sig_type; + vector_init(&sym->vlines, sizeof(struct line_info), 64); + vector_init(&sym->vchildren, sizeof(struct symt*), 8); + sym->num_ranges = num_ranges; + } + return sym; }
struct symt_function* symt_new_function(struct module* module, @@ -343,10 +347,11 @@ struct symt_function* symt_new_function(struct module* module,
TRACE_(dbghelp_symt)("Adding global function %s:%s @%Ix-%Ix\n", debugstr_w(module->modulename), name, addr, addr + size - 1); - if ((sym = pool_alloc(&module->pool, sizeof(*sym)))) + if ((sym = init_function_or_inlinesite(module, SymTagFunction, &compiland->symt, name, sig_type, 1))) { struct symt** p; - init_function_or_inlinesite(sym, module, SymTagFunction, &compiland->symt, name, addr, size, sig_type); + sym->ranges[0].low = addr; + sym->ranges[0].high = addr + size; sym->next_inlinesite = NULL; /* first of list */ symt_add_module_ht(module, (struct symt_ht*)sym); if (compiland) @@ -358,25 +363,24 @@ struct symt_function* symt_new_function(struct module* module, return sym; }
-struct symt_inlinesite* symt_new_inlinesite(struct module* module, - struct symt_function* func, - struct symt* container, - const char* name, - struct symt* sig_type, - unsigned num_ranges) +struct symt_function* symt_new_inlinesite(struct module* module, + struct symt_function* func, + struct symt* container, + const char* name, + struct symt* sig_type, + unsigned num_ranges) { - struct symt_inlinesite* sym; + struct symt_function* sym;
TRACE_(dbghelp_symt)("Adding inline site %s\n", name); - if ((sym = pool_alloc(&module->pool, offsetof(struct symt_inlinesite, ranges[num_ranges])))) + if ((sym = init_function_or_inlinesite(module, SymTagInlineSite, container, name, sig_type, num_ranges))) { struct symt** p; assert(container); - init_function_or_inlinesite(&sym->func, module, SymTagInlineSite, container, name, 0, 0, sig_type); + /* chain inline sites */ - sym->func.next_inlinesite = func->next_inlinesite; + sym->next_inlinesite = func->next_inlinesite; func->next_inlinesite = sym; - sym->num_ranges = num_ranges; if (container->tag == SymTagFunction || container->tag == SymTagInlineSite) p = vector_add(&((struct symt_function*)container)->vchildren, &module->pool); else @@ -384,7 +388,7 @@ struct symt_inlinesite* symt_new_inlinesite(struct module* module, assert(container->tag == SymTagBlock); p = vector_add(&((struct symt_block*)container)->vchildren, &module->pool); } - *p = &sym->func.symt; + *p = &sym->symt; } return sym; } @@ -1201,13 +1205,13 @@ void copy_symbolW(SYMBOL_INFOW* siw, const SYMBOL_INFO* si) }
/* return the lowest inline site inside a function */ -struct symt_inlinesite* symt_find_lowest_inlined(struct symt_function* func, DWORD64 addr) +struct symt_function* symt_find_lowest_inlined(struct symt_function* func, DWORD64 addr) { - struct symt_inlinesite* current; + struct symt_function* current; int i;
assert(func->symt.tag == SymTagFunction); - for (current = func->next_inlinesite; current; current = current->func.next_inlinesite) + for (current = func->next_inlinesite; current; current = current->next_inlinesite) { for (i = 0; i < current->num_ranges; ++i) { @@ -1220,9 +1224,9 @@ struct symt_inlinesite* symt_find_lowest_inlined(struct symt_function* func, DWO }
/* from an inline function, get either the enclosing inlined function, or the top function when no inlined */ -struct symt* symt_get_upper_inlined(struct symt_inlinesite* inlined) +struct symt* symt_get_upper_inlined(struct symt_function* inlined) { - struct symt* symt = &inlined->func.symt; + struct symt* symt = &inlined->symt;
do { @@ -1237,18 +1241,18 @@ struct symt* symt_get_upper_inlined(struct symt_inlinesite* inlined) }
/* lookup in module for an inline site (from addr and inline_ctx) */ -struct symt_inlinesite* symt_find_inlined_site(struct module* module, DWORD64 addr, DWORD inline_ctx) +struct symt_function* symt_find_inlined_site(struct module* module, DWORD64 addr, DWORD inline_ctx) { struct symt_ht* symt = symt_find_symbol_at(module, addr);
if (symt_check_tag(&symt->symt, SymTagFunction)) { struct symt_function* func = (struct symt_function*)symt; - struct symt_inlinesite* curr = symt_find_lowest_inlined(func, addr); + struct symt_function* curr = symt_find_lowest_inlined(func, addr); DWORD depth = IFC_DEPTH(inline_ctx);
if (curr) - for ( ; &curr->func != func; curr = (struct symt_inlinesite*)symt_get_upper_inlined(curr)) + for ( ; curr != func; curr = (struct symt_function*)symt_get_upper_inlined(curr)) if (depth-- == 0) return curr; } return NULL; @@ -1264,10 +1268,10 @@ DWORD symt_get_inlinesite_depth(HANDLE hProcess, DWORD64 addr) struct symt_ht* symt = symt_find_symbol_at(pair.effective, addr); if (symt_check_tag(&symt->symt, SymTagFunction)) { - struct symt_inlinesite* inlined = symt_find_lowest_inlined((struct symt_function*)symt, addr); + struct symt_function* inlined = symt_find_lowest_inlined((struct symt_function*)symt, addr); if (inlined) { - for ( ; &inlined->func.symt != &symt->symt; inlined = (struct symt_inlinesite*)symt_get_upper_inlined(inlined)) + for ( ; &inlined->symt != &symt->symt; inlined = (struct symt_function*)symt_get_upper_inlined(inlined)) ++depth; } } @@ -2673,7 +2677,7 @@ PWSTR WINAPI SymSetHomeDirectoryW(HANDLE hProcess, PCWSTR dir) BOOL WINAPI SymFromInlineContext(HANDLE hProcess, DWORD64 addr, ULONG inline_ctx, PDWORD64 disp, PSYMBOL_INFO si) { struct module_pair pair; - struct symt_inlinesite* inlined; + struct symt_function* inlined;
TRACE("(%p, %#I64x, 0x%lx, %p, %p)\n", hProcess, addr, inline_ctx, disp, si);
@@ -2684,8 +2688,8 @@ BOOL WINAPI SymFromInlineContext(HANDLE hProcess, DWORD64 addr, ULONG inline_ctx inlined = symt_find_inlined_site(pair.effective, addr, inline_ctx); if (inlined) { - symt_fill_sym_info(&pair, NULL, &inlined->func.symt, si); - if (disp) *disp = addr - inlined->func.ranges[0].low; + symt_fill_sym_info(&pair, NULL, &inlined->symt, si); + if (disp) *disp = addr - inlined->ranges[0].low; return TRUE; } /* fall through */ @@ -2728,14 +2732,14 @@ static BOOL get_line_from_inline_context(HANDLE hProcess, DWORD64 addr, ULONG in struct internal_line_t* intl) { struct module_pair pair; - struct symt_inlinesite* inlined; + struct symt_function* inlined;
if (!module_init_pair(&pair, hProcess, mod_addr ? mod_addr : addr)) return FALSE; switch (IFC_MODE(inline_ctx)) { case IFC_MODE_INLINE: inlined = symt_find_inlined_site(pair.effective, addr, inline_ctx); - if (inlined && get_line_from_function(&pair, &inlined->func, addr, disp, intl)) + if (inlined && get_line_from_function(&pair, inlined, addr, disp, intl)) return TRUE; /* fall through: check if we can find line info at top function level */ case IFC_MODE_IGNORE: diff --git a/dlls/dbghelp/type.c b/dlls/dbghelp/type.c index f847656beb7..b5e284fdb6c 100644 --- a/dlls/dbghelp/type.c +++ b/dlls/dbghelp/type.c @@ -94,8 +94,8 @@ const char* symt_get_name(const struct symt* sym) { /* lexical tree */ case SymTagData: return ((const struct symt_data*)sym)->hash_elt.name; - case SymTagFunction: return ((const struct symt_function*)sym)->hash_elt.name; - case SymTagInlineSite: return ((const struct symt_inlinesite*)sym)->func.hash_elt.name; + case SymTagFunction: + case SymTagInlineSite: return ((const struct symt_function*)sym)->hash_elt.name; case SymTagPublicSymbol: return ((const struct symt_public*)sym)->hash_elt.name; case SymTagLabel: return ((const struct symt_hierarchy_point*)sym)->hash_elt.name; case SymTagThunk: return ((const struct symt_thunk*)sym)->hash_elt.name; @@ -153,10 +153,8 @@ BOOL symt_get_address(const struct symt* type, ULONG64* addr) *addr = ((const struct symt_block*)type)->ranges[0].low; break; case SymTagFunction: - *addr = ((const struct symt_function*)type)->ranges[0].low; - break; case SymTagInlineSite: - *addr = ((const struct symt_inlinesite*)type)->func.ranges[0].low; + *addr = ((const struct symt_function*)type)->ranges[0].low; break; case SymTagPublicSymbol: *addr = ((const struct symt_public*)type)->address; @@ -685,8 +683,8 @@ BOOL symt_get_info(struct module* module, const struct symt* type, case SymTagUDT: v = &((const struct symt_udt*)type)->vchildren; break; case SymTagEnum: v = &((const struct symt_enum*)type)->vchildren; break; case SymTagFunctionType: v = &((const struct symt_function_signature*)type)->vchildren; break; - case SymTagFunction: v = &((const struct symt_function*)type)->vchildren; break; - case SymTagInlineSite: v = &((const struct symt_inlinesite*)type)->func.vchildren; break; + case SymTagFunction: + case SymTagInlineSite: v = &((const struct symt_function*)type)->vchildren; break; case SymTagBlock: v = &((const struct symt_block*)type)->vchildren; break; case SymTagPointerType: case SymTagArrayType: @@ -756,10 +754,8 @@ BOOL symt_get_info(struct module* module, const struct symt* type, X(DWORD) = vector_length(&((const struct symt_function_signature*)type)->vchildren); break; case SymTagFunction: - X(DWORD) = vector_length(&((const struct symt_function*)type)->vchildren); - break; case SymTagInlineSite: - X(DWORD) = vector_length(&((const struct symt_inlinesite*)type)->func.vchildren); + X(DWORD) = vector_length(&((const struct symt_function*)type)->vchildren); break; case SymTagBlock: X(DWORD) = vector_length(&((const struct symt_block*)type)->vchildren); @@ -898,10 +894,8 @@ BOOL symt_get_info(struct module* module, const struct symt* type, X(DWORD) = symt_ptr2index(module, ((const struct symt_data*)type)->container); break; case SymTagFunction: - X(DWORD) = symt_ptr2index(module, ((const struct symt_function*)type)->container); - break; case SymTagInlineSite: - X(DWORD) = symt_ptr2index(module, ((const struct symt_inlinesite*)type)->func.container); + X(DWORD) = symt_ptr2index(module, ((const struct symt_function*)type)->container); break; case SymTagThunk: X(DWORD) = symt_ptr2index(module, ((const struct symt_thunk*)type)->container); @@ -1043,10 +1037,8 @@ BOOL symt_get_info(struct module* module, const struct symt* type, X(DWORD) = symt_ptr2index(module, ((const struct symt_data*)type)->type); break; case SymTagFunction: - X(DWORD) = symt_ptr2index(module, ((const struct symt_function*)type)->type); - break; case SymTagInlineSite: - X(DWORD) = symt_ptr2index(module, ((const struct symt_inlinesite*)type)->func.type); + X(DWORD) = symt_ptr2index(module, ((const struct symt_function*)type)->type); break; case SymTagEnum: X(DWORD) = symt_ptr2index(module, ((const struct symt_enum*)type)->base_type);