diff options
Diffstat (limited to 'ld')
-rw-r--r-- | ld/ChangeLog | 21 | ||||
-rw-r--r-- | ld/NEWS | 5 | ||||
-rw-r--r-- | ld/ld.h | 5 | ||||
-rw-r--r-- | ld/ld.texinfo | 23 | ||||
-rw-r--r-- | ld/ldgram.y | 4 | ||||
-rw-r--r-- | ld/ldlang.c | 18 | ||||
-rw-r--r-- | ld/ldlex.h | 1 | ||||
-rw-r--r-- | ld/ldlex.l | 1 | ||||
-rw-r--r-- | ld/ldmain.c | 6 | ||||
-rw-r--r-- | ld/lexsup.c | 6 | ||||
-rw-r--r-- | ld/testsuite/ld-elf/group11.d | 6 | ||||
-rw-r--r-- | ld/testsuite/ld-elf/group12.d | 6 | ||||
-rw-r--r-- | ld/testsuite/ld-elf/group12.ld | 14 |
13 files changed, 112 insertions, 4 deletions
diff --git a/ld/ChangeLog b/ld/ChangeLog index 0e52c27..e80477f 100644 --- a/ld/ChangeLog +++ b/ld/ChangeLog @@ -1,3 +1,24 @@ +2017-06-06 Andrew Burgess <andrew.burgess@embecosm.com> + + * ld.h (struct args_type): Add force_group_allocation field. + * ldgram.y: Add support for FORCE_GROUP_ALLOCATION. + * ldlex.h: Likewise. + * ldlex.l: Likewise. + * lexsup.c: Likewise. + * ldlang.c (unique_section_p): Check resolve_section_groups flag + not the relaxable link flag. + (lang_add_section): Discard section groups when we're resolving + groups. Clear the SEC_LINK_ONCE flag if we're resolving section + groups. + * ldmain.c (main): Initialise resolve_section_groups flag in + link_info based on command line flags. + * testsuite/ld-elf/group11.d: New file. + * testsuite/ld-elf/group12.d: New file. + * testsuite/ld-elf/group12.ld: New file. + * NEWS: Mention new features. + * ld.texinfo (Options): Document --force-group-allocation. + (Miscellaneous Commands): Document FORCE_GROUP_ALLOCATION. + 2017-06-05 H.J. Lu <hongjiu.lu@intel.com> PR ld/21529 @@ -15,6 +15,11 @@ * Orphan sections placed after an empty section that has an AT(LMA) will now take an load memory address starting from LMA. +* Section groups can now be resolved (the group deleted and the group members + placed like normal sections) at partial link time either using the new linker + option --force-group-allocation or by placing FORCE_GROUP_ALLOCATION into the + linker script. + Changes in 2.28: * The EXCLUDE_FILE linker script construct can now be applied outside of the @@ -172,6 +172,11 @@ typedef struct /* If set, display the target memory usage (per memory region). */ bfd_boolean print_memory_usage; + /* Shold we force section groups to be resolved? Controlled with + --force-group-allocation on the command line or FORCE_GROUP_ALLOCATION + in the linker script. */ + bfd_boolean force_group_allocation; + /* Big or little endian as set on command line. */ enum endian_enum endian; diff --git a/ld/ld.texinfo b/ld/ld.texinfo index edf1e31..790b52f 100644 --- a/ld/ld.texinfo +++ b/ld/ld.texinfo @@ -1484,6 +1484,18 @@ 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. +@cindex group allocation in linker script +@cindex section groups +@cindex COMDAT +@kindex --force-group-allocation +@item --force-group-allocation +This option causes the linker to place section group members like +normal input sections, and to delete the section groups. This is the +default behaviour for a final link but this option can be used to +change the behaviour of a relocatable link (@samp{-r}). The script +command @code{FORCE_GROUP_ALLOCATION} has the same +effect. @xref{Miscellaneous Commands}. + @cindex symbols, from command line @kindex --defsym=@var{symbol}=@var{exp} @item --defsym=@var{symbol}=@var{expression} @@ -3726,6 +3738,17 @@ This command has the same effect as the @samp{--no-define-common} command-line option: to make @code{ld} omit the assignment of addresses to common symbols even for a non-relocatable output file. +@item FORCE_GROUP_ALLOCATION +@kindex FORCE_GROUP_ALLOCATION +@cindex group allocation in linker script +@cindex section groups +@cindex COMDAT +This command has the same effect as the +@samp{--force-group-allocation} command-line option: to make +@command{ld} place section group members like normal input sections, +and to delete the section groups even if a relocatable output file is +specified (@samp{-r}). + @item INSERT [ AFTER | BEFORE ] @var{output_section} @kindex INSERT @cindex insert user script into default script diff --git a/ld/ldgram.y b/ld/ldgram.y index 849f272..4c1efdc 100644 --- a/ld/ldgram.y +++ b/ld/ldgram.y @@ -131,7 +131,7 @@ static int error_index; %token SORT_BY_INIT_PRIORITY %token '{' '}' %token SIZEOF_HEADERS OUTPUT_FORMAT FORCE_COMMON_ALLOCATION OUTPUT_ARCH -%token INHIBIT_COMMON_ALLOCATION +%token INHIBIT_COMMON_ALLOCATION FORCE_GROUP_ALLOCATION %token SEGMENT_START %token INCLUDE %token MEMORY @@ -336,6 +336,8 @@ ifile_p1: { ldfile_set_output_arch ($3, bfd_arch_unknown); } | FORCE_COMMON_ALLOCATION { command_line.force_common_definition = TRUE ; } + | FORCE_GROUP_ALLOCATION + { command_line.force_group_allocation = TRUE ; } | INHIBIT_COMMON_ALLOCATION { command_line.inhibit_common_definition = TRUE ; } | INPUT '(' input_list ')' diff --git a/ld/ldlang.c b/ld/ldlang.c index ed7e552..252400b 100644 --- a/ld/ldlang.c +++ b/ld/ldlang.c @@ -207,7 +207,7 @@ unique_section_p (const asection *sec, struct unique_sections *unam; const char *secnam; - if (bfd_link_relocatable (&link_info) + if (!link_info.resolve_section_groups && sec->owner != NULL && bfd_is_group_section (sec->owner, sec)) return !(os != NULL @@ -2349,6 +2349,12 @@ lang_add_section (lang_statement_list_type *ptr, if (strcmp (output->name, DISCARD_SECTION_NAME) == 0) discard = TRUE; + /* Discard the group descriptor sections when we're finally placing the + sections from within the group. */ + if ((section->flags & SEC_GROUP) == SEC_GROUP + && link_info.resolve_section_groups) + discard = TRUE; + /* Discard debugging sections if we are stripping debugging information. */ if ((link_info.strip == strip_debugger || link_info.strip == strip_all) @@ -2389,8 +2395,14 @@ lang_add_section (lang_statement_list_type *ptr, already been processed. One reason to do this is that on pe format targets, .text$foo sections go into .text and it's odd to see .text with SEC_LINK_ONCE set. */ - - if (!bfd_link_relocatable (&link_info)) + if ((flags & (SEC_LINK_ONCE | SEC_GROUP)) == (SEC_LINK_ONCE | SEC_GROUP)) + { + if (link_info.resolve_section_groups) + flags &= ~(SEC_LINK_ONCE | SEC_LINK_DUPLICATES | SEC_RELOC); + else + flags &= ~(SEC_LINK_DUPLICATES | SEC_RELOC); + } + else if (!bfd_link_relocatable (&link_info)) flags &= ~(SEC_LINK_ONCE | SEC_LINK_DUPLICATES | SEC_RELOC); switch (output->sectype) @@ -146,6 +146,7 @@ enum option_values OPTION_PRINT_MEMORY_USAGE, OPTION_REQUIRE_DEFINED_SYMBOL, OPTION_ORPHAN_HANDLING, + OPTION_FORCE_GROUP_ALLOCATION, }; /* The initial parser states. */ @@ -274,6 +274,7 @@ V_IDENTIFIER [*?.$_a-zA-Z\[\]\-\!\^\\]([*?.$_a-zA-Z0-9\[\]\-\!\^\\]|::)* <BOTH,SCRIPT>"CREATE_OBJECT_SYMBOLS" { RTOKEN(CREATE_OBJECT_SYMBOLS);} <BOTH,SCRIPT>"CONSTRUCTORS" { RTOKEN( CONSTRUCTORS);} <BOTH,SCRIPT>"FORCE_COMMON_ALLOCATION" { RTOKEN(FORCE_COMMON_ALLOCATION);} +<BOTH,SCRIPT>"FORCE_GROUP_ALLOCATION" { RTOKEN(FORCE_GROUP_ALLOCATION);} <BOTH,SCRIPT>"INHIBIT_COMMON_ALLOCATION" { RTOKEN(INHIBIT_COMMON_ALLOCATION);} <BOTH,SCRIPT>"SECTIONS" { RTOKEN(SECTIONS);} <BOTH,SCRIPT>"INSERT" { RTOKEN(INSERT_K);} diff --git a/ld/ldmain.c b/ld/ldmain.c index 2b3a591..ee5ab11 100644 --- a/ld/ldmain.c +++ b/ld/ldmain.c @@ -386,6 +386,12 @@ main (int argc, char **argv) info_msg ("\n==================================================\n"); } + if (command_line.force_group_allocation + || !bfd_link_relocatable (&link_info)) + link_info.resolve_section_groups = TRUE; + else + link_info.resolve_section_groups = FALSE; + if (command_line.print_output_format) info_msg ("%s\n", lang_get_output_target ()); diff --git a/ld/lexsup.c b/ld/lexsup.c index 0b7d497..95c7e59 100644 --- a/ld/lexsup.c +++ b/ld/lexsup.c @@ -112,6 +112,9 @@ static const struct ld_option ld_options[] = 'd', NULL, N_("Force common symbols to be defined"), ONE_DASH }, { {"dp", no_argument, NULL, 'd'}, '\0', NULL, NULL, ONE_DASH }, + { {"force-group-allocation", no_argument, NULL, + OPTION_FORCE_GROUP_ALLOCATION}, + '\0', NULL, N_("Force group members out of groups"), TWO_DASHES }, { {"entry", required_argument, NULL, 'e'}, 'e', N_("ADDRESS"), N_("Set start address"), TWO_DASHES }, { {"export-dynamic", no_argument, NULL, OPTION_EXPORT_DYNAMIC}, @@ -767,6 +770,9 @@ parse_args (unsigned argc, char **argv) case 'd': command_line.force_common_definition = TRUE; break; + case OPTION_FORCE_GROUP_ALLOCATION: + command_line.force_group_allocation = TRUE; + break; case OPTION_DEFSYM: lex_string = optarg; lex_redirect (optarg, "--defsym", ++defsym_count); diff --git a/ld/testsuite/ld-elf/group11.d b/ld/testsuite/ld-elf/group11.d new file mode 100644 index 0000000..245cf440 --- /dev/null +++ b/ld/testsuite/ld-elf/group11.d @@ -0,0 +1,6 @@ +#source: group1a.s +#source: group1b.s +#ld: -r --force-group-allocation +#readelf: -g + +There are no section groups in this file. diff --git a/ld/testsuite/ld-elf/group12.d b/ld/testsuite/ld-elf/group12.d new file mode 100644 index 0000000..3fa7be8 --- /dev/null +++ b/ld/testsuite/ld-elf/group12.d @@ -0,0 +1,6 @@ +#source: group1a.s +#source: group1b.s +#ld: -r -T group12.ld +#readelf: -g + +There are no section groups in this file. diff --git a/ld/testsuite/ld-elf/group12.ld b/ld/testsuite/ld-elf/group12.ld new file mode 100644 index 0000000..4a36ee5 --- /dev/null +++ b/ld/testsuite/ld-elf/group12.ld @@ -0,0 +1,14 @@ +FORCE_GROUP_ALLOCATION + +PHDRS +{ + header PT_PHDR PHDRS ; + image PT_LOAD PHDRS; +} + +SECTIONS +{ + . = 0x1000; + .text : { *(.text) *(.rodata.brlt) } :image :header + /DISCARD/ : { *(.dropme) *(.reginfo) *(.MIPS.abiflags) } +} |