diff options
author | Jakub Jelinek <jakub@redhat.com> | 2002-04-22 12:06:01 +0000 |
---|---|---|
committer | Jakub Jelinek <jakub@redhat.com> | 2002-04-22 12:06:01 +0000 |
commit | 1a417d846c970c9c788a9f78b2b0eb217957e45b (patch) | |
tree | 617cdfafc46976fb6317af4a0940cb6c3797d49a /bfd | |
parent | 128faaf757bb0b3a15550cc90da759b6080dd1e7 (diff) | |
download | gdb-1a417d846c970c9c788a9f78b2b0eb217957e45b.tar.gz |
* elf-eh-frame.c (struct eh_cie_fde): Add per_encoding_relative.
(_bfd_elf_discard_section_eh_frame): Set it for CIEs with pcrel
encoded personality.
(_bfd_elf_write_section_eh_frame): Adjust pcrel encoded personality
for CIE/FDE removal.
Diffstat (limited to 'bfd')
-rw-r--r-- | bfd/ChangeLog | 9 | ||||
-rw-r--r-- | bfd/elf-eh-frame.c | 22 |
2 files changed, 29 insertions, 2 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog index d09f7e8d90d..78eec86852b 100644 --- a/bfd/ChangeLog +++ b/bfd/ChangeLog @@ -1,3 +1,12 @@ +2002-04-22 Richard Smith <richard@ex-parrot.com> + Jakub Jelinek <jakub@redhat.com> + + * elf-eh-frame.c (struct eh_cie_fde): Add per_encoding_relative. + (_bfd_elf_discard_section_eh_frame): Set it for CIEs with pcrel + encoded personality. + (_bfd_elf_write_section_eh_frame): Adjust pcrel encoded personality + for CIE/FDE removal. + 2002-04-20 Tom Rix <trix@redhat.com> * coff64-rs6000.c (_bfd_xcoff64_swap_aux_in): Fix C_FILE auxent. diff --git a/bfd/elf-eh-frame.c b/bfd/elf-eh-frame.c index 20cbfb22c83..83ccfe9c54e 100644 --- a/bfd/elf-eh-frame.c +++ b/bfd/elf-eh-frame.c @@ -64,6 +64,7 @@ struct eh_cie_fde unsigned char removed : 1; unsigned char make_relative : 1; unsigned char make_lsda_relative : 1; + unsigned char per_encoding_relative : 1; }; struct eh_frame_sec_info @@ -469,6 +470,8 @@ _bfd_elf_discard_section_eh_frame (abfd, info, sec, ehdrsec, = cie.make_relative; sec_info->entry[last_cie_ndx].make_lsda_relative = cie.make_lsda_relative; + sec_info->entry[last_cie_ndx].per_encoding_relative + = (cie.per_encoding & 0x70) == DW_EH_PE_pcrel; } } @@ -689,6 +692,7 @@ _bfd_elf_discard_section_eh_frame (abfd, info, sec, ehdrsec, { sec_info->entry[i].make_relative = make_relative; sec_info->entry[i].make_lsda_relative = make_lsda_relative; + sec_info->entry[i].per_encoding_relative = 0; } } else if (sec_info->entry[i].cie && sec_info->entry[i].sec == sec) @@ -947,7 +951,8 @@ _bfd_elf_write_section_eh_frame (abfd, sec, ehdrsec, contents) /* CIE */ cie_offset = sec_info->entry[i].new_offset; if (sec_info->entry[i].make_relative - || sec_info->entry[i].make_lsda_relative) + || sec_info->entry[i].make_lsda_relative + || sec_info->entry[i].per_encoding_relative) { unsigned char *aug; unsigned int action; @@ -956,7 +961,8 @@ _bfd_elf_write_section_eh_frame (abfd, sec, ehdrsec, contents) /* Need to find 'R' or 'L' augmentation's argument and modify DW_EH_PE_* value. */ action = (sec_info->entry[i].make_relative ? 1 : 0) - | (sec_info->entry[i].make_lsda_relative ? 2 : 0); + | (sec_info->entry[i].make_lsda_relative ? 2 : 0) + | (sec_info->entry[i].per_encoding_relative ? 4 : 0); buf = contents + sec_info->entry[i].offset; /* Skip length, id and version. */ buf += 9; @@ -988,10 +994,22 @@ _bfd_elf_write_section_eh_frame (abfd, sec, ehdrsec, contents) per_width = get_DW_EH_PE_width (per_encoding, ptr_size); BFD_ASSERT (per_width != 0); + BFD_ASSERT (((per_encoding & 0x70) == DW_EH_PE_pcrel) + == sec_info->entry[i].per_encoding_relative); if ((per_encoding & 0xf0) == DW_EH_PE_aligned) buf = (contents + ((buf - contents + per_width - 1) & ~((bfd_size_type) per_width - 1))); + if (action & 4) + { + bfd_vma value; + + value = read_value (abfd, buf, per_width); + value += (sec_info->entry[i].offset + - sec_info->entry[i].new_offset); + write_value (abfd, buf, value, per_width); + action &= ~4; + } buf += per_width; break; case 'R': |