diff options
author | Roland McGrath <roland@redhat.com> | 2010-02-24 03:06:47 +0000 |
---|---|---|
committer | Dmitry V. Levin <ldv@altlinux.org> | 2010-02-24 03:06:47 +0000 |
commit | 50cdcf8ad0c6e4402f319fbd9f391b3b0506be35 (patch) | |
tree | 3a590c25ab7db9379558c6803ad85459ec3d3754 /elfutils/src/readelf.c | |
parent | b35baa53df420c2d0816c6a65ef71deec0760836 (diff) | |
download | elfutils-0.145-1.tar.gz |
0.145-10.145-1
- Update to 0.145
- Fix build with --disable-dependency-tracking. (#564646)
- Fix build with most recent glibc headers.
- libdw: Fix CFI decoding. (#563528)
- libdwfl: Fix address bias returned by CFI accessors. (#563528)
Fix core file module layout identification. (#559836)
- readelf: Fix CFI decoding.
Diffstat (limited to 'elfutils/src/readelf.c')
-rw-r--r-- | elfutils/src/readelf.c | 59 |
1 files changed, 21 insertions, 38 deletions
diff --git a/elfutils/src/readelf.c b/elfutils/src/readelf.c index 44648669..7b3c4f8b 100644 --- a/elfutils/src/readelf.c +++ b/elfutils/src/readelf.c @@ -49,6 +49,7 @@ #include <time.h> #include <unistd.h> #include <sys/param.h> +#include <sys/stat.h> #include <system.h> #include "../libelf/libelfP.h" @@ -4704,8 +4705,7 @@ print_encoding_base (const char *pfx, unsigned int fde_encoding) { unsigned int w = fde_encoding; - if (w & 0xf) - w = print_encoding (w); + w = print_encoding (w); if (w & 0x70) { @@ -4727,6 +4727,10 @@ static const unsigned char * read_encoded (unsigned int encoding, const unsigned char *readp, const unsigned char *const endp, uint64_t *res, Dwarf *dbg) { + if ((encoding & 0xf) == DW_EH_PE_absptr) + encoding = gelf_getclass (dbg->elf) == ELFCLASS32 + ? DW_EH_PE_udata4 : DW_EH_PE_udata8; + switch (encoding & 0xf) { case DW_EH_PE_uleb128: @@ -4914,6 +4918,9 @@ print_debug_frame_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr, unsigned int augmentationlen; get_uleb128 (augmentationlen, readp); + if (augmentationlen > (size_t) (dataend - readp)) + error (1, 0, gettext ("invalid augmentation length")); + const char *hdr = "Augmentation data:"; const char *cp = augmentation + 1; while (*cp != '\0') @@ -4940,51 +4947,27 @@ print_debug_frame_section (Dwfl_Module *dwflmod, Ebl *ebl, GElf_Ehdr *ehdr, const unsigned char *startp = readp; unsigned int encoding = *readp++; uint64_t val = 0; - int64_t sval = 0; - bool is_signed = false; + readp = read_encoded (encoding, readp, + readp - 1 + augmentationlen, + &val, dbg); + + while (++startp < readp) + printf ("%#x ", *startp); + putchar ('('); + print_encoding (encoding); + putchar (' '); switch (encoding & 0xf) { - case DW_EH_PE_uleb128: - get_uleb128 (val, readp); - break; case DW_EH_PE_sleb128: - get_sleb128 (sval, readp); - is_signed = true; - break; - case DW_EH_PE_udata2: - val = read_2ubyte_unaligned_inc (dbg, readp); - break; - case DW_EH_PE_udata4: - val = read_4ubyte_unaligned_inc (dbg, readp); - break; - case DW_EH_PE_udata8: - val = read_8ubyte_unaligned_inc (dbg, readp); - break; case DW_EH_PE_sdata2: - val = read_2sbyte_unaligned_inc (dbg, readp); - is_signed = true; - break; case DW_EH_PE_sdata4: - val = read_4sbyte_unaligned_inc (dbg, readp); - is_signed = true; - break; - case DW_EH_PE_sdata8: - val = read_8sbyte_unaligned_inc (dbg, readp); - is_signed = true; + printf ("%" PRId64 ")\n", val); break; default: - error (1, 0, - gettext ("invalid augmentation encoding")); + printf ("%#" PRIx64 ")\n", val); + break; } - - while (++startp < readp) - printf ("%#x ", *startp); - - if (is_signed) - printf ("(%" PRId64 ")\n", sval); - else - printf ("(%" PRIu64 ")\n", val); } else printf ("(%x)\n", *readp++); |