*** empty log message ***
[deliverable/binutils-gdb.git] / ld / emultempl / elf32.em
index ca5eafdff93d2675d5c5a81d59628d1920b84cf7..0425d15b78bf935cd1a11caeeb3a0bd5e0010aa4 100644 (file)
@@ -31,10 +31,11 @@ GNU General Public License for more details.
 
 You should have received a copy of the GNU General Public License
 along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
+Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
 
 #define TARGET_IS_${EMULATION_NAME}
 
+#include "config.h"
 #include "bfd.h"
 #include "sysdep.h"
 #include "libiberty.h"
@@ -52,6 +53,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
 #include "ldemul.h"
 #include <ldgram.h>
 #include "elf/common.h"
+#include "elf-bfd.h"
 
 /* Declare functions used by various EXTRA_EM_FILEs.  */
 static void gld${EMULATION_NAME}_before_parse (void);
@@ -59,13 +61,14 @@ static void gld${EMULATION_NAME}_after_open (void);
 static void gld${EMULATION_NAME}_before_allocation (void);
 static bfd_boolean gld${EMULATION_NAME}_place_orphan
   (lang_input_statement_type *file, asection *s);
-static void gld${EMULATION_NAME}_finish (void);
+static void gld${EMULATION_NAME}_layout_sections_again (void);
+static void gld${EMULATION_NAME}_finish (void) ATTRIBUTE_UNUSED;
 
 EOF
 
 if [ "x${USE_LIBPATH}" = xyes ] ; then
   case ${target} in
-    *-*-linux-*)
+    *-*-linux-* | *-*-k*bsd*-*)
   cat >>e${EMULATION_NAME}.c <<EOF
 #ifdef HAVE_GLOB
 #include <glob.h>
@@ -122,6 +125,11 @@ gld${EMULATION_NAME}_load_symbols (lang_input_statement_type *entry)
   if (!entry->add_needed)
     class |= DYN_NO_ADD_NEEDED;
 
+  if (entry->just_syms_flag
+      && (bfd_get_file_flags (entry->the_bfd) & DYNAMIC) != 0)
+    einfo (_("%P%F: --just-symbols may not be used on DSO: %B\n"),
+          entry->the_bfd);
+
   if (!class
       || (bfd_get_file_flags (entry->the_bfd) & DYNAMIC) == 0)
     return FALSE;
@@ -226,6 +234,9 @@ gld${EMULATION_NAME}_stat_needed (lang_input_statement_type *s)
     return;
   if (s->the_bfd == NULL)
     return;
+  if (s->as_needed
+      && (bfd_elf_get_dyn_lib_class (s->the_bfd) & DYN_AS_NEEDED) != 0)
+    return;
 
   if (bfd_stat (s->the_bfd, &st) != 0)
     {
@@ -347,7 +358,7 @@ gld${EMULATION_NAME}_try_needed (struct dt_needed *needed,
 
 EOF
 case ${target} in
-  *-*-linux-*)
+  *-*-linux-* | *-*-k*bsd*-*)
     cat >>e${EMULATION_NAME}.c <<EOF
          {
            struct bfd_link_needed_list *l;
@@ -519,7 +530,7 @@ gld${EMULATION_NAME}_add_sysroot (const char *path)
 
 EOF
   case ${target} in
-    *-*-linux-*)
+    *-*-linux-* | *-*-k*bsd*-*)
       cat >>e${EMULATION_NAME}.c <<EOF
 /* For a native linker, check the file /etc/ld.so.conf for directories
    in which we may find shared libraries.  /etc/ld.so.conf is really
@@ -733,6 +744,13 @@ gld${EMULATION_NAME}_check_needed (lang_input_statement_type *s)
   if (global_found)
     return;
 
+  /* If this input file was an as-needed entry, and wasn't found to be
+     needed at the stage it was linked, then don't say we have loaded it.  */
+  if (s->as_needed
+      && (s->the_bfd == NULL
+         || (bfd_elf_get_dyn_lib_class (s->the_bfd) & DYN_AS_NEEDED) != 0))
+    return;
+
   if (s->filename != NULL)
     {
       const char *f;
@@ -922,7 +940,7 @@ cat >>e${EMULATION_NAME}.c <<EOF
 EOF
 if [ "x${USE_LIBPATH}" = xyes ] ; then
   case ${target} in
-    *-*-linux-*)
+    *-*-linux-* | *-*-k*bsd*-*)
       cat >>e${EMULATION_NAME}.c <<EOF
          if (gld${EMULATION_NAME}_check_ld_so_conf (l->name, force))
            break;
