aboutsummaryrefslogtreecommitdiff
path: root/binutils
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2001-05-11 12:36:47 +0000
committerJakub Jelinek <jakub@redhat.com>2001-05-11 12:36:47 +0000
commit579f31ac74d806de9c148fb324a32c488634742a (patch)
tree3cf71d4822aa0765c4ec9267d264dbc26a56cea8 /binutils
parent8550eb6e64bdd0582528498c5cad6f80014b7deb (diff)
downloadgdb-579f31ac74d806de9c148fb324a32c488634742a.zip
gdb-579f31ac74d806de9c148fb324a32c488634742a.tar.gz
gdb-579f31ac74d806de9c148fb324a32c488634742a.tar.bz2
* elfxx-ia64.c (is_unwind_section_name): Consider linkonce unwind
sections as well. (elfNN_ia64_final_write_processing): Map .gnu.linkonce.ia64unw.FOO to .gnu.linkonce.t.FOO text section. * readelf.c (process_unwind): Print all unwind sections, not just one. * config/tc-ia64.c (special_linkonce_name): New. (make_unw_section): Map .gnu.linkonce.t.FOO text section into .gnu.linkonce.ia64unw{,i}.FOO. (ia64_elf_section_type): Handle .gnu.linkonce.ia64unw{,i}.FOO. (dot_endp): Add comment about it. * elf/ia64.h (ELF_STRING_ia64_unwind_once): Define. (ELF_STRING_ia64_unwind_info_once): Define. * emulparams/elf64_ia64.sh (OTHER_READONLY_SECTIONS): Put .gnu.linkonce.ia64unw{,i} sections into corresponding .IA_64.unwind* output sections. * emulparams/elf64_aix.sh (OTHER_READONLY_SECTIONS): Likewise.
Diffstat (limited to 'binutils')
-rw-r--r--binutils/ChangeLog5
-rw-r--r--binutils/readelf.c106
2 files changed, 88 insertions, 23 deletions
diff --git a/binutils/ChangeLog b/binutils/ChangeLog
index f2c82dc..311f833 100644
--- a/binutils/ChangeLog
+++ b/binutils/ChangeLog
@@ -1,3 +1,8 @@
+2001-05-11 Jakub Jelinek <jakub@redhat.com>
+
+ * readelf.c (process_unwind): Print all unwind sections, not just
+ one.
+
2001-05-07 Thiemo Seufer <seufer@csv.ica.uni-stuttgart.de>
* readelf.c (process_unwind): Remove const specifier.
diff --git a/binutils/readelf.c b/binutils/readelf.c
index fa583e4..b7aecde 100644
--- a/binutils/readelf.c
+++ b/binutils/readelf.c
@@ -3408,7 +3408,7 @@ process_unwind (file)
FILE * file;
{
Elf32_Internal_Shdr *sec, *unwsec = NULL, *strsec;
- unsigned long i, addr_size;
+ unsigned long i, addr_size, unwcount = 0, unwstart = 0;
struct unw_aux_info aux;
if (!do_unwind)
@@ -3437,40 +3437,100 @@ process_unwind (file)
aux.strtab, char *, "string table");
}
else if (sec->sh_type == SHT_IA_64_UNWIND)
- unwsec = sec;
- else if (strcmp (SECTION_NAME (sec), ELF_STRING_ia64_unwind_info) == 0)
+ unwcount++;
+ }
+
+ if (!unwcount)
+ printf (_("\nThere are no unwind sections in this file.\n"));
+
+ while (unwcount-- > 0)
+ {
+ char *suffix;
+ size_t len, len2;
+
+ for (i = unwstart, sec = section_headers + unwstart;
+ i < elf_header.e_shnum; ++i, ++sec)
+ if (sec->sh_type == SHT_IA_64_UNWIND)
+ {
+ unwsec = sec;
+ break;
+ }
+
+ unwstart = i + 1;
+ len = sizeof (ELF_STRING_ia64_unwind_once) - 1;
+
+ if (strncmp (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind_once,
+ len) == 0)
+ {
+ /* .gnu.linkonce.ia64unw.FOO -> .gnu.linkonce.ia64unwi.FOO */
+ len2 = sizeof (ELF_STRING_ia64_unwind_info_once) - 1;
+ suffix = SECTION_NAME (unwsec) + len;
+ for (i = 0, sec = section_headers; i < elf_header.e_shnum;
+ ++i, ++sec)
+ if (strncmp (SECTION_NAME (sec),
+ ELF_STRING_ia64_unwind_info_once, len2) == 0
+ && strcmp (SECTION_NAME (sec) + len2, suffix) == 0)
+ break;
+ }
+ else
+ {
+ /* .IA_64.unwindFOO -> .IA_64.unwind_infoFOO
+ .IA_64.unwind or BAR -> .IA_64.unwind_info */
+ len = sizeof (ELF_STRING_ia64_unwind) - 1;
+ len2 = sizeof (ELF_STRING_ia64_unwind_info) - 1;
+ suffix = "";
+ if (strncmp (SECTION_NAME (unwsec), ELF_STRING_ia64_unwind,
+ len) == 0)
+ suffix = SECTION_NAME (unwsec) + len;
+ for (i = 0, sec = section_headers; i < elf_header.e_shnum;
+ ++i, ++sec)
+ if (strncmp (SECTION_NAME (sec),
+ ELF_STRING_ia64_unwind_info, len2) == 0
+ && strcmp (SECTION_NAME (sec) + len2, suffix) == 0)
+ break;
+ }
+
+ if (i == elf_header.e_shnum)
+ {
+ printf (_("\nCould not find unwind info section for "));
+
+ if (string_table == NULL)
+ printf ("%d", unwsec->sh_name);
+ else
+ printf ("'%s'", SECTION_NAME (unwsec));
+ }
+ else
{
aux.info_size = sec->sh_size;
aux.info_addr = sec->sh_addr;
GET_DATA_ALLOC (sec->sh_offset, aux.info_size, aux.info,
char *, "unwind info");
- }
- }
- if (unwsec)
- {
- printf (_("\nUnwind section "));
+ printf (_("\nUnwind section "));
- if (string_table == NULL)
- printf ("%d", unwsec->sh_name);
- else
- printf ("'%s'", SECTION_NAME (unwsec));
+ if (string_table == NULL)
+ printf ("%d", unwsec->sh_name);
+ else
+ printf ("'%s'", SECTION_NAME (unwsec));
- printf (_(" at offset 0x%lx contains %lu entries:\n"),
- unwsec->sh_offset, (unsigned long) (unwsec->sh_size / (3 * addr_size)));
+ printf (_(" at offset 0x%lx contains %lu entries:\n"),
+ unwsec->sh_offset,
+ (unsigned long) (unwsec->sh_size / (3 * addr_size)));
- (void) slurp_ia64_unwind_table (file, & aux, unwsec);
+ (void) slurp_ia64_unwind_table (file, & aux, unwsec);
- if (aux.table_len > 0)
- dump_ia64_unwind (& aux);
+ if (aux.table_len > 0)
+ dump_ia64_unwind (& aux);
+
+ if (aux.table)
+ free ((char *) aux.table);
+ if (aux.info)
+ free ((char *) aux.info);
+ aux.table = NULL;
+ aux.info = NULL;
+ }
}
- else
- printf (_("\nThere are no unwind sections in this file.\n"));
- if (aux.table)
- free ((char *) aux.table);
- if (aux.info)
- free ((char *) aux.info);
if (aux.symtab)
free (aux.symtab);
if (aux.strtab)