diff options
author | Roland McGrath <roland@redhat.com> | 2005-12-12 08:35:55 +0000 |
---|---|---|
committer | Roland McGrath <roland@redhat.com> | 2005-12-12 08:35:55 +0000 |
commit | dec3a24331194d06145b28011336d121c3440ac7 (patch) | |
tree | 0b2687a09281926da06218e142c1059752ea881c /libdw | |
parent | ba72ab102a8ca35371072311379d2474f8ec674f (diff) | |
download | elfutils-dec3a24331194d06145b28011336d121c3440ac7.tar.gz |
2005-12-12 Roland McGrath <roland@redhat.com>
* dwarf_ranges.c: Copy CU base address-finding code from
dwarf_getlocation.
Diffstat (limited to 'libdw')
-rw-r--r-- | libdw/ChangeLog | 5 | ||||
-rw-r--r-- | libdw/dwarf_ranges.c | 27 |
2 files changed, 26 insertions, 6 deletions
diff --git a/libdw/ChangeLog b/libdw/ChangeLog index 77c18ce4..a4e770de 100644 --- a/libdw/ChangeLog +++ b/libdw/ChangeLog @@ -1,3 +1,8 @@ +2005-12-12 Roland McGrath <roland@redhat.com> + + * dwarf_ranges.c: Copy CU base address-finding code from + dwarf_getlocation. + 2005-12-09 Roland McGrath <roland@redhat.com> * dwarf_getlocation.c (dwarf_getlocation_addr): Add some unlikelys. diff --git a/libdw/dwarf_ranges.c b/libdw/dwarf_ranges.c index 5d6710a0..007ffc8f 100644 --- a/libdw/dwarf_ranges.c +++ b/libdw/dwarf_ranges.c @@ -65,8 +65,26 @@ dwarf_ranges (Dwarf_Die *die, ptrdiff_t offset, Dwarf_Addr *basep, assert ((Dwarf_Word) offset == start_offset); /* Fetch the CU's base address. */ - if (INTUSE(dwarf_lowpc) (&CUDIE (attr->cu), basep) != 0) - return -1; + Dwarf_Die cudie = CUDIE (attr->cu); + + /* Find the base address of the compilation unit. It will + normally be specified by DW_AT_low_pc. In DWARF-3 draft 4, + the base address could be overridden by DW_AT_entry_pc. It's + been removed, but GCC emits DW_AT_entry_pc and not DW_AT_lowpc + for compilation units with discontinuous ranges. */ + if (unlikely (INTUSE(dwarf_lowpc) (&cudie, basep) != 0) + && INTUSE(dwarf_formaddr) (INTUSE(dwarf_attr) (&cudie, + DW_AT_entry_pc, + &attr_mem), + basep) != 0) + { + if (INTUSE(dwarf_errno) () == 0) + { + invalid: + __libdw_seterrno (DWARF_E_INVALID_DWARF); + } + return -1; + } } else if (offset < 0 || (size_t) offset >= d->d_size) { @@ -79,10 +97,7 @@ dwarf_ranges (Dwarf_Die *die, ptrdiff_t offset, Dwarf_Addr *basep, next: if ((unsigned char *) d->d_buf + d->d_size - readp < die->cu->address_size * 2) - { - __libdw_seterrno (DWARF_E_INVALID_DWARF); - return -1; - } + goto invalid; Dwarf_Addr begin; Dwarf_Addr end; |