* addr2line.c (long_options): Add new option 'section'.

(usage): Document new -j/--section option.
	(find_offset_in_section): New function.
	(translate_addresses): Add 'section' parameter.
	If it is non-null, call find_offset_in_section on it.
	(process_file): Add 'section_name' parameter.
	If it is non-null, look for the section in the BFD object.
	Pass the section to translate_addresses.
	(main): Handle new -j option.
	Pass the section name to process_file.
	* doc/binutils.texi (addr2line): Document new -j/--section option.
This commit is contained in:
Eric Botcazou 2006-04-05 16:12:01 +00:00
parent dfcffada0b
commit c5f8c3881a
3 changed files with 80 additions and 19 deletions

View File

@ -1,3 +1,17 @@
2006-04-05 Eric Botcazou <ebotcazou@adacore.com>
* addr2line.c (long_options): Add new option 'section'.
(usage): Document new -j/--section option.
(find_offset_in_section): New function.
(translate_addresses): Add 'section' parameter.
If it is non-null, call find_offset_in_section on it.
(process_file): Add 'section_name' parameter.
If it is non-null, look for the section in the BFD object.
Pass the section to translate_addresses.
(main): Handle new -j option.
Pass the section name to process_file.
* doc/binutils.texi (addr2line): Document new -j/--section option.
2006-03-29 Ben Elliston <bje@au.ibm.com>
* resbin.c: Avoid duplicating constants in calls to reswr_alloc.

View File

