nios2: Call _bfd_elf_maybe_set_textrel to set DF_TEXTREL
[deliverable/binutils-gdb.git] / bfd / elflink.c
index c157aea90dc527e3625a831c8d85ba505a2e34de..ce6282a9dcfc0691ff05979222adba6e816d1c2f 100644 (file)
@@ -7650,6 +7650,37 @@ _bfd_elf_link_hash_copy_indirect (struct bfd_link_info *info,
 {
   struct elf_link_hash_table *htab;
 
+  if (ind->dyn_relocs != NULL)
+    {
+      if (dir->dyn_relocs != NULL)
+       {
+         struct elf_dyn_relocs **pp;
+         struct elf_dyn_relocs *p;
+
+         /* Add reloc counts against the indirect sym to the direct sym
+            list.  Merge any entries against the same section.  */
+         for (pp = &ind->dyn_relocs; (p = *pp) != NULL; )
+           {
+             struct elf_dyn_relocs *q;
+
+             for (q = dir->dyn_relocs; q != NULL; q = q->next)
+               if (q->sec == p->sec)
+                 {
+                   q->pc_count += p->pc_count;
+                   q->count += p->count;
+                   *pp = p->next;
+                   break;
+                 }
+             if (q == NULL)
+               pp = &p->next;
+           }
+         *pp = dir->dyn_relocs;
+       }
+
+      dir->dyn_relocs = ind->dyn_relocs;
+      ind->dyn_relocs = NULL;
+    }
+
   /* Copy down any references that we may have already seen to the
      symbol which just became indirect.  */
 
@@ -12896,8 +12927,7 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info)
        goto error_return;
 
       /* Check for DT_TEXTREL (late, in case the backend removes it).  */
-      if (((info->warn_shared_textrel && bfd_link_pic (info))
-          || info->error_textrel)
+      if (bfd_link_textrel_check (info)
          && (o = bfd_get_linker_section (dynobj, ".dynamic")) != NULL)
        {
          bfd_byte *dyncon, *dynconend;
@@ -12912,12 +12942,15 @@ bfd_elf_final_link (bfd *abfd, struct bfd_link_info *info)
 
              if (dyn.d_tag == DT_TEXTREL)
                {
-                 if (info->error_textrel)
+                 if (info->textrel_check == textrel_check_error)
                    info->callbacks->einfo
                      (_("%P%X: read-only segment has dynamic relocations\n"));
+                 else if (bfd_link_dll (info))
+                   info->callbacks->einfo
+                     (_("%P: warning: creating DT_TEXTREL in a shared object\n"));
                  else
                    info->callbacks->einfo
-                     (_("%P: warning: creating a DT_TEXTREL in a shared object\n"));
+                     (_("%P: warning: creating DT_TEXTREL in a PIE\n"));
                  break;
                }
            }
@@ -14791,3 +14824,54 @@ bfd_elf_define_start_stop (struct bfd_link_info *info,
     }
   return NULL;
 }
+
+/* Find dynamic relocs for H that apply to read-only sections.  */
+
+asection *
+_bfd_elf_readonly_dynrelocs (struct elf_link_hash_entry *h)
+{
+  struct elf_dyn_relocs *p;
+
+  for (p = h->dyn_relocs; p != NULL; p = p->next)
+    {
+      asection *s = p->sec->output_section;
+
+      if (s != NULL && (s->flags & SEC_READONLY) != 0)
+       return p->sec;
+    }
+  return NULL;
+}
+
+/* Set DF_TEXTREL if we find any dynamic relocs that apply to
+   read-only sections.  */
+
+bfd_boolean
+_bfd_elf_maybe_set_textrel (struct elf_link_hash_entry *h, void *inf)
+{
+  asection *sec;
+
+  if (h->root.type == bfd_link_hash_indirect)
+    return TRUE;
+
+  sec = _bfd_elf_readonly_dynrelocs (h);
+  if (sec != NULL)
+    {
+      struct bfd_link_info *info = (struct bfd_link_info *) inf;
+
+      info->flags |= DF_TEXTREL;
+      /* xgettext:c-format */
+      info->callbacks->minfo (_("%pB: dynamic relocation against `%pT' "
+                               "in read-only section `%pA'\n"),
+                             sec->owner, h->root.root.string, sec);
+
+      if (bfd_link_textrel_check (info))
+       /* xgettext:c-format */
+       info->callbacks->einfo (_("%P: %pB: warning: relocation against `%s' "
+                                 "in read-only section `%pA'\n"),
+                               sec->owner, h->root.root.string, sec);
+
+      /* Not an error, just cut short the traversal.  */
+      return FALSE;
+    }
+  return TRUE;
+}
This page took 0.02506 seconds and 4 git commands to generate.