ELF DWARF in PE output
authorAlan Modra <amodra@gmail.com>
Sat, 6 Mar 2021 11:26:15 +0000 (21:56 +1030)
committerAlan Modra <amodra@gmail.com>
Tue, 9 Mar 2021 23:23:51 +0000 (09:53 +1030)
* elf.c (bfd_elf_generic_reloc): Make references between debug
sections use section relative values.

bfd/ChangeLog
bfd/elf.c

index 6c633ebe0b64e10cc25f1bcff5f3a979d5faf0c1..fe3808596bb6575767d78f717daffb36ffdee19d 100644 (file)
@@ -1,3 +1,9 @@
+2021-03-10  Alan Modra  <amodra@gmail.com>
+           Jan Beulich  <jbeulich@suse.com>
+
+       * elf.c (bfd_elf_generic_reloc): Make references between debug
+       sections use section relative values.
+
 2021-03-09  Jan Beulich  <jbeulich@suse.com>
 
        * peXXigen.c (_bfd_XXi_swap_scnhdr_out): Diagnose out of range RVA.
index 553fa65a1184118f706bf35682ef10f01a06c2d9..35c31cf40bfb226a7a5d7743d51ac91122cf1b2b 100644 (file)
--- a/bfd/elf.c
+++ b/bfd/elf.c
@@ -1302,8 +1302,7 @@ const char *const bfd_elf_section_type_names[] =
    change anything about the way the reloc is handled, since it will
    all be done at final link time.  Rather than put special case code
    into bfd_perform_relocation, all the reloc types use this howto
-   function.  It just short circuits the reloc if producing
-   relocatable output against an external symbol.  */
+   function, or should call this function for relocatable output.  */
 
 bfd_reloc_status_type
 bfd_elf_generic_reloc (bfd *abfd ATTRIBUTE_UNUSED,
@@ -1323,6 +1322,20 @@ bfd_elf_generic_reloc (bfd *abfd ATTRIBUTE_UNUSED,
       return bfd_reloc_ok;
     }
 
+  /* In some cases the relocation should be treated as output section
+     relative, as when linking ELF DWARF into PE COFF.  Many ELF
+     targets lack section relative relocations and instead use
+     ordinary absolute relocations for references between DWARF
+     sections.  That is arguably a bug in those targets but it happens
+     to work for the usual case of linking to non-loaded ELF debug
+     sections with VMAs forced to zero.  PE COFF on the other hand
+     doesn't allow a section VMA of zero.  */
+  if (output_bfd == NULL
+      && !reloc_entry->howto->pc_relative
+      && (symbol->section->flags & SEC_DEBUGGING) != 0
+      && (input_section->flags & SEC_DEBUGGING) != 0)
+    reloc_entry->addend -= symbol->section->output_section->vma;
+
   return bfd_reloc_continue;
 }
 \f