OSDN Git Service

PR ld/11375
authoramodra <amodra>
Fri, 26 Mar 2010 09:35:57 +0000 (09:35 +0000)
committeramodra <amodra>
Fri, 26 Mar 2010 09:35:57 +0000 (09:35 +0000)
* elf64-ppc.c (ppc64_elf_relocate_section): Always look up a
possible stub on branches.

bfd/ChangeLog
bfd/elf64-ppc.c

index 0e1b2fa..e0061dc 100644 (file)
@@ -1,3 +1,9 @@
+2010-03-26  Alan Modra  <amodra@gmail.com>
+
+       PR ld/11375
+       * elf64-ppc.c (ppc64_elf_relocate_section): Always look up a
+       possible stub on branches.
+
 2010-03-25  Joseph Myers  <joseph@codesourcery.com>
 
        * Makefile.am (ALL_MACHINES): Add cpu-tic6x.lo.
index b1527f9..306c15e 100644 (file)
@@ -11914,23 +11914,13 @@ ppc64_elf_relocate_section (bfd *output_bfd,
             linkage stubs needs to be followed by a nop, as the nop
             will be replaced with an instruction to restore the TOC
             base pointer.  */
-         stub_entry = NULL;
          fdh = h;
          if (h != NULL
              && h->oh != NULL
              && h->oh->is_func_descriptor)
            fdh = ppc_follow_link (h->oh);
-         if (((fdh != NULL
-               && fdh->elf.plt.plist != NULL)
-              || (sec != NULL
-                  && sec->output_section != NULL
-                  && sec->id <= htab->top_id
-                  && (htab->stub_group[sec->id].toc_off
-                      != htab->stub_group[input_section->id].toc_off))
-              || (h == NULL
-                  && ELF_ST_TYPE (sym->st_info) == STT_GNU_IFUNC))
-             && (stub_entry = ppc_get_stub_entry (input_section, sec, fdh,
-                                                  rel, htab)) != NULL
+         stub_entry = ppc_get_stub_entry (input_section, sec, fdh, rel, htab);
+         if (stub_entry != NULL
              && (stub_entry->stub_type == ppc_stub_plt_call
                  || stub_entry->stub_type == ppc_stub_plt_branch_r2off
                  || stub_entry->stub_type == ppc_stub_long_branch_r2off))
@@ -12015,7 +12005,9 @@ ppc64_elf_relocate_section (bfd *output_bfd,
                unresolved_reloc = FALSE;
            }
 
-         if (stub_entry == NULL
+         if ((stub_entry == NULL
+              || stub_entry->stub_type == ppc_stub_long_branch
+              || stub_entry->stub_type == ppc_stub_plt_branch)
              && get_opd_info (sec) != NULL)
            {
              /* The branch destination is the value of the opd entry. */
@@ -12036,13 +12028,15 @@ ppc64_elf_relocate_section (bfd *output_bfd,
                  + input_section->output_offset
                  + input_section->output_section->vma);
 
-         if (stub_entry == NULL
-             && (relocation + addend - from + max_br_offset
-                 >= 2 * max_br_offset)
-             && r_type != R_PPC64_ADDR14_BRTAKEN
-             && r_type != R_PPC64_ADDR14_BRNTAKEN)
-           stub_entry = ppc_get_stub_entry (input_section, sec, fdh, rel,
-                                            htab);
+         if (stub_entry != NULL
+             && (stub_entry->stub_type == ppc_stub_long_branch
+                 || stub_entry->stub_type == ppc_stub_plt_branch)
+             && (r_type == R_PPC64_ADDR14_BRTAKEN
+                 || r_type == R_PPC64_ADDR14_BRNTAKEN
+                 || (relocation + addend - from + max_br_offset
+                     < 2 * max_br_offset)))
+           /* Don't use the stub if this branch is in range.  */
+           stub_entry = NULL;
 
          if (stub_entry != NULL)
            {