gdb/
[deliverable/binutils-gdb.git] / bfd / elf64-ppc.c
index 8fff7fb99d3f8c0c7ae1d45df216571a0c39f1cc..359d2f80c0bc8926654e135e4d3b7058814d05a6 100644 (file)
@@ -34,6 +34,7 @@
 #include "elf-bfd.h"
 #include "elf/ppc64.h"
 #include "elf64-ppc.h"
+#include "dwarf2.h"
 
 static bfd_reloc_status_type ppc64_elf_ha_reloc
   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
@@ -80,7 +81,7 @@ static bfd_vma opd_entry_value
 #define bfd_elf64_mkobject                   ppc64_elf_mkobject
 #define bfd_elf64_bfd_reloc_type_lookup              ppc64_elf_reloc_type_lookup
 #define bfd_elf64_bfd_reloc_name_lookup              ppc64_elf_reloc_name_lookup
-#define bfd_elf64_bfd_merge_private_bfd_data  ppc64_elf_merge_private_bfd_data
+#define bfd_elf64_bfd_merge_private_bfd_data  _bfd_generic_verify_endian_match
 #define bfd_elf64_new_section_hook           ppc64_elf_new_section_hook
 #define bfd_elf64_bfd_link_hash_table_create  ppc64_elf_link_hash_table_create
 #define bfd_elf64_bfd_link_hash_table_free    ppc64_elf_link_hash_table_free
@@ -2727,35 +2728,6 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type,
     }
 }
 
-/* Merge backend specific data from an object file to the output
-   object file when linking.  */
-
-static bfd_boolean
-ppc64_elf_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
-{
-  /* Check if we have the same endianess.  */
-  if (ibfd->xvec->byteorder != obfd->xvec->byteorder
-      && ibfd->xvec->byteorder != BFD_ENDIAN_UNKNOWN
-      && obfd->xvec->byteorder != BFD_ENDIAN_UNKNOWN)
-    {
-      const char *msg;
-
-      if (bfd_big_endian (ibfd))
-       msg = _("%B: compiled for a big endian system "
-               "and target is little endian");
-      else
-       msg = _("%B: compiled for a little endian system "
-               "and target is big endian");
-
-      (*_bfd_error_handler) (msg, ibfd);
-
-      bfd_set_error (bfd_error_wrong_format);
-      return FALSE;
-    }
-
-  return TRUE;
-}
-
 /* Add extra PPC sections.  */
 
 static const struct bfd_elf_special_section ppc64_elf_special_sections[]=
@@ -3749,6 +3721,7 @@ struct ppc_link_hash_table
   asection *sfpr;
   asection *brlt;
   asection *relbrlt;
+  asection *glink_eh_frame;
 
   /* Shortcut to .__tls_get_addr and __tls_get_addr.  */
   struct ppc_link_hash_entry *tls_get_addr;
@@ -3763,6 +3736,9 @@ struct ppc_link_hash_table
   /* Number of stubs against global syms.  */
   unsigned long stub_globals;
 
+  /* Set if PLT call stubs should load r11.  */
+  unsigned int plt_static_chain:1;
+
   /* Set if we should emit symbols for stubs.  */
   unsigned int emit_stub_syms:1;
 
@@ -4196,6 +4172,18 @@ create_linkage_sections (bfd *dynobj, struct bfd_link_info *info)
       || ! bfd_set_section_alignment (dynobj, htab->glink, 3))
     return FALSE;
 
