New gold linker option -z,text-unlikely-segment.
2017-10-04 Sriraman Tallam <tmsriram@google.com> * options.h (-z,text_unlikely_segment): New option. * layout.cc (Layout::layout): Create new output section for .text.unlikely sections with the new option. (Layout::segment_precedes): Check for the new option when segment flags match. * testsuite/text_unlikely_segment.cc: New test source. * testsuite/text_unlikely_segment.sh: New test script. * testsuite/Makefile.am (text_unlikely_segment): New test. * testsuite/Makefile.in: Regenerate.
This commit is contained in:
parent
f3012016f0
commit
3b4190ccb3
7 changed files with 178 additions and 25 deletions
|
@ -1,3 +1,15 @@
|
|||
2017-10-04 Sriraman Tallam <tmsriram@google.com>
|
||||
|
||||
* options.h (-z,text_unlikely_segment): New option.
|
||||
* layout.cc (Layout::layout): Create new output section
|
||||
for .text.unlikely sections with the new option.
|
||||
(Layout::segment_precedes): Check for the new option
|
||||
when segment flags match.
|
||||
* testsuite/text_unlikely_segment.cc: New test source.
|
||||
* testsuite/text_unlikely_segment.sh: New test script.
|
||||
* testsuite/Makefile.am (text_unlikely_segment): New test.
|
||||
* testsuite/Makefile.in: Regenerate.
|
||||
|
||||
2017-10-19 Umesh Kalappa <ukalappa@cisco.com>
|
||||
|
||||
* arm.cc (Stub::do_fixed_endian_write):Far call stubs support for arm
|
||||
|
|
|
@ -1178,38 +1178,62 @@ Layout::layout(Sized_relobj_file<size, big_endian>* object, unsigned int shndx,
|
|||
}
|
||||
else
|
||||
{
|
||||
// Plugins can choose to place one or more subsets of sections in
|
||||
// unique segments and this is done by mapping these section subsets
|
||||
// to unique output sections. Check if this section needs to be
|
||||
// remapped to a unique output section.
|
||||
Section_segment_map::iterator it
|
||||
= this->section_segment_map_.find(Const_section_id(object, shndx));
|
||||
if (it == this->section_segment_map_.end())
|
||||
{
|
||||
os = this->choose_output_section(object, name, sh_type,
|
||||
shdr.get_sh_flags(), true,
|
||||
ORDER_INVALID, false, false,
|
||||
true);
|
||||
}
|
||||
else
|
||||
{
|
||||
// We know the name of the output section, directly call
|
||||
// get_output_section here by-passing choose_output_section.
|
||||
// All ".text.unlikely.*" sections can be moved to a unique
|
||||
// segment with --text-unlikely-segment option.
|
||||
bool text_unlikely_segment
|
||||
= (parameters->options().text_unlikely_segment()
|
||||
&& is_prefix_of(".text.unlikely",
|
||||
object->section_name(shndx).c_str()));
|
||||
if (text_unlikely_segment)
|
||||
{
|
||||
elfcpp::Elf_Xword flags
|
||||
= this->get_output_section_flags(shdr.get_sh_flags());
|
||||
|
||||
const char* os_name = it->second->name;
|
||||
Stringpool::Key name_key;
|
||||
os_name = this->namepool_.add(os_name, true, &name_key);
|
||||
const char* os_name = this->namepool_.add(".text.unlikely", true,
|
||||
&name_key);
|
||||
os = this->get_output_section(os_name, name_key, sh_type, flags,
|
||||
ORDER_INVALID, false);
|
||||
if (!os->is_unique_segment())
|
||||
// Map this output section to a unique segment. This is done to
|
||||
// separate "text" that is not likely to be executed from "text"
|
||||
// that is likely executed.
|
||||
os->set_is_unique_segment();
|
||||
}
|
||||
else
|
||||
{
|
||||
// Plugins can choose to place one or more subsets of sections in
|
||||
// unique segments and this is done by mapping these section subsets
|
||||
// to unique output sections. Check if this section needs to be
|
||||
// remapped to a unique output section.
|
||||
Section_segment_map::iterator it
|
||||
= this->section_segment_map_.find(Const_section_id(object, shndx));
|
||||
if (it == this->section_segment_map_.end())
|
||||
{
|
||||
os->set_is_unique_segment();
|
||||
os->set_extra_segment_flags(it->second->flags);
|
||||
os->set_segment_alignment(it->second->align);
|
||||
os = this->choose_output_section(object, name, sh_type,
|
||||
shdr.get_sh_flags(), true,
|
||||
ORDER_INVALID, false, false,
|
||||
true);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// We know the name of the output section, directly call
|
||||
// get_output_section here by-passing choose_output_section.
|
||||
elfcpp::Elf_Xword flags
|
||||
= this->get_output_section_flags(shdr.get_sh_flags());
|
||||
|
||||
const char* os_name = it->second->name;
|
||||
Stringpool::Key name_key;
|
||||
os_name = this->namepool_.add(os_name, true, &name_key);
|
||||
os = this->get_output_section(os_name, name_key, sh_type, flags,
|
||||
ORDER_INVALID, false);
|
||||
if (!os->is_unique_segment())
|
||||
{
|
||||
os->set_is_unique_segment();
|
||||
os->set_extra_segment_flags(it->second->flags);
|
||||
os->set_segment_alignment(it->second->align);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (os == NULL)
|
||||
return NULL;
|
||||
}
|
||||
|
@ -3449,7 +3473,8 @@ Layout::segment_precedes(const Output_segment* seg1,
|
|||
// here if plugins want unique segments for subsets of sections.
|
||||
gold_assert(this->script_options_->saw_phdrs_clause()
|
||||
|| parameters->options().any_section_start()
|
||||
|| this->is_unique_segment_for_sections_specified());
|
||||
|| this->is_unique_segment_for_sections_specified()
|
||||
|| parameters->options().text_unlikely_segment());
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
|
@ -1492,6 +1492,11 @@ class General_options
|
|||
DEFINE_bool_alias(textoff, text, options::DASH_Z, '\0',
|
||||
N_("Permit relocations in read-only segments"),
|
||||
NULL, true);
|
||||
DEFINE_bool(text_unlikely_segment, options::DASH_Z, '\0', false,
|
||||
N_("Move .text.unlikely sections to a separate segment."),
|
||||
N_("Do not move .text.unlikely sections to a separate "
|
||||
"segment."));
|
||||
|
||||
|
||||
public:
|
||||
typedef options::Dir_list Dir_list;
|
||||
|
|
|
@ -340,6 +340,16 @@ section_sorting_name: section_sorting_name.o gcctestdir/ld
|
|||
section_sorting_name.stdout: section_sorting_name
|
||||
$(TEST_NM) -n --synthetic section_sorting_name > section_sorting_name.stdout
|
||||
|
||||
check_SCRIPTS += text_unlikely_segment.sh
|
||||
check_DATA += text_unlikely_segment_readelf.stdout
|
||||
MOSTLYCLEANFILES += text_unlikely_segment
|
||||
text_unlikely_segment.o: text_unlikely_segment.cc
|
||||
$(CXXCOMPILE) -O0 -c -ffunction-sections -g -o $@ $<
|
||||
text_unlikely_segment: text_unlikely_segment.o gcctestdir/ld
|
||||
$(CXXLINK) -Bgcctestdir/ -Wl,-z,text-unlikely-segment text_unlikely_segment.o
|
||||
text_unlikely_segment_readelf.stdout: text_unlikely_segment
|
||||
$(TEST_READELF) -Wl $< >$@
|
||||
|
||||
check_PROGRAMS += icf_virtual_function_folding_test
|
||||
MOSTLYCLEANFILES += icf_virtual_function_folding_test icf_virtual_function_folding_test.map
|
||||
icf_virtual_function_folding_test.o: icf_virtual_function_folding_test.cc
|
||||
|
|
|
@ -87,6 +87,7 @@ check_PROGRAMS = $(am__EXEEXT_1) $(am__EXEEXT_2) $(am__EXEEXT_3) \
|
|||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ final_layout.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_section_grouping.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ section_sorting_name.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_unlikely_segment.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_preemptible_functions_test.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_string_merge_test.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_sht_rel_addend_test.sh \
|
||||
|
@ -114,6 +115,7 @@ check_PROGRAMS = $(am__EXEEXT_1) $(am__EXEEXT_2) $(am__EXEEXT_3) \
|
|||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_section_grouping.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_section_no_grouping.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ section_sorting_name.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_unlikely_segment_readelf.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_preemptible_functions_test.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_string_merge_test.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_sht_rel_addend_test.stdout \
|
||||
|
@ -139,6 +141,7 @@ check_PROGRAMS = $(am__EXEEXT_1) $(am__EXEEXT_2) $(am__EXEEXT_3) \
|
|||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_section_grouping \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_section_no_grouping \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ section_sorting_name \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ text_unlikely_segment \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_virtual_function_folding_test \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_virtual_function_folding_test.map \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ icf_preemptible_functions_test \
|
||||
|
@ -5148,6 +5151,8 @@ text_section_grouping.sh.log: text_section_grouping.sh
|
|||
@p='text_section_grouping.sh'; $(am__check_pre) $(LOG_COMPILE) "$$tst" $(am__check_post)
|
||||
section_sorting_name.sh.log: section_sorting_name.sh
|
||||
@p='section_sorting_name.sh'; $(am__check_pre) $(LOG_COMPILE) "$$tst" $(am__check_post)
|
||||
text_unlikely_segment.sh.log: text_unlikely_segment.sh
|
||||
@p='text_unlikely_segment.sh'; $(am__check_pre) $(LOG_COMPILE) "$$tst" $(am__check_post)
|
||||
icf_preemptible_functions_test.sh.log: icf_preemptible_functions_test.sh
|
||||
@p='icf_preemptible_functions_test.sh'; $(am__check_pre) $(LOG_COMPILE) "$$tst" $(am__check_post)
|
||||
icf_string_merge_test.sh.log: icf_string_merge_test.sh
|
||||
|
@ -6015,6 +6020,12 @@ uninstall-am:
|
|||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(CXXLINK) -Bgcctestdir/ -Wl,--sort-section=name section_sorting_name.o
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@section_sorting_name.stdout: section_sorting_name
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(TEST_NM) -n --synthetic section_sorting_name > section_sorting_name.stdout
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@text_unlikely_segment.o: text_unlikely_segment.cc
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(CXXCOMPILE) -O0 -c -ffunction-sections -g -o $@ $<
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@text_unlikely_segment: text_unlikely_segment.o gcctestdir/ld
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(CXXLINK) -Bgcctestdir/ -Wl,-z,text-unlikely-segment text_unlikely_segment.o
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@text_unlikely_segment_readelf.stdout: text_unlikely_segment
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(TEST_READELF) -Wl $< >$@
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@icf_virtual_function_folding_test.o: icf_virtual_function_folding_test.cc
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ $(CXXCOMPILE) -O0 -c -ffunction-sections -fPIE -g -o $@ $<
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@icf_virtual_function_folding_test: icf_virtual_function_folding_test.o gcctestdir/ld
|
||||
|
|
30
gold/testsuite/text_unlikely_segment.cc
Normal file
30
gold/testsuite/text_unlikely_segment.cc
Normal file
|
@ -0,0 +1,30 @@
|
|||
/* text_unlikey_segment.cc -- a test case for gold
|
||||
|
||||
Copyright (C) 2017 onwards Free Software Foundation, Inc.
|
||||
Written by Sriraman Tallam <tmsriram@google.com>
|
||||
|
||||
This file is part of gold.
|
||||
|
||||
This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
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., 51 Franklin Street - Fifth Floor, Boston,
|
||||
MA 02110-1301, USA. */
|
||||
|
||||
__attribute__((section(".text.unlikely")))
|
||||
int foo(void) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main(void) {
|
||||
return 0;
|
||||
}
|
60
gold/testsuite/text_unlikely_segment.sh
Executable file
60
gold/testsuite/text_unlikely_segment.sh
Executable file
|
@ -0,0 +1,60 @@
|
|||
#!/bin/sh
|
||||
|
||||
# plugin_final_layout.sh -- test
|
||||
|
||||
# Copyright (C) 2011-2017 Free Software Foundation, Inc.
|
||||
# Written by Sriraman Tallam <tmsriram@google.com>.
|
||||
|
||||
# This file is part of gold.
|
||||
|
||||
# This program is free software; you can redistribute it and/or modify
|
||||
# it under the terms of the GNU General Public License as published by
|
||||
# the Free Software Foundation; either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# 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., 51 Franklin Street - Fifth Floor, Boston,
|
||||
# MA 02110-1301, USA.
|
||||
|
||||
# The goal of this program is to verify if -z,text-unlikely-segment works as
|
||||
# intended. File text_unlikely_segment.cc is part of this test.
|
||||
|
||||
|
||||
set -e
|
||||
|
||||
# With readelf -l, an ELF Section to Segment mapping is printed as :
|
||||
##############################################
|
||||
# Section to Segment mapping:
|
||||
# Segment Sections...
|
||||
# ...
|
||||
# 0x .text.unlikely
|
||||
# ...
|
||||
##############################################
|
||||
# Check if .text.unlikely is the only section in the segment.
|
||||
check_unique_segment()
|
||||
{
|
||||
awk "
|
||||
BEGIN { saw_section = 0; saw_unique = 0; }
|
||||
/$2/ { saw_section = 1; }
|
||||
/[ ]*0[0-9][ ]*$2[ ]*\$/ { saw_unique = 1; }
|
||||
END {
|
||||
if (!saw_section)
|
||||
{
|
||||
printf \"Section $2 not seen in output\\n\";
|
||||
exit 1;
|
||||
}
|
||||
else if (!saw_unique)
|
||||
{
|
||||
printf \"Unique segment not seen for: $2\\n\";
|
||||
exit 1;
|
||||
}
|
||||
}" $1
|
||||
}
|
||||
|
||||
check_unique_segment text_unlikely_segment_readelf.stdout ".text.unlikely"
|
Loading…
Add table
Reference in a new issue