OSDN Git Service

place_orphan optimisations
authorAlan Modra <amodra@bigpond.net.au>
Tue, 25 Apr 2000 05:14:16 +0000 (05:14 +0000)
committerAlan Modra <amodra@bigpond.net.au>
Tue, 25 Apr 2000 05:14:16 +0000 (05:14 +0000)
ld/ChangeLog
ld/emultempl/armelf.em
ld/emultempl/elf32.em
ld/emultempl/pe.em
ld/ldlang.c
ld/ldlang.h

index 36bd2db..9e8e0e5 100644 (file)
@@ -1,3 +1,26 @@
+2000-04-25  Alan Modra  <alan@linuxcare.com.au>
+
+       * emultempl/elf32.em (gld${EMULATION_NAME}_place_section): Delete.
+       (output_rel_find): New function.
+       (hold_section, hold_use): Delete.
+       (hold_text, hold_rodata, hold_data, hold_bss, hold_rel,
+       hold_interp): Make local to place_orphan.
+       (gld${EMULATION_NAME}_place_orphan): Use lang_output_section_find
+       rather than place_section to find possible previous use of orphan.
+       Similarly find the place-holder output sections.  Use returned
+       value from lang_enter_output_section_statement rather than calling
+       lang_output_section_statement_lookup.
+       * emultempl/armelf.em: Same here.
+       * emultempl/pe.em: Similar to above, but no need for output_rel_find.
+
+       * ldlang.c (lang_enter_output_section_statement): Return output
+       section statement.
+       * ldlang.h (lang_enter_output_section_statement): Change
+       declaration too.
+
+       * ldlang.h (lang_output_section_statement): Export it.
+       * ldlang.c (lang_output_section_statement): Ditto.
+
 2000-04-24  Nick Clifton  <nickc@cygnus.com>
 
        * ld.texinfo (Output Section Data): Add note that section data
index 8de6c9b..a1a3968 100644 (file)
@@ -61,8 +61,7 @@ static void gld${EMULATION_NAME}_find_statement_assignment
 static void gld${EMULATION_NAME}_find_exp_assignment PARAMS ((etree_type *));
 static boolean gld${EMULATION_NAME}_place_orphan
   PARAMS ((lang_input_statement_type *, asection *));
-static void gld${EMULATION_NAME}_place_section
-  PARAMS ((lang_statement_union_type *));
+static lang_output_section_statement_type *output_rel_find PARAMS ((void));
 static void gld${EMULATION_NAME}_before_parse PARAMS ((void));
 static void gld${EMULATION_NAME}_before_allocation PARAMS ((void));
 static char *gld${EMULATION_NAME}_get_script PARAMS ((int *isfile));
@@ -783,21 +782,12 @@ gld${EMULATION_NAME}_vercheck (s)
 /* Place an orphan section.  We use this to put random SHF_ALLOC
    sections in the right segment.  */
 
-static asection *hold_section;
-static lang_output_section_statement_type *hold_use;
-
 struct orphan_save
 {
   lang_output_section_statement_type *os;
   asection **section;
   lang_statement_union_type **stmt;
 };
-static struct orphan_save hold_text;
-static struct orphan_save hold_rodata;
-static struct orphan_save hold_data;
-static struct orphan_save hold_bss;
-static struct orphan_save hold_rel;
-static struct orphan_save hold_interp;
 
 /*ARGSUSED*/
 static boolean