@ -1,5 +1,5 @@
/* addr2line.c -- convert addresses to line number and function name
Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004
Copyright 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2006
Free Software Foundation, Inc.
Contributed by Ulrich Lauther <Ulrich.Lauther@mchp.siemens.de>
@ -56,6 +56,7 @@ static struct option long_options[] =
{"exe", required_argument, NULL, 'e'},
{"functions", no_argument, NULL, 'f'},
{"inlines", no_argument, NULL, 'i'},
{"section", required_argument, NULL, 'j'},
{"target", required_argument, NULL, 'b'},
{"help", no_argument, NULL, 'H'},
{"version", no_argument, NULL, 'V'},
@ -65,8 +66,9 @@ static struct option long_options[] =
static void usage (FILE *, int);
static void slurp_symtab (bfd *);
static void find_address_in_section (bfd *, asection *, void *);
static void translate_addresses (bfd *);
static void process_file (const char *, const char *);
static void find_offset_in_section (bfd *, asection *);
static void translate_addresses (bfd *, asection *);
static void process_file (const char *, const char *, const char *);
/* Print a usage message to STREAM and exit with STATUS. */
@ -80,7 +82,8 @@ usage (FILE *stream, int status)
@<file> Read options from <file>\n\
-b --target=<bfdname> Set the binary file format\n\
-e --exe=<executable> Set the input file name (default is a.out)\n\
-i --inlines Unwind inlined functions\n\
-i --inlines Unwind inlined functions\n\
-j --section=<name> Read section-relative offsets instead of addresses\n\
-s --basenames Strip directory names\n\
-f --functions Show function names\n\
-C --demangle[=style] Demangle function names\n\
@ -150,11 +153,32 @@ find_address_in_section (bfd *abfd, asection *section,
&filename, &functionname, &line);
}
/* Look for an offset in a section. This is directly called. */
static void
find_offset_in_section (bfd *abfd, asection *section)
{
bfd_size_type size;
if (found)
return;
if ((bfd_get_section_flags (abfd, section) & SEC_ALLOC) == 0)
return;
size = bfd_get_section_size (section);
if (pc >= size)
return;
found = bfd_find_nearest_line (abfd, section, syms, pc,
&filename, &functionname, &line);
}
/* Read hexadecimal addresses from stdin, translate into
file_name:line_number and optionally function name. */
static void
translate_addresses (bfd *abfd)
translate_addresses (bfd *abfd, asection *section)
{
int read_stdin = (naddr == 0);
@ -177,7 +201,10 @@ translate_addresses (bfd *abfd)
}
found = FALSE;
bfd_map_over_sections (abfd, find_address_in_section, NULL);
if (section)
find_offset_in_section (abfd, section);
else
bfd_map_over_sections (abfd, find_address_in_section, NULL);
if (! found)
{
@ -237,9 +264,11 @@ translate_addresses (bfd *abfd)
/* Process a file. */
static void
process_file (const char *file_name, const char *target)
process_file (const char *file_name, const char *section_name,
const char *target)
{
bfd *abfd;
asection *section;
char **matching;
if (get_file_size (file_name) < 1)
@ -250,7 +279,7 @@ process_file (const char *file_name, const char *target)
bfd_fatal (file_name);
if (bfd_check_format (abfd, bfd_archive))
fatal (_("%s: can not get addresses from archive"), file_name);
fatal (_("%s: cannot get addresses from archive"), file_name);
if (! bfd_check_format_matches (abfd, bfd_object, &matching))
{
@ -263,9 +292,18 @@ process_file (const char *file_name, const char *target)
xexit (1);
}
if (section_name != NULL)
{
section = bfd_get_section_by_name (abfd, section_name);
if (section == NULL)
fatal (_("%s: cannot find section %s"), file_name, section_name);
}
else
section = NULL;
slurp_symtab (abfd);
translate_addresses (abfd);
translate_addresses (abfd, section);
if (syms != NULL)
{
@ -276,12 +314,11 @@ process_file (const char *file_name, const char *target)
bfd_close (abfd);
}
int main (int, char **);
int
main (int argc, char **argv)
{
const char *file_name;
const char *section_name;
char *target;
int c;
@ -303,8 +340,9 @@ main (int argc, char **argv)
set_default_bfd_target ();
file_name = NULL;
section_name = NULL;
target = NULL;
while ((c = getopt_long (argc, argv, "b:Ce:sfHhiVv", long_options, (int *) 0))
while ((c = getopt_long (argc, argv, "b:Ce:sfHhij:Vv", long_options, (int *) 0))
!= EOF)
{
switch (c)
@ -348,6 +386,9 @@ main (int argc, char **argv)
case 'i':
unwind_inlines = TRUE;
break;
case 'j':
section_name = optarg;
break;
default:
usage (stderr, 1);
break;
@ -360,7 +401,7 @@ main (int argc, char **argv)
addr = argv + optind;
naddr = argc - optind;
process_file (file_name, target);
process_file (file_name, section_name, target);
return 0;
}

View File

@ -2601,6 +2601,7 @@ addr2line [@option{-b} @var{bfdname}|@option{--target=}@var{bfdname}]
[@option{-e} @var{filename}|@option{--exe=}@var{filename}]
[@option{-f}|@option{--functions}] [@option{-s}|@option{--basename}]
[@option{-i}|@option{--inlines}]
[@option{-j}|@option{--section=}@var{name}]
[@option{-H}|@option{--help}] [@option{-V}|@option{--version}]
[addr addr @dots{}]
@c man end
@ -2608,13 +2609,14 @@ addr2line [@option{-b} @var{bfdname}|@option{--target=}@var{bfdname}]
@c man begin DESCRIPTION addr2line
@command{addr2line} translates program addresses into file names and line
numbers. Given an address and an executable, it uses the debugging
information in the executable to figure out which file name and line
number are associated with a given address.
@command{addr2line} translates addresses into file names and line numbers.
Given an address in an executable or an offset in a section of a relocatable
object, it uses the debugging information to figure out which file name and
line number are associated with it.
The executable to use is specified with the @option{-e} option. The
default is the file @file{a.out}.
The executable or relocatable object to use is specified with the @option{-e}
option. The default is the file @file{a.out}. The section in the relocatable
object to use is specified with the @option{-j} option.
@command{addr2line} has two modes of operation.
@ -2682,6 +2684,10 @@ function will also be printed. For example, if @code{main} inlines
@code{callee1} which inlines @code{callee2}, and address is from
@code{callee2}, the source information for @code{callee1} and @code{main}
will also be printed.
@item -j
@itemx --section
Read offsets relative to the specified section instead of absolute addresses.
@end table
@c man end