+  if (!info->no_ld_generated_unwind_info)
+    {
+      flags = (SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_HAS_CONTENTS
+              | SEC_IN_MEMORY | SEC_LINKER_CREATED);
+      htab->glink_eh_frame = bfd_make_section_anyway_with_flags (dynobj,
+                                                                ".eh_frame",
+                                                                flags);
+      if (htab->glink_eh_frame == NULL
+         || !bfd_set_section_alignment (abfd, htab->glink_eh_frame, 2))
+       return FALSE;
+    }
+
   flags = SEC_ALLOC | SEC_LINKER_CREATED;
   htab->iplt = bfd_make_section_anyway_with_flags (dynobj, ".iplt", flags);
   if (htab->iplt == NULL
@@ -4378,6 +4366,29 @@ ppc64_elf_copy_indirect_symbol (struct bfd_link_info *info,
   edir = (struct ppc_link_hash_entry *) dir;
   eind = (struct ppc_link_hash_entry *) ind;
 
+  edir->is_func |= eind->is_func;
+  edir->is_func_descriptor |= eind->is_func_descriptor;
+  edir->tls_mask |= eind->tls_mask;
+  if (eind->oh != NULL)
+    edir->oh = ppc_follow_link (eind->oh);
+
+  /* If called to transfer flags for a weakdef during processing
+     of elf_adjust_dynamic_symbol, don't copy NON_GOT_REF.
+     We clear it ourselves for ELIMINATE_COPY_RELOCS.  */
+  if (!(ELIMINATE_COPY_RELOCS
+       && eind->elf.root.type != bfd_link_hash_indirect
+       && edir->elf.dynamic_adjusted))
+    edir->elf.non_got_ref |= eind->elf.non_got_ref;
+
+  edir->elf.ref_dynamic |= eind->elf.ref_dynamic;
+  edir->elf.ref_regular |= eind->elf.ref_regular;
+  edir->elf.ref_regular_nonweak |= eind->elf.ref_regular_nonweak;
+  edir->elf.needs_plt |= eind->elf.needs_plt;
+
+  /* If we were called to copy over info for a weak sym, that's all.  */
+  if (eind->elf.root.type != bfd_link_hash_indirect)
+    return;
+
   /* Copy over any dynamic relocs we may have on the indirect sym.  */
   if (eind->dyn_relocs != NULL)
     {
@@ -4410,29 +4421,6 @@ ppc64_elf_copy_indirect_symbol (struct bfd_link_info *info,
       eind->dyn_relocs = NULL;
     }
 
-  edir->is_func |= eind->is_func;
-  edir->is_func_descriptor |= eind->is_func_descriptor;
-  edir->tls_mask |= eind->tls_mask;
-  if (eind->oh != NULL)
-    edir->oh = ppc_follow_link (eind->oh);
-
-  /* If called to transfer flags for a weakdef during processing
-     of elf_adjust_dynamic_symbol, don't copy NON_GOT_REF.
-     We clear it ourselves for ELIMINATE_COPY_RELOCS.  */
-  if (!(ELIMINATE_COPY_RELOCS
-       && eind->elf.root.type != bfd_link_hash_indirect
-       && edir->elf.dynamic_adjusted))
-    edir->elf.non_got_ref |= eind->elf.non_got_ref;
-
-  edir->elf.ref_dynamic |= eind->elf.ref_dynamic;
-  edir->elf.ref_regular |= eind->elf.ref_regular;
-  edir->elf.ref_regular_nonweak |= eind->elf.ref_regular_nonweak;
-  edir->elf.needs_plt |= eind->elf.needs_plt;
-
-  /* If we were called to copy over info for a weak sym, that's all.  */
-  if (eind->elf.root.type != bfd_link_hash_indirect)
-    return;
-
   /* Copy over got entries that we may have already seen to the
      symbol which just became indirect.  */
   if (eind->elf.got.glist != NULL)
@@ -5669,9 +5657,6 @@ ppc64_elf_gc_mark_dynamic_ref (struct elf_link_hash_entry *h, void *inf)
   struct ppc_link_hash_entry *eh = (struct ppc_link_hash_entry *) h;
   struct ppc_link_hash_entry *fdh;
 
-  if (eh->elf.root.type == bfd_link_hash_warning)
-    eh = (struct ppc_link_hash_entry *) eh->elf.root.u.i.link;
-
   /* Dynamic linking info is on the func descriptor sym.  */
   fdh = defined_func_desc (eh);
   if (fdh != NULL)
@@ -6214,9 +6199,6 @@ func_desc_adjust (struct elf_link_hash_entry *h, void *inf)
   if (fh->elf.root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (fh->elf.root.type == bfd_link_hash_warning)
-    fh = (struct ppc_link_hash_entry *) fh->elf.root.u.i.link;
-
   info = inf;
   htab = ppc_hash_table (info);
   if (htab == NULL)
@@ -6742,9 +6724,6 @@ adjust_opd_syms (struct elf_link_hash_entry *h, void *inf ATTRIBUTE_UNUSED)
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   if (h->root.type != bfd_link_hash_defined
       && h->root.type != bfd_link_hash_defweak)
     return TRUE;
@@ -7905,9 +7884,6 @@ adjust_toc_syms (struct elf_link_hash_entry *h, void *inf)
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   if (h->root.type != bfd_link_hash_defined
       && h->root.type != bfd_link_hash_defweak)
     return TRUE;
@@ -8603,9 +8579,6 @@ allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   info = (struct bfd_link_info *) inf;
   htab = ppc_hash_table (info);
   if (htab == NULL)
@@ -8846,9 +8819,6 @@ readonly_dynrelocs (struct elf_link_hash_entry *h, void *inf)
   struct ppc_link_hash_entry *eh;
   struct elf_dyn_relocs *p;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   eh = (struct ppc_link_hash_entry *) h;
   for (p = eh->dyn_relocs; p != NULL; p = p->next)
     {
@@ -9069,6 +9039,12 @@ ppc64_elf_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
          /* Strip this section if we don't need it; see the
             comment below.  */
        }
+      else if (s == htab->glink_eh_frame)
+       {
+         if (!bfd_is_abs_section (s->output_section))
+           /* Not sized yet.  */
+           continue;
+       }
       else if (CONST_STRNEQ (s->name, ".rela"))
        {
          if (s->size != 0)
@@ -9300,7 +9276,8 @@ ppc_type_of_stub (asection *input_sec,
 /* Build a .plt call stub.  */
 
 static inline bfd_byte *
-build_plt_stub (bfd *obfd, bfd_byte *p, int offset, Elf_Internal_Rela *r)
+build_plt_stub (bfd *obfd, bfd_byte *p, int offset, Elf_Internal_Rela *r,
+               bfd_boolean plt_static_chain)
 {
 #define PPC_LO(v) ((v) & 0xffff)
 #define PPC_HI(v) (((v) >> 16) & 0xffff)
@@ -9333,14 +9310,15 @@ build_plt_stub (bfd *obfd, bfd_byte *p, int offset, Elf_Internal_Rela *r)
       bfd_put_32 (obfd, ADDIS_R12_R2 | PPC_HA (offset), p),    p += 4;
       bfd_put_32 (obfd, STD_R2_40R1, p),                       p += 4;
       bfd_put_32 (obfd, LD_R11_0R12 | PPC_LO (offset), p),     p += 4;
-      if (PPC_HA (offset + 16) != PPC_HA (offset))
+      if (PPC_HA (offset + 8 + 8 * plt_static_chain) != PPC_HA (offset))
        {
          bfd_put_32 (obfd, ADDI_R12_R12 | PPC_LO (offset), p), p += 4;
          offset = 0;
        }
       bfd_put_32 (obfd, MTCTR_R11, p),                         p += 4;
       bfd_put_32 (obfd, LD_R2_0R12 | PPC_LO (offset + 8), p),  p += 4;
-      bfd_put_32 (obfd, LD_R11_0R12 | PPC_LO (offset + 16), p),        p += 4;
+      if (plt_static_chain)
+       bfd_put_32 (obfd, LD_R11_0R12 | PPC_LO (offset + 16), p), p += 4;
       bfd_put_32 (obfd, BCTR, p),                              p += 4;
     }
   else
@@ -9367,13 +9345,14 @@ build_plt_stub (bfd *obfd, bfd_byte *p, int offset, Elf_Internal_Rela *r)
        }
       bfd_put_32 (obfd, STD_R2_40R1, p),                       p += 4;
       bfd_put_32 (obfd, LD_R11_0R2 | PPC_LO (offset), p),      p += 4;
-      if (PPC_HA (offset + 16) != PPC_HA (offset))
+      if (PPC_HA (offset + 8 + 8 * plt_static_chain) != PPC_HA (offset))
        {
          bfd_put_32 (obfd, ADDI_R2_R2 | PPC_LO (offset), p),   p += 4;
          offset = 0;
        }
       bfd_put_32 (obfd, MTCTR_R11, p),                         p += 4;
-      bfd_put_32 (obfd, LD_R11_0R2 | PPC_LO (offset + 16), p), p += 4;
+      if (plt_static_chain)
+       bfd_put_32 (obfd, LD_R11_0R2 | PPC_LO (offset + 16), p), p += 4;
       bfd_put_32 (obfd, LD_R2_0R2 | PPC_LO (offset + 8), p),   p += 4;
       bfd_put_32 (obfd, BCTR, p),                              p += 4;
     }
@@ -9398,7 +9377,7 @@ build_plt_stub (bfd *obfd, bfd_byte *p, int offset, Elf_Internal_Rela *r)
 
 static inline bfd_byte *
 build_tls_get_addr_stub (bfd *obfd, bfd_byte *p, int offset,
-                        Elf_Internal_Rela *r)
+                        Elf_Internal_Rela *r, bfd_boolean plt_static_chain)
 {
   bfd_put_32 (obfd, LD_R11_0R3 + 0, p),                p += 4;
   bfd_put_32 (obfd, LD_R12_0R3 + 8, p),                p += 4;
@@ -9412,7 +9391,7 @@ build_tls_get_addr_stub (bfd *obfd, bfd_byte *p, int offset,
 
   if (r != NULL)
     r[0].r_offset += 9 * 4;
-  p = build_plt_stub (obfd, p, offset, r);
+  p = build_plt_stub (obfd, p, offset, r, plt_static_chain);
   bfd_put_32 (obfd, BCTRL, p - 4);
 
   bfd_put_32 (obfd, LD_R11_0R1 + 32, p),       p += 4;
@@ -9842,9 +9821,11 @@ ppc_build_one_stub (struct bfd_hash_entry *gen_entry, void *in_arg)
          && (stub_entry->h == htab->tls_get_addr_fd
              || stub_entry->h == htab->tls_get_addr)
          && !htab->no_tls_get_addr_opt)
-       p = build_tls_get_addr_stub (htab->stub_bfd, loc, off, r);
+       p = build_tls_get_addr_stub (htab->stub_bfd, loc, off, r,
+                                    htab->plt_static_chain);
       else
-       p = build_plt_stub (htab->stub_bfd, loc, off, r);
+       p = build_plt_stub (htab->stub_bfd, loc, off, r,
+                           htab->plt_static_chain);
       size = p - loc;
       break;
 
@@ -9931,6 +9912,8 @@ ppc_size_one_stub (struct bfd_hash_entry *gen_entry, void *in_arg)
              - htab->stub_group[stub_entry->id_sec->id].toc_off);
 
       size = PLT_CALL_STUB_SIZE;
+      if (!htab->plt_static_chain)
+       size -= 4;
       if (PPC_HA (off) == 0)
        size -= 4;
       if (PPC_HA (off + 16) != PPC_HA (off))
@@ -10217,9 +10200,6 @@ merge_global_got (struct elf_link_hash_entry *h, void *inf ATTRIBUTE_UNUSED)
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   merge_got_entries (&h->got.glist);
 
   return TRUE;
@@ -10236,9 +10216,6 @@ reallocate_got (struct elf_link_hash_entry *h, void *inf)
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   for (gent = h->got.glist; gent != NULL; gent = gent->next)
     if (!gent->is_indirect)
       allocate_got (h, (struct bfd_link_info *) inf, gent);
@@ -10869,6 +10846,20 @@ group_sections (struct ppc_link_hash_table *htab,
 #undef PREV_SEC
 }
 
+static const unsigned char glink_eh_frame_cie[] =
+{
+  0, 0, 0, 16,                         /* length.  */
+  0, 0, 0, 0,                          /* id.  */
+  1,                                   /* CIE version.  */
+  'z', 'R', 0,                         /* Augmentation string.  */
+  4,                                   /* Code alignment.  */
+  0x78,                                        /* Data alignment.  */
+  65,                                  /* RA reg.  */
+  1,                                   /* Augmentation size.  */
+  DW_EH_PE_pcrel | DW_EH_PE_sdata4,    /* FDE encoding.  */
+  DW_CFA_def_cfa, 1, 0                 /* def_cfa: r1 offset 0.  */
+};
+
 /* Determine and set the size of the stub section for a final link.
 
    The basic idea here is to examine all the relocations looking for
@@ -10876,7 +10867,8 @@ group_sections (struct ppc_link_hash_table *htab,
    instruction.  */
 
 bfd_boolean
-ppc64_elf_size_stubs (struct bfd_link_info *info, bfd_signed_vma group_size)
+ppc64_elf_size_stubs (struct bfd_link_info *info, bfd_signed_vma group_size,
+                     bfd_boolean plt_static_chain)
 {
   bfd_size_type stub_group_size;
   bfd_boolean stubs_always_before_branch;
@@ -10885,6 +10877,7 @@ ppc64_elf_size_stubs (struct bfd_link_info *info, bfd_signed_vma group_size)
   if (htab == NULL)
     return FALSE;
 
+  htab->plt_static_chain = plt_static_chain;
   stubs_always_before_branch = group_size < 0;
   if (group_size < 0)
     stub_group_size = -group_size;
@@ -11210,6 +11203,25 @@ ppc64_elf_size_stubs (struct bfd_link_info *info, bfd_signed_vma group_size)
          htab->glink->flags |= SEC_RELOC;
        }
 
+      if (htab->glink_eh_frame != NULL
+         && !bfd_is_abs_section (htab->glink_eh_frame->output_section)
+         && (htab->glink_eh_frame->flags & SEC_EXCLUDE) == 0)
+       {
+         bfd_size_type size = 0;
+
+         for (stub_sec = htab->stub_bfd->sections;
+              stub_sec != NULL;
+              stub_sec = stub_sec->next)
+           if ((stub_sec->flags & SEC_LINKER_CREATED) == 0)
+             size += 20;
+         if (htab->glink != NULL && htab->glink->size != 0)
+           size += 24;
+         if (size != 0)
+           size += sizeof (glink_eh_frame_cie);
+         htab->glink_eh_frame->rawsize = htab->glink_eh_frame->size;
+         htab->glink_eh_frame->size = size;
+       }
+
       for (stub_sec = htab->stub_bfd->sections;
           stub_sec != NULL;
           stub_sec = stub_sec->next)
@@ -11219,7 +11231,9 @@ ppc64_elf_size_stubs (struct bfd_link_info *info, bfd_signed_vma group_size)
 
       /* Exit from this loop when no stubs have been added, and no stubs
         have changed size.  */
-      if (stub_sec == NULL)
+      if (stub_sec == NULL
+         && (htab->glink_eh_frame == NULL
+             || htab->glink_eh_frame->rawsize == htab->glink_eh_frame->size))
        break;
 
       /* Ask the linker to do its stuff.  */
@@ -11434,6 +11448,100 @@ ppc64_elf_build_stubs (bfd_boolean emit_stub_syms,
        return FALSE;
     }
 
+  if (htab->glink_eh_frame != NULL
+      && htab->glink_eh_frame->size != 0)
+    {
+      bfd_vma val;
+
+      p = bfd_zalloc (htab->glink_eh_frame->owner, htab->glink_eh_frame->size);
+      if (p == NULL)
+       return FALSE;
+      htab->glink_eh_frame->contents = p;
+
+      htab->glink_eh_frame->rawsize = htab->glink_eh_frame->size;
+
+      memcpy (p, glink_eh_frame_cie, sizeof (glink_eh_frame_cie));
+      /* CIE length (rewrite in case little-endian).  */
+      bfd_put_32 (htab->elf.dynobj, sizeof (glink_eh_frame_cie) - 4, p);
+      p += sizeof (glink_eh_frame_cie);
+
+      for (stub_sec = htab->stub_bfd->sections;
+          stub_sec != NULL;
+          stub_sec = stub_sec->next)
+       if ((stub_sec->flags & SEC_LINKER_CREATED) == 0)
+         {
+           /* FDE length.  */
+           bfd_put_32 (htab->elf.dynobj, 16, p);
+           p += 4;
+           /* CIE pointer.  */
+           val = p - htab->glink_eh_frame->contents;
+           bfd_put_32 (htab->elf.dynobj, val, p);
+           p += 4;
+           /* Offset to stub section.  */
+           val = (stub_sec->output_section->vma
+                  + stub_sec->output_offset);
+           val -= (htab->glink_eh_frame->output_section->vma
+                   + htab->glink_eh_frame->output_offset);
+           val -= p - htab->glink_eh_frame->contents;
+           if (val + 0x80000000 > 0xffffffff)
+             {
+               info->callbacks->einfo
+                 (_("%s offset too large for .eh_frame sdata4 encoding"),
+                  stub_sec->name);
+               return FALSE;
+             }
+           bfd_put_32 (htab->elf.dynobj, val, p);
+           p += 4;
+           /* stub section size.  */
+           bfd_put_32 (htab->elf.dynobj, stub_sec->rawsize, p);
+           p += 4;
+           /* Augmentation.  */
+           p += 1;
+           /* Pad.  */
+           p += 3;
+         }
+      if (htab->glink != NULL && htab->glink->size != 0)
+       {
+         /* FDE length.  */
+         bfd_put_32 (htab->elf.dynobj, 20, p);
+         p += 4;
+         /* CIE pointer.  */
+         val = p - htab->glink_eh_frame->contents;
+         bfd_put_32 (htab->elf.dynobj, val, p);
+         p += 4;
+         /* Offset to .glink.  */
+         val = (htab->glink->output_section->vma
+                + htab->glink->output_offset
+                + 8);
+         val -= (htab->glink_eh_frame->output_section->vma
+                 + htab->glink_eh_frame->output_offset);
+         val -= p - htab->glink_eh_frame->contents;
+         if (val + 0x80000000 > 0xffffffff)
+           {
+             info->callbacks->einfo
+               (_("%s offset too large for .eh_frame sdata4 encoding"),
+                htab->glink->name);
+             return FALSE;
+           }
+         bfd_put_32 (htab->elf.dynobj, val, p);
+         p += 4;
+         /* .glink size.  */
+         bfd_put_32 (htab->elf.dynobj, htab->glink->rawsize - 8, p);
+         p += 4;
+         /* Augmentation.  */
+         p += 1;
+
+         *p++ = DW_CFA_advance_loc + 1;
+         *p++ = DW_CFA_register;
+         *p++ = 65;
+         *p++ = 12;
+         *p++ = DW_CFA_advance_loc + 4;
+         *p++ = DW_CFA_restore_extended;
+         *p++ = 65;
+       }
+      htab->glink_eh_frame->size = p - htab->glink_eh_frame->contents;
+    }
+
   /* Build the stubs as directed by the stub hash table.  */
   bfd_hash_traverse (&htab->stub_hash_table, ppc_build_one_stub, info);
 
@@ -11451,7 +11559,9 @@ ppc64_elf_build_stubs (bfd_boolean emit_stub_syms,
       }
 
   if (stub_sec != NULL
-      || htab->glink->rawsize != htab->glink->size)
+      || htab->glink->rawsize != htab->glink->size
+      || (htab->glink_eh_frame != NULL
+         && htab->glink_eh_frame->rawsize != htab->glink_eh_frame->size))
     {
       htab->stub_error = TRUE;
       info->callbacks->einfo (_("stubs don't match calculated size\n"));
@@ -11493,9 +11603,6 @@ undo_symbol_twiddle (struct elf_link_hash_entry *h, void *inf ATTRIBUTE_UNUSED)
   if (h->root.type == bfd_link_hash_indirect)
     return TRUE;
 
-  if (h->root.type == bfd_link_hash_warning)
-    h = (struct elf_link_hash_entry *) h->root.u.i.link;
-
   eh = (struct ppc_link_hash_entry *) h;
   if (eh->elf.root.type != bfd_link_hash_undefweak || !eh->was_undefined)
     return TRUE;
@@ -13603,6 +13710,14 @@ ppc64_elf_finish_dynamic_sections (bfd *output_bfd,
                                       NULL))
     return FALSE;
 
+
+  if (htab->glink_eh_frame != NULL
+      && htab->glink_eh_frame->sec_info_type == ELF_INFO_TYPE_EH_FRAME
+      && !_bfd_elf_write_section_eh_frame (output_bfd, info,
+                                          htab->glink_eh_frame,
+                                          htab->glink_eh_frame->contents))
+    return FALSE;
+
   /* We need to handle writing out multiple GOT sections ourselves,
      since we didn't add them to DYNOBJ.  We know dynobj is the first
      bfd.  */
This page took 0.034048 seconds and 4 git commands to generate.