@@ -969,8 +987,8 @@ gld${EMULATION_NAME}_find_exp_assignment (etree_type *exp)
         will do no harm.  */
       if (strcmp (exp->assign.dst, ".") != 0)
        {
-         if (!bfd_elf_record_link_assignment (output_bfd, &link_info,
-                                              exp->assign.dst, provide))
+         if (!bfd_elf_record_link_assignment (&link_info, exp->assign.dst,
+                                              provide))
            einfo ("%P%F: failed to record assignment to %s: %E\n",
                   exp->assign.dst);
        }
@@ -1055,6 +1073,7 @@ gld${EMULATION_NAME}_before_allocation (void)
          (const char * const *) command_line.auxiliary_filters,
          &link_info, &sinterp, lang_elf_version_info)))
     einfo ("%P%F: failed to set dynamic section sizes: %E\n");
+
 ${ELF_INTERPRETER_SET_DEFAULT}
   /* Let the user override the dynamic linker we are using.  */
   if (command_line.interpreter != NULL
@@ -1111,6 +1130,11 @@ ${ELF_INTERPRETER_SET_DEFAULT}
        s->flags |= SEC_EXCLUDE;
       }
   }
+
+  before_allocation_default ();
+
+  if (!bfd_elf_size_dynsym_hash_dynstr (output_bfd, &link_info))
+    einfo ("%P%F: failed to set dynamic section sizes: %E\n");
 }
 
 EOF
@@ -1301,19 +1325,34 @@ gld${EMULATION_NAME}_place_orphan (lang_input_statement_type *file, asection *s)
   lang_output_section_statement_type *after;
   lang_output_section_statement_type *os;
   int isdyn = 0;
+  int iself = s->owner->xvec->flavour == bfd_target_elf_flavour;
+  unsigned int sh_type = iself ? elf_section_type (s) : SHT_NULL;
 
   secname = bfd_get_section_name (s->owner, s);
 
   if (! link_info.relocatable
       && link_info.combreloc
-      && (s->flags & SEC_ALLOC)
-      && strncmp (secname, ".rel", 4) == 0)
+      && (s->flags & SEC_ALLOC))
     {
-      if (secname[4] == 'a')
-       secname = ".rela.dyn";
-      else
-       secname = ".rel.dyn";
-      isdyn = 1;
+      if (iself)
+       switch (sh_type)
+         {
+         case SHT_RELA:
+           secname = ".rela.dyn";
+           isdyn = 1;
+           break;
+         case SHT_REL:
+           secname = ".rel.dyn";
+           isdyn = 1;
+           break;
+         default:
+           break;
+         }
+      else if (strncmp (secname, ".rel", 4) == 0)
+       {
+         secname = secname[4] == 'a' ? ".rela.dyn" : ".rel.dyn";
+         isdyn = 1;
+       }
     }
 
   if (isdyn || (!config.unique_orphan_sections && !unique_section_p (s)))
