Improve the speed of scanning PE binaries for line number information.
PR binutils/18025 * coff-bfd.h (struct coff_section_data): Add new fields: saved_bias and bias. * coffgen.c (coff_find_nearest_line_with_names): Cache the bias computed for PE binaries. * dwarf2.c (scan_unit_for_symbols): Only warn once about each missing abbrev.
This commit is contained in:
parent
7cc0cd2903
commit
e643cb45bf
@ -1,3 +1,13 @@
|
|||||||
|
2017-03-29 Nick Clifton <nickc@redhat.com>
|
||||||
|
|
||||||
|
PR binutils/18025
|
||||||
|
* coff-bfd.h (struct coff_section_data): Add new fields:
|
||||||
|
saved_bias and bias.
|
||||||
|
* coffgen.c (coff_find_nearest_line_with_names): Cache the bias
|
||||||
|
computed for PE binaries.
|
||||||
|
* dwarf2.c (scan_unit_for_symbols): Only warn once about each
|
||||||
|
missing abbrev.
|
||||||
|
|
||||||
2017-03-28 Hans-Peter Nilsson <hp@axis.com>
|
2017-03-28 Hans-Peter Nilsson <hp@axis.com>
|
||||||
|
|
||||||
PR ld/16044
|
PR ld/16044
|
||||||
|
@ -50,6 +50,8 @@ struct coff_section_tdata
|
|||||||
/* If this is TRUE, the contents entry may not be freed. */
|
/* If this is TRUE, the contents entry may not be freed. */
|
||||||
bfd_boolean keep_contents;
|
bfd_boolean keep_contents;
|
||||||
/* Information cached by coff_find_nearest_line. */
|
/* Information cached by coff_find_nearest_line. */
|
||||||
|
bfd_boolean saved_bias;
|
||||||
|
bfd_signed_vma bias;
|
||||||
bfd_vma offset;
|
bfd_vma offset;
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
const char *function;
|
const char *function;
|
||||||
|
@ -2259,6 +2259,8 @@ coff_find_nearest_line_with_names (bfd *abfd,
|
|||||||
&coff_data(abfd)->dwarf2_find_line_info))
|
&coff_data(abfd)->dwarf2_find_line_info))
|
||||||
return TRUE;
|
return TRUE;
|
||||||
|
|
||||||
|
sec_data = coff_section_data (abfd, section);
|
||||||
|
|
||||||
/* If the DWARF lookup failed, but there is DWARF information available
|
/* If the DWARF lookup failed, but there is DWARF information available
|
||||||
then the problem might be that the file has been rebased. This tool
|
then the problem might be that the file has been rebased. This tool
|
||||||
changes the VMAs of all the sections, but it does not update the DWARF
|
changes the VMAs of all the sections, but it does not update the DWARF
|
||||||
@ -2267,8 +2269,26 @@ coff_find_nearest_line_with_names (bfd *abfd,
|
|||||||
{
|
{
|
||||||
bfd_signed_vma bias;
|
bfd_signed_vma bias;
|
||||||
|
|
||||||
bias = _bfd_dwarf2_find_symbol_bias (symbols,
|
/* Create a cache of the result for the next call. */
|
||||||
& coff_data (abfd)->dwarf2_find_line_info);
|
if (sec_data == NULL && section->owner == abfd)
|
||||||
|
{
|
||||||
|
amt = sizeof (struct coff_section_tdata);
|
||||||
|
section->used_by_bfd = bfd_zalloc (abfd, amt);
|
||||||
|
sec_data = (struct coff_section_tdata *) section->used_by_bfd;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (sec_data != NULL && sec_data->saved_bias)
|
||||||
|
bias = sec_data->saved_bias;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
bias = _bfd_dwarf2_find_symbol_bias (symbols,
|
||||||
|
& coff_data (abfd)->dwarf2_find_line_info);
|
||||||
|
if (sec_data)
|
||||||
|
{
|
||||||
|
sec_data->saved_bias = TRUE;
|
||||||
|
sec_data->bias = bias;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (bias
|
if (bias
|
||||||
&& _bfd_dwarf2_find_nearest_line (abfd, symbols, NULL, section,
|
&& _bfd_dwarf2_find_nearest_line (abfd, symbols, NULL, section,
|
||||||
@ -2363,10 +2383,16 @@ coff_find_nearest_line_with_names (bfd *abfd,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Now wander though the raw linenumbers of the section. */
|
if (section->lineno_count == 0)
|
||||||
/* If we have been called on this section before, and the offset we
|
{
|
||||||
want is further down then we can prime the lookup loop. */
|
*functionname_ptr = NULL;
|
||||||
sec_data = coff_section_data (abfd, section);
|
*line_ptr = 0;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Now wander though the raw linenumbers of the section.
|
||||||
|
If we have been called on this section before, and the offset
|
||||||
|
we want is further down then we can prime the lookup loop. */
|
||||||
if (sec_data != NULL
|
if (sec_data != NULL
|
||||||
&& sec_data->i > 0
|
&& sec_data->i > 0
|
||||||
&& offset >= sec_data->offset)
|
&& offset >= sec_data->offset)
|
||||||
@ -2395,6 +2421,7 @@ coff_find_nearest_line_with_names (bfd *abfd,
|
|||||||
coff_symbol_type *coff = (coff_symbol_type *) (l->u.sym);
|
coff_symbol_type *coff = (coff_symbol_type *) (l->u.sym);
|
||||||
if (coff->symbol.value > offset)
|
if (coff->symbol.value > offset)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
*functionname_ptr = coff->symbol.name;
|
*functionname_ptr = coff->symbol.name;
|
||||||
last_value = coff->symbol.value;
|
last_value = coff->symbol.value;
|
||||||
if (coff->native)
|
if (coff->native)
|
||||||
@ -2451,6 +2478,7 @@ coff_find_nearest_line_with_names (bfd *abfd,
|
|||||||
section->used_by_bfd = bfd_zalloc (abfd, amt);
|
section->used_by_bfd = bfd_zalloc (abfd, amt);
|
||||||
sec_data = (struct coff_section_tdata *) section->used_by_bfd;
|
sec_data = (struct coff_section_tdata *) section->used_by_bfd;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sec_data != NULL)
|
if (sec_data != NULL)
|
||||||
{
|
{
|
||||||
sec_data->offset = offset;
|
sec_data->offset = offset;
|
||||||
|
20
bfd/dwarf2.c
20
bfd/dwarf2.c
@ -2738,12 +2738,19 @@ scan_unit_for_symbols (struct comp_unit *unit)
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
abbrev = lookup_abbrev (abbrev_number,unit->abbrevs);
|
abbrev = lookup_abbrev (abbrev_number, unit->abbrevs);
|
||||||
if (! abbrev)
|
if (! abbrev)
|
||||||
{
|
{
|
||||||
_bfd_error_handler
|
static unsigned int previous_failed_abbrev = -1U;
|
||||||
(_("Dwarf Error: Could not find abbrev number %u."),
|
|
||||||
abbrev_number);
|
/* Avoid multiple reports of the same missing abbrev. */
|
||||||
|
if (abbrev_number != previous_failed_abbrev)
|
||||||
|
{
|
||||||
|
_bfd_error_handler
|
||||||
|
(_("Dwarf Error: Could not find abbrev number %u."),
|
||||||
|
abbrev_number);
|
||||||
|
previous_failed_abbrev = abbrev_number;
|
||||||
|
}
|
||||||
bfd_set_error (bfd_error_bad_value);
|
bfd_set_error (bfd_error_bad_value);
|
||||||
goto fail;
|
goto fail;
|
||||||
}
|
}
|
||||||
@ -2760,7 +2767,7 @@ scan_unit_for_symbols (struct comp_unit *unit)
|
|||||||
func->tag = abbrev->tag;
|
func->tag = abbrev->tag;
|
||||||
func->prev_func = unit->function_table;
|
func->prev_func = unit->function_table;
|
||||||
unit->function_table = func;
|
unit->function_table = func;
|
||||||
unit->number_of_functions++;
|
unit->number_of_functions++;
|
||||||
BFD_ASSERT (!unit->cached);
|
BFD_ASSERT (!unit->cached);
|
||||||
|
|
||||||
if (func->tag == DW_TAG_inlined_subroutine)
|
if (func->tag == DW_TAG_inlined_subroutine)
|
||||||
@ -2785,7 +2792,8 @@ scan_unit_for_symbols (struct comp_unit *unit)
|
|||||||
var->stack = 1;
|
var->stack = 1;
|
||||||
var->prev_var = unit->variable_table;
|
var->prev_var = unit->variable_table;
|
||||||
unit->variable_table = var;
|
unit->variable_table = var;
|
||||||
BFD_ASSERT (!unit->cached);
|
/* PR 18205: Missing debug information can cause this
|
||||||
|
var to be attached to an already cached unit. */
|
||||||
}
|
}
|
||||||
|
|
||||||
/* No inline function in scope at this nesting level. */
|
/* No inline function in scope at this nesting level. */
|
||||||
|
Loading…
Reference in New Issue
Block a user