@@ -805,6 +795,12 @@ gld${EMULATION_NAME}_place_orphan (file, s)
      lang_input_statement_type *file;
      asection *s;
 {
+  static struct orphan_save hold_text;
+  static struct orphan_save hold_rodata;
+  static struct orphan_save hold_data;
+  static struct orphan_save hold_bss;
+  static struct orphan_save hold_rel;
+  static struct orphan_save hold_interp;
   struct orphan_save *place;
   lang_statement_list_type *old;
   lang_statement_list_type add;
@@ -813,19 +809,22 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   const char *outsecname;
   lang_output_section_statement_type *os;
 
+  secname = bfd_get_section_name (s->owner, s);
+
   /* Look through the script to see where to place this section.  */
-  hold_section = s;
-  hold_use = NULL;
-  lang_for_each_statement (gld${EMULATION_NAME}_place_section);
+  os = lang_output_section_find (secname);
 
-  if (hold_use != NULL)
+  if (os != NULL
+      && os->bfd_section != NULL
+      && ((s->flags ^ os->bfd_section->flags) & (SEC_LOAD | SEC_ALLOC)) == 0)
     {
       /* We have already placed a section with this name.  */
-      wild_doit (&hold_use->children, s, hold_use, file);
+      wild_doit (&os->children, s, os, file);
       return true;
     }
 
-  secname = bfd_get_section_name (s->owner, s);
+  if (hold_text.os == NULL)
+    hold_text.os = lang_output_section_find (".text");
 
   /* If this is a final link, then always put .gnu.warning.SYMBOL
      sections into the .text section to get them out of the way.  */
@@ -843,26 +842,30 @@ gld${EMULATION_NAME}_place_orphan (file, s)
      right after the .interp section, so that the PT_NOTE segment is
      stored right after the program headers where the OS can read it
      in the first page.  */
+#define HAVE_SECTION(hold, name) \
+(hold.os != NULL || (hold.os = lang_output_section_find (name)) != NULL)
+
   if (s->flags & SEC_EXCLUDE)
     return false;
   else if ((s->flags & SEC_ALLOC) == 0)
     place = NULL;
   else if ((s->flags & SEC_LOAD) != 0
           && strncmp (secname, ".note", 4) == 0
-          && hold_interp.os != NULL)
+          && HAVE_SECTION (hold_interp, ".interp"))
     place = &hold_interp;
   else if ((s->flags & SEC_HAS_CONTENTS) == 0
-          && hold_bss.os != NULL)
+          && HAVE_SECTION (hold_bss, ".bss"))
     place = &hold_bss;
   else if ((s->flags & SEC_READONLY) == 0
-          && hold_data.os != NULL)
+          && HAVE_SECTION (hold_data, ".data"))
     place = &hold_data;
   else if (strncmp (secname, ".rel", 4) == 0
-          && hold_rel.os != NULL)
+          && (hold_rel.os != NULL
+              || (hold_rel.os = output_rel_find ()) != NULL))
     place = &hold_rel;
   else if ((s->flags & SEC_CODE) == 0
           && (s->flags & SEC_READONLY) != 0
-          && hold_rodata.os != NULL)
+          && HAVE_SECTION (hold_rodata, ".rodata"))
     place = &hold_rodata;
   else if ((s->flags & SEC_READONLY) != 0
           && hold_text.os != NULL)
@@ -870,6 +873,8 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   else
     place = NULL;
 
+#undef HAVE_SECTION
+
   /* Choose a unique name for the section.  This will be needed if the
      same section name appears in the input file with different
      loadable or allocateable characteristics.  */
@@ -924,13 +929,12 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   else
     address = NULL;
 
-  lang_enter_output_section_statement (outsecname, address, 0,
-                                      (bfd_vma) 0,
-                                      (etree_type *) NULL,
-                                      (etree_type *) NULL,
-                                      (etree_type *) NULL);
+  os = lang_enter_output_section_statement (outsecname, address, 0,
+                                           (bfd_vma) 0,
+                                           (etree_type *) NULL,
+                                           (etree_type *) NULL,
+                                           (etree_type *) NULL);
 
-  os = lang_output_section_statement_lookup (outsecname);
   wild_doit (&os->children, s, os, file);
 
   lang_leave_output_section_statement
@@ -1004,38 +1008,26 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   return true;
 }
 
-static void
-gld${EMULATION_NAME}_place_section (s)
-     lang_statement_union_type *s;
+/* A variant of lang_output_section_find.  */
+static lang_output_section_statement_type *
+output_rel_find ()
 {
-  lang_output_section_statement_type *os;
-
-  if (s->header.type != lang_output_section_statement_enum)
-    return;
+  lang_statement_union_type *u;
+  lang_output_section_statement_type *lookup;
 
-  os = &s->output_section_statement;
-
-  if (strcmp (os->name, hold_section->name) == 0
-      && os->bfd_section != NULL
-      && ((hold_section->flags & (SEC_LOAD | SEC_ALLOC))
-         == (os->bfd_section->flags & (SEC_LOAD | SEC_ALLOC))))
-    hold_use = os;
-
-  if (strcmp (os->name, ".text") == 0)
-    hold_text.os = os;
-  else if (strcmp (os->name, ".rodata") == 0)
-    hold_rodata.os = os;
-  else if (strcmp (os->name, ".data") == 0)
-    hold_data.os = os;
-  else if (strcmp (os->name, ".bss") == 0)
-    hold_bss.os = os;
-  else if (hold_rel.os == NULL
-          && os->bfd_section != NULL
-          && (os->bfd_section->flags & SEC_ALLOC) != 0
-          && strncmp (os->name, ".rel", 4) == 0)
-    hold_rel.os = os;
-  else if (strcmp (os->name, ".interp") == 0)
-    hold_interp.os = os;
+  for (u = lang_output_section_statement.head;
+       u != (lang_statement_union_type *) NULL;
+       u = lookup->next)
+    {
+      lookup = &u->output_section_statement;
+      if (strncmp (".rel", lookup->name, 4) == 0
+         && lookup->bfd_section != NULL
+         && (lookup->bfd_section->flags & SEC_ALLOC) != 0)
+       {
+         return lookup;
+       }
+    }
+  return (lang_output_section_statement_type *) NULL;
 }
 
 /* Look through an expression for an assignment statement.  */