@@ -1324,8 +1363,11 @@ gld${EMULATION_NAME}_place_orphan (lang_input_statement_type *file, asection *s)
       if (os != NULL
          && (os->bfd_section == NULL
              || os->bfd_section->flags == 0
-             || ((s->flags ^ os->bfd_section->flags)
-                 & (SEC_LOAD | SEC_ALLOC)) == 0))
+             || (bfd_match_sections_by_type (output_bfd,
+                                             os->bfd_section,
+                                             s->owner, s)
+                 && ((s->flags ^ os->bfd_section->flags)
+                     & (SEC_LOAD | SEC_ALLOC)) == 0)))
        {
          /* We already have an output section statement with this
             name, and its bfd section, if any, has compatible flags.
@@ -1372,7 +1414,8 @@ gld${EMULATION_NAME}_place_orphan (lang_input_statement_type *file, asection *s)
   if ((s->flags & SEC_ALLOC) == 0)
     ;
   else if ((s->flags & SEC_LOAD) != 0
-          && strncmp (secname, ".note", 5) == 0)
+          && ((iself && sh_type == SHT_NOTE)
+              || (!iself && strncmp (secname, ".note", 5) == 0)))
     place = &hold[orphan_interp];
   else if ((s->flags & (SEC_LOAD | SEC_HAS_CONTENTS)) == 0)
     place = &hold[orphan_bss];
@@ -1380,7 +1423,8 @@ gld${EMULATION_NAME}_place_orphan (lang_input_statement_type *file, asection *s)
     place = &hold[orphan_sdata];
   else if ((s->flags & SEC_READONLY) == 0)
     place = &hold[orphan_data];
-  else if (strncmp (secname, ".rel", 4) == 0
+  else if (((iself && (sh_type == SHT_RELA || sh_type == SHT_REL))
+           || (!iself && strncmp (secname, ".rel", 4) == 0))
           && (s->flags & SEC_LOAD) != 0)
     place = &hold[orphan_rel];
   else if ((s->flags & SEC_CODE) == 0)
@@ -1428,102 +1472,27 @@ if test x"$LDEMUL_FINISH" != xgld"$EMULATION_NAME"_finish; then
 cat >>e${EMULATION_NAME}.c <<EOF
 
 static void
-gld${EMULATION_NAME}_provide_bound_symbols (const char *sec,
-                                           const char *start,
-                                           const char *end)
+gld${EMULATION_NAME}_layout_sections_again (void)
 {
-  asection *s;
-  bfd_vma start_val, end_val;
+  lang_reset_memory_regions ();
 
-  s = bfd_get_section_by_name (output_bfd, sec);
-  if (s != NULL)
-    {
-      start_val = s->vma;
-      end_val = start_val + s->size;
-    }
-  else
-    {
-      start_val = 0;
-      end_val = 0;
-    }
-  _bfd_elf_provide_symbol (&link_info, start, start_val);
-  _bfd_elf_provide_symbol (&link_info, end, end_val);
+  /* Resize the sections.  */
+  lang_size_sections (NULL, TRUE);
+
+  /* Redo special stuff.  */
+  ldemul_after_allocation ();
+
+  /* Do the assignments again.  */
+  lang_do_assignments ();
 }
 
 static void
 gld${EMULATION_NAME}_finish (void)
 {
   if (bfd_elf_discard_info (output_bfd, &link_info))
-    {
-      lang_reset_memory_regions ();
-
-      /* Resize the sections.  */
-      lang_size_sections (stat_ptr->head, abs_output_section,
-                         &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
-
-      /* Redo special stuff.  */
-      ldemul_after_allocation ();
-
-      /* Do the assignments again.  */
-      lang_do_assignments (stat_ptr->head, abs_output_section,
-                          (fill_type *) 0, (bfd_vma) 0);
-    }
-
-  if (!link_info.relocatable)
-    {
-      lang_output_section_statement_type *os;
-
-      for (os = &lang_output_section_statement.head->output_section_statement;
-          os != NULL;
-          os = os->next)
-       {
-         asection *s;
+    gld${EMULATION_NAME}_layout_sections_again ();
 
-         if (os == abs_output_section || os->constraint == -1)
-           continue;
-         s = os->bfd_section;
-         if (s != NULL && s->size == 0 && (s->flags & SEC_KEEP) == 0)
-           {
-             asection **p;
-
-             for (p = &output_bfd->sections; *p; p = &(*p)->next)
-               if (*p == s)
-                 {
-                   bfd_section_list_remove (output_bfd, p);
-                   output_bfd->section_count--;
-                   break;
-                 }
-           }
-       }
-
-      /* If not building shared library, provide
-
-        __preinit_array_start
-        __preinit_array_end
-        __init_array_start
-        __init_array_end
-        __fini_array_start
-        __fini_array_end
-
-        They are set here rather than via PROVIDE in the linker
-        script, because using PROVIDE inside an output section
-        statement results in unnecessary output sections.  Using
-        PROVIDE outside an output section statement runs the risk of
-        section alignment affecting where the section starts.  */
-
-      if (!link_info.shared)
-       {
-         gld${EMULATION_NAME}_provide_bound_symbols
-           (".preinit_array", "__preinit_array_start",
-            "__preinit_array_end");
-         gld${EMULATION_NAME}_provide_bound_symbols
-           (".init_array", "__init_array_start",
-            "__init_array_end");
-         gld${EMULATION_NAME}_provide_bound_symbols
-           (".fini_array", "__fini_array_start",
-            "__fini_array_end");
-       }
-    }
+  finish_default ();
 }
 EOF
 fi
This page took 0.029798 seconds and 4 git commands to generate.