aboutsummaryrefslogtreecommitdiff
path: root/ld
diff options
context:
space:
mode:
Diffstat (limited to 'ld')
-rw-r--r--ld/ChangeLog46
-rw-r--r--ld/emultempl/elf32.em64
-rw-r--r--ld/ld.texinfo16
-rw-r--r--ld/ldlang.c115
-rw-r--r--ld/testsuite/ld-elf/pr21562a.d9
-rw-r--r--ld/testsuite/ld-elf/pr21562a.s8
-rw-r--r--ld/testsuite/ld-elf/pr21562a.t3
-rw-r--r--ld/testsuite/ld-elf/pr21562b.d9
-rw-r--r--ld/testsuite/ld-elf/pr21562b.s8
-rw-r--r--ld/testsuite/ld-elf/pr21562b.t5
-rw-r--r--ld/testsuite/ld-elf/pr21562c.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562c.t7
-rw-r--r--ld/testsuite/ld-elf/pr21562d.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562d.t5
-rw-r--r--ld/testsuite/ld-elf/pr21562e.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562f.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562g.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562h.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562i.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562j.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562k.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562l.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562m.d10
-rw-r--r--ld/testsuite/ld-elf/pr21562n.d10
-rw-r--r--ld/testsuite/ld-gc/gc.exp6
-rw-r--r--ld/testsuite/ld-gc/pr19161.d2
-rw-r--r--ld/testsuite/ld-gc/pr20022.d11
-rw-r--r--ld/testsuite/ld-gc/pr20022a.s8
-rw-r--r--ld/testsuite/ld-gc/pr20022b.s8
-rw-r--r--ld/testsuite/ld-gc/start.d2
-rw-r--r--ld/testsuite/ld-x86-64/lea1a.d2
-rw-r--r--ld/testsuite/ld-x86-64/lea1b.d2
-rw-r--r--ld/testsuite/ld-x86-64/lea1d.d2
-rw-r--r--ld/testsuite/ld-x86-64/lea1e.d2
34 files changed, 381 insertions, 79 deletions
diff --git a/ld/ChangeLog b/ld/ChangeLog
index 309bb3a..dcfc602 100644
--- a/ld/ChangeLog
+++ b/ld/ChangeLog
@@ -1,5 +1,51 @@
2017-06-13 H.J. Lu <hongjiu.lu@intel.com>
+ PR ld/20022
+ PR ld/21557
+ PR ld/21562
+ PR ld/21571
+ * ld.texinfo: Update __start_SECNAME/__stop_SECNAME symbols.
+ * ldlang.c (lang_insert_orphan): Move handling of __start_SECNAME
+ and __stop_SECNAME symbols to ...
+ (lang_set_startof): Here. Also define __start_SECNAME and
+ __stop_SECNAME for -Ur.
+ * emultempl/elf32.em (gld${EMULATION_NAME}_after_open): Mark
+ referenced __start_SECNAME and __stop_SECNAME symbols as hidden
+ and set start_stop for garbage collection.
+ * testsuite/ld-elf/pr21562a.d: New file.
+ * testsuite/ld-elf/pr21562a.s: Likewise.
+ * testsuite/ld-elf/pr21562a.t: Likewise.
+ * testsuite/ld-elf/pr21562b.d: Likewise.
+ * testsuite/ld-elf/pr21562b.s: Likewise.
+ * testsuite/ld-elf/pr21562b.t: Likewise.
+ * testsuite/ld-elf/pr21562c.d: Likewise.
+ * testsuite/ld-elf/pr21562c.t: Likewise.
+ * testsuite/ld-elf/pr21562d.d: Likewise.
+ * testsuite/ld-elf/pr21562d.t: Likewise.
+ * testsuite/ld-elf/pr21562e.d: Likewise.
+ * testsuite/ld-elf/pr21562f.d: Likewise.
+ * testsuite/ld-elf/pr21562g.d: Likewise.
+ * testsuite/ld-elf/pr21562h.d: Likewise.
+ * testsuite/ld-elf/pr21562i.d: Likewise.
+ * testsuite/ld-elf/pr21562j.d: Likewise.
+ * testsuite/ld-elf/pr21562k.d: Likewise.
+ * testsuite/ld-elf/pr21562l.d: Likewise.
+ * testsuite/ld-elf/pr21562m.d: Likewise.
+ * testsuite/ld-elf/pr21562n.d: Likewise.
+ * testsuite/ld-gc/pr20022.d: Likewise.
+ * testsuite/ld-gc/pr20022a.s: Likewise.
+ * testsuite/ld-gc/pr20022b.s: Likewise.
+ * testsuite/ld-gc/gc.exp: Run PR ld/20022 tests.
+ * testsuite/ld-gc/pr19161.d: Also accept local __start_SECNAME
+ symbol.
+ * testsuite/ld-gc/start.d: Likewise.
+ * testsuite/ld-x86-64/lea1a.d: Updated.
+ * testsuite/ld-x86-64/lea1b.d: Updated.
+ * testsuite/ld-x86-64/lea1d.d: Updated.
+ * testsuite/ld-x86-64/lea1e.d: Likewise.
+
+2017-06-13 H.J. Lu <hongjiu.lu@intel.com>
+
* testsuite/ld-elf/sizeof.d: New file.
* testsuite/ld-elf/sizeof.s: Likewise.
* testsuite/ld-elf/startof.d: Likewise.
diff --git a/ld/emultempl/elf32.em b/ld/emultempl/elf32.em
index 0260b7a..9468f7d 100644
--- a/ld/emultempl/elf32.em
+++ b/ld/emultempl/elf32.em
@@ -1216,6 +1216,9 @@ gld${EMULATION_NAME}_after_open (void)
{
struct bfd_link_needed_list *needed, *l;
struct elf_link_hash_table *htab;
+ asection *s;
+ bfd *abfd;
+ char leading_char;
after_open_default ();
@@ -1239,8 +1242,6 @@ gld${EMULATION_NAME}_after_open (void)
if (emit_note_gnu_build_id != NULL)
{
- bfd *abfd;
-
/* Find an ELF input. */
for (abfd = link_info.input_bfds;
abfd != (bfd *) NULL; abfd = abfd->link.next)
@@ -1276,11 +1277,66 @@ gld${EMULATION_NAME}_after_open (void)
return;
}
+ leading_char = bfd_get_symbol_leading_char (link_info.output_bfd);
+
+ /* Check for input sections whose names match references to
+ __start_SECNAME or __stop_SECNAME symbols. Mark the matched
+ symbols as hidden and set start_stop for garbage collection. */
+ for (abfd = link_info.input_bfds; abfd; abfd = abfd->link.next)
+ for (s = abfd->sections; s; s = s->next)
+ {
+ const char *name = bfd_get_section_name (abfd, s);
+ const char *ps;
+
+ for (ps = name; *ps != '\0'; ps++)
+ if (!ISALNUM ((unsigned char) *ps) && *ps != '_')
+ break;
+ if (*ps == '\0')
+ {
+ struct elf_link_hash_entry *h;
+ char *symbol = (char *) xmalloc (ps - name
+ + sizeof "__start_" + 1);
+
+ symbol[0] = leading_char;
+ sprintf (symbol + (leading_char != 0), "__start_%s", name);
+ h = elf_link_hash_lookup (elf_hash_table (&link_info),
+ symbol, FALSE, FALSE, TRUE);
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ && h->u2.start_stop_section == NULL)
+ {
+ h->start_stop = 1;
+ h->u2.start_stop_section = s;
+ _bfd_elf_link_hash_hide_symbol (&link_info, h, TRUE);
+ if (ELF_ST_VISIBILITY (h->other) != STV_INTERNAL)
+ h->other = ((h->other & ~ELF_ST_VISIBILITY (-1))
+ | STV_HIDDEN);
+ }
+
+ symbol[0] = leading_char;
+ sprintf (symbol + (leading_char != 0), "__stop_%s", name);
+ h = elf_link_hash_lookup (elf_hash_table (&link_info),
+ symbol, FALSE, FALSE, TRUE);
+ if (h != NULL
+ && (h->root.type == bfd_link_hash_undefined
+ || h->root.type == bfd_link_hash_undefweak)
+ && h->u2.start_stop_section == NULL)
+ {
+ h->start_stop = 1;
+ h->u2.start_stop_section = s;
+ _bfd_elf_link_hash_hide_symbol (&link_info, h, TRUE);
+ if (ELF_ST_VISIBILITY (h->other) != STV_INTERNAL)
+ h->other = ((h->other & ~ELF_ST_VISIBILITY (-1))
+ | STV_HIDDEN);
+ }
+ }
+ }
+
if (!link_info.traditional_format)
{
- bfd *abfd, *elfbfd = NULL;
+ bfd *elfbfd = NULL;
bfd_boolean warn_eh_frame = FALSE;
- asection *s;
int seen_type = 0;
for (abfd = link_info.input_bfds; abfd; abfd = abfd->link.next)
diff --git a/ld/ld.texinfo b/ld/ld.texinfo
index 790b52f..44ad84b 100644
--- a/ld/ld.texinfo
+++ b/ld/ld.texinfo
@@ -4657,6 +4657,14 @@ SECTIONS @{
@end group
@end smallexample
+If an output section's name is the same as the input section's name
+and is representable as a C identifier, then the linker will
+automatically @pxref{PROVIDE} two symbols: __start_SECNAME and
+__stop_SECNAME, where SECNAME is the name of the section. These
+indicate the start address and end address of the output section
+respectively. Note: most section names are not representable as
+C identifiers because they contain a @samp{.} character.
+
@node Output Section Data
@subsection Output Section Data
@cindex data
@@ -5841,14 +5849,6 @@ The command line options @samp{--orphan-handling} and @samp{--unique}
(@pxref{Options,,Command Line Options}) can be used to control which
output sections an orphan is placed in.
-If an orphaned section's name is representable as a C identifier then
-the linker will automatically @pxref{PROVIDE} two symbols:
-__start_SECNAME and __stop_SECNAME, where SECNAME is the name of the
-section. These indicate the start address and end address of the
-orphaned section respectively. Note: most section names are not
-representable as C identifiers because they contain a @samp{.}
-character.
-
@node Location Counter
@subsection The Location Counter
@kindex .
diff --git a/ld/ldlang.c b/ld/ldlang.c
index 252400b..f8e4f52 100644
--- a/ld/ldlang.c
+++ b/ld/ldlang.c
@@ -1829,8 +1829,6 @@ lang_insert_orphan (asection *s,
lang_statement_list_type *add_child)
{
lang_statement_list_type add;
- const char *ps;
- lang_assignment_statement_type *start_assign;
lang_output_section_statement_type *os;
lang_output_section_statement_type **os_tail;
@@ -1852,29 +1850,6 @@ lang_insert_orphan (asection *s,
os = lang_enter_output_section_statement (secname, address, normal_section,
NULL, NULL, NULL, constraint, 0);
- ps = NULL;
- start_assign = NULL;
- if (config.build_constructors && *os_tail == os)
- {
- /* If the name of the section is representable in C, then create
- symbols to mark the start and the end of the section. */
- for (ps = secname; *ps != '\0'; ps++)
- if (!ISALNUM ((unsigned char) *ps) && *ps != '_')
- break;
- if (*ps == '\0')
- {
- char *symname;
-
- symname = (char *) xmalloc (ps - secname + sizeof "__start_" + 1);
- symname[0] = bfd_get_symbol_leading_char (link_info.output_bfd);
- sprintf (symname + (symname[0] != 0), "__start_%s", secname);
- start_assign
- = lang_add_assignment (exp_provide (symname,
- exp_nameop (NAME, "."),
- FALSE));
- }
- }
-
if (add_child == NULL)
add_child = &os->children;
lang_add_section (add_child, s, NULL, os);
@@ -1894,27 +1869,6 @@ lang_insert_orphan (asection *s,
lang_leave_output_section_statement (NULL, DEFAULT_MEMORY_REGION, NULL,
NULL);
- if (start_assign != NULL)
- {
- char *symname;
- lang_assignment_statement_type *stop_assign;
- bfd_vma dot;
-
- symname = (char *) xmalloc (ps - secname + sizeof "__stop_" + 1);
- symname[0] = bfd_get_symbol_leading_char (link_info.output_bfd);
- sprintf (symname + (symname[0] != 0), "__stop_%s", secname);
- stop_assign
- = lang_add_assignment (exp_provide (symname,
- exp_nameop (NAME, "."),
- FALSE));
- /* Evaluate the expression to define the symbol if referenced,
- before sizing dynamic sections. */
- dot = os->bfd_section->vma;
- exp_fold_tree (start_assign->exp, os->bfd_section, &dot);
- dot += TO_ADDR (s->size);
- exp_fold_tree (stop_assign->exp, os->bfd_section, &dot);
- }
-
/* Restore the global list pointer. */
if (after != NULL)
pop_stat_ptr ();
@@ -5924,20 +5878,25 @@ section_for_dot (void)
return bfd_abs_section_ptr;
}
-/* Fix any .startof. or .sizeof. symbols. When the assemblers see the
- operator .startof. (section_name), it produces an undefined symbol
- .startof.section_name. Similarly, when it sees
+/* Fix any .startof., .sizeof., __start or __stop symbols. When the
+ assemblers see the operator .startof. (section_name), it produces
+ an undefined symbol .startof.section_name. Similarly, when it sees
.sizeof. (section_name), it produces an undefined symbol
- .sizeof.section_name. For all the output sections, we look for
- such symbols, and set them to the correct value. */
+ .sizeof.section_name. Also for ELF linker, __start_XXX or __stop_XXX
+ symbols should be resolved to the start and end of section XXX. For
+ all the output sections, we look for such symbols, and set them to
+ the correct value. */
static void
lang_set_startof (void)
{
asection *s;
+ char leading_char;
+ bfd_boolean is_elf = (bfd_get_flavour (link_info.output_bfd)
+ == bfd_target_elf_flavour);
+ bfd_boolean is_elocatable = bfd_link_relocatable (&link_info);
- if (bfd_link_relocatable (&link_info))
- return;
+ leading_char = bfd_get_symbol_leading_char (link_info.output_bfd);
for (s = link_info.output_bfd->sections; s != NULL; s = s->next)
{
@@ -5948,24 +5907,58 @@ lang_set_startof (void)
secname = bfd_get_section_name (link_info.output_bfd, s);
buf = (char *) xmalloc (10 + strlen (secname));
- sprintf (buf, ".startof.%s", secname);
- h = bfd_link_hash_lookup (link_info.hash, buf, FALSE, FALSE, TRUE);
- if (h != NULL && h->type == bfd_link_hash_undefined)
+ if (!is_elocatable)
+ {
+ sprintf (buf, ".startof.%s", secname);
+ h = bfd_link_hash_lookup (link_info.hash, buf, FALSE, FALSE,
+ TRUE);
+ if (h != NULL && h->type == bfd_link_hash_undefined)
+ {
+ h->type = bfd_link_hash_defined;
+ h->u.def.value = 0;
+ h->u.def.section = s;
+ }
+
+ sprintf (buf, ".sizeof.%s", secname);
+ h = bfd_link_hash_lookup (link_info.hash, buf, FALSE, FALSE,
+ TRUE);
+ if (h != NULL && h->type == bfd_link_hash_undefined)
+ {
+ h->type = bfd_link_hash_defined;
+ h->u.def.value = TO_ADDR (s->size);
+ h->u.def.section = bfd_abs_section_ptr;
+ }
+ }
+
+ buf[0] = leading_char;
+ sprintf (buf + (buf[0] != 0), "__start_%s", secname);
+ h = bfd_link_hash_lookup (link_info.hash, buf, FALSE, FALSE,
+ TRUE);
+ if (h != NULL
+ && (h->type == bfd_link_hash_undefined
+ || h->type == bfd_link_hash_undefweak))
{
h->type = bfd_link_hash_defined;
h->u.def.value = 0;
h->u.def.section = s;
+ if (is_elf)
+ ((struct elf_link_hash_entry *) h)->def_regular = 1;
}
- sprintf (buf, ".sizeof.%s", secname);
- h = bfd_link_hash_lookup (link_info.hash, buf, FALSE, FALSE, TRUE);
- if (h != NULL && h->type == bfd_link_hash_undefined)
+ buf[0] = leading_char;
+ sprintf (buf + (buf[0] != 0), "__stop_%s", secname);
+ h = bfd_link_hash_lookup (link_info.hash, buf, FALSE, FALSE,
+ TRUE);
+ if (h != NULL
+ && (h->type == bfd_link_hash_undefined
+ || h->type == bfd_link_hash_undefweak))
{
h->type = bfd_link_hash_defined;
h->u.def.value = TO_ADDR (s->size);
- h->u.def.section = bfd_abs_section_ptr;
+ h->u.def.section = s;
+ if (is_elf)
+ ((struct elf_link_hash_entry *) h)->def_regular = 1;
}
-
free (buf);
}
}
diff --git a/ld/testsuite/ld-elf/pr21562a.d b/ld/testsuite/ld-elf/pr21562a.d
new file mode 100644
index 0000000..009dcfc
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562a.d
@@ -0,0 +1,9 @@
+#ld: -shared -z defs --gc-sections
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562a.s b/ld/testsuite/ld-elf/pr21562a.s
new file mode 100644
index 0000000..ec36da4
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562a.s
@@ -0,0 +1,8 @@
+ .section scnfoo,"aw",%progbits
+ .zero 0x10
+
+ .globl bar
+ .data
+ .type bar, %object
+bar:
+ .dc.a __start_scnfoo
diff --git a/ld/testsuite/ld-elf/pr21562a.t b/ld/testsuite/ld-elf/pr21562a.t
new file mode 100644
index 0000000..5e05ab3
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562a.t
@@ -0,0 +1,3 @@
+SECTIONS {
+ scnfoo : { *(scnfoo) }
+}
diff --git a/ld/testsuite/ld-elf/pr21562b.d b/ld/testsuite/ld-elf/pr21562b.d
new file mode 100644
index 0000000..a03dbad
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562b.d
@@ -0,0 +1,9 @@
+#ld: -shared -z defs --gc-sections
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562b.s b/ld/testsuite/ld-elf/pr21562b.s
new file mode 100644
index 0000000..1732ee2
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562b.s
@@ -0,0 +1,8 @@
+ .section scnfoo,"aw",%progbits
+ .zero 0x10
+
+ .globl bar
+ .data
+ .type bar, %object
+bar:
+ .dc.a __stop_scnfoo
diff --git a/ld/testsuite/ld-elf/pr21562b.t b/ld/testsuite/ld-elf/pr21562b.t
new file mode 100644
index 0000000..b30b521
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562b.t
@@ -0,0 +1,5 @@
+SECTIONS {
+ PROVIDE (__start_scnfoo = .);
+ scnfoo : { *(scnfoo) }
+ PROVIDE (__stop_scnfoo = .);
+}
diff --git a/ld/testsuite/ld-elf/pr21562c.d b/ld/testsuite/ld-elf/pr21562c.d
new file mode 100644
index 0000000..9de035f
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562c.d
@@ -0,0 +1,10 @@
+#source: pr21562a.s
+#ld: -shared -z defs --gc-sections -T pr21562a.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562c.t b/ld/testsuite/ld-elf/pr21562c.t
new file mode 100644
index 0000000..f9cb901
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562c.t
@@ -0,0 +1,7 @@
+SECTIONS {
+ .foo : {
+ PROVIDE (__start_scnfoo = .);
+ *(scnfoo)
+ PROVIDE (__stop_scnfoo = .);
+ }
+}
diff --git a/ld/testsuite/ld-elf/pr21562d.d b/ld/testsuite/ld-elf/pr21562d.d
new file mode 100644
index 0000000..e5344ef
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562d.d
@@ -0,0 +1,10 @@
+#source: pr21562b.s
+#ld: -shared -z defs --gc-sections -T pr21562a.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562d.t b/ld/testsuite/ld-elf/pr21562d.t
new file mode 100644
index 0000000..c0cea61
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562d.t
@@ -0,0 +1,5 @@
+SECTIONS {
+ PROVIDE (__start_scnfoo = .);
+ .foo : { *(scnfoo) }
+ PROVIDE (__stop_scnfoo = .);
+}
diff --git a/ld/testsuite/ld-elf/pr21562e.d b/ld/testsuite/ld-elf/pr21562e.d
new file mode 100644
index 0000000..afaf7e5
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562e.d
@@ -0,0 +1,10 @@
+#source: pr21562a.s
+#ld: -shared -z defs
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562f.d b/ld/testsuite/ld-elf/pr21562f.d
new file mode 100644
index 0000000..b9c324a
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562f.d
@@ -0,0 +1,10 @@
+#source: pr21562b.s
+#ld: -shared -z defs
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562g.d b/ld/testsuite/ld-elf/pr21562g.d
new file mode 100644
index 0000000..a813594
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562g.d
@@ -0,0 +1,10 @@
+#source: pr21562a.s
+#ld: -shared -z defs -T pr21562a.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562h.d b/ld/testsuite/ld-elf/pr21562h.d
new file mode 100644
index 0000000..6adabd7
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562h.d
@@ -0,0 +1,10 @@
+#source: pr21562b.s
+#ld: -shared -z defs -T pr21562a.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562i.d b/ld/testsuite/ld-elf/pr21562i.d
new file mode 100644
index 0000000..49eb2ec
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562i.d
@@ -0,0 +1,10 @@
+#source: pr21562a.s
+#ld: -shared -z defs --gc-sections -T pr21562b.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562j.d b/ld/testsuite/ld-elf/pr21562j.d
new file mode 100644
index 0000000..14bb035
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562j.d
@@ -0,0 +1,10 @@
+#source: pr21562b.s
+#ld: -shared -z defs --gc-sections -T pr21562b.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] scnfoo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562k.d b/ld/testsuite/ld-elf/pr21562k.d
new file mode 100644
index 0000000..1bf1e93
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562k.d
@@ -0,0 +1,10 @@
+#source: pr21562a.s
+#ld: -shared -z defs --gc-sections -T pr21562c.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] \.foo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562l.d b/ld/testsuite/ld-elf/pr21562l.d
new file mode 100644
index 0000000..8297ec2
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562l.d
@@ -0,0 +1,10 @@
+#source: pr21562b.s
+#ld: -shared -z defs --gc-sections -T pr21562c.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] \.foo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562m.d b/ld/testsuite/ld-elf/pr21562m.d
new file mode 100644
index 0000000..34f8df0
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562m.d
@@ -0,0 +1,10 @@
+#source: pr21562a.s
+#ld: -shared -z defs --gc-sections -T pr21562d.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] \.foo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start_scnfoo
+#pass
diff --git a/ld/testsuite/ld-elf/pr21562n.d b/ld/testsuite/ld-elf/pr21562n.d
new file mode 100644
index 0000000..e4b1919
--- /dev/null
+++ b/ld/testsuite/ld-elf/pr21562n.d
@@ -0,0 +1,10 @@
+#source: pr21562b.s
+#ld: -shared -z defs --gc-sections -T pr21562d.t
+#readelf: -s -S --wide
+#target: *-*-linux* *-*-gnu*
+
+#...
+ \[[ 0-9]+\] \.foo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +0*10[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__stop_scnfoo
+#pass
diff --git a/ld/testsuite/ld-gc/gc.exp b/ld/testsuite/ld-gc/gc.exp
index ba5c46b..364c73b 100644
--- a/ld/testsuite/ld-gc/gc.exp
+++ b/ld/testsuite/ld-gc/gc.exp
@@ -119,6 +119,12 @@ if { [is_elf_format] && [check_shared_lib_support] } then {
run_dump_test "personality"
}
run_dump_test "pr18223"
+ if {![ld_assemble_flags $as $gasopt $srcdir/$subdir/pr20022a.s tmpdir/pr20022a.o]
+ || ![ld_link $ld tmpdir/pr20022.so "-shared --gc-sections tmpdir/pr20022a.o"] } then {
+ fail pr20022
+ } else {
+ run_dump_test "pr20022"
+ }
}
if { [is_remote host] || [which $CC] != 0 } {
diff --git a/ld/testsuite/ld-gc/pr19161.d b/ld/testsuite/ld-gc/pr19161.d
index c36e663..baee8da 100644
--- a/ld/testsuite/ld-gc/pr19161.d
+++ b/ld/testsuite/ld-gc/pr19161.d
@@ -6,5 +6,5 @@
#xfail: mips64vr-*-* msp430-*-* powerpc*-*-eabivle rl78-*-* rx-*-* sh*-*-*
#...
-0*[1-9a-f]+[0-9a-f]*[ ](D)[ ]_*__start_my_section
+0*[1-9a-f]+[0-9a-f]*[ ](d|D)[ ]_*__start_my_section
#...
diff --git a/ld/testsuite/ld-gc/pr20022.d b/ld/testsuite/ld-gc/pr20022.d
new file mode 100644
index 0000000..b51ec19
--- /dev/null
+++ b/ld/testsuite/ld-gc/pr20022.d
@@ -0,0 +1,11 @@
+#source: pr20022b.s
+#ld: --gc-sections -e _start tmpdir/pr20022.so
+#readelf: -SsW
+#target: *-*-linux* *-*-gnu*
+#notarget: *-*-*aout *-*-*oldld frv-*-linux* metag-*-linux*
+
+#...
+ \[[ 0-9]+\] _foo[ \t]+PROGBITS[ \t]+[0-9a-f]+ +[0-9a-f]+ +[0-9a-f]+[ \t]+.*
+#...
+ +[0-9]+: +[0-9a-f]+ +[0-9a-f]+ +NOTYPE +LOCAL +DEFAULT +[0-9]+ +__start__foo
+#pass
diff --git a/ld/testsuite/ld-gc/pr20022a.s b/ld/testsuite/ld-gc/pr20022a.s
new file mode 100644
index 0000000..6bd346f
--- /dev/null
+++ b/ld/testsuite/ld-gc/pr20022a.s
@@ -0,0 +1,8 @@
+ .data
+ .globl bar
+ .type bar,%object
+bar:
+ .dc.a __start__foo
+ .section _foo,"aw",%progbits
+foo:
+ .ascii "This is bar"
diff --git a/ld/testsuite/ld-gc/pr20022b.s b/ld/testsuite/ld-gc/pr20022b.s
new file mode 100644
index 0000000..2306c59
--- /dev/null
+++ b/ld/testsuite/ld-gc/pr20022b.s
@@ -0,0 +1,8 @@
+ .text
+ .globl _start
+_start:
+ .dc.a __start__foo
+ .dc.a bar
+ .section _foo,"aw",%progbits
+foo:
+ .ascii "This is foo"
diff --git a/ld/testsuite/ld-gc/start.d b/ld/testsuite/ld-gc/start.d
index 18e74c1..9113b48 100644
--- a/ld/testsuite/ld-gc/start.d
+++ b/ld/testsuite/ld-gc/start.d
@@ -5,5 +5,5 @@
#notarget: *-*-*aout *-*-*oldld frv-*-linux* metag-*-linux*
#...
-[0-9a-f]+ D +__start__foo
+[0-9a-f]+ d +__start__foo
#...
diff --git a/ld/testsuite/ld-x86-64/lea1a.d b/ld/testsuite/ld-x86-64/lea1a.d
index 9b662cb..28ea4b9 100644
--- a/ld/testsuite/ld-x86-64/lea1a.d
+++ b/ld/testsuite/ld-x86-64/lea1a.d
@@ -15,5 +15,5 @@ Disassembly of section .text:
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea -0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <foo>
[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <bar>
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <__start_my_section>
-[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <__stop_my_section>
+[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <.*>
#pass
diff --git a/ld/testsuite/ld-x86-64/lea1b.d b/ld/testsuite/ld-x86-64/lea1b.d
index 9108149..c7873cd 100644
--- a/ld/testsuite/ld-x86-64/lea1b.d
+++ b/ld/testsuite/ld-x86-64/lea1b.d
@@ -15,5 +15,5 @@ Disassembly of section .text:
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea -0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <foo>
[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <bar>
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <__start_my_section>
-[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <__stop_my_section>
+[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <.*>
#pass
diff --git a/ld/testsuite/ld-x86-64/lea1d.d b/ld/testsuite/ld-x86-64/lea1d.d
index 4d708d2..70fc603 100644
--- a/ld/testsuite/ld-x86-64/lea1d.d
+++ b/ld/testsuite/ld-x86-64/lea1d.d
@@ -15,5 +15,5 @@ Disassembly of section .text:
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea -0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <foo>
[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <bar>
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <__start_my_section>
-[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <__stop_my_section>
+[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <.*>
#pass
diff --git a/ld/testsuite/ld-x86-64/lea1e.d b/ld/testsuite/ld-x86-64/lea1e.d
index da60137..123fcd2 100644
--- a/ld/testsuite/ld-x86-64/lea1e.d
+++ b/ld/testsuite/ld-x86-64/lea1e.d
@@ -15,5 +15,5 @@ Disassembly of section .text:
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea -0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <foo>
[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <bar>
[ ]*[a-f0-9]+: 48 8d 05 ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%rax # [a-f0-9]+ <__start_my_section>
-[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <__stop_my_section>
+[ ]*[a-f0-9]+: 4c 8d 1d ([0-9a-f]{2} ){4} * lea 0x[a-f0-9]+\(%rip\),%r11 # [a-f0-9]+ <.*>
#pass