index d57aadb..9615285 100644 (file)
@@ -65,8 +65,7 @@ static void gld${EMULATION_NAME}_find_statement_assignment
 static void gld${EMULATION_NAME}_find_exp_assignment PARAMS ((etree_type *));
 static boolean gld${EMULATION_NAME}_place_orphan
   PARAMS ((lang_input_statement_type *, asection *));
-static void gld${EMULATION_NAME}_place_section
-  PARAMS ((lang_statement_union_type *));
+static lang_output_section_statement_type *output_rel_find PARAMS ((void));
 static char *gld${EMULATION_NAME}_get_script PARAMS ((int *isfile));
 
 static void
@@ -865,21 +864,12 @@ gld${EMULATION_NAME}_find_exp_assignment (exp)
 /* Place an orphan section.  We use this to put random SHF_ALLOC
    sections in the right segment.  */
 
-static asection *hold_section;
-static lang_output_section_statement_type *hold_use;
-
 struct orphan_save
 {
   lang_output_section_statement_type *os;
   asection **section;
   lang_statement_union_type **stmt;
 };
-static struct orphan_save hold_text;
-static struct orphan_save hold_rodata;
-static struct orphan_save hold_data;
-static struct orphan_save hold_bss;
-static struct orphan_save hold_rel;
-static struct orphan_save hold_interp;
 
 /*ARGSUSED*/
 static boolean
@@ -887,6 +877,12 @@ gld${EMULATION_NAME}_place_orphan (file, s)
      lang_input_statement_type *file;
      asection *s;
 {
+  static struct orphan_save hold_text;
+  static struct orphan_save hold_rodata;
+  static struct orphan_save hold_data;
+  static struct orphan_save hold_bss;
+  static struct orphan_save hold_rel;
+  static struct orphan_save hold_interp;
   struct orphan_save *place;
   lang_statement_list_type *old;
   lang_statement_list_type add;
@@ -895,19 +891,22 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   const char *outsecname;
   lang_output_section_statement_type *os;
 
+  secname = bfd_get_section_name (s->owner, s);
+
   /* Look through the script to see where to place this section.  */
-  hold_section = s;
-  hold_use = NULL;
-  lang_for_each_statement (gld${EMULATION_NAME}_place_section);
+  os = lang_output_section_find (secname);
 
-  if (hold_use != NULL)
+  if (os != NULL
+      && os->bfd_section != NULL
+      && ((s->flags ^ os->bfd_section->flags) & (SEC_LOAD | SEC_ALLOC)) == 0)
     {
       /* We have already placed a section with this name.  */
-      wild_doit (&hold_use->children, s, hold_use, file);
+      wild_doit (&os->children, s, os, file);
       return true;
     }
 
-  secname = bfd_get_section_name (s->owner, s);
+  if (hold_text.os == NULL)
+    hold_text.os = lang_output_section_find (".text");
 
   /* If this is a final link, then always put .gnu.warning.SYMBOL
      sections into the .text section to get them out of the way.  */
@@ -925,26 +924,30 @@ gld${EMULATION_NAME}_place_orphan (file, s)
      right after the .interp section, so that the PT_NOTE segment is
      stored right after the program headers where the OS can read it
      in the first page.  */
+#define HAVE_SECTION(hold, name) \
+(hold.os != NULL || (hold.os = lang_output_section_find (name)) != NULL)
+
   if (s->flags & SEC_EXCLUDE)
     return false;
   else if ((s->flags & SEC_ALLOC) == 0)
     place = NULL;
   else if ((s->flags & SEC_LOAD) != 0
           && strncmp (secname, ".note", 4) == 0
-          && hold_interp.os != NULL)
+          && HAVE_SECTION (hold_interp, ".interp"))
     place = &hold_interp;
   else if ((s->flags & SEC_HAS_CONTENTS) == 0
-          && hold_bss.os != NULL)
+          && HAVE_SECTION (hold_bss, ".bss"))
     place = &hold_bss;
   else if ((s->flags & SEC_READONLY) == 0
-          && hold_data.os != NULL)
+          && HAVE_SECTION (hold_data, ".data"))
     place = &hold_data;
   else if (strncmp (secname, ".rel", 4) == 0
-          && hold_rel.os != NULL)
+          && (hold_rel.os != NULL
+              || (hold_rel.os = output_rel_find ()) != NULL))
     place = &hold_rel;
   else if ((s->flags & SEC_CODE) == 0
           && (s->flags & SEC_READONLY) != 0
-          && hold_rodata.os != NULL)
+          && HAVE_SECTION (hold_rodata, ".rodata"))
     place = &hold_rodata;
   else if ((s->flags & SEC_READONLY) != 0
           && hold_text.os != NULL)
@@ -952,6 +955,8 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   else
     place = NULL;
 
+#undef HAVE_SECTION
+
   /* Choose a unique name for the section.  This will be needed if the
      same section name appears in the input file with different
      loadable or allocateable characteristics.  */
@@ -1006,13 +1011,12 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   else
     address = NULL;
 
-  lang_enter_output_section_statement (outsecname, address, 0,
-                                      (bfd_vma) 0,
-                                      (etree_type *) NULL,
-                                      (etree_type *) NULL,
-                                      (etree_type *) NULL);
+  os = lang_enter_output_section_statement (outsecname, address, 0,
+                                           (bfd_vma) 0,
+                                           (etree_type *) NULL,
+                                           (etree_type *) NULL,
+                                           (etree_type *) NULL);
 
-  os = lang_output_section_statement_lookup (outsecname);
   wild_doit (&os->children, s, os, file);
 
   lang_leave_output_section_statement
@@ -1086,38 +1090,26 @@ gld${EMULATION_NAME}_place_orphan (file, s)
   return true;
 }
 
-static void
-gld${EMULATION_NAME}_place_section (s)
-     lang_statement_union_type *s;
+/* A variant of lang_output_section_find.  */
+static lang_output_section_statement_type *
+output_rel_find ()
 {
-  lang_output_section_statement_type *os;
-
-  if (s->header.type != lang_output_section_statement_enum)
-    return;
+  lang_statement_union_type *u;
+  lang_output_section_statement_type *lookup;
 
-  os = &s->output_section_statement;
-
-  if (strcmp (os->name, hold_section->name) == 0
-      && os->bfd_section != NULL
-      && ((hold_section->flags & (SEC_LOAD | SEC_ALLOC))
-         == (os->bfd_section->flags & (SEC_LOAD | SEC_ALLOC))))
-    hold_use = os;
-
-  if (strcmp (os->name, ".text") == 0)
-    hold_text.os = os;
-  else if (strcmp (os->name, ".rodata") == 0)
-    hold_rodata.os = os;
-  else if (strcmp (os->name, ".data") == 0)
-    hold_data.os = os;
-  else if (strcmp (os->name, ".bss") == 0)
-    hold_bss.os = os;
-  else if (hold_rel.os == NULL
-          && os->bfd_section != NULL
-          && (os->bfd_section->flags & SEC_ALLOC) != 0
-          && strncmp (os->name, ".rel", 4) == 0)
-    hold_rel.os = os;
-  else if (strcmp (os->name, ".interp") == 0)
-    hold_interp.os = os;
+  for (u = lang_output_section_statement.head;
+       u != (lang_statement_union_type *) NULL;
+       u = lookup->next)
+    {
+      lookup = &u->output_section_statement;
+      if (strncmp (".rel", lookup->name, 4) == 0
+         && lookup->bfd_section != NULL
+         && (lookup->bfd_section->flags & SEC_ALLOC) != 0)
+       {
+         return lookup;
+       }
+    }
+  return (lang_output_section_statement_type *) NULL;
 }
 
 static char *
index aeecb61..06ae868 100644 (file)
@@ -102,8 +102,6 @@ static void gld_${EMULATION_NAME}_after_parse PARAMS ((void));
 static void gld_${EMULATION_NAME}_before_allocation PARAMS ((void));
 static boolean gld_${EMULATION_NAME}_place_orphan
   PARAMS ((lang_input_statement_type *, asection *));
-static void gld${EMULATION_NAME}_place_section
-  PARAMS ((lang_statement_union_type *));
 static char *gld_${EMULATION_NAME}_get_script PARAMS ((int *));
 static int gld_${EMULATION_NAME}_parse_args PARAMS ((int, char **));
 static void gld_${EMULATION_NAME}_finish PARAMS ((void));
@@ -1074,23 +1072,12 @@ gld_${EMULATION_NAME}_finish ()
    default linker script using wildcards, and are sorted by
    sort_sections.  */
 
-static asection *hold_section;
-static char *hold_section_name;
-static lang_output_section_statement_type *hold_use;
-
 struct orphan_save
 {
   lang_output_section_statement_type *os;
   asection **section;
   lang_statement_union_type **stmt;
 };
-static struct orphan_save hold_text;
-static struct orphan_save hold_rdata;
-static struct orphan_save hold_data;
-static struct orphan_save hold_bss;
-
-/* Place an orphan section.  We use this to put random SHF_ALLOC
-   sections in the right segment.  */
 
 /*ARGSUSED*/
 static boolean
@@ -1099,15 +1086,15 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
      asection *s;
 {
   const char *secname;
+  char *hold_section_name;
   char *dollar = NULL;
+  lang_output_section_statement_type *os;
   lang_statement_list_type add_child;
 
   secname = bfd_get_section_name (s->owner, s);
 
   /* Look through the script to see where to place this section.  */
 
-  hold_section = s;
-
   hold_section_name = xstrdup (secname);
   if (!link_info.relocateable)
     {
@@ -1116,18 +1103,23 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
        *dollar = '\0';
     }
 
-  hold_use = NULL;
-  lang_for_each_statement (gld${EMULATION_NAME}_place_section);
+  os = lang_output_section_find (hold_section_name);
 
   lang_list_init (&add_child);
 
-  if (hold_use != NULL)
+  if (os != NULL
+      && os->bfd_section != NULL
+      && ((s->flags ^ os->bfd_section->flags) & (SEC_LOAD | SEC_ALLOC)) == 0)
     {
-      wild_doit (&add_child, s, hold_use, file);
+      wild_doit (&add_child, s, os, file);
     }
   else
     {
       struct orphan_save *place;
+      static struct orphan_save hold_text;
+      static struct orphan_save hold_rdata;
+      static struct orphan_save hold_data;
+      static struct orphan_save hold_bss;
       char *outsecname;
       lang_statement_list_type *old;
       lang_statement_list_type add;
@@ -1135,23 +1127,28 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
 
       /* Try to put the new output section in a reasonable place based
         on the section name and section flags.  */
+#define HAVE_SECTION(hold, name) \
+(hold.os != NULL || (hold.os = lang_output_section_find (name)) != NULL)
+
       place = NULL;
       if ((s->flags & SEC_ALLOC) == 0)
        ;
       else if ((s->flags & SEC_HAS_CONTENTS) == 0
-              && hold_bss.os != NULL)
+              && HAVE_SECTION (hold_bss, ".bss"))
        place = &hold_bss;
       else if ((s->flags & SEC_READONLY) == 0
-              && hold_data.os != NULL)
+              && HAVE_SECTION (hold_data, ".data"))
        place = &hold_data;
       else if ((s->flags & SEC_CODE) == 0
               && (s->flags & SEC_READONLY) != 0
-              && hold_rdata.os != NULL)
+              && HAVE_SECTION (hold_rdata, ".rdata"))
        place = &hold_rdata;
       else if ((s->flags & SEC_READONLY) != 0
-              && hold_text.os != NULL)
+              && HAVE_SECTION (hold_text, ".text"))
        place = &hold_text;
 
+#undef HAVE_SECTION
+
       /* Choose a unique name for the section.  This will be needed if
         the same section name appears in the input file with
         different loadable or allocateable characteristics.  */
@@ -1192,19 +1189,17 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
                              exp_nameop (NAME, "__section_alignment__"));
        }
 
-      lang_enter_output_section_statement (outsecname, address, 0,
-                                          (bfd_vma) 0,
-                                          (etree_type *) NULL,
-                                          (etree_type *) NULL,
-                                          (etree_type *) NULL);
+      os = lang_enter_output_section_statement (outsecname, address, 0,
+                                               (bfd_vma) 0,
+                                               (etree_type *) NULL,
+                                               (etree_type *) NULL,
+                                               (etree_type *) NULL);
 
