aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorH.J. Lu <hjl.tools@gmail.com>2017-08-06 08:18:53 -0700
committerH.J. Lu <hjl.tools@gmail.com>2017-08-06 08:19:04 -0700
commita4819f54c0006554179631189131080be859eefb (patch)
treef6058c1da96aa3065bba0be6352946163aa5186d
parente2a084f2c152f6358ba926df22a313d3ef8d8509 (diff)
downloadfsf-binutils-gdb-a4819f54c0006554179631189131080be859eefb.zip
fsf-binutils-gdb-a4819f54c0006554179631189131080be859eefb.tar.gz
fsf-binutils-gdb-a4819f54c0006554179631189131080be859eefb.tar.bz2
Treat common symbol as undefined for --no-define-common
When --no-define-common is used to build shared library, treat common symbol as undefined so that common symbols that are referenced from a shared library to be assigned addresses only in the main program. This eliminates the unused duplicate space in the shared library, and also prevents any possible confusion over resolving to the wrong duplicate when there are many dynamic modules with specialized search paths for runtime symbol resolution. --no-define-common is only allowed when building a shared library. bfd/ PR ld/21903: * elflink.c (elf_link_add_object_symbols): Treat common symbol as undefined for --no-define-common. include/ PR ld/21903: * bfdlink.h (bfd_link_info): Add inhibit_common_definition. ld/ PR ld/21903: * ld.h (command_line): Remove inhibit_common_definition. * ldgram.y: Replace command_line.inhibit_common_definition with link_info.inhibit_common_definition. * ldlang.c (lang_common): Likewise. * lexsup.c (parse_args): Likewise. * ldmain.c (main): Only allow --no-define-common with -shared. * testsuite/ld-elf/pr21903.s: New file. * testsuite/ld-elf/pr21903a.d: Likewise. * testsuite/ld-elf/pr21903b.d: Likewise. * testsuite/ld-elf/pr21903c.d: Likewise. * testsuite/ld-elf/pr21903d.d: Likewise. * testsuite/ld-elf/pr21903e.d: Likewise.
-rw-r--r--bfd/ChangeLog6
-rw-r--r--bfd/elflink.c5
-rw-r--r--include/ChangeLog5
-rw-r--r--include/bfdlink.h3
-rw-r--r--ld/ChangeLog16
-rw-r--r--ld/ld.h3
-rw-r--r--ld/ldgram.y2
-rw-r--r--ld/ldlang.c2
-rw-r--r--ld/ldmain.c3
-rw-r--r--ld/lexsup.c2
-rw-r--r--ld/testsuite/ld-elf/pr21903.s15
-rw-r--r--ld/testsuite/ld-elf/pr21903a.d8
-rw-r--r--ld/testsuite/ld-elf/pr21903b.d8
-rw-r--r--ld/testsuite/ld-elf/pr21903c.d3
-rw-r--r--ld/testsuite/ld-elf/pr21903d.d4
-rw-r--r--ld/testsuite/ld-elf/pr21903e.d3
16 files changed, 82 insertions, 6 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index 63813e47..7c58a86 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,3 +1,9 @@
+2017-08-06 H.J. Lu <hongjiu.lu@intel.com>
+
+ PR ld/21903:
+ * elflink.c (elf_link_add_object_symbols): Treat common symbol
+ as undefined for --no-define-common.
+
2017-08-05 Alan Modra <amodra@gmail.com>
* elf32-hppa.c (elf32_hppa_set_gp): Don't require an
diff --git a/bfd/elflink.c b/bfd/elflink.c
index eff53ac..0cc5f87 100644
--- a/bfd/elflink.c
+++ b/bfd/elflink.c
@@ -4250,6 +4250,11 @@ error_free_dyn:
override = FALSE;
+ /* Treat common symbol as undefined for --no-define-common. */
+ if (isym->st_shndx == SHN_COMMON
+ && info->inhibit_common_definition)
+ isym->st_shndx = SHN_UNDEF;
+
flags = BSF_NO_FLAGS;
sec = NULL;
value = isym->st_value;
diff --git a/include/ChangeLog b/include/ChangeLog
index 443cab0..332ae93 100644
--- a/include/ChangeLog
+++ b/include/ChangeLog
@@ -1,3 +1,8 @@
+2017-08-06 H.J. Lu <hongjiu.lu@intel.com>
+
+ PR ld/21903:
+ * bfdlink.h (bfd_link_info): Add inhibit_common_definition.
+
2017-07-31 Nick Clifton <nickc@redhat.com>
PR 21850
diff --git a/include/bfdlink.h b/include/bfdlink.h
index e7c7836..2370c0d 100644
--- a/include/bfdlink.h
+++ b/include/bfdlink.h
@@ -489,6 +489,9 @@ struct bfd_link_info
/* TRUE if generate a 1-byte NOP as suffix for x86 call instruction. */
unsigned int call_nop_as_suffix : 1;
+ /* TRUE if common symbols should be treated as undefined. */
+ unsigned int inhibit_common_definition : 1;
+
/* The 1-byte NOP for x86 call instruction. */
char call_nop_byte;
diff --git a/ld/ChangeLog b/ld/ChangeLog
index eb002e9..a041f0a 100644
--- a/ld/ChangeLog
+++ b/ld/ChangeLog
@@ -1,3 +1,19 @@
+2017-08-06 H.J. Lu <hongjiu.lu@intel.com>
+
+ PR ld/21903:
+ * ld.h (command_line): Remove inhibit_common_definition.
+ * ldgram.y: Replace command_line.inhibit_common_definition with
+ link_info.inhibit_common_definition.
+ * ldlang.c (lang_common): Likewise.
+ * lexsup.c (parse_args): Likewise.
+ * ldmain.c (main): Only allow --no-define-common with -shared.
+ * testsuite/ld-elf/pr21903.s: New file.
+ * testsuite/ld-elf/pr21903a.d: Likewise.
+ * testsuite/ld-elf/pr21903b.d: Likewise.
+ * testsuite/ld-elf/pr21903c.d: Likewise.
+ * testsuite/ld-elf/pr21903d.d: Likewise.
+ * testsuite/ld-elf/pr21903e.d: Likewise.
+
2017-08-05 Alan Modra <amodra@gmail.com>
* testsuite/ld-unique/pr21529.d: Don't xfail hppa.
diff --git a/ld/ld.h b/ld/ld.h
index 162e156..c6fa124 100644
--- a/ld/ld.h
+++ b/ld/ld.h
@@ -132,9 +132,6 @@ typedef struct
/* 1 => assign space to common symbols even if `relocatable_output'. */
bfd_boolean force_common_definition;
- /* 1 => do not assign addresses to common symbols. */
- bfd_boolean inhibit_common_definition;
-
/* If TRUE, build MIPS embedded PIC relocation tables in the output
file. */
bfd_boolean embedded_relocs;
diff --git a/ld/ldgram.y b/ld/ldgram.y
index 771d990..e2998f1 100644
--- a/ld/ldgram.y
+++ b/ld/ldgram.y
@@ -339,7 +339,7 @@ ifile_p1:
| FORCE_GROUP_ALLOCATION
{ command_line.force_group_allocation = TRUE ; }
| INHIBIT_COMMON_ALLOCATION
- { command_line.inhibit_common_definition = TRUE ; }
+ { link_info.inhibit_common_definition = TRUE ; }
| INPUT '(' input_list ')'
| GROUP
{ lang_enter_group (); }
diff --git a/ld/ldlang.c b/ld/ldlang.c
index b8b214d..196b2cc 100644
--- a/ld/ldlang.c
+++ b/ld/ldlang.c
@@ -6260,7 +6260,7 @@ lang_check (void)
static void
lang_common (void)
{
- if (command_line.inhibit_common_definition)
+ if (link_info.inhibit_common_definition)
return;
if (bfd_link_relocatable (&link_info)
&& !command_line.force_common_definition)
diff --git a/ld/ldmain.c b/ld/ldmain.c
index 5d1a3f4..cb1e2d1 100644
--- a/ld/ldmain.c
+++ b/ld/ldmain.c
@@ -395,6 +395,9 @@ main (int argc, char **argv)
if (argc == 2 && version_printed)
xexit (0);
+ if (link_info.inhibit_common_definition && !bfd_link_dll (&link_info))
+ einfo (_("%P%F: --no-define-common may not be used without -shared\n"));
+
if (!lang_has_input_file)
{
if (version_printed || command_line.print_output_format)
diff --git a/ld/lexsup.c b/ld/lexsup.c
index 08106bc..effa277 100644
--- a/ld/lexsup.c
+++ b/ld/lexsup.c
@@ -908,7 +908,7 @@ parse_args (unsigned argc, char **argv)
input_flags.dynamic = FALSE;
break;
case OPTION_NO_DEFINE_COMMON:
- command_line.inhibit_common_definition = TRUE;
+ link_info.inhibit_common_definition = TRUE;
break;
case OPTION_NO_DEMANGLE:
demangling = FALSE;
diff --git a/ld/testsuite/ld-elf/pr21903.s b/ld/testsuite/ld-elf/pr21903.s
new file mode 100644
index 0000000..9dbf96c
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21903.s
@@ -0,0 +1,15 @@
+ .text
+ .global start /* Used by SH targets. */
+start:
+ .global _start
+_start:
+ .global __start
+__start:
+ .global main /* Used by HPPA targets. */
+main:
+ .dc.a foo
+ .ifdef HPUX
+foo .comm 4
+ .else
+ .comm foo, 4, 4
+ .endif
diff --git a/ld/testsuite/ld-elf/pr21903a.d b/ld/testsuite/ld-elf/pr21903a.d
new file mode 100644
index 0000000..020c561
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21903a.d
@@ -0,0 +1,8 @@
+#source: pr21903.s
+#ld: -shared --no-define-common
+#readelf: --dyn-syms
+#target: *-*-linux* *-*-gnu*
+
+#...
+.*: 0+0 +0 +OBJECT +GLOBAL +DEFAULT +UND foo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21903b.d b/ld/testsuite/ld-elf/pr21903b.d
new file mode 100644
index 0000000..decd4f3
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21903b.d
@@ -0,0 +1,8 @@
+#source: pr21903.s
+#ld: -shared
+#readelf: --dyn-syms
+#target: *-*-linux* *-*-gnu*
+
+#...
+.*: [0-9a-f]+ +4 +OBJECT +GLOBAL +DEFAULT +[0-9]+ foo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21903c.d b/ld/testsuite/ld-elf/pr21903c.d
new file mode 100644
index 0000000..d3910ec
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21903c.d
@@ -0,0 +1,3 @@
+#source: pr21903.s
+#ld: --no-define-common
+#error: --no-define-common may not be used without -shared
diff --git a/ld/testsuite/ld-elf/pr21903d.d b/ld/testsuite/ld-elf/pr21903d.d
new file mode 100644
index 0000000..ec72900
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21903d.d
@@ -0,0 +1,4 @@
+#source: pr21903.s
+#ld: --no-define-common -pie
+#target: *-*-linux* *-*-gnu*
+#error: --no-define-common may not be used without -shared
diff --git a/ld/testsuite/ld-elf/pr21903e.d b/ld/testsuite/ld-elf/pr21903e.d
new file mode 100644
index 0000000..894c595
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21903e.d
@@ -0,0 +1,3 @@
+#source: pr21903.s
+#ld: -r --no-define-common
+#error: --no-define-common may not be used without -shared