mirror of
https://github.com/darlinghq/darling-gdb.git
synced 2024-11-30 23:40:24 +00:00
* layout.cc (Layout::layout): If we see an input section with a
name that needs sorting, set the must_sort flag for the output section. (Layout::make_output_section): If the name of the output section indicates that it might require sorting, set the may_sort flag. * output.h (Output_section::may_sort_attached_input_sections): New function. (Output_section::set_may_sort_attached_input_sections): New function. (Output_section::must_sort_attached_input_sections): New function. (Output_section::set_must_sort_attached_input_sections): New function. (class Output_section): Declare Input_section_sort_entry. Define Input_section_sort_compare. Declare sort_attached_input_sections. Add new fields: may_sort_attached_input_sections_, must_sort_attached_input_sections_, attached_input_sections_are_sorted_. * output.cc (Output_section::Output_section): Initialize new fields. (Output_section::add_input_section): Add an entry to input_sections_ if may_sort or must_sort are true. (Output_section::set_final_data_size): Call sort_attached_input_sections if necessary. (Output_section::Input_section_sort_entry): Define new class. (Output_section::Input_section_sort_compare::operator()): New function. (Output_section::sort_attached_input_sections): New function. * configure.ac: Check whether the compiler supports constructor priorities. Define a CONSTRUCTOR_PRIORITY automake conditional. * testsuite/initpri1.c: New file. * testsuite/Makefile.am (check_PROGRAMS): Add initpri1 if CONSTRUCTOR_PRIORITY. (initpri1_SOURCES, initpri1_DEPENDENCIES): New variables. (initpri1_LDFLAGS): New variable. * configure, Makefile.in, testsuite/Makefile.in: Rebuild.
This commit is contained in:
parent
2460c166ae
commit
2fd322316e
@ -1,3 +1,43 @@
|
||||
2008-03-28 Ian Lance Taylor <iant@google.com>
|
||||
|
||||
* layout.cc (Layout::layout): If we see an input section with a
|
||||
name that needs sorting, set the must_sort flag for the output
|
||||
section.
|
||||
(Layout::make_output_section): If the name of the output section
|
||||
indicates that it might require sorting, set the may_sort flag.
|
||||
* output.h (Output_section::may_sort_attached_input_sections): New
|
||||
function.
|
||||
(Output_section::set_may_sort_attached_input_sections): New
|
||||
function.
|
||||
(Output_section::must_sort_attached_input_sections): New
|
||||
function.
|
||||
(Output_section::set_must_sort_attached_input_sections): New
|
||||
function.
|
||||
(class Output_section): Declare Input_section_sort_entry. Define
|
||||
Input_section_sort_compare. Declare
|
||||
sort_attached_input_sections. Add new fields:
|
||||
may_sort_attached_input_sections_,
|
||||
must_sort_attached_input_sections_,
|
||||
attached_input_sections_are_sorted_.
|
||||
* output.cc (Output_section::Output_section): Initialize new
|
||||
fields.
|
||||
(Output_section::add_input_section): Add an entry to
|
||||
input_sections_ if may_sort or must_sort are true.
|
||||
(Output_section::set_final_data_size): Call
|
||||
sort_attached_input_sections if necessary.
|
||||
(Output_section::Input_section_sort_entry): Define new class.
|
||||
(Output_section::Input_section_sort_compare::operator()): New
|
||||
function.
|
||||
(Output_section::sort_attached_input_sections): New function.
|
||||
* configure.ac: Check whether the compiler supports constructor
|
||||
priorities. Define a CONSTRUCTOR_PRIORITY automake conditional.
|
||||
* testsuite/initpri1.c: New file.
|
||||
* testsuite/Makefile.am (check_PROGRAMS): Add initpri1 if
|
||||
CONSTRUCTOR_PRIORITY.
|
||||
(initpri1_SOURCES, initpri1_DEPENDENCIES): New variables.
|
||||
(initpri1_LDFLAGS): New variable.
|
||||
* configure, Makefile.in, testsuite/Makefile.in: Rebuild.
|
||||
|
||||
2008-03-27 Ian Lance Taylor <iant@google.com>
|
||||
|
||||
* common.cc (Sort_commons::operator): Correct sorting algorithm.
|
||||
|
@ -163,6 +163,8 @@ CATOBJEXT = @CATOBJEXT@
|
||||
CC = @CC@
|
||||
CCDEPMODE = @CCDEPMODE@
|
||||
CFLAGS = @CFLAGS@
|
||||
CONSTRUCTOR_PRIORITY_FALSE = @CONSTRUCTOR_PRIORITY_FALSE@
|
||||
CONSTRUCTOR_PRIORITY_TRUE = @CONSTRUCTOR_PRIORITY_TRUE@
|
||||
CPP = @CPP@
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
CXX = @CXX@
|
||||
|
64
gold/configure
vendored
64
gold/configure
vendored
@ -309,7 +309,7 @@ ac_includes_default="\
|
||||
# include <unistd.h>
|
||||
#endif"
|
||||
|
||||
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar THREADS_TRUE THREADS_FALSE TARGETOBJS CC CFLAGS LDFLAGS CPPFLAGS ac_ct_CC EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CXX CXXFLAGS ac_ct_CXX CXXDEPMODE am__fastdepCXX_TRUE am__fastdepCXX_FALSE YACC RANLIB ac_ct_RANLIB LN_S USE_NLS LIBINTL LIBINTL_DEP INCINTL XGETTEXT GMSGFMT POSUB CATALOGS DATADIRNAME INSTOBJEXT GENCAT CATOBJEXT MKINSTALLDIRS MSGFMT MSGMERGE NATIVE_LINKER_TRUE NATIVE_LINKER_FALSE GCC_TRUE GCC_FALSE OBJDUMP_AND_CPPFILT_TRUE OBJDUMP_AND_CPPFILT_FALSE READELF_TRUE READELF_FALSE FN_PTRS_IN_SO_WITHOUT_PIC_TRUE FN_PTRS_IN_SO_WITHOUT_PIC_FALSE TLS_TRUE TLS_FALSE STATIC_TLS_TRUE STATIC_TLS_FALSE WARN_CFLAGS NO_WERROR WARN_CXXFLAGS LFS_CFLAGS LIBOBJS CPP EGREP CXXCPP MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT LTLIBOBJS'
|
||||
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar THREADS_TRUE THREADS_FALSE TARGETOBJS CC CFLAGS LDFLAGS CPPFLAGS ac_ct_CC EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CXX CXXFLAGS ac_ct_CXX CXXDEPMODE am__fastdepCXX_TRUE am__fastdepCXX_FALSE YACC RANLIB ac_ct_RANLIB LN_S USE_NLS LIBINTL LIBINTL_DEP INCINTL XGETTEXT GMSGFMT POSUB CATALOGS DATADIRNAME INSTOBJEXT GENCAT CATOBJEXT MKINSTALLDIRS MSGFMT MSGMERGE NATIVE_LINKER_TRUE NATIVE_LINKER_FALSE GCC_TRUE GCC_FALSE OBJDUMP_AND_CPPFILT_TRUE OBJDUMP_AND_CPPFILT_FALSE READELF_TRUE READELF_FALSE FN_PTRS_IN_SO_WITHOUT_PIC_TRUE FN_PTRS_IN_SO_WITHOUT_PIC_FALSE TLS_TRUE TLS_FALSE STATIC_TLS_TRUE STATIC_TLS_FALSE CONSTRUCTOR_PRIORITY_TRUE CONSTRUCTOR_PRIORITY_FALSE WARN_CFLAGS NO_WERROR WARN_CXXFLAGS LFS_CFLAGS LIBOBJS CPP EGREP CXXCPP MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT LTLIBOBJS'
|
||||
ac_subst_files=''
|
||||
|
||||
# Initialize some variables set by options.
|
||||
@ -4651,6 +4651,59 @@ else
|
||||
fi
|
||||
|
||||
|
||||
echo "$as_me:$LINENO: checking for constructor priorities" >&5
|
||||
echo $ECHO_N "checking for constructor priorities... $ECHO_C" >&6
|
||||
if test "${gold_cv_c_conprio+set}" = set; then
|
||||
echo $ECHO_N "(cached) $ECHO_C" >&6
|
||||
else
|
||||
cat >conftest.$ac_ext <<_ACEOF
|
||||
void f() __attribute__ ((constructor (1)));
|
||||
_ACEOF
|
||||
rm -f conftest.$ac_objext
|
||||
if { (eval echo "$as_me:$LINENO: \"$ac_compile\"") >&5
|
||||
(eval $ac_compile) 2>conftest.er1
|
||||
ac_status=$?
|
||||
grep -v '^ *+' conftest.er1 >conftest.err
|
||||
rm -f conftest.er1
|
||||
cat conftest.err >&5
|
||||
echo "$as_me:$LINENO: \$? = $ac_status" >&5
|
||||
(exit $ac_status); } &&
|
||||
{ ac_try='test -z "$ac_c_werror_flag"
|
||||
|| test ! -s conftest.err'
|
||||
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
|
||||
(eval $ac_try) 2>&5
|
||||
ac_status=$?
|
||||
echo "$as_me:$LINENO: \$? = $ac_status" >&5
|
||||
(exit $ac_status); }; } &&
|
||||
{ ac_try='test -s conftest.$ac_objext'
|
||||
{ (eval echo "$as_me:$LINENO: \"$ac_try\"") >&5
|
||||
(eval $ac_try) 2>&5
|
||||
ac_status=$?
|
||||
echo "$as_me:$LINENO: \$? = $ac_status" >&5
|
||||
(exit $ac_status); }; }; then
|
||||
gold_cv_c_conprio=yes
|
||||
else
|
||||
echo "$as_me: failed program was:" >&5
|
||||
sed 's/^/| /' conftest.$ac_ext >&5
|
||||
|
||||
gold_cv_c_conprio=no
|
||||
fi
|
||||
rm -f conftest.err conftest.$ac_objext conftest.$ac_ext
|
||||
fi
|
||||
echo "$as_me:$LINENO: result: $gold_cv_c_conprio" >&5
|
||||
echo "${ECHO_T}$gold_cv_c_conprio" >&6
|
||||
|
||||
|
||||
|
||||
if test "$gold_cv_c_conprio" = "yes"; then
|
||||
CONSTRUCTOR_PRIORITY_TRUE=
|
||||
CONSTRUCTOR_PRIORITY_FALSE='#'
|
||||
else
|
||||
CONSTRUCTOR_PRIORITY_TRUE='#'
|
||||
CONSTRUCTOR_PRIORITY_FALSE=
|
||||
fi
|
||||
|
||||
|
||||
|
||||
GCC_WARN_CFLAGS="-W -Wall -Wstrict-prototypes -Wmissing-prototypes"
|
||||
|
||||
@ -6501,6 +6554,13 @@ echo "$as_me: error: conditional \"STATIC_TLS\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&2;}
|
||||
{ (exit 1); exit 1; }; }
|
||||
fi
|
||||
if test -z "${CONSTRUCTOR_PRIORITY_TRUE}" && test -z "${CONSTRUCTOR_PRIORITY_FALSE}"; then
|
||||
{ { echo "$as_me:$LINENO: error: conditional \"CONSTRUCTOR_PRIORITY\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&5
|
||||
echo "$as_me: error: conditional \"CONSTRUCTOR_PRIORITY\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&2;}
|
||||
{ (exit 1); exit 1; }; }
|
||||
fi
|
||||
if test -z "${MAINTAINER_MODE_TRUE}" && test -z "${MAINTAINER_MODE_FALSE}"; then
|
||||
{ { echo "$as_me:$LINENO: error: conditional \"MAINTAINER_MODE\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&5
|
||||
@ -7142,6 +7202,8 @@ s,@TLS_TRUE@,$TLS_TRUE,;t t
|
||||
s,@TLS_FALSE@,$TLS_FALSE,;t t
|
||||
s,@STATIC_TLS_TRUE@,$STATIC_TLS_TRUE,;t t
|
||||
s,@STATIC_TLS_FALSE@,$STATIC_TLS_FALSE,;t t
|
||||
s,@CONSTRUCTOR_PRIORITY_TRUE@,$CONSTRUCTOR_PRIORITY_TRUE,;t t
|
||||
s,@CONSTRUCTOR_PRIORITY_FALSE@,$CONSTRUCTOR_PRIORITY_FALSE,;t t
|
||||
s,@WARN_CFLAGS@,$WARN_CFLAGS,;t t
|
||||
s,@NO_WERROR@,$NO_WERROR,;t t
|
||||
s,@WARN_CXXFLAGS@,$WARN_CXXFLAGS,;t t
|
||||
|
@ -223,6 +223,14 @@ error
|
||||
|
||||
AM_CONDITIONAL(STATIC_TLS, test "$gold_cv_lib_glibc24" = "yes")
|
||||
|
||||
dnl Check whether the compiler supports constructor priorities in
|
||||
dnl attributes, which were added in gcc 4.3.
|
||||
AC_CACHE_CHECK([for constructor priorities], [gold_cv_c_conprio],
|
||||
[AC_COMPILE_IFELSE([void f() __attribute__ ((constructor (1)));],
|
||||
[gold_cv_c_conprio=yes], [gold_cv_c_conprio=no])])
|
||||
|
||||
AM_CONDITIONAL(CONSTRUCTOR_PRIORITY, test "$gold_cv_c_conprio" = "yes")
|
||||
|
||||
AM_BINUTILS_WARNINGS
|
||||
|
||||
WARN_CXXFLAGS=`echo ${WARN_CFLAGS} | sed -e 's/-Wstrict-prototypes//' -e 's/-Wmissing-prototypes//'`
|
||||
|
@ -404,6 +404,17 @@ Layout::layout(Sized_relobj<size, big_endian>* object, unsigned int shndx,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// By default the GNU linker sorts input sections whose names match
|
||||
// .ctor.*, .dtor.*, .init_array.*, or .fini_array.*. The sections
|
||||
// are sorted by name. This is used to implement constructor
|
||||
// priority ordering. We are compatible.
|
||||
if (!this->script_options_->saw_sections_clause()
|
||||
&& (is_prefix_of(".ctors.", name)
|
||||
|| is_prefix_of(".dtors.", name)
|
||||
|| is_prefix_of(".init_array.", name)
|
||||
|| is_prefix_of(".fini_array.", name)))
|
||||
os->set_must_sort_attached_input_sections();
|
||||
|
||||
// FIXME: Handle SHF_LINK_ORDER somewhere.
|
||||
|
||||
*off = os->add_input_section(object, shndx, name, shdr, reloc_shndx,
|
||||
@ -671,6 +682,16 @@ Layout::make_output_section(const char* name, elfcpp::Elf_Word type,
|
||||
else
|
||||
this->attach_to_segment(os, flags);
|
||||
|
||||
// The GNU linker by default sorts some sections by priority, so we
|
||||
// do the same. We need to know that this might happen before we
|
||||
// attach any input sections.
|
||||
if (!this->script_options_->saw_sections_clause()
|
||||
&& (strcmp(name, ".ctors") == 0
|
||||
|| strcmp(name, ".dtors") == 0
|
||||
|| strcmp(name, ".init_array") == 0
|
||||
|| strcmp(name, ".fini_array") == 0))
|
||||
os->set_may_sort_attached_input_sections();
|
||||
|
||||
return os;
|
||||
}
|
||||
|
||||
|
248
gold/output.cc
248
gold/output.cc
@ -1595,6 +1595,9 @@ Output_section::Output_section(const char* name, elfcpp::Elf_Word type,
|
||||
found_in_sections_clause_(false),
|
||||
has_load_address_(false),
|
||||
info_uses_section_index_(false),
|
||||
may_sort_attached_input_sections_(false),
|
||||
must_sort_attached_input_sections_(false),
|
||||
attached_input_sections_are_sorted_(false),
|
||||
tls_offset_(0)
|
||||
{
|
||||
// An unallocated section has no address. Forcing this means that
|
||||
@ -1711,9 +1714,14 @@ Output_section::add_input_section(Sized_relobj<size, big_endian>* object,
|
||||
+ shdr.get_sh_size());
|
||||
|
||||
// We need to keep track of this section if we are already keeping
|
||||
// track of sections, or if we are relaxing. FIXME: Add test for
|
||||
// track of sections, or if we are relaxing. Also, if this is a
|
||||
// section which requires sorting, or which may require sorting in
|
||||
// the future, we keep track of the sections. FIXME: Add test for
|
||||
// relaxing.
|
||||
if (have_sections_script || !this->input_sections_.empty())
|
||||
if (have_sections_script
|
||||
|| !this->input_sections_.empty()
|
||||
|| this->may_sort_attached_input_sections()
|
||||
|| this->must_sort_attached_input_sections())
|
||||
this->input_sections_.push_back(Input_section(object, shndx,
|
||||
shdr.get_sh_size(),
|
||||
addralign));
|
||||
@ -1943,6 +1951,9 @@ Output_section::set_final_data_size()
|
||||
return;
|
||||
}
|
||||
|
||||
if (this->must_sort_attached_input_sections())
|
||||
this->sort_attached_input_sections();
|
||||
|
||||
uint64_t address = this->address();
|
||||
off_t startoff = this->offset();
|
||||
off_t off = startoff + this->first_input_offset_;
|
||||
@ -1978,6 +1989,239 @@ Output_section::do_set_tls_offset(uint64_t tls_base)
|
||||
this->tls_offset_ = this->address() - tls_base;
|
||||
}
|
||||
|
||||
// In a few cases we need to sort the input sections attached to an
|
||||
// output section. This is used to implement the type of constructor
|
||||
// priority ordering implemented by the GNU linker, in which the
|
||||
// priority becomes part of the section name and the sections are
|
||||
// sorted by name. We only do this for an output section if we see an
|
||||
// attached input section matching ".ctor.*", ".dtor.*",
|
||||
// ".init_array.*" or ".fini_array.*".
|
||||
|
||||
class Output_section::Input_section_sort_entry
|
||||
{
|
||||
public:
|
||||
Input_section_sort_entry()
|
||||
: input_section_(), index_(-1U), section_has_name_(false),
|
||||
section_name_()
|
||||
{ }
|
||||
|
||||
Input_section_sort_entry(const Input_section& input_section,
|
||||
unsigned int index)
|
||||
: input_section_(input_section), index_(index),
|
||||
section_has_name_(input_section.is_input_section())
|
||||
{
|
||||
if (this->section_has_name_)
|
||||
{
|
||||
// This is only called single-threaded from Layout::finalize,
|
||||
// so it is OK to lock. Unfortunately we have no way to pass
|
||||
// in a Task token.
|
||||
const Task* dummy_task = reinterpret_cast<const Task*>(-1);
|
||||
Object* obj = input_section.relobj();
|
||||
Task_lock_obj<Object> tl(dummy_task, obj);
|
||||
|
||||
// This is a slow operation, which should be cached in
|
||||
// Layout::layout if this becomes a speed problem.
|
||||
this->section_name_ = obj->section_name(input_section.shndx());
|
||||
}
|
||||
}
|
||||
|
||||
// Return the Input_section.
|
||||
const Input_section&
|
||||
input_section() const
|
||||
{
|
||||
gold_assert(this->index_ != -1U);
|
||||
return this->input_section_;
|
||||
}
|
||||
|
||||
// The index of this entry in the original list. This is used to
|
||||
// make the sort stable.
|
||||
unsigned int
|
||||
index() const
|
||||
{
|
||||
gold_assert(this->index_ != -1U);
|
||||
return this->index_;
|
||||
}
|
||||
|
||||
// Whether there is a section name.
|
||||
bool
|
||||
section_has_name() const
|
||||
{ return this->section_has_name_; }
|
||||
|
||||
// The section name.
|
||||
const std::string&
|
||||
section_name() const
|
||||
{
|
||||
gold_assert(this->section_has_name_);
|
||||
return this->section_name_;
|
||||
}
|
||||
|
||||
// Return true if the section name is either SECTION_NAME1 or
|
||||
// SECTION_NAME2.
|
||||
bool
|
||||
match_section_name(const char* section_name1, const char* section_name2) const
|
||||
{
|
||||
gold_assert(this->section_has_name_);
|
||||
return (this->section_name_ == section_name1
|
||||
|| this->section_name_ == section_name2);
|
||||
}
|
||||
|
||||
// Return true if PREFIX1 or PREFIX2 is a prefix of the section
|
||||
// name.
|
||||
bool
|
||||
match_section_name_prefix(const char* prefix1, const char* prefix2) const
|
||||
{
|
||||
gold_assert(this->section_has_name_);
|
||||
return (this->section_name_.compare(0, strlen(prefix1), prefix1) == 0
|
||||
|| this->section_name_.compare(0, strlen(prefix2), prefix2) == 0);
|
||||
}
|
||||
|
||||
// Return true if this is for a section named SECTION_NAME1 or
|
||||
// SECTION_NAME2 in an input file whose base name matches FILE_NAME.
|
||||
// The base name must have an extension of ".o", and must be exactly
|
||||
// FILE_NAME.o or FILE_NAME, one character, ".o". This is to match
|
||||
// crtbegin.o as well as crtbeginS.o without getting confused by
|
||||
// other possibilities. Overall matching the file name this way is
|
||||
// a dreadful hack, but the GNU linker does it in order to better
|
||||
// support gcc, and we need to be compatible.
|
||||
bool
|
||||
match_section_file(const char* section_name1, const char* section_name2,
|
||||
const char* match_file_name) const
|
||||
{
|
||||
gold_assert(this->section_has_name_);
|
||||
if (this->section_name_ != section_name1
|
||||
&& this->section_name_ != section_name2)
|
||||
return false;
|
||||
const std::string& file_name(this->input_section_.relobj()->name());
|
||||
const char* base_name = lbasename(file_name.c_str());
|
||||
size_t match_len = strlen(match_file_name);
|
||||
if (strncmp(base_name, match_file_name, match_len) != 0)
|
||||
return false;
|
||||
size_t base_len = strlen(base_name);
|
||||
if (base_len != match_len + 2 && base_len != match_len + 3)
|
||||
return false;
|
||||
return memcmp(base_name + base_len - 2, ".o", 2) == 0;
|
||||
}
|
||||
|
||||
private:
|
||||
// The Input_section we are sorting.
|
||||
Input_section input_section_;
|
||||
// The index of this Input_section in the original list.
|
||||
unsigned int index_;
|
||||
// Whether this Input_section has a section name--it won't if this
|
||||
// is some random Output_section_data.
|
||||
bool section_has_name_;
|
||||
// The section name if there is one.
|
||||
std::string section_name_;
|
||||
};
|
||||
|
||||
// Return true if S1 should come before S2 in the output section.
|
||||
|
||||
bool
|
||||
Output_section::Input_section_sort_compare::operator()(
|
||||
const Output_section::Input_section_sort_entry& s1,
|
||||
const Output_section::Input_section_sort_entry& s2) const
|
||||
{
|
||||
// We sort all the sections with no names to the end.
|
||||
if (!s1.section_has_name() || !s2.section_has_name())
|
||||
{
|
||||
if (s1.section_has_name())
|
||||
return true;
|
||||
if (s2.section_has_name())
|
||||
return false;
|
||||
return s1.index() < s2.index();
|
||||
}
|
||||
|
||||
// A .ctors or .dtors section from crtbegin.o must come before any
|
||||
// other .ctors* or .dtors* section.
|
||||
bool s1_begin = s1.match_section_file(".ctors", ".dtors", "crtbegin");
|
||||
bool s2_begin = s2.match_section_file(".ctors", ".dtors", "crtbegin");
|
||||
if (s1_begin || s2_begin)
|
||||
{
|
||||
if (!s1_begin)
|
||||
return false;
|
||||
if (!s2_begin)
|
||||
return true;
|
||||
return s1.index() < s2.index();
|
||||
}
|
||||
|
||||
// A .ctors or .dtors section from crtend.o must come after any
|
||||
// other .ctors* or .dtors* section.
|
||||
bool s1_end = s1.match_section_file(".ctors", ".dtors", "crtend");
|
||||
bool s2_end = s2.match_section_file(".ctors", ".dtors", "crtend");
|
||||
if (s1_end || s2_end)
|
||||
{
|
||||
if (!s1_end)
|
||||
return true;
|
||||
if (!s2_end)
|
||||
return false;
|
||||
return s1.index() < s2.index();
|
||||
}
|
||||
|
||||
// A .ctors or .init_array section with a priority precedes a .ctors
|
||||
// or .init_array section without a priority.
|
||||
if (s1.match_section_name_prefix(".ctors.", ".init_array.")
|
||||
&& s2.match_section_name(".ctors", ".init_array"))
|
||||
return true;
|
||||
if (s2.match_section_name_prefix(".ctors.", ".init_array.")
|
||||
&& s1.match_section_name(".ctors", ".init_array"))
|
||||
return false;
|
||||
|
||||
// A .dtors or .fini_array section with a priority follows a .dtors
|
||||
// or .fini_array section without a priority.
|
||||
if (s1.match_section_name_prefix(".dtors.", ".fini_array.")
|
||||
&& s2.match_section_name(".dtors", ".fini_array"))
|
||||
return false;
|
||||
if (s2.match_section_name_prefix(".dtors.", ".fini_array.")
|
||||
&& s1.match_section_name(".dtors", ".fini_array"))
|
||||
return true;
|
||||
|
||||
// Otherwise we sort by name.
|
||||
int compare = s1.section_name().compare(s2.section_name());
|
||||
if (compare != 0)
|
||||
return compare < 0;
|
||||
|
||||
// Otherwise we keep the input order.
|
||||
return s1.index() < s2.index();
|
||||
}
|
||||
|
||||
// Sort the input sections attached to an output section.
|
||||
|
||||
void
|
||||
Output_section::sort_attached_input_sections()
|
||||
{
|
||||
if (this->attached_input_sections_are_sorted_)
|
||||
return;
|
||||
|
||||
// The only thing we know about an input section is the object and
|
||||
// the section index. We need the section name. Recomputing this
|
||||
// is slow but this is an unusual case. If this becomes a speed
|
||||
// problem we can cache the names as required in Layout::layout.
|
||||
|
||||
// We start by building a larger vector holding a copy of each
|
||||
// Input_section, plus its current index in the list and its name.
|
||||
std::vector<Input_section_sort_entry> sort_list;
|
||||
|
||||
unsigned int i = 0;
|
||||
for (Input_section_list::iterator p = this->input_sections_.begin();
|
||||
p != this->input_sections_.end();
|
||||
++p, ++i)
|
||||
sort_list.push_back(Input_section_sort_entry(*p, i));
|
||||
|
||||
// Sort the input sections.
|
||||
std::sort(sort_list.begin(), sort_list.end(), Input_section_sort_compare());
|
||||
|
||||
// Copy the sorted input sections back to our list.
|
||||
this->input_sections_.clear();
|
||||
for (std::vector<Input_section_sort_entry>::iterator p = sort_list.begin();
|
||||
p != sort_list.end();
|
||||
++p)
|
||||
this->input_sections_.push_back(p->input_section());
|
||||
|
||||
// Remember that we sorted the input sections, since we might get
|
||||
// called again.
|
||||
this->attached_input_sections_are_sorted_ = true;
|
||||
}
|
||||
|
||||
// Write the section header to *OSHDR.
|
||||
|
||||
template<int size, bool big_endian>
|
||||
|
@ -1869,6 +1869,32 @@ class Output_section : public Output_data
|
||||
this->dynsym_index_ = index;
|
||||
}
|
||||
|
||||
// Return whether the input sections sections attachd to this output
|
||||
// section may require sorting. This is used to handle constructor
|
||||
// priorities compatibly with GNU ld.
|
||||
bool
|
||||
may_sort_attached_input_sections() const
|
||||
{ return this->may_sort_attached_input_sections_; }
|
||||
|
||||
// Record that the input sections attached to this output section
|
||||
// may require sorting.
|
||||
void
|
||||
set_may_sort_attached_input_sections()
|
||||
{ this->may_sort_attached_input_sections_ = true; }
|
||||
|
||||
// Return whether the input sections attached to this output section
|
||||
// require sorting. This is used to handle constructor priorities
|
||||
// compatibly with GNU ld.
|
||||
bool
|
||||
must_sort_attached_input_sections() const
|
||||
{ return this->must_sort_attached_input_sections_; }
|
||||
|
||||
// Record that the input sections attached to this output section
|
||||
// require sorting.
|
||||
void
|
||||
set_must_sort_attached_input_sections()
|
||||
{ this->must_sort_attached_input_sections_ = true; }
|
||||
|
||||
// Return whether this section should be written after all the input
|
||||
// sections are complete.
|
||||
bool
|
||||
@ -2310,6 +2336,17 @@ class Output_section : public Output_data
|
||||
|
||||
typedef std::vector<Input_section> Input_section_list;
|
||||
|
||||
// This class is used to sort the input sections.
|
||||
class Input_section_sort_entry;
|
||||
|
||||
// This is the sort comparison function.
|
||||
struct Input_section_sort_compare
|
||||
{
|
||||
bool
|
||||
operator()(const Input_section_sort_entry&,
|
||||
const Input_section_sort_entry&) const;
|
||||
};
|
||||
|
||||
// Fill data. This is used to fill in data between input sections.
|
||||
// It is also used for data statements (BYTE, WORD, etc.) in linker
|
||||
// scripts. When we have to keep track of the input sections, we
|
||||
@ -2360,6 +2397,10 @@ class Output_section : public Output_data
|
||||
add_output_merge_section(Output_section_data* posd, bool is_string,
|
||||
uint64_t entsize);
|
||||
|
||||
// Sort the attached input sections.
|
||||
void
|
||||
sort_attached_input_sections();
|
||||
|
||||
// Most of these fields are only valid after layout.
|
||||
|
||||
// The name of the section. This will point into a Stringpool.
|
||||
@ -2443,6 +2484,15 @@ class Output_section : public Output_data
|
||||
// section, false if it means the symbol index of the corresponding
|
||||
// section symbol.
|
||||
bool info_uses_section_index_ : 1;
|
||||
// True if the input sections attached to this output section may
|
||||
// need sorting.
|
||||
bool may_sort_attached_input_sections_ : 1;
|
||||
// True if the input sections attached to this output section must
|
||||
// be sorted.
|
||||
bool must_sort_attached_input_sections_ : 1;
|
||||
// True if the input sections attached to this output section have
|
||||
// already been sorted.
|
||||
bool attached_input_sections_are_sorted_ : 1;
|
||||
// For SHT_TLS sections, the offset of this section relative to the base
|
||||
// of the TLS segment.
|
||||
uint64_t tls_offset_;
|
||||
|
@ -417,6 +417,16 @@ endif FN_PTRS_IN_SO_WITHOUT_PIC
|
||||
endif TLS
|
||||
|
||||
|
||||
if CONSTRUCTOR_PRIORITY
|
||||
|
||||
check_PROGRAMS += initpri1
|
||||
initpri1_SOURCES = initpri1.c
|
||||
initpri1_DEPENDENCIES = gcctestdir/ld
|
||||
initpri1_LDFLAGS = -Bgcctestdir/
|
||||
|
||||
endif
|
||||
|
||||
|
||||
# Test --detect-odr-violations
|
||||
check_SCRIPTS += debug_msg.sh
|
||||
|
||||
|
@ -45,7 +45,7 @@ target_triplet = @target@
|
||||
check_PROGRAMS = object_unittest$(EXEEXT) binary_unittest$(EXEEXT) \
|
||||
$(am__EXEEXT_1) $(am__EXEEXT_2) $(am__EXEEXT_3) \
|
||||
$(am__EXEEXT_4) $(am__EXEEXT_5) $(am__EXEEXT_6) \
|
||||
$(am__EXEEXT_7) $(am__EXEEXT_8)
|
||||
$(am__EXEEXT_7) $(am__EXEEXT_8) $(am__EXEEXT_9)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_1 = basic_test \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ basic_static_test basic_pic_test \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ basic_static_pic_test \
|
||||
@ -150,11 +150,24 @@ check_PROGRAMS = object_unittest$(EXEEXT) binary_unittest$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@STATIC_TLS_TRUE@@TLS_TRUE@am__append_5 = tls_static_test \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@STATIC_TLS_TRUE@@TLS_TRUE@ tls_static_pic_test
|
||||
@FN_PTRS_IN_SO_WITHOUT_PIC_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@@TLS_TRUE@am__append_6 = tls_shared_nonpic_test
|
||||
@CONSTRUCTOR_PRIORITY_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_7 = initpri1
|
||||
@CONSTRUCTOR_PRIORITY_FALSE@initpri1_DEPENDENCIES = libgoldtest.a \
|
||||
@CONSTRUCTOR_PRIORITY_FALSE@ ../libgold.a \
|
||||
@CONSTRUCTOR_PRIORITY_FALSE@ ../../libiberty/libiberty.a \
|
||||
@CONSTRUCTOR_PRIORITY_FALSE@ $(am__DEPENDENCIES_1) \
|
||||
@CONSTRUCTOR_PRIORITY_FALSE@ $(am__DEPENDENCIES_1)
|
||||
@GCC_FALSE@initpri1_DEPENDENCIES = libgoldtest.a ../libgold.a \
|
||||
@GCC_FALSE@ ../../libiberty/libiberty.a $(am__DEPENDENCIES_1) \
|
||||
@GCC_FALSE@ $(am__DEPENDENCIES_1)
|
||||
@NATIVE_LINKER_FALSE@initpri1_DEPENDENCIES = libgoldtest.a \
|
||||
@NATIVE_LINKER_FALSE@ ../libgold.a ../../libiberty/libiberty.a \
|
||||
@NATIVE_LINKER_FALSE@ $(am__DEPENDENCIES_1) \
|
||||
@NATIVE_LINKER_FALSE@ $(am__DEPENDENCIES_1)
|
||||
|
||||
# Test --detect-odr-violations
|
||||
|
||||
# Similar to --detect-odr-violations: check for undefined symbols in .so's
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_7 = debug_msg.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_8 = debug_msg.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ undef_symbol.sh
|
||||
|
||||
# Create the data files that debug_msg.sh analyzes.
|
||||
@ -163,11 +176,11 @@ check_PROGRAMS = object_unittest$(EXEEXT) binary_unittest$(EXEEXT) \
|
||||
|
||||
# We also want to make sure we do something reasonable when there's no
|
||||
# debug info available. For the best test, we use .so's.
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_8 = debug_msg.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_9 = debug_msg.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ debug_msg_so.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ debug_msg_ndebug.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ undef_symbol.err
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_9 = debug_msg.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_10 = debug_msg.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ debug_msg_so.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ debug_msg_ndebug.err \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ undef_symbol.err
|
||||
@ -180,16 +193,16 @@ check_PROGRAMS = object_unittest$(EXEEXT) binary_unittest$(EXEEXT) \
|
||||
# sections, because it requires output-file resizing.
|
||||
|
||||
# Test symbol versioning.
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_10 = flagstest_compress_debug_sections \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__append_11 = flagstest_compress_debug_sections \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ flagstest_o_specialfile \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ flagstest_o_specialfile_and_compress_debug_sections \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ ver_test ver_test_2 ver_test_6 \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ script_test_1 script_test_2 \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ justsyms binary_test
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@am__append_11 = \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@am__append_12 = \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@ ver_test_2.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@ ver_test_5.sh
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@am__append_12 = \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@am__append_13 = \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@ ver_test_2.syms \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@READELF_TRUE@ ver_test_5.syms
|
||||
@GCC_FALSE@script_test_1_DEPENDENCIES = libgoldtest.a ../libgold.a \
|
||||
@ -220,13 +233,13 @@ check_PROGRAMS = object_unittest$(EXEEXT) binary_unittest$(EXEEXT) \
|
||||
@NATIVE_LINKER_FALSE@ ../libgold.a ../../libiberty/libiberty.a \
|
||||
@NATIVE_LINKER_FALSE@ $(am__DEPENDENCIES_1) \
|
||||
@NATIVE_LINKER_FALSE@ $(am__DEPENDENCIES_1)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_13 = ver_matching_test.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_14 = ver_matching_test.sh \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@ script_test_3.sh
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_14 = ver_matching_test.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@ script_test_3.stdout
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_15 = ver_matching_test.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@ script_test_3.stdout
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_16 = script_test_3
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_16 = ver_matching_test.stdout \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@ script_test_3.stdout
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__append_17 = script_test_3
|
||||
subdir = testsuite
|
||||
DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in
|
||||
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
|
||||
@ -289,7 +302,8 @@ libgoldtest_a_OBJECTS = $(am_libgoldtest_a_OBJECTS)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@STATIC_TLS_TRUE@@TLS_TRUE@am__EXEEXT_5 = tls_static_test$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@STATIC_TLS_TRUE@@TLS_TRUE@ tls_static_pic_test$(EXEEXT)
|
||||
@FN_PTRS_IN_SO_WITHOUT_PIC_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@@TLS_TRUE@am__EXEEXT_6 = tls_shared_nonpic_test$(EXEEXT)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__EXEEXT_7 = flagstest_compress_debug_sections$(EXEEXT) \
|
||||
@CONSTRUCTOR_PRIORITY_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@am__EXEEXT_7 = initpri1$(EXEEXT)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am__EXEEXT_8 = flagstest_compress_debug_sections$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ flagstest_o_specialfile$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ flagstest_o_specialfile_and_compress_debug_sections$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ ver_test$(EXEEXT) \
|
||||
@ -299,7 +313,7 @@ libgoldtest_a_OBJECTS = $(am_libgoldtest_a_OBJECTS)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ script_test_2$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ justsyms$(EXEEXT) \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ binary_test$(EXEEXT)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__EXEEXT_8 = script_test_3$(EXEEXT)
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@@OBJDUMP_AND_CPPFILT_TRUE@am__EXEEXT_9 = script_test_3$(EXEEXT)
|
||||
basic_pic_test_SOURCES = basic_pic_test.c
|
||||
basic_pic_test_OBJECTS = basic_pic_test.$(OBJEXT)
|
||||
basic_pic_test_LDADD = $(LDADD)
|
||||
@ -425,6 +439,10 @@ flagstest_o_specialfile_and_compress_debug_sections_LDADD = $(LDADD)
|
||||
flagstest_o_specialfile_and_compress_debug_sections_DEPENDENCIES = \
|
||||
libgoldtest.a ../libgold.a ../../libiberty/libiberty.a \
|
||||
$(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1)
|
||||
am__initpri1_SOURCES_DIST = initpri1.c
|
||||
@CONSTRUCTOR_PRIORITY_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@am_initpri1_OBJECTS = initpri1.$(OBJEXT)
|
||||
initpri1_OBJECTS = $(am_initpri1_OBJECTS)
|
||||
initpri1_LDADD = $(LDADD)
|
||||
am__justsyms_SOURCES_DIST = justsyms_1.cc
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@am_justsyms_OBJECTS = \
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ justsyms_1.$(OBJEXT)
|
||||
@ -638,10 +656,10 @@ SOURCES = $(libgoldtest_a_SOURCES) basic_pic_test.c \
|
||||
$(exception_static_test_SOURCES) $(exception_test_SOURCES) \
|
||||
flagstest_compress_debug_sections.c flagstest_o_specialfile.c \
|
||||
flagstest_o_specialfile_and_compress_debug_sections.c \
|
||||
$(justsyms_SOURCES) $(object_unittest_SOURCES) \
|
||||
$(script_test_1_SOURCES) $(script_test_2_SOURCES) \
|
||||
script_test_3.c $(tls_pic_test_SOURCES) \
|
||||
$(tls_shared_ie_test_SOURCES) \
|
||||
$(initpri1_SOURCES) $(justsyms_SOURCES) \
|
||||
$(object_unittest_SOURCES) $(script_test_1_SOURCES) \
|
||||
$(script_test_2_SOURCES) script_test_3.c \
|
||||
$(tls_pic_test_SOURCES) $(tls_shared_ie_test_SOURCES) \
|
||||
$(tls_shared_nonpic_test_SOURCES) $(tls_shared_test_SOURCES) \
|
||||
$(tls_static_pic_test_SOURCES) $(tls_static_test_SOURCES) \
|
||||
$(tls_test_SOURCES) $(two_file_mixed_2_shared_test_SOURCES) \
|
||||
@ -678,8 +696,8 @@ DIST_SOURCES = $(libgoldtest_a_SOURCES) basic_pic_test.c \
|
||||
$(am__exception_test_SOURCES_DIST) \
|
||||
flagstest_compress_debug_sections.c flagstest_o_specialfile.c \
|
||||
flagstest_o_specialfile_and_compress_debug_sections.c \
|
||||
$(am__justsyms_SOURCES_DIST) $(object_unittest_SOURCES) \
|
||||
$(am__script_test_1_SOURCES_DIST) \
|
||||
$(am__initpri1_SOURCES_DIST) $(am__justsyms_SOURCES_DIST) \
|
||||
$(object_unittest_SOURCES) $(am__script_test_1_SOURCES_DIST) \
|
||||
$(am__script_test_2_SOURCES_DIST) script_test_3.c \
|
||||
$(am__tls_pic_test_SOURCES_DIST) \
|
||||
$(am__tls_shared_ie_test_SOURCES_DIST) \
|
||||
@ -724,6 +742,8 @@ CATOBJEXT = @CATOBJEXT@
|
||||
CC = @CC@
|
||||
CCDEPMODE = @CCDEPMODE@
|
||||
CFLAGS = @CFLAGS@
|
||||
CONSTRUCTOR_PRIORITY_FALSE = @CONSTRUCTOR_PRIORITY_FALSE@
|
||||
CONSTRUCTOR_PRIORITY_TRUE = @CONSTRUCTOR_PRIORITY_TRUE@
|
||||
CPP = @CPP@
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
CXX = @CXX@
|
||||
@ -862,13 +882,13 @@ INCLUDES = \
|
||||
# .o's), but not all of them (such as .so's and .err files). We
|
||||
# improve on that here. automake-1.9 info docs say "mostlyclean" is
|
||||
# the right choice for files 'make' builds that people rebuild.
|
||||
MOSTLYCLEANFILES = *.so $(am__append_9) $(am__append_15)
|
||||
MOSTLYCLEANFILES = *.so $(am__append_10) $(am__append_16)
|
||||
|
||||
# We will add to these later, for each individual test. Note
|
||||
# that we add each test under check_SCRIPTS or check_PROGRAMS;
|
||||
# the TESTS variable is automatically populated from these.
|
||||
check_SCRIPTS = $(am__append_7) $(am__append_11) $(am__append_13)
|
||||
check_DATA = $(am__append_8) $(am__append_12) $(am__append_14)
|
||||
check_SCRIPTS = $(am__append_8) $(am__append_12) $(am__append_14)
|
||||
check_DATA = $(am__append_9) $(am__append_13) $(am__append_15)
|
||||
TESTS = $(check_SCRIPTS) $(check_PROGRAMS)
|
||||
|
||||
# ---------------------------------------------------------------------
|
||||
@ -1074,6 +1094,9 @@ binary_unittest_SOURCES = binary_unittest.cc
|
||||
@FN_PTRS_IN_SO_WITHOUT_PIC_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@@TLS_TRUE@tls_shared_nonpic_test_DEPENDENCIES = gcctestdir/ld tls_test_shared_nonpic.so
|
||||
@FN_PTRS_IN_SO_WITHOUT_PIC_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@@TLS_TRUE@tls_shared_nonpic_test_LDFLAGS = -Bgcctestdir/ -Wl,-R,.
|
||||
@FN_PTRS_IN_SO_WITHOUT_PIC_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@@TLS_TRUE@tls_shared_nonpic_test_LDADD = tls_test_shared_nonpic.so -lpthread
|
||||
@CONSTRUCTOR_PRIORITY_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@initpri1_SOURCES = initpri1.c
|
||||
@CONSTRUCTOR_PRIORITY_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@initpri1_DEPENDENCIES = gcctestdir/ld
|
||||
@CONSTRUCTOR_PRIORITY_TRUE@@GCC_TRUE@@NATIVE_LINKER_TRUE@initpri1_LDFLAGS = -Bgcctestdir/
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ver_test_SOURCES = ver_test_main.cc
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ver_test_DEPENDENCIES = gcctestdir/ld ver_test_1.so ver_test_2.so ver_test_4.so
|
||||
@GCC_TRUE@@NATIVE_LINKER_TRUE@ver_test_LDFLAGS = -Bgcctestdir/ -Wl,-R,.
|
||||
@ -1219,6 +1242,9 @@ exception_test$(EXEEXT): $(exception_test_OBJECTS) $(exception_test_DEPENDENCIES
|
||||
@NATIVE_LINKER_FALSE@flagstest_o_specialfile_and_compress_debug_sections$(EXEEXT): $(flagstest_o_specialfile_and_compress_debug_sections_OBJECTS) $(flagstest_o_specialfile_and_compress_debug_sections_DEPENDENCIES)
|
||||
@NATIVE_LINKER_FALSE@ @rm -f flagstest_o_specialfile_and_compress_debug_sections$(EXEEXT)
|
||||
@NATIVE_LINKER_FALSE@ $(LINK) $(flagstest_o_specialfile_and_compress_debug_sections_LDFLAGS) $(flagstest_o_specialfile_and_compress_debug_sections_OBJECTS) $(flagstest_o_specialfile_and_compress_debug_sections_LDADD) $(LIBS)
|
||||
initpri1$(EXEEXT): $(initpri1_OBJECTS) $(initpri1_DEPENDENCIES)
|
||||
@rm -f initpri1$(EXEEXT)
|
||||
$(LINK) $(initpri1_LDFLAGS) $(initpri1_OBJECTS) $(initpri1_LDADD) $(LIBS)
|
||||
justsyms$(EXEEXT): $(justsyms_OBJECTS) $(justsyms_DEPENDENCIES)
|
||||
@rm -f justsyms$(EXEEXT)
|
||||
$(CXXLINK) $(justsyms_LDFLAGS) $(justsyms_OBJECTS) $(justsyms_LDADD) $(LIBS)
|
||||
@ -1348,6 +1374,7 @@ distclean-compile:
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/flagstest_compress_debug_sections.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/flagstest_o_specialfile.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/flagstest_o_specialfile_and_compress_debug_sections.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/initpri1.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/justsyms_1.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/object_unittest.Po@am__quote@
|
||||
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/script_test_1.Po@am__quote@
|
||||
|
87
gold/testsuite/initpri1.c
Normal file
87
gold/testsuite/initpri1.c
Normal file
@ -0,0 +1,87 @@
|
||||
/* initpri1.c -- test constructor priorities.
|
||||
|
||||
Copyright 2007, 2008 Free Software Foundation, Inc.
|
||||
Copied from the gcc testsuite, where the test was contributed by
|
||||
Mark Mitchell <mark@codesourcery.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.
|
||||
|
||||
This is a test of a common symbol in the main program and a
|
||||
versioned symbol in a shared library. The common symbol in the
|
||||
main program should override the shared library symbol. */
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
int i;
|
||||
int j;
|
||||
|
||||
void c1() __attribute__((constructor (500)));
|
||||
void c2() __attribute__((constructor (700)));
|
||||
void c3() __attribute__((constructor (600)));
|
||||
|
||||
void c1() {
|
||||
if (i++ != 0)
|
||||
abort ();
|
||||
}
|
||||
|
||||
void c2() {
|
||||
if (i++ != 2)
|
||||
abort ();
|
||||
}
|
||||
|
||||
void c3() {
|
||||
if (i++ != 1)
|
||||
abort ();
|
||||
}
|
||||
|
||||
void d1() __attribute__((destructor (500)));
|
||||
void d2() __attribute__((destructor (700)));
|
||||
void d3() __attribute__((destructor (600)));
|
||||
|
||||
void d1() {
|
||||
if (--i != 0)
|
||||
abort ();
|
||||
}
|
||||
|
||||
void d2() {
|
||||
if (--i != 2)
|
||||
abort ();
|
||||
}
|
||||
|
||||
void d3() {
|
||||
if (j != 2)
|
||||
abort ();
|
||||
if (--i != 1)
|
||||
abort ();
|
||||
}
|
||||
|
||||
void cd4() __attribute__((constructor (800), destructor (800)));
|
||||
|
||||
void cd4() {
|
||||
if (i != 3)
|
||||
abort ();
|
||||
++j;
|
||||
}
|
||||
|
||||
int main () {
|
||||
if (i != 3)
|
||||
return 1;
|
||||
if (j != 1)
|
||||
abort ();
|
||||
return 0;
|
||||
}
|
Loading…
Reference in New Issue
Block a user