This is the mail archive of the
binutils@sourceware.cygnus.com
mailing list for the binutils project.
Re: How to stop --gc-sections nukeing all sections?
- To: Ian Lance Taylor <ian at zembu dot com>
- Subject: Re: How to stop --gc-sections nukeing all sections?
- From: Alan Modra <alan at linuxcare dot com dot au>
- Date: Sat, 8 Apr 2000 21:12:40 +1000 (EST)
- cc: greyham at research dot canon dot com dot au, binutils at sourceware dot cygnus dot com
Here's a working patch that keeps orphan sections in the order they appear
in the input (modulo text,data,bss etc. ordering given by the ld script).
OK to install? If so, I'll make equivalent changes to the other .em
files.
--
Linuxcare. Support for the Revolution.
ld/ChangeLog
* emultempl/elf32.em (struct orphan_save): New.
(hold_text, hold_rodata, hold_data, hold_bss, hold_rel,
hold_interp): Make them struct orphan_save.
(gld${EMULATION_NAME}_place_section): Modify for new hold_*.
(gld${EMULATION_NAME}_place_orphan): Add new orphan sections to
the end of the relevant section list. Also add associated section
statements to the end of any previous orphan statements.
Index: emultempl/elf32.em
===================================================================
RCS file: /cvs/src/src/ld/emultempl/elf32.em,v
retrieving revision 1.12
diff -u -p -r1.12 elf32.em
--- elf32.em 2000/02/29 05:53:53 1.12
+++ elf32.em 2000/04/08 11:06:07
@@ -867,20 +867,26 @@ gld${EMULATION_NAME}_find_exp_assignment
static asection *hold_section;
static lang_output_section_statement_type *hold_use;
-static lang_output_section_statement_type *hold_text;
-static lang_output_section_statement_type *hold_rodata;
-static lang_output_section_statement_type *hold_data;
-static lang_output_section_statement_type *hold_bss;
-static lang_output_section_statement_type *hold_rel;
-static lang_output_section_statement_type *hold_interp;
+struct orphan_save
+{
+ lang_output_section_statement_type *os;
+ 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
gld${EMULATION_NAME}_place_orphan (file, s)
lang_input_statement_type *file;
asection *s;
{
- lang_output_section_statement_type *place;
+ struct orphan_save *place;
asection *snew, **pps;
lang_statement_list_type *old;
lang_statement_list_type add;
@@ -911,9 +917,9 @@ gld${EMULATION_NAME}_place_orphan (file,
if (! link_info.shared
&& ! link_info.relocateable
&& strncmp (secname, ".gnu.warning.", sizeof ".gnu.warning." - 1) == 0
- && hold_text != NULL)
+ && hold_text.os != NULL)
{
- wild_doit (&hold_text->children, s, hold_text, file);
+ wild_doit (&hold_text.os->children, s, hold_text.os, file);
return true;
}
@@ -922,30 +928,29 @@ gld${EMULATION_NAME}_place_orphan (file,
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. */
- place = NULL;
if (s->flags & SEC_EXCLUDE)
return false;
else if ((s->flags & SEC_LOAD) != 0
- && strncmp (secname, ".note", 4) == 0
- && hold_interp != NULL)
- place = hold_interp;
+ && strncmp (secname, ".note", 4) == 0
+ && hold_interp.os != NULL)
+ place = &hold_interp;
else if ((s->flags & SEC_HAS_CONTENTS) == 0
- && hold_bss != NULL)
- place = hold_bss;
+ && hold_bss.os != NULL)
+ place = &hold_bss;
else if ((s->flags & SEC_READONLY) == 0
- && hold_data != NULL)
- place = hold_data;
+ && hold_data.os != NULL)
+ place = &hold_data;
else if (strncmp (secname, ".rel", 4) == 0
- && hold_rel != NULL)
- place = hold_rel;
+ && hold_rel.os != NULL)
+ place = &hold_rel;
else if ((s->flags & SEC_CODE) == 0
&& (s->flags & SEC_READONLY) != 0
- && hold_rodata != NULL)
- place = hold_rodata;
+ && hold_rodata.os != NULL)
+ place = &hold_rodata;
else if ((s->flags & SEC_READONLY) != 0
- && hold_text != NULL)
- place = hold_text;
- if (place == NULL)
+ && hold_text.os != NULL)
+ place = &hold_text;
+ else
return false;
/* Choose a unique name for the section. This will be needed if the
@@ -978,13 +983,17 @@ gld${EMULATION_NAME}_place_orphan (file,
if (snew == NULL)
einfo ("%P%F: output format %s cannot represent section called %s\n",
output_bfd->xvec->name, outsecname);
- if (place->bfd_section != NULL)
+ if (place->os->bfd_section != NULL)
{
+ /* Unlink it first. */
for (pps = &output_bfd->sections; *pps != snew; pps = &(*pps)->next)
;
*pps = snew->next;
- snew->next = place->bfd_section->next;
- place->bfd_section->next = snew;
+ snew->next = NULL;
+ /* Now tack it on to the end of the "place->os" section list. */
+ for (pps = &place->os->bfd_section; *pps; pps = &(*pps)->next)
+ ;
+ *pps = snew;
}
/* Start building a list of statements for this section. */
@@ -1038,9 +1047,19 @@ gld${EMULATION_NAME}_place_orphan (file,
exp_nameop (NAME, ".")));
}
- /* Now stick the new statement list right after PLACE. */
- *add.tail = place->header.next;
- place->header.next = add.head;
+ if (! place->stmt)
+ {
+ /* Put the new statement list right at the head. */
+ *add.tail = place->os->header.next;
+ place->os->header.next = add.head;
+ }
+ else
+ {
+ /* Put it after the last orphan statement we added. */
+ *add.tail = *place->stmt;
+ *place->stmt = add.head;
+ }
+ place->stmt = add.tail; /* Save the end of this list. */
stat_ptr = old;
@@ -1065,20 +1084,20 @@ gld${EMULATION_NAME}_place_section (s)
hold_use = os;
if (strcmp (os->name, ".text") == 0)
- hold_text = os;
+ hold_text.os = os;
else if (strcmp (os->name, ".rodata") == 0)
- hold_rodata = os;
+ hold_rodata.os = os;
else if (strcmp (os->name, ".data") == 0)
- hold_data = os;
+ hold_data.os = os;
else if (strcmp (os->name, ".bss") == 0)
- hold_bss = os;
- else if (hold_rel == NULL
+ 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;
+ hold_rel.os = os;
else if (strcmp (os->name, ".interp") == 0)
- hold_interp = os;
+ hold_interp.os = os;
}
static char *