summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAlexander Ivchenko <alexander.ivchenko@intel.com>2013-01-25 14:35:38 +0400
committerAlexander Ivchenko <alexander.ivchenko@intel.com>2013-01-25 15:38:32 +0400
commit43cc3f59831134ed0b2447bb21767371417ac54a (patch)
treec10353fa1c13ac509d4d2269f8d15ac71d78eee4
parent8415ff0aaeb157307bb01a45373dba81919882fc (diff)
downloadtoolchain_binutils-43cc3f59831134ed0b2447bb21767371417ac54a.zip
toolchain_binutils-43cc3f59831134ed0b2447bb21767371417ac54a.tar.gz
toolchain_binutils-43cc3f59831134ed0b2447bb21767371417ac54a.tar.bz2
[2.22.90] Backport of two patches from mainline that enable
sorting of text sections Author: Sriraman Tallam <tmsriram@google.com> Date: Thu Jan 10 00:18:14 2013 +0000 Make linker scripts and section ordering via --section-ordering-file or linker plugins work. This patch lets linker scripts take precedence. 2013-01-09 Sriraman Tallam <tmsriram@google.com> * output.h (sort_attached_input_sections): Change to be public. * script-sections.cc (Output_section_definition::set_section_addresses): Sort attached input sections according to section order before linker script assigns section addresses. (Orphan_output_section::set_section_addresses): Sort attached input sections according to section order before linker script assigns section addresses. * Makefile.am (final_layout.sh): Use a simple linker script to check if section ordering still works. * Makefile.in: Regenerate. Author: Ian Lance Taylor <ian@airs.com> Date: Fri Dec 21 06:24:31 2012 +0000 * layout.cc (Layout::special_ordering_of_input_section): New function. (Layout::layout): If input section requires special ordering, must sort input sections. (Layout::make_output_section): May sort .text input sections. (Layout::is_section_name_prefix_grouped): Remove. * layout.h (class Layout): Declare special_ordering_of_input_section. Don't declare is_section_name_prefix_grouped. * output.cc (Output_section::add_input_section): Revert last change. (Output_section::Input_section_sort::match_file_name): Don't crash if called on output section data. (Output_section::Input_section_sort_compare): Sort based on special ordering. (Output_section::Input_section_sort_section_order_index_compare): Revert last patch. (Output_section::sort_attached_input_sections): Likewise. Change-Id: I385c609300f697abcdeb82324c9af903259fe2b6
-rw-r--r--binutils-2.22/gold/layout.cc43
-rw-r--r--binutils-2.22/gold/layout.h8
-rw-r--r--binutils-2.22/gold/output.cc19
3 files changed, 69 insertions, 1 deletions
diff --git a/binutils-2.22/gold/layout.cc b/binutils-2.22/gold/layout.cc
index ad667ab..cc800cd 100644
--- a/binutils-2.22/gold/layout.cc
+++ b/binutils-2.22/gold/layout.cc
@@ -993,6 +993,33 @@ Layout::init_fixed_output_section(const char* name,
return os;
}
+// Return the index by which an input section should be ordered. This
+// is used to sort some .text sections, for compatibility with GNU ld.
+
+int
+Layout::special_ordering_of_input_section(const char* name)
+{
+ // The GNU linker has some special handling for some sections that
+ // wind up in the .text section. Sections that start with these
+ // prefixes must appear first, and must appear in the order listed
+ // here.
+ static const char* const text_section_sort[] =
+ {
+ ".text.unlikely",
+ ".text.exit",
+ ".text.startup",
+ ".text.hot"
+ };
+
+ for (size_t i = 0;
+ i < sizeof(text_section_sort) / sizeof(text_section_sort[0]);
+ i++)
+ if (is_prefix_of(text_section_sort[i], name))
+ return i;
+
+ return -1;
+}
+
// Return the output section to use for input section SHNDX, with name
// NAME, with header HEADER, from object OBJECT. RELOC_SHNDX is the
// index of a relocation section which applies to this section, or 0
@@ -1052,6 +1079,13 @@ Layout::layout(Sized_relobj_file<size, big_endian>* object, unsigned int shndx,
|| strcmp(name, ".dtors") == 0))))
os->set_must_sort_attached_input_sections();
+ // By default the GNU linker sorts some special text sections ahead
+ // of others. We are compatible.
+ if (!this->script_options_->saw_sections_clause()
+ && !parameters->options().relocatable()
+ && Layout::special_ordering_of_input_section(name) >= 0)
+ os->set_must_sort_attached_input_sections();
+
// If this is a .ctors or .ctors.* section being mapped to a
// .init_array section, or a .dtors or .dtors.* section being mapped
// to a .fini_array section, we will need to reverse the words if
@@ -1530,6 +1564,15 @@ Layout::make_output_section(const char* name, elfcpp::Elf_Word type,
|| strcmp(name, ".dtors") == 0))))
os->set_may_sort_attached_input_sections();
+ // The GNU linker by default sorts .text.{unlikely,exit,startup,hot}
+ // sections before other .text sections. We are compatible. We
+ // need to know that this might happen before we attach any input
+ // sections.
+ if (!this->script_options_->saw_sections_clause()
+ && !parameters->options().relocatable()
+ && strcmp(name, ".text") == 0)
+ os->set_may_sort_attached_input_sections();
+
// Check for .stab*str sections, as .stab* sections need to link to
// them.
if (type == elfcpp::SHT_STRTAB
diff --git a/binutils-2.22/gold/layout.h b/binutils-2.22/gold/layout.h
index 4643e32..fc8675f 100644
--- a/binutils-2.22/gold/layout.h
+++ b/binutils-2.22/gold/layout.h
@@ -528,6 +528,14 @@ class Layout
get_section_order_map()
{ return &this->section_order_map_; }
+ // Some input sections require special ordering, for compatibility
+ // with GNU ld. Given the name of an input section, return -1 if it
+ // does not require special ordering. Otherwise, return the index
+ // by which it should be ordered compared to other input sections
+ // that require special ordering.
+ static int
+ special_ordering_of_input_section(const char* name);
+
bool
is_section_ordering_specified()
{ return this->section_ordering_specified_; }
diff --git a/binutils-2.22/gold/output.cc b/binutils-2.22/gold/output.cc
index aceee1b..82e2ea7 100644
--- a/binutils-2.22/gold/output.cc
+++ b/binutils-2.22/gold/output.cc
@@ -3259,7 +3259,11 @@ class Output_section::Input_section_sort_entry
// in order to better support gcc, and we need to be compatible.
bool
match_file_name(const char* file_name) const
- { return Layout::match_file_name(this->input_section_.relobj(), file_name); }
+ {
+ if (this->input_section_.is_output_section_data())
+ return false;
+ return Layout::match_file_name(this->input_section_.relobj(), file_name);
+ }
// Returns 1 if THIS should appear before S in section order, -1 if S
// appears before THIS and 0 if they are not comparable.
@@ -3331,6 +3335,19 @@ Output_section::Input_section_sort_compare::operator()(
return s1.index() < s2.index();
}
+ // Some input section names have special ordering requirements.
+ int o1 = Layout::special_ordering_of_input_section(s1.section_name().c_str());
+ int o2 = Layout::special_ordering_of_input_section(s2.section_name().c_str());
+ if (o1 != o2)
+ {
+ if (o1 < 0)
+ return false;
+ else if (o2 < 0)
+ return true;
+ else
+ return o1 < o2;
+ }
+
// A section with a priority follows a section without a priority.
bool s1_has_priority = s1.has_priority();
bool s2_has_priority = s2.has_priority();