-      hold_use = lang_output_section_statement_lookup (outsecname);
-      wild_doit (&add_child, s, hold_use, file);
+      wild_doit (&add_child, s, os, file);
 
       lang_leave_output_section_statement
        ((bfd_vma) 0, "*default*",
-        (struct lang_output_section_phdr_list *) NULL,
-       "*default*");
+        (struct lang_output_section_phdr_list *) NULL, "*default*");
 
       stat_ptr = old;
 
@@ -1212,7 +1207,7 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
        {
          asection *snew, **pps;
 
-         snew = hold_use->bfd_section;
+         snew = os->bfd_section;
          if (place->os->bfd_section != NULL || place->section != NULL)
            {
              /* Shuffle the section to make the output file look neater.  */
@@ -1261,7 +1256,7 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
     }
 
   {
-    lang_statement_union_type **pl = &hold_use->children.head;
+    lang_statement_union_type **pl = &os->children.head;
 
     if (dollar != NULL)
       {
@@ -1308,33 +1303,6 @@ gld_${EMULATION_NAME}_place_orphan (file, s)
   return true;
 }
 
-static void
-gld${EMULATION_NAME}_place_section (s)
-     lang_statement_union_type *s;
-{
-  lang_output_section_statement_type *os;
-
-  if (s->header.type != lang_output_section_statement_enum)
-    return;
-
-  os = &s->output_section_statement;
-
-  if (strcmp (os->name, hold_section_name) == 0
-      && os->bfd_section != NULL
-      && ((hold_section->flags & (SEC_LOAD | SEC_ALLOC))
-         == (os->bfd_section->flags & (SEC_LOAD | SEC_ALLOC))))
-    hold_use = os;
-
-  if (strcmp (os->name, ".text") == 0)
-    hold_text.os = os;
-  else if (strcmp (os->name, ".rdata") == 0)
-    hold_rdata.os = os;
-  else if (strcmp (os->name, ".data") == 0)
-    hold_data.os = os;
-  else if (strcmp (os->name, ".bss") == 0)
-    hold_bss.os = os;
-}
-
 static int
 gld_${EMULATION_NAME}_find_potential_libraries (name, entry)
      char * name;
index d40ff07..8f0c607 100644 (file)
@@ -58,7 +58,6 @@ static lang_output_section_statement_type *default_common_section;
 static boolean map_option_f;
 static bfd_vma print_dot;
 static lang_input_statement_type *first_file;
-static lang_statement_list_type lang_output_section_statement;
 static CONST char *current_target;
 static CONST char *output_target;
 static lang_statement_list_type statement_list;
@@ -166,6 +165,7 @@ static char * get_first_input_target PARAMS ((void));
                                        
 /* EXPORTS */
 lang_output_section_statement_type *abs_output_section;
+lang_statement_list_type lang_output_section_statement;
 lang_statement_list_type *stat_ptr = &statement_list;
 lang_statement_list_type file_chain = { NULL, NULL };
 const char *entry_symbol = NULL;
@@ -3813,7 +3813,7 @@ topower (x)
   return 0;
 }
 
-void
+lang_output_section_statement_type *
 lang_enter_output_section_statement (output_section_statement_name,
                                     address_exp, sectype, block_value,
                                     align, subalign, ebase)
@@ -3861,6 +3861,7 @@ lang_enter_output_section_statement (output_section_statement_name,
                     "section alignment", 0));
 
   os->load_base = ebase;
+  return os;
 }
 
 
index 068cd96..553db4b 100644 (file)
@@ -371,6 +371,7 @@ struct lang_nocrossrefs
 extern struct lang_nocrossrefs *nocrossref_list;
 
 extern lang_output_section_statement_type *abs_output_section;
+extern lang_statement_list_type lang_output_section_statement;
 extern boolean lang_has_input_file;
 extern etree_type *base;
 extern lang_statement_list_type *stat_ptr;
@@ -388,7 +389,7 @@ extern void lang_map PARAMS ((void));
 extern void lang_set_flags PARAMS ((lang_memory_region_type *, const char *,
                                    int));
 extern void lang_add_output PARAMS ((const char *, int from_script));
-extern void lang_enter_output_section_statement
+extern lang_output_section_statement_type *lang_enter_output_section_statement
   PARAMS ((const char *output_section_statement_name,
           etree_type * address_exp,
           enum section_type sectype,