This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] gold: Ignore definition from a dynamic object for __start/__stop


On Wed, Nov 8, 2017 at 3:50 PM, Cary Coutant <ccoutant@gmail.com> wrote:
> +   // Skip if the old definition is from a regular object.
> +   if (!oldsym->is_from_dynobj())
> +     return NULL;
> +
> +   // If the symbol has the hidden or internal visibility, ignore
> +   // definition and reference from a dynamic object.
> +   if ((visibility == elfcpp::STV_HIDDEN
> +        || visibility == elfcpp::STV_INTERNAL)
> +       && !oldsym->in_reg())
>
> s/the hidden/hidden/
>
> The last if statement really just ignores the symbol if it hasn't been
> referenced in a regular object. The first if statement takes care of
> the case where the definition was in a dynamic object.
>
> OK with updated comment.
>

This is what I am checking in.


H.J.
From 33f692f6bffedfb5477eacbf82eb80ed8090b5fb Mon Sep 17 00:00:00 2001
From: "H.J. Lu" <hjl.tools@gmail.com>
Date: Wed, 8 Nov 2017 15:56:54 -0800
Subject: [PATCH] gold: Ignore def/ref from a dynamic object for special
 symbols

Since special symbol must be defined in a regular object, definition
from a dynamic object should be ignored.  If special symbol has the
hidden or internal visibility, reference from a dynamic object should
also be ignored.  Also __start and __stop symbols in a dynamic object
shouldn't be preempted.

	PR gold/22291
	* layout.cc (Layout::define_section_symbols): Use STV_PROTECTED
	for __start and __stop symbols.
	* symtab.cc (Symbol_table::define_special_symbol): Add an
	argument, visibility.  Ignore definition and reference from
	a dynamic object, depending on visibility.
	(Symbol_table::do_define_in_output_data): Pass visibility to
	define_special_symbol.
	(Symbol_table::do_define_in_output_segment): Likewise.
	(Symbol_table::do_define_as_constant): Likewise.
	(Symbol_table::add_undefined_symbol_from_command_line): Pass
	STV_DEFAULT to define_special_symbol.
	* symtab.h (Symbol_table::define_special_symbol): Add an
	argument, visibility.
---
 gold/ChangeLog | 17 +++++++++++++++++
 gold/layout.cc |  4 ++--
 gold/symtab.cc | 48 +++++++++++++++++++++++++++++++++++++++---------
 gold/symtab.h  |  3 ++-
 4 files changed, 60 insertions(+), 12 deletions(-)

diff --git a/gold/ChangeLog b/gold/ChangeLog
index c4c171d785..bd842a67d8 100644
--- a/gold/ChangeLog
+++ b/gold/ChangeLog
@@ -1,3 +1,20 @@
+2017-11-08  H.J. Lu  <hongjiu.lu@intel.com>
+
+	PR gold/22291
+	* layout.cc (Layout::define_section_symbols): Use STV_PROTECTED
+	for __start and __stop symbols.
+	* symtab.cc (Symbol_table::define_special_symbol): Add an
+	argument, visibility.  Ignore definition and reference from
+	a dynamic object, depending on visibility.
+	(Symbol_table::do_define_in_output_data): Pass visibility to
+	define_special_symbol.
+	(Symbol_table::do_define_in_output_segment): Likewise.
+	(Symbol_table::do_define_as_constant): Likewise.
+	(Symbol_table::add_undefined_symbol_from_command_line): Pass
+	STV_DEFAULT to define_special_symbol.
+	* symtab.h (Symbol_table::define_special_symbol): Add an
+	argument, visibility.
+
 2017-11-08  James Clarke  <jrtc27@jrtc27.com>
 
 	PR gold/22266
diff --git a/gold/layout.cc b/gold/layout.cc
index 15c54344de..351c4b4d4f 100644
--- a/gold/layout.cc
+++ b/gold/layout.cc
@@ -2252,7 +2252,7 @@ Layout::define_section_symbols(Symbol_table* symtab)
 					0, // symsize
 					elfcpp::STT_NOTYPE,
 					elfcpp::STB_GLOBAL,
-					elfcpp::STV_DEFAULT,
+					elfcpp::STV_PROTECTED,
 					0, // nonvis
 					false, // offset_is_from_end
 					true); // only_if_ref
@@ -2265,7 +2265,7 @@ Layout::define_section_symbols(Symbol_table* symtab)
 					0, // symsize
 					elfcpp::STT_NOTYPE,
 					elfcpp::STB_GLOBAL,
-					elfcpp::STV_DEFAULT,
+					elfcpp::STV_PROTECTED,
 					0, // nonvis
 					true, // offset_is_from_end
 					true); // only_if_ref
diff --git a/gold/symtab.cc b/gold/symtab.cc
index 7ebcd6b568..d1f71e02d0 100644
--- a/gold/symtab.cc
+++ b/gold/symtab.cc
@@ -1761,6 +1761,7 @@ template<int size, bool big_endian>
 Sized_symbol<size>*
 Symbol_table::define_special_symbol(const char** pname, const char** pversion,
 				    bool only_if_ref,
+				    elfcpp::STV visibility,
                                     Sized_symbol<size>** poldsym,
 				    bool* resolve_oldsym, bool is_forced_local)
 {
@@ -1799,8 +1800,21 @@ Symbol_table::define_special_symbol(const char** pname, const char** pversion,
       oldsym = this->lookup(*pname, *pversion);
       if (oldsym == NULL && is_default_version)
 	oldsym = this->lookup(*pname, NULL);
-      if (oldsym == NULL || !oldsym->is_undefined())
+      if (oldsym == NULL)
 	return NULL;
+      if (!oldsym->is_undefined())
+	{
+	  // Skip if the old definition is from a regular object.
+	  if (!oldsym->is_from_dynobj())
+	    return NULL;
+
+	  // If the symbol has hidden or internal visibility, ignore
+	  // definition and reference from a dynamic object.
+	  if ((visibility == elfcpp::STV_HIDDEN
+	       || visibility == elfcpp::STV_INTERNAL)
+	      && !oldsym->in_reg())
+	    return NULL;
+	}
 
       *pname = oldsym->name();
       if (is_default_version)
@@ -1975,7 +1989,9 @@ Symbol_table::do_define_in_output_data(
     {
 #if defined(HAVE_TARGET_32_BIG) || defined(HAVE_TARGET_64_BIG)
       sym = this->define_special_symbol<size, true>(&name, &version,
-						    only_if_ref, &oldsym,
+						    only_if_ref,
+						    visibility,
+						    &oldsym,
 						    &resolve_oldsym,
 						    is_forced_local);
 #else
@@ -1986,7 +2002,9 @@ Symbol_table::do_define_in_output_data(
     {
 #if defined(HAVE_TARGET_32_LITTLE) || defined(HAVE_TARGET_64_LITTLE)
       sym = this->define_special_symbol<size, false>(&name, &version,
-						     only_if_ref, &oldsym,
+						     only_if_ref,
+						     visibility,
+						     &oldsym,
 						     &resolve_oldsym,
 						     is_forced_local);
 #else
@@ -2094,7 +2112,9 @@ Symbol_table::do_define_in_output_segment(
     {
 #if defined(HAVE_TARGET_32_BIG) || defined(HAVE_TARGET_64_BIG)
       sym = this->define_special_symbol<size, true>(&name, &version,
-						    only_if_ref, &oldsym,
+						    only_if_ref,
+						    visibility,
+						    &oldsym,
 						    &resolve_oldsym,
 						    is_forced_local);
 #else
@@ -2105,7 +2125,9 @@ Symbol_table::do_define_in_output_segment(
     {
 #if defined(HAVE_TARGET_32_LITTLE) || defined(HAVE_TARGET_64_LITTLE)
       sym = this->define_special_symbol<size, false>(&name, &version,
-						     only_if_ref, &oldsym,
+						     only_if_ref,
+						     visibility,
+						     &oldsym,
 						     &resolve_oldsym,
 						     is_forced_local);
 #else
@@ -2211,7 +2233,9 @@ Symbol_table::do_define_as_constant(
     {
 #if defined(HAVE_TARGET_32_BIG) || defined(HAVE_TARGET_64_BIG)
       sym = this->define_special_symbol<size, true>(&name, &version,
-						    only_if_ref, &oldsym,
+						    only_if_ref,
+						    visibility,
+						    &oldsym,
 						    &resolve_oldsym,
 						    is_forced_local);
 #else
@@ -2222,7 +2246,9 @@ Symbol_table::do_define_as_constant(
     {
 #if defined(HAVE_TARGET_32_LITTLE) || defined(HAVE_TARGET_64_LITTLE)
       sym = this->define_special_symbol<size, false>(&name, &version,
-						     only_if_ref, &oldsym,
+						     only_if_ref,
+						     visibility,
+						     &oldsym,
 						     &resolve_oldsym,
 						     is_forced_local);
 #else
@@ -2449,7 +2475,9 @@ Symbol_table::add_undefined_symbol_from_command_line(const char* name)
     {
 #if defined(HAVE_TARGET_32_BIG) || defined(HAVE_TARGET_64_BIG)
       sym = this->define_special_symbol<size, true>(&name, &version,
-						    false, &oldsym,
+						    false,
+						    elfcpp::STV_DEFAULT,
+						    &oldsym,
 						    &resolve_oldsym,
 						    false);
 #else
@@ -2460,7 +2488,9 @@ Symbol_table::add_undefined_symbol_from_command_line(const char* name)
     {
 #if defined(HAVE_TARGET_32_LITTLE) || defined(HAVE_TARGET_64_LITTLE)
       sym = this->define_special_symbol<size, false>(&name, &version,
-						     false, &oldsym,
+						     false,
+						     elfcpp::STV_DEFAULT,
+						     &oldsym,
 						     &resolve_oldsym,
 						     false);
 #else
diff --git a/gold/symtab.h b/gold/symtab.h
index a67d5eb90d..edf1c1729c 100644
--- a/gold/symtab.h
+++ b/gold/symtab.h
@@ -1830,7 +1830,8 @@ class Symbol_table
   template<int size, bool big_endian>
   Sized_symbol<size>*
   define_special_symbol(const char** pname, const char** pversion,
-			bool only_if_ref, Sized_symbol<size>** poldsym,
+			bool only_if_ref, elfcpp::STV visibility,
+			Sized_symbol<size>** poldsym,
 			bool* resolve_oldsym, bool is_forced_local);
 
   // Define a symbol in an Output_data, sized version.
-- 
2.13.6


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]