2004-07-21  H.J. Lu  <hongjiu.lu@intel.com>

	* aout-adobe.c (aout_32_section_already_linked): Defined.
	* aout-target.h (MY_section_already_linked): Likewise.
	* aout-tic30.c (MY_section_already_linked): Likewise.
	* binary.c (binary_section_already_linked): Likewise.
	* bout.c (b_out_section_already_linked): Likewise.
	* coff-alpha.c (_bfd_ecoff_section_already_linked): Likewise.
	* coff-mips.c (_bfd_ecoff_section_already_linked): Likewise.
	* coffcode.h (coff_section_already_linked): Likewise.
	* i386msdos.c (msdos_section_already_linked): Likewise.
	* i386os9k.c (os9k_section_already_linked): Likewise.
	* ieee.c (ieee_section_already_linked): Likewise.
	* ihex.c (ihex_section_already_linked): Likewise.
	* mach-o.c (bfd_mach_o_section_already_linked): Likewise.
	* mmo.c (mmo_section_already_linked): Likewise.
	* nlm-target.h (nlm_section_already_linked): Likewise.
	* oasys.c (oasys_section_already_linked): Likewise.
	* pef.c (bfd_pef_section_already_linked): Likewise.
	* ppcboot.c (ppcboot_section_already_linked): Likewise.
	* som.c (som_bfd_discard_group): Likewise.
	* srec.c (srec_section_already_linked): Likewise.
	* tekhex.c (tekhex_section_already_linked): Likewise.
	* versados.c (versados_section_already_linked): Likewise.
	* vms.c (vms_section_already_linked): Likewise.
	* coff-target.h (_bfd_xcoff_section_already_linked): Likewise.
	* xsym.c (bfd_sym_section_already_linked): Likewise.

	* bfd-in.h (bfd_section_already_linked_table_init): New.
	(bfd_section_already_linked_table_free): Likewise.

	* coff-rs6000.c (rs6000coff_vec): Add
	_bfd_generic_section_already_linked.
	(pmac_xcoff_vec): Likewise.
	* coff64-rs6000.c (rs6000coff64_vec): Likewise.
	(aix5coff64_vec): Likewise.

	* elf-bfd.h (_bfd_elf_section_already_linked): New prototype.
	* elflink.c (_bfd_elf_section_already_linked): New function.

	* elfxx-target.h (bfd_elfNN_section_already_linked): Defined.

	* libbfd-in.h (_bfd_nolink_section_already_linked): Defined.
	(_bfd_generic_section_already_linked): New.
	(bfd_section_already_linked_hash_entry): Likewise.
	(bfd_section_already_linked): Likewise.
	(bfd_section_already_linked_table_lookup): Likewise.
	(bfd_section_already_linked_table_insert): Likewise.

	* linker.c (bfd_section_already_linked): New.
	(_bfd_section_already_linked_table): Likewise.
	(bfd_section_already_linked_table_lookup): Likewise.
	(bfd_section_already_linked_table_insert): Likewise.
	(already_linked_newfunc): Likewise.
	(bfd_section_already_linked_table_init): Likewise.
	(bfd_section_already_linked_table_free): Likewise.
	(_bfd_generic_section_already_linked): Likewise.

	* section.c (bfd_section): Remove comdat.
	(bfd_comdat_info): Moved to ...
	* bfd-in.h (coff_comdat_info): Here.
	(bfd_coff_get_comdat_section): New.
	* coffgen.c (bfd_coff_get_comdat_section): Likewise.
	* libcoff-in.h (coff_section_tdata): Add comdat.
	* coffcode.h (handle_COMDAT): Updated.
	* cofflink.c (coff_link_add_symbols): Likewise.
	* ecoff.c (bfd_debug_section): Likewise.

	* targets.c (bfd_target): Add _section_already_linked.
	(BFD_JUMP_TABLE_LINK): Updated.

	* bfd-in2.h: Regenerated.
	* libbfd.h: Likewise.
	* libcoff.h: Likewise.

binutils/

2004-07-21  H.J. Lu  <hongjiu.lu@intel.com>

	* objcopy.c (filter_symbols): Use bfd_coff_get_comdat_section
	to access comdat.
	* objdump.c (dump_section_header): Likewise.

ld/

2004-07-21  H.J. Lu  <hongjiu.lu@intel.com>

	* ldlang.c (already_linked_hash_entry): Removed.
	(already_linked): Likewise.
	(already_linked_table): Likewise.
	(section_already_linked): Call bfd_section_already_linked.
	(lang_process): Replace already_linked_table_init with
	bfd_section_already_linked_table_init and check return. Replace
	already_linked_table_free with bfd_section_already_linked_table_free.
This commit is contained in:
H.J. Lu 2004-07-21 15:42:58 +00:00
parent 76d7af2d04
commit 082b729701
48 changed files with 591 additions and 218 deletions

View File

@ -1,3 +1,78 @@
2004-07-21 H.J. Lu <hongjiu.lu@intel.com>
* aout-adobe.c (aout_32_section_already_linked): Defined.
* aout-target.h (MY_section_already_linked): Likewise.
* aout-tic30.c (MY_section_already_linked): Likewise.
* binary.c (binary_section_already_linked): Likewise.
* bout.c (b_out_section_already_linked): Likewise.
* coff-alpha.c (_bfd_ecoff_section_already_linked): Likewise.
* coff-mips.c (_bfd_ecoff_section_already_linked): Likewise.
* coffcode.h (coff_section_already_linked): Likewise.
* i386msdos.c (msdos_section_already_linked): Likewise.
* i386os9k.c (os9k_section_already_linked): Likewise.
* ieee.c (ieee_section_already_linked): Likewise.
* ihex.c (ihex_section_already_linked): Likewise.
* mach-o.c (bfd_mach_o_section_already_linked): Likewise.
* mmo.c (mmo_section_already_linked): Likewise.
* nlm-target.h (nlm_section_already_linked): Likewise.
* oasys.c (oasys_section_already_linked): Likewise.
* pef.c (bfd_pef_section_already_linked): Likewise.
* ppcboot.c (ppcboot_section_already_linked): Likewise.
* som.c (som_bfd_discard_group): Likewise.
* srec.c (srec_section_already_linked): Likewise.
* tekhex.c (tekhex_section_already_linked): Likewise.
* versados.c (versados_section_already_linked): Likewise.
* vms.c (vms_section_already_linked): Likewise.
* coff-target.h (_bfd_xcoff_section_already_linked): Likewise.
* xsym.c (bfd_sym_section_already_linked): Likewise.
* bfd-in.h (bfd_section_already_linked_table_init): New.
(bfd_section_already_linked_table_free): Likewise.
* coff-rs6000.c (rs6000coff_vec): Add
_bfd_generic_section_already_linked.
(pmac_xcoff_vec): Likewise.
* coff64-rs6000.c (rs6000coff64_vec): Likewise.
(aix5coff64_vec): Likewise.
* elf-bfd.h (_bfd_elf_section_already_linked): New prototype.
* elflink.c (_bfd_elf_section_already_linked): New function.
* elfxx-target.h (bfd_elfNN_section_already_linked): Defined.
* libbfd-in.h (_bfd_nolink_section_already_linked): Defined.
(_bfd_generic_section_already_linked): New.
(bfd_section_already_linked_hash_entry): Likewise.
(bfd_section_already_linked): Likewise.
(bfd_section_already_linked_table_lookup): Likewise.
(bfd_section_already_linked_table_insert): Likewise.
* linker.c (bfd_section_already_linked): New.
(_bfd_section_already_linked_table): Likewise.
(bfd_section_already_linked_table_lookup): Likewise.
(bfd_section_already_linked_table_insert): Likewise.
(already_linked_newfunc): Likewise.
(bfd_section_already_linked_table_init): Likewise.
(bfd_section_already_linked_table_free): Likewise.
(_bfd_generic_section_already_linked): Likewise.
* section.c (bfd_section): Remove comdat.
(bfd_comdat_info): Moved to ...
* bfd-in.h (coff_comdat_info): Here.
(bfd_coff_get_comdat_section): New.
* coffgen.c (bfd_coff_get_comdat_section): Likewise.
* libcoff-in.h (coff_section_tdata): Add comdat.
* coffcode.h (handle_COMDAT): Updated.
* cofflink.c (coff_link_add_symbols): Likewise.
* ecoff.c (bfd_debug_section): Likewise.
* targets.c (bfd_target): Add _section_already_linked.
(BFD_JUMP_TABLE_LINK): Updated.
* bfd-in2.h: Regenerated.
* libbfd.h: Likewise.
* libcoff.h: Likewise.
2003-07-21 Paul Brook <paul@codesourcery.com>
* elflink.c (elf_get_linked_section_vma, compare_link_order,

View File

@ -518,6 +518,8 @@ aout_adobe_sizeof_headers (ignore_abfd, ignore)
#define aout_32_bfd_merge_sections bfd_generic_merge_sections
#define aout_32_bfd_is_group_section bfd_generic_is_group_section
#define aout_32_bfd_discard_group bfd_generic_discard_group
#define aout_32_section_already_linked \
_bfd_generic_section_already_linked
#define aout_32_bfd_link_hash_table_create \
_bfd_generic_link_hash_table_create
#define aout_32_bfd_link_hash_table_free \

View File

@ -519,6 +519,10 @@ MY_bfd_final_link (abfd, info)
#ifndef MY_bfd_discard_group
#define MY_bfd_discard_group bfd_generic_discard_group
#endif
#ifndef MY_section_already_linked
#define MY_section_already_linked \
_bfd_generic_section_already_linked
#endif
#ifndef MY_bfd_reloc_type_lookup
#define MY_bfd_reloc_type_lookup NAME(aout,reloc_type_lookup)
#endif

View File

@ -976,6 +976,10 @@ tic30_aout_set_arch_mach (abfd, arch, machine)
#ifndef MY_bfd_discard_group
#define MY_bfd_discard_group bfd_generic_discard_group
#endif
#ifndef MY_section_already_linked
#define MY_section_already_linked \
_bfd_generic_section_already_linked
#endif
#ifndef MY_bfd_reloc_type_lookup
#define MY_bfd_reloc_type_lookup tic30_aout_reloc_type_lookup
#endif

View File

@ -559,6 +559,9 @@ void bfd_putl16 (bfd_vma, void *);
bfd_uint64_t bfd_get_bits (const void *, int, bfd_boolean);
void bfd_put_bits (bfd_uint64_t, void *, int, bfd_boolean);
extern bfd_boolean bfd_section_already_linked_table_init (void);
extern void bfd_section_already_linked_table_free (void);
/* Externally visible ECOFF routines. */
@ -847,3 +850,23 @@ extern void bfd_elf32_ia64_after_parse
extern void bfd_elf64_ia64_after_parse
(int);
/* This structure is used for a comdat section, as in PE. A comdat
section is associated with a particular symbol. When the linker
sees a comdat section, it keeps only one of the sections with a
given name and associated with a given symbol. */
struct coff_comdat_info
{
/* The name of the symbol associated with a comdat section. */
const char *name;
/* The local symbol table index of the symbol associated with a
comdat section. This is only meaningful to the object file format
specific code; it is not an index into the list returned by
bfd_canonicalize_symtab. */
long symbol;
};
extern struct coff_comdat_info *bfd_coff_get_comdat_section
(bfd *, struct bfd_section *);

View File

@ -566,6 +566,9 @@ void bfd_putl16 (bfd_vma, void *);
bfd_uint64_t bfd_get_bits (const void *, int, bfd_boolean);
void bfd_put_bits (bfd_uint64_t, void *, int, bfd_boolean);
extern bfd_boolean bfd_section_already_linked_table_init (void);
extern void bfd_section_already_linked_table_free (void);
/* Externally visible ECOFF routines. */
@ -854,6 +857,26 @@ extern void bfd_elf32_ia64_after_parse
extern void bfd_elf64_ia64_after_parse
(int);
/* This structure is used for a comdat section, as in PE. A comdat
section is associated with a particular symbol. When the linker
sees a comdat section, it keeps only one of the sections with a
given name and associated with a given symbol. */
struct coff_comdat_info
{
/* The name of the symbol associated with a comdat section. */
const char *name;
/* The local symbol table index of the symbol associated with a
comdat section. This is only meaningful to the object file format
specific code; it is not an index into the list returned by
bfd_canonicalize_symtab. */
long symbol;
};
extern struct coff_comdat_info *bfd_coff_get_comdat_section
(bfd *, struct bfd_section *);
/* Extracted from init.c. */
void bfd_init (void);
@ -1019,23 +1042,6 @@ long bfd_get_size (bfd *abfd);
/* Extracted from bfdwin.c. */
/* Extracted from section.c. */
/* This structure is used for a comdat section, as in PE. A comdat
section is associated with a particular symbol. When the linker
sees a comdat section, it keeps only one of the sections with a
given name and associated with a given symbol. */
struct bfd_comdat_info
{
/* The name of the symbol associated with a comdat section. */
const char *name;
/* The local symbol table index of the symbol associated with a
comdat section. This is only meaningful to the object file format
specific code; it is not an index into the list returned by
bfd_canonicalize_symtab. */
long symbol;
};
typedef struct bfd_section
{
/* The name of the section; the name isn't a copy, the pointer is
@ -1359,9 +1365,6 @@ typedef struct bfd_section
/* Entity size for merging purposes. */
unsigned int entsize;
/* Optional information about a COMDAT entry; NULL if not COMDAT. */
struct bfd_comdat_info *comdat;
/* Points to the kept section if this section is a link-once section,
and is discarded. */
struct bfd_section *kept_section;
@ -4430,7 +4433,8 @@ typedef struct bfd_target
NAME##_bfd_gc_sections, \
NAME##_bfd_merge_sections, \
NAME##_bfd_is_group_section, \
NAME##_bfd_discard_group
NAME##_bfd_discard_group, \
NAME##_section_already_linked \
int (*_bfd_sizeof_headers) (bfd *, bfd_boolean);
bfd_byte * (*_bfd_get_relocated_section_contents)
@ -4473,6 +4477,10 @@ typedef struct bfd_target
/* Discard members of a group. */
bfd_boolean (*_bfd_discard_group) (bfd *, struct bfd_section *);
/* Check if SEC has been already linked during a reloceatable or
final link. */
void (*_section_already_linked) (bfd *, struct bfd_section *);
/* Routines to handle dynamic symbols and relocs. */
#define BFD_JUMP_TABLE_DYNAMIC(NAME) \
NAME##_get_dynamic_symtab_upper_bound, \
@ -4530,6 +4538,11 @@ bfd_boolean bfd_link_split_section (bfd *abfd, asection *sec);
#define bfd_link_split_section(abfd, sec) \
BFD_SEND (abfd, _bfd_link_split_section, (abfd, sec))
void bfd_section_already_linked (bfd *abfd, asection *sec);
#define bfd_section_already_linked(abfd, sec) \
BFD_SEND (abfd, _section_already_linked, (abfd, sec))
/* Extracted from simple.c. */
bfd_byte *bfd_simple_get_relocated_section_contents
(bfd *abfd, asection *sec, bfd_byte *outbuf, asymbol **symbol_table);

View File

@ -341,6 +341,8 @@ binary_sizeof_headers (abfd, exec)
#define binary_bfd_merge_sections bfd_generic_merge_sections
#define binary_bfd_is_group_section bfd_generic_is_group_section
#define binary_bfd_discard_group bfd_generic_discard_group
#define binary_section_already_linked \
_bfd_generic_section_already_linked
#define binary_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define binary_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define binary_bfd_link_just_syms _bfd_generic_link_just_syms

View File

@ -1487,6 +1487,8 @@ b_out_bfd_get_relocated_section_contents (output_bfd, link_info, link_order,
#define b_out_bfd_merge_sections bfd_generic_merge_sections
#define b_out_bfd_is_group_section bfd_generic_is_group_section
#define b_out_bfd_discard_group bfd_generic_discard_group
#define b_out_section_already_linked \
_bfd_generic_section_already_linked
#define aout_32_get_section_contents_in_window \
_bfd_generic_get_section_contents_in_window

View File

@ -2356,6 +2356,8 @@ static const struct ecoff_backend_data alpha_ecoff_backend_data =
#define _bfd_ecoff_bfd_merge_sections bfd_generic_merge_sections
#define _bfd_ecoff_bfd_is_group_section bfd_generic_is_group_section
#define _bfd_ecoff_bfd_discard_group bfd_generic_discard_group
#define _bfd_ecoff_section_already_linked \
_bfd_generic_section_already_linked
const bfd_target ecoffalpha_little_vec =
{

View File

@ -1395,6 +1395,8 @@ static const struct ecoff_backend_data mips_ecoff_backend_data =
#define _bfd_ecoff_bfd_is_group_section bfd_generic_is_group_section
#define _bfd_ecoff_bfd_discard_group bfd_generic_discard_group
#define _bfd_ecoff_section_already_linked \
_bfd_generic_section_already_linked
extern const bfd_target ecoff_big_vec;

View File

@ -4198,6 +4198,7 @@ const bfd_target rs6000coff_vec =
bfd_generic_merge_sections,
bfd_generic_is_group_section,
bfd_generic_discard_group,
_bfd_generic_section_already_linked,
/* Dynamic */
_bfd_xcoff_get_dynamic_symtab_upper_bound,
@ -4443,6 +4444,7 @@ const bfd_target pmac_xcoff_vec =
bfd_generic_merge_sections,
bfd_generic_is_group_section,
bfd_generic_discard_group,
_bfd_generic_section_already_linked,
/* Dynamic */
_bfd_xcoff_get_dynamic_symtab_upper_bound,

View File

@ -2739,6 +2739,7 @@ const bfd_target rs6000coff64_vec =
bfd_generic_merge_sections,
bfd_generic_is_group_section,
bfd_generic_discard_group,
_bfd_generic_section_already_linked,
/* Dynamic */
_bfd_xcoff_get_dynamic_symtab_upper_bound,
@ -2985,6 +2986,7 @@ const bfd_target aix5coff64_vec =
bfd_generic_merge_sections,
bfd_generic_is_group_section,
bfd_generic_discard_group,
_bfd_generic_section_already_linked,
/* Dynamic */
_bfd_xcoff_get_dynamic_symtab_upper_bound,

View File

@ -965,12 +965,13 @@ handle_COMDAT (abfd, sec_flags, hdr, name, section)
Intel puts the two adjacent, but Alpha (at
least) spreads them out. */
amt = sizeof (struct bfd_comdat_info);
section->comdat = bfd_alloc (abfd, amt);
if (section->comdat == NULL)
amt = sizeof (struct coff_comdat_info);
coff_section_data (abfd, section)->comdat
= bfd_alloc (abfd, amt);
if (coff_section_data (abfd, section)->comdat == NULL)
abort ();
section->comdat->symbol =
coff_section_data (abfd, section)->comdat->symbol =
(esym - esymstart) / bfd_coff_symesz (abfd);
amt = strlen (symname) + 1;
@ -979,7 +980,8 @@ handle_COMDAT (abfd, sec_flags, hdr, name, section)
abort ();
strcpy (newname, symname);
section->comdat->name = newname;
coff_section_data (abfd, section)->comdat->name
= newname;
}
goto breakloop;
@ -5586,6 +5588,11 @@ static const bfd_coff_backend_data ticoff1_swap_table =
#define coff_bfd_discard_group bfd_generic_discard_group
#endif
#ifndef coff_section_already_linked
#define coff_section_already_linked \
_bfd_generic_section_already_linked
#endif
#define CREATE_BIG_COFF_TARGET_VEC(VAR, NAME, EXTRA_O_FLAGS, EXTRA_S_FLAGS, UNDER, ALTERNATIVE, SWAP_TABLE) \
const bfd_target VAR = \
{ \

View File

@ -2496,3 +2496,12 @@ bfd_coff_set_symbol_class (abfd, symbol, class)
return TRUE;
}
struct coff_comdat_info *
bfd_coff_get_comdat_section (bfd *abfd, struct bfd_section *sec)
{
if (bfd_get_flavour (abfd) == bfd_target_coff_flavour)
return coff_section_data (abfd, sec)->comdat;
else
return NULL;
}

View File

@ -435,18 +435,18 @@ coff_link_add_symbols (bfd *abfd,
if (obj_pe (abfd)
&& (classification == COFF_SYMBOL_GLOBAL
|| classification == COFF_SYMBOL_PE_SECTION)
&& section->comdat != NULL
&& coff_section_data (abfd, section)->comdat != NULL
&& strncmp (name, "??_", 3) == 0
&& strcmp (name, section->comdat->name) == 0)
&& strcmp (name, coff_section_data (abfd, section)->comdat->name) == 0)
{
if (*sym_hash == NULL)
*sym_hash = coff_link_hash_lookup (coff_hash_table (info),
name, FALSE, copy, FALSE);
if (*sym_hash != NULL
&& (*sym_hash)->root.type == bfd_link_hash_defined
&& (*sym_hash)->root.u.def.section->comdat != NULL
&& strcmp ((*sym_hash)->root.u.def.section->comdat->name,
section->comdat->name) == 0)
&& coff_section_data (abfd, (*sym_hash)->root.u.def.section)->comdat != NULL
&& strcmp (coff_section_data (abfd, (*sym_hash)->root.u.def.section)->comdat->name,
coff_section_data (abfd, section)->comdat->name) == 0)
addit = FALSE;
}

View File

@ -92,8 +92,8 @@ static asection bfd_debug_section =
NULL, NULL, 0, 0, 0,
/* line_filepos, userdata, contents, lineno, lineno_count, */
0, NULL, NULL, NULL, 0,
/* entsize, comdat, kept_section, moving_line_filepos, */
0, NULL, NULL, 0,
/* entsize, kept_section, moving_line_filepos, */
0, NULL, 0,
/* target_index, used_by_bfd, constructor_chain, owner, */
0, NULL, NULL, NULL,
/* symbol, */

View File

@ -1394,6 +1394,8 @@ extern bfd_boolean bfd_elf_is_group_section
(bfd *, const struct bfd_section *);
extern bfd_boolean bfd_elf_discard_group
(bfd *, struct bfd_section *);
extern void _bfd_elf_section_already_linked
(bfd *, struct bfd_section *);
extern void bfd_elf_set_group_contents
(bfd *, asection *, void *);
extern void _bfd_elf_link_just_syms

View File

@ -9154,3 +9154,89 @@ bfd_elf_discard_info (bfd *output_bfd, struct bfd_link_info *info)
return ret;
}
void
_bfd_elf_section_already_linked (bfd *abfd, struct bfd_section * sec)
{
flagword flags;
const char *name;
struct bfd_section_already_linked *l;
struct bfd_section_already_linked_hash_entry *already_linked_list;
flags = sec->flags;
if ((flags & SEC_LINK_ONCE) == 0)
return;
/* FIXME: When doing a relocatable link, we may have trouble
copying relocations in other sections that refer to local symbols
in the section being discarded. Those relocations will have to
be converted somehow; as of this writing I'm not sure that any of
the backends handle that correctly.
It is tempting to instead not discard link once sections when
doing a relocatable link (technically, they should be discarded
whenever we are building constructors). However, that fails,
because the linker winds up combining all the link once sections
into a single large link once section, which defeats the purpose
of having link once sections in the first place.
Also, not merging link once sections in a relocatable link
causes trouble for MIPS ELF, which relies on link once semantics
to handle the .reginfo section correctly. */
name = bfd_get_section_name (abfd, sec);
already_linked_list = bfd_section_already_linked_table_lookup (name);
for (l = already_linked_list->entry; l != NULL; l = l->next)
{
/* We may have 3 different sections on the list: group section,
comdat section and linkonce section. SEC may be a linkonce or
group section. We match a group section with a group section,
a linkonce section with a linkonce section, and ignore comdat
section. */
if ((sec->flags & SEC_GROUP) == (l->sec->flags & SEC_GROUP)
&& bfd_coff_get_comdat_section (l->sec->owner, l->sec) == NULL)
{
/* The section has already been linked. See if we should
issue a warning. */
switch (flags & SEC_LINK_DUPLICATES)
{
default:
abort ();
case SEC_LINK_DUPLICATES_DISCARD:
break;
case SEC_LINK_DUPLICATES_ONE_ONLY:
(*_bfd_error_handler)
(_("%s: %s: warning: ignoring duplicate section `%s'\n"),
bfd_archive_filename (abfd), name);
break;
case SEC_LINK_DUPLICATES_SAME_SIZE:
if (sec->size != l->sec->size)
(*_bfd_error_handler)
(_("%s: %s: warning: duplicate section `%s' has different size\n"),
bfd_archive_filename (abfd), name);
break;
}
/* Set the output_section field so that lang_add_section
does not create a lang_input_section structure for this
section. Since there might be a symbol in the section
being discarded, we must retain a pointer to the section
which we are really going to use. */
sec->output_section = bfd_abs_section_ptr;
sec->kept_section = l->sec;
if (flags & SEC_GROUP)
bfd_elf_discard_group (abfd, sec);
return;
}
}
/* This is the first section with this name. Record it. */
bfd_section_already_linked_table_insert (already_linked_list, sec);
}

View File

@ -144,6 +144,11 @@
#define bfd_elfNN_bfd_discard_group bfd_elf_discard_group
#endif
#ifndef bfd_elfNN_section_already_linked
#define bfd_elfNN_section_already_linked \
_bfd_elf_section_already_linked
#endif
#ifndef bfd_elfNN_bfd_make_debug_symbol
#define bfd_elfNN_bfd_make_debug_symbol \
((asymbol * (*) (bfd *, void *, unsigned long)) bfd_nullvoidptr)

View File

@ -177,6 +177,8 @@ msdos_set_section_contents (abfd, section, location, offset, count)
#define msdos_bfd_merge_sections bfd_generic_merge_sections
#define msdos_bfd_is_group_section bfd_generic_is_group_section
#define msdos_bfd_discard_group bfd_generic_discard_group
#define msdos_section_already_linked \
_bfd_generic_section_already_linked
#define msdos_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define msdos_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define msdos_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -335,6 +335,8 @@ os9k_sizeof_headers (ignore_abfd, ignore)
#define os9k_bfd_merge_sections bfd_generic_merge_sections
#define os9k_bfd_is_group_section bfd_generic_is_group_section
#define os9k_bfd_discard_group bfd_generic_discard_group
#define os9k_section_already_linked \
_bfd_generic_section_already_linked
#define os9k_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define os9k_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define os9k_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -4039,6 +4039,8 @@ ieee_bfd_debug_info_accumulate (abfd, section)
#define ieee_bfd_merge_sections bfd_generic_merge_sections
#define ieee_bfd_is_group_section bfd_generic_is_group_section
#define ieee_bfd_discard_group bfd_generic_discard_group
#define ieee_section_already_linked \
_bfd_generic_section_already_linked
#define ieee_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define ieee_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define ieee_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -990,6 +990,8 @@ ihex_sizeof_headers (abfd, exec)
#define ihex_bfd_merge_sections bfd_generic_merge_sections
#define ihex_bfd_is_group_section bfd_generic_is_group_section
#define ihex_bfd_discard_group bfd_generic_discard_group
#define ihex_section_already_linked \
_bfd_generic_section_already_linked
#define ihex_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define ihex_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define ihex_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -375,6 +375,8 @@ extern bfd_boolean _bfd_generic_set_section_contents
((bfd_boolean (*) (bfd *, struct bfd_link_info *)) bfd_false)
#define _bfd_nolink_bfd_link_split_section \
((bfd_boolean (*) (bfd *, struct bfd_section *)) bfd_false)
#define _bfd_nolink_section_already_linked \
((void (*) (bfd *, struct bfd_section *)) bfd_void)
/* Routines to use for BFD_JUMP_TABLE_DYNAMIC for targets which do not
have dynamic symbols or relocs. Use BFD_JUMP_TABLE_DYNAMIC
@ -474,6 +476,9 @@ extern bfd_boolean _bfd_generic_final_link
extern bfd_boolean _bfd_generic_link_split_section
(bfd *, struct bfd_section *);
extern void _bfd_generic_section_already_linked
(bfd *, struct bfd_section *);
/* Generic reloc_link_order processing routine. */
extern bfd_boolean _bfd_generic_reloc_link_order
(bfd *, struct bfd_link_info *, asection *, struct bfd_link_order *);
@ -653,3 +658,24 @@ extern bfd_boolean _bfd_sh_align_load_span
bfd_boolean (*) (bfd *, asection *, void *, bfd_byte *, bfd_vma),
void *, bfd_vma **, bfd_vma *, bfd_vma, bfd_vma, bfd_boolean *);
#endif
/* This is the shape of the elements inside the already_linked hash
table. It maps a name onto a list of already_linked elements with
the same name. */
struct bfd_section_already_linked_hash_entry
{
struct bfd_hash_entry root;
struct bfd_section_already_linked *entry;
};
struct bfd_section_already_linked
{
struct bfd_section_already_linked *next;
asection *sec;
};
extern struct bfd_section_already_linked_hash_entry *
bfd_section_already_linked_table_lookup (const char *);
extern void bfd_section_already_linked_table_insert
(struct bfd_section_already_linked_hash_entry *, asection *);

View File

@ -380,6 +380,8 @@ extern bfd_boolean _bfd_generic_set_section_contents
((bfd_boolean (*) (bfd *, struct bfd_link_info *)) bfd_false)
#define _bfd_nolink_bfd_link_split_section \
((bfd_boolean (*) (bfd *, struct bfd_section *)) bfd_false)
#define _bfd_nolink_section_already_linked \
((void (*) (bfd *, struct bfd_section *)) bfd_void)
/* Routines to use for BFD_JUMP_TABLE_DYNAMIC for targets which do not
have dynamic symbols or relocs. Use BFD_JUMP_TABLE_DYNAMIC
@ -479,6 +481,9 @@ extern bfd_boolean _bfd_generic_final_link
extern bfd_boolean _bfd_generic_link_split_section
(bfd *, struct bfd_section *);
extern void _bfd_generic_section_already_linked
(bfd *, struct bfd_section *);
/* Generic reloc_link_order processing routine. */
extern bfd_boolean _bfd_generic_reloc_link_order
(bfd *, struct bfd_link_info *, asection *, struct bfd_link_order *);
@ -658,6 +663,27 @@ extern bfd_boolean _bfd_sh_align_load_span
bfd_boolean (*) (bfd *, asection *, void *, bfd_byte *, bfd_vma),
void *, bfd_vma **, bfd_vma *, bfd_vma, bfd_vma, bfd_boolean *);
#endif
/* This is the shape of the elements inside the already_linked hash
table. It maps a name onto a list of already_linked elements with
the same name. */
struct bfd_section_already_linked_hash_entry
{
struct bfd_hash_entry root;
struct bfd_section_already_linked *entry;
};
struct bfd_section_already_linked
{
struct bfd_section_already_linked *next;
asection *sec;
};
extern struct bfd_section_already_linked_hash_entry *
bfd_section_already_linked_table_lookup (const char *);
extern void bfd_section_already_linked_table_insert
(struct bfd_section_already_linked_hash_entry *, asection *);
/* Extracted from init.c. */
/* Extracted from libbfd.c. */
bfd_boolean bfd_write_bigendian_4byte_int (bfd *, unsigned int);

View File

@ -194,6 +194,8 @@ struct coff_section_tdata
bfd_vma offset;
unsigned int i;
const char *function;
/* Optional information about a COMDAT entry; NULL if not COMDAT. */
struct coff_comdat_info *comdat;
int line_base;
/* A pointer used for .stab linking optimizations. */
PTR stab_info;

View File

@ -198,6 +198,8 @@ struct coff_section_tdata
bfd_vma offset;
unsigned int i;
const char *function;
/* Optional information about a COMDAT entry; NULL if not COMDAT. */
struct coff_comdat_info *comdat;
int line_base;
/* A pointer used for .stab linking optimizations. */
PTR stab_info;

View File

@ -2827,3 +2827,197 @@ _bfd_generic_link_split_section (bfd *abfd ATTRIBUTE_UNUSED,
{
return FALSE;
}
/*
FUNCTION
bfd_section_already_linked
SYNOPSIS
void bfd_section_already_linked (bfd *abfd, asection *sec);
DESCRIPTION
Check if @var{sec} has been already linked during a reloceatable
or final link.
.#define bfd_section_already_linked(abfd, sec) \
. BFD_SEND (abfd, _section_already_linked, (abfd, sec))
.
*/
/* Sections marked with the SEC_LINK_ONCE flag should only be linked
once into the output. This routine checks each section, and
arrange to discard it if a section of the same name has already
been linked. This code assumes that all relevant sections have the
SEC_LINK_ONCE flag set; that is, it does not depend solely upon the
section name. bfd_section_already_linked is called via
bfd_map_over_sections. */
/* The hash table. */
static struct bfd_hash_table _bfd_section_already_linked_table;
/* Support routines for the hash table used by section_already_linked,
initialize the table, lookup, fill in an entry and remove the
table. */
struct bfd_section_already_linked_hash_entry *
bfd_section_already_linked_table_lookup (const char *name)
{
return ((struct bfd_section_already_linked_hash_entry *)
bfd_hash_lookup (&_bfd_section_already_linked_table, name,
TRUE, FALSE));
}
void
bfd_section_already_linked_table_insert
(struct bfd_section_already_linked_hash_entry *already_linked_list,
asection *sec)
{
struct bfd_section_already_linked *l;
/* Allocate the memory from the same obstack as the hash table is
kept in. */
l = bfd_hash_allocate (&_bfd_section_already_linked_table, sizeof *l);
l->sec = sec;
l->next = already_linked_list->entry;
already_linked_list->entry = l;
}
static struct bfd_hash_entry *
already_linked_newfunc (struct bfd_hash_entry *entry ATTRIBUTE_UNUSED,
struct bfd_hash_table *table,
const char *string ATTRIBUTE_UNUSED)
{
struct bfd_section_already_linked_hash_entry *ret =
bfd_hash_allocate (table, sizeof *ret);
ret->entry = NULL;
return &ret->root;
}
bfd_boolean
bfd_section_already_linked_table_init (void)
{
return bfd_hash_table_init_n (&_bfd_section_already_linked_table,
already_linked_newfunc, 42);
}
void
bfd_section_already_linked_table_free (void)
{
bfd_hash_table_free (&_bfd_section_already_linked_table);
}
/* This is used on non-ELF inputs. */
void
_bfd_generic_section_already_linked (bfd *abfd, asection *sec)
{
flagword flags;
const char *name;
struct bfd_section_already_linked *l;
struct bfd_section_already_linked_hash_entry *already_linked_list;
flags = sec->flags;
if ((flags & SEC_LINK_ONCE) == 0)
return;
/* FIXME: When doing a relocatable link, we may have trouble
copying relocations in other sections that refer to local symbols
in the section being discarded. Those relocations will have to
be converted somehow; as of this writing I'm not sure that any of
the backends handle that correctly.
It is tempting to instead not discard link once sections when
doing a relocatable link (technically, they should be discarded
whenever we are building constructors). However, that fails,
because the linker winds up combining all the link once sections
into a single large link once section, which defeats the purpose
of having link once sections in the first place. */
name = bfd_get_section_name (abfd, sec);
already_linked_list = bfd_section_already_linked_table_lookup (name);
for (l = already_linked_list->entry; l != NULL; l = l->next)
{
bfd_boolean skip = FALSE;
struct coff_comdat_info *s_comdat
= bfd_coff_get_comdat_section (abfd, sec);
struct coff_comdat_info *l_comdat
= bfd_coff_get_comdat_section (l->sec->owner, l->sec);
/* We may have 3 different sections on the list: group section,
comdat section and linkonce section. SEC may be a linkonce or
comdat section. We always ignore group section. For non-COFF
inputs, we also ignore comdat section.
FIXME: Is that safe to match a linkonce section with a comdat
section for COFF inputs? */
if ((l->sec->flags & SEC_GROUP) != 0)
skip = TRUE;
else if (bfd_get_flavour (abfd) == bfd_target_coff_flavour)
{
if (s_comdat != NULL
&& l_comdat != NULL
&& strcmp (s_comdat->name, l_comdat->name) != 0)
skip = TRUE;
}
else if (l_comdat != NULL)
skip = TRUE;
if (!skip)
{
/* The section has already been linked. See if we should
issue a warning. */
switch (flags & SEC_LINK_DUPLICATES)
{
default:
abort ();
case SEC_LINK_DUPLICATES_DISCARD:
break;
case SEC_LINK_DUPLICATES_ONE_ONLY:
if (s_comdat == NULL)
(*_bfd_error_handler)
(_("%s: %s: warning: ignoring duplicate section `%s'\n"),
bfd_archive_filename (abfd), name);
else
(*_bfd_error_handler)
(_("%s: %s: warning: ignoring duplicate `%s' section symbol `%s'\n"),
bfd_archive_filename (abfd), name, s_comdat->name);
break;
case SEC_LINK_DUPLICATES_SAME_CONTENTS:
/* FIXME: We should really dig out the contents of both
sections and memcmp them. The COFF/PE spec says that
the Microsoft linker does not implement this
correctly, so I'm not going to bother doing it
either. */
/* Fall through. */
case SEC_LINK_DUPLICATES_SAME_SIZE:
if (sec->size != l->sec->size)
(*_bfd_error_handler)
(_("%s: %s: warning: duplicate section `%s' has different size\n"),
bfd_archive_filename (abfd), name);
break;
}
/* Set the output_section field so that lang_add_section
does not create a lang_input_section structure for this
section. Since there might be a symbol in the section
being discarded, we must retain a pointer to the section
which we are really going to use. */
sec->output_section = bfd_abs_section_ptr;
sec->kept_section = l->sec;
return;
}
}
/* This is the first section with this name. Record it. */
bfd_section_already_linked_table_insert (already_linked_list, sec);
}

View File

@ -70,6 +70,8 @@
#define bfd_mach_o_bfd_merge_sections bfd_generic_merge_sections
#define bfd_mach_o_bfd_is_group_section bfd_generic_is_group_section
#define bfd_mach_o_bfd_discard_group bfd_generic_discard_group
#define bfd_mach_o_section_already_linked \
_bfd_generic_section_already_linked
#define bfd_mach_o_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
static bfd_boolean bfd_mach_o_bfd_copy_private_symbol_data

View File

@ -3286,6 +3286,8 @@ mmo_canonicalize_reloc (abfd, section, relptr, symbols)
#define mmo_bfd_merge_sections bfd_generic_merge_sections
#define mmo_bfd_is_group_section bfd_generic_is_group_section
#define mmo_bfd_discard_group bfd_generic_discard_group
#define mmo_section_already_linked \
_bfd_generic_section_already_linked
/* objcopy will be upset if we return -1 from bfd_get_reloc_upper_bound by
using BFD_JUMP_TABLE_RELOCS (_bfd_norelocs) rather than 0. FIXME: Most

View File

@ -46,6 +46,8 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#define nlm_bfd_merge_sections bfd_generic_merge_sections
#define nlm_bfd_is_group_section bfd_generic_is_group_section
#define nlm_bfd_discard_group bfd_generic_discard_group
#define nlm_section_already_linked \
_bfd_generic_section_already_linked
#define nlm_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define nlm_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define nlm_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -1508,6 +1508,8 @@ oasys_sizeof_headers (abfd, exec)
#define oasys_bfd_merge_sections bfd_generic_merge_sections
#define oasys_bfd_is_group_section bfd_generic_is_group_section
#define oasys_bfd_discard_group bfd_generic_discard_group
#define oasys_section_already_linked \
_bfd_generic_section_already_linked
#define oasys_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define oasys_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define oasys_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -54,6 +54,7 @@
#define bfd_pef_bfd_merge_sections bfd_generic_merge_sections
#define bfd_pef_bfd_is_group_section bfd_generic_is_group_section
#define bfd_pef_bfd_discard_group bfd_generic_discard_group
#define bfd_pef_section_already_linked _bfd_generic_section_already_linked
#define bfd_pef_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define bfd_pef_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define bfd_pef_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -471,6 +471,8 @@ ppcboot_bfd_print_private_bfd_data (abfd, farg)
#define ppcboot_bfd_merge_sections bfd_generic_merge_sections
#define ppcboot_bfd_is_group_section bfd_generic_is_group_section
#define ppcboot_bfd_discard_group bfd_generic_discard_group
#define ppcboot_section_already_linked \
_bfd_generic_section_already_linked
#define ppcboot_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define ppcboot_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define ppcboot_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -149,23 +149,6 @@ SUBSECTION
CODE_FRAGMENT
.
.{* This structure is used for a comdat section, as in PE. A comdat
. section is associated with a particular symbol. When the linker
. sees a comdat section, it keeps only one of the sections with a
. given name and associated with a given symbol. *}
.
.struct bfd_comdat_info
.{
. {* The name of the symbol associated with a comdat section. *}
. const char *name;
.
. {* The local symbol table index of the symbol associated with a
. comdat section. This is only meaningful to the object file format
. specific code; it is not an index into the list returned by
. bfd_canonicalize_symtab. *}
. long symbol;
.};
.
.typedef struct bfd_section
.{
. {* The name of the section; the name isn't a copy, the pointer is
@ -489,9 +472,6 @@ CODE_FRAGMENT
. {* Entity size for merging purposes. *}
. unsigned int entsize;
.
. {* Optional information about a COMDAT entry; NULL if not COMDAT. *}
. struct bfd_comdat_info *comdat;
.
. {* Points to the kept section if this section is a link-once section,
. and is discarded. *}
. struct bfd_section *kept_section;
@ -634,8 +614,8 @@ static const asymbol global_syms[] =
/* line_filepos, userdata, contents, lineno, lineno_count, */ \
0, NULL, NULL, NULL, 0, \
\
/* entsize, comdat, kept_section, moving_line_filepos, */ \
0, NULL, NULL, 0, \
/* entsize, kept_section, moving_line_filepos, */ \
0, NULL, 0, \
\
/* target_index, used_by_bfd, constructor_chain, owner, */ \
0, NULL, NULL, NULL, \

View File

@ -6404,6 +6404,8 @@ som_bfd_link_split_section (abfd, sec)
#define som_bfd_merge_sections bfd_generic_merge_sections
#define som_bfd_is_group_section bfd_generic_is_group_section
#define som_bfd_discard_group bfd_generic_discard_group
#define som_section_already_linked \
_bfd_generic_section_already_linked
const bfd_target som_vec = {
"som", /* name */

View File

@ -1286,6 +1286,8 @@ srec_print_symbol (abfd, afile, symbol, how)
#define srec_bfd_merge_sections bfd_generic_merge_sections
#define srec_bfd_is_group_section bfd_generic_is_group_section
#define srec_bfd_discard_group bfd_generic_discard_group
#define srec_section_already_linked \
_bfd_generic_section_already_linked
#define srec_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define srec_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define srec_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -412,7 +412,8 @@ BFD_JUMP_TABLE macros.
. NAME##_bfd_gc_sections, \
. NAME##_bfd_merge_sections, \
. NAME##_bfd_is_group_section, \
. NAME##_bfd_discard_group
. NAME##_bfd_discard_group, \
. NAME##_section_already_linked \
.
. int (*_bfd_sizeof_headers) (bfd *, bfd_boolean);
. bfd_byte * (*_bfd_get_relocated_section_contents)
@ -455,6 +456,10 @@ BFD_JUMP_TABLE macros.
. {* Discard members of a group. *}
. bfd_boolean (*_bfd_discard_group) (bfd *, struct bfd_section *);
.
. {* Check if SEC has been already linked during a reloceatable or
. final link. *}
. void (*_section_already_linked) (bfd *, struct bfd_section *);
.
. {* Routines to handle dynamic symbols and relocs. *}
.#define BFD_JUMP_TABLE_DYNAMIC(NAME) \
. NAME##_get_dynamic_symtab_upper_bound, \

View File

@ -1003,6 +1003,8 @@ tekhex_print_symbol (abfd, filep, symbol, how)
#define tekhex_bfd_merge_sections bfd_generic_merge_sections
#define tekhex_bfd_is_group_section bfd_generic_is_group_section
#define tekhex_bfd_discard_group bfd_generic_discard_group
#define tekhex_section_already_linked \
_bfd_generic_section_already_linked
#define tekhex_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define tekhex_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define tekhex_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -874,6 +874,8 @@ versados_canonicalize_reloc (abfd, section, relptr, symbols)
#define versados_bfd_merge_sections bfd_generic_merge_sections
#define versados_bfd_is_group_section bfd_generic_is_group_section
#define versados_bfd_discard_group bfd_generic_discard_group
#define versados_section_already_linked \
_bfd_generic_section_already_linked
#define versados_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define versados_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define versados_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -168,6 +168,8 @@ static bfd_boolean vms_bfd_set_private_flags
#define vms_bfd_link_just_syms _bfd_generic_link_just_syms
#define vms_bfd_is_group_section bfd_generic_is_group_section
#define vms_bfd_discard_group bfd_generic_discard_group
#define vms_section_already_linked \
_bfd_generic_section_already_linked
#define vms_bfd_copy_private_header_data \
_bfd_generic_bfd_copy_private_header_data

View File

@ -99,6 +99,8 @@ extern int lynx_core_file_failing_signal PARAMS ((bfd *abfd));
#define _bfd_xcoff_bfd_gc_sections coff_bfd_gc_sections
#define _bfd_xcoff_bfd_merge_sections coff_bfd_merge_sections
#define _bfd_xcoff_bfd_discard_group bfd_generic_discard_group
#define _bfd_xcoff_section_already_linked \
_bfd_generic_section_already_linked
#define _bfd_xcoff_bfd_link_split_section coff_bfd_link_split_section
/* XCOFF archives do not have anything which corresponds to an

View File

@ -44,6 +44,8 @@
#define bfd_sym_bfd_merge_sections bfd_generic_merge_sections
#define bfd_sym_bfd_is_group_section bfd_generic_is_group_section
#define bfd_sym_bfd_discard_group bfd_generic_discard_group
#define bfd_sym_section_already_linked \
_bfd_generic_section_already_linked
#define bfd_sym_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
#define bfd_sym_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
#define bfd_sym_bfd_link_add_symbols _bfd_generic_link_add_symbols

View File

@ -1,3 +1,9 @@
2004-07-21 H.J. Lu <hongjiu.lu@intel.com>
* objcopy.c (filter_symbols): Use bfd_coff_get_comdat_section
to access comdat.
* objdump.c (dump_section_header): Likewise.
2004-07-15 Aravinda PR <aravindapr@rediffmail.com>
* nlmconv.c (main): Pass map_file argument to link_inputs.

View File

@ -891,7 +891,7 @@ filter_symbols (bfd *abfd, bfd *obfd, asymbol **osyms,
keep = (strip_symbols != STRIP_DEBUG
&& strip_symbols != STRIP_UNNEEDED
&& ! convert_debugging);
else if (bfd_get_section (sym)->comdat)
else if (bfd_coff_get_comdat_section (abfd, bfd_get_section (sym)))
/* COMDAT sections store special information in local
symbols, so we cannot risk stripping any of them. */
keep = 1;

View File

@ -331,6 +331,7 @@ dump_section_header (bfd *abfd ATTRIBUTE_UNUSED, asection *section,
if ((section->flags & SEC_LINK_ONCE) != 0)
{
const char *ls;
struct coff_comdat_info *comdat;
switch (section->flags & SEC_LINK_DUPLICATES)
{
@ -351,9 +352,9 @@ dump_section_header (bfd *abfd ATTRIBUTE_UNUSED, asection *section,
}
printf ("%s%s", comma, ls);
if (section->comdat != NULL)
printf (" (COMDAT %s %ld)", section->comdat->name,
section->comdat->symbol);
comdat = bfd_coff_get_comdat_section (abfd, section);
if (comdat != NULL)
printf (" (COMDAT %s %ld)", comdat->name, comdat->symbol);
comma = ", ";
}

View File

@ -1,3 +1,13 @@
2004-07-21 H.J. Lu <hongjiu.lu@intel.com>
* ldlang.c (already_linked_hash_entry): Removed.
(already_linked): Likewise.
(already_linked_table): Likewise.
(section_already_linked): Call bfd_section_already_linked.
(lang_process): Replace already_linked_table_init with
bfd_section_already_linked_table_init and check return. Replace
already_linked_table_free with bfd_section_already_linked_table_free.
2004-07-21 Nick Clifton <nickc@redhat.com>
* ldlang.c (init_os): Make sure that the newly allocated userdata

View File

@ -886,44 +886,10 @@ exp_init_os (etree_type *exp)
}
}
/* Sections marked with the SEC_LINK_ONCE flag should only be linked
once into the output. This routine checks each section, and
arrange to discard it if a section of the same name has already
been linked. If the section has COMDAT information, then it uses
that to decide whether the section should be included. This code
assumes that all relevant sections have the SEC_LINK_ONCE flag set;
that is, it does not depend solely upon the section name.
section_already_linked is called via bfd_map_over_sections. */
/* This is the shape of the elements inside the already_linked hash
table. It maps a name onto a list of already_linked elements with
the same name. It's possible to get more than one element in a
list if the COMDAT sections have different names. */
struct already_linked_hash_entry
{
struct bfd_hash_entry root;
struct already_linked *entry;
};
struct already_linked
{
struct already_linked *next;
asection *sec;
};
/* The hash table. */
static struct bfd_hash_table already_linked_table;
static void
section_already_linked (bfd *abfd, asection *sec, void *data)
{
lang_input_statement_type *entry = data;
flagword flags;
const char *name;
struct already_linked *l;
struct already_linked_hash_entry *already_linked_list;
/* If we are only reading symbols from this object, then we want to
discard all sections. */
@ -933,128 +899,7 @@ section_already_linked (bfd *abfd, asection *sec, void *data)
return;
}
flags = sec->flags;
if ((flags & SEC_LINK_ONCE) == 0)
return;
/* FIXME: When doing a relocatable link, we may have trouble
copying relocations in other sections that refer to local symbols
in the section being discarded. Those relocations will have to
be converted somehow; as of this writing I'm not sure that any of
the backends handle that correctly.
It is tempting to instead not discard link once sections when
doing a relocatable link (technically, they should be discarded
whenever we are building constructors). However, that fails,
because the linker winds up combining all the link once sections
into a single large link once section, which defeats the purpose
of having link once sections in the first place.
Also, not merging link once sections in a relocatable link
causes trouble for MIPS ELF, which relies on link once semantics
to handle the .reginfo section correctly. */
name = bfd_get_section_name (abfd, sec);
already_linked_list =
((struct already_linked_hash_entry *)
bfd_hash_lookup (&already_linked_table, name, TRUE, FALSE));
for (l = already_linked_list->entry; l != NULL; l = l->next)
{
if (sec->comdat == NULL
|| l->sec->comdat == NULL
|| strcmp (sec->comdat->name, l->sec->comdat->name) == 0)
{
/* The section has already been linked. See if we should
issue a warning. */
switch (flags & SEC_LINK_DUPLICATES)
{
default:
abort ();
case SEC_LINK_DUPLICATES_DISCARD:
break;
case SEC_LINK_DUPLICATES_ONE_ONLY:
if (sec->comdat == NULL)
einfo (_("%P: %B: warning: ignoring duplicate section `%s'\n"),
abfd, name);
else
einfo (_("%P: %B: warning: ignoring duplicate `%s'"
" section symbol `%s'\n"),
abfd, name, sec->comdat->name);
break;
case SEC_LINK_DUPLICATES_SAME_CONTENTS:
/* FIXME: We should really dig out the contents of both
sections and memcmp them. The COFF/PE spec says that
the Microsoft linker does not implement this
correctly, so I'm not going to bother doing it
either. */
/* Fall through. */
case SEC_LINK_DUPLICATES_SAME_SIZE:
if (sec->size != l->sec->size)
einfo (_("%P: %B: warning: duplicate section `%s'"
" has different size\n"),
abfd, name);
break;
}
/* Set the output_section field so that lang_add_section
does not create a lang_input_section structure for this
section. Since there might be a symbol in the section
being discarded, we must retain a pointer to the section
which we are really going to use. */
sec->output_section = bfd_abs_section_ptr;
sec->kept_section = l->sec;
if (flags & SEC_GROUP)
bfd_discard_group (abfd, sec);
return;
}
}
/* This is the first section with this name. Record it. Allocate
the memory from the same obstack as the hash table is kept in. */
l = bfd_hash_allocate (&already_linked_table, sizeof *l);
l->sec = sec;
l->next = already_linked_list->entry;
already_linked_list->entry = l;
}
/* Support routines for the hash table used by section_already_linked,
initialize the table, fill in an entry and remove the table. */
static struct bfd_hash_entry *
already_linked_newfunc (struct bfd_hash_entry *entry ATTRIBUTE_UNUSED,
struct bfd_hash_table *table,
const char *string ATTRIBUTE_UNUSED)
{
struct already_linked_hash_entry *ret =
bfd_hash_allocate (table, sizeof (struct already_linked_hash_entry));
ret->entry = NULL;
return &ret->root;
}
static void
already_linked_table_init (void)
{
if (! bfd_hash_table_init_n (&already_linked_table,
already_linked_newfunc,
42))
einfo (_("%P%F: Failed to create hash table\n"));
}
static void
already_linked_table_free (void)
{
bfd_hash_table_free (&already_linked_table);
bfd_section_already_linked (abfd, sec);
}
/* The wild routines.
@ -4347,7 +4192,8 @@ lang_process (void)
/* Add to the hash table all undefineds on the command line. */
lang_place_undefineds ();
already_linked_table_init ();
if (!bfd_section_already_linked_table_init ())
einfo (_("%P%F: Failed to create hash table\n"));
/* Create a bfd for each input file. */
current_target = default_target;
@ -4359,7 +4205,7 @@ lang_process (void)
ldemul_after_open ();
already_linked_table_free ();
bfd_section_already_linked_table_free ();
/* Make sure that we're not mixing architectures. We call this
after all the input files have been opened, but before we do any