#include "safe-ctype.h"
#include "libiberty.h"
+/* Define a symbol in a dynamic linkage section. */
+
+struct elf_link_hash_entry *
+_bfd_elf_define_linkage_sym (bfd *abfd,
+ struct bfd_link_info *info,
+ asection *sec,
+ const char *name)
+{
+ struct elf_link_hash_entry *h;
+ struct bfd_link_hash_entry *bh;
+ const struct elf_backend_data *bed;
+
+ h = elf_link_hash_lookup (elf_hash_table (info), name, FALSE, FALSE, FALSE);
+ if (h != NULL)
+ {
+ /* Zap symbol defined in an as-needed lib that wasn't linked.
+ This is a symptom of a larger problem: Absolute symbols
+ defined in shared libraries can't be overridden, because we
+ lose the link to the bfd which is via the symbol section. */
+ h->root.type = bfd_link_hash_new;
+ }
+
+ bh = &h->root;
+ if (!_bfd_generic_link_add_one_symbol (info, abfd, name, BSF_GLOBAL,
+ sec, 0, NULL, FALSE,
+ get_elf_backend_data (abfd)->collect,
+ &bh))
+ return NULL;
+ h = (struct elf_link_hash_entry *) bh;
+ h->def_regular = 1;
+ h->type = STT_OBJECT;
+ h->other = (h->other & ~ELF_ST_VISIBILITY (-1)) | STV_HIDDEN;
+
+ bed = get_elf_backend_data (abfd);
+ (*bed->elf_backend_hide_symbol) (info, h, TRUE);
+ return h;
+}
+
bfd_boolean
_bfd_elf_create_got_section (bfd *abfd, struct bfd_link_info *info)
{
flagword flags;
asection *s;
struct elf_link_hash_entry *h;
- struct bfd_link_hash_entry *bh;
const struct elf_backend_data *bed = get_elf_backend_data (abfd);
int ptralign;
(or .got.plt) section. We don't do this in the linker script
because we don't want to define the symbol if we are not creating
a global offset table. */
- bh = NULL;
- if (!(_bfd_generic_link_add_one_symbol
- (info, abfd, "_GLOBAL_OFFSET_TABLE_", BSF_GLOBAL, s,
- 0, NULL, FALSE, bed->collect, &bh)))
- return FALSE;
- h = (struct elf_link_hash_entry *) bh;
- h->def_regular = 1;
- h->type = STT_OBJECT;
- h->other = STV_HIDDEN;
-
- if (! info->executable
- && ! bfd_elf_link_record_dynamic_symbol (info, h))
- return FALSE;
-
+ h = _bfd_elf_define_linkage_sym (abfd, info, s, "_GLOBAL_OFFSET_TABLE_");
elf_hash_table (info)->hgot = h;
+ if (h == NULL)
+ return FALSE;
}
/* The first bit of the global offset table is the header. */
{
flagword flags;
register asection *s;
- struct elf_link_hash_entry *h;
- struct bfd_link_hash_entry *bh;
const struct elf_backend_data *bed;
if (! is_elf_hash_table (info->hash))
section. We don't want to define it if there is no .dynamic
section, since on some ELF platforms the start up code examines it
to decide how to initialize the process. */
- h = elf_link_hash_lookup (elf_hash_table (info), "_DYNAMIC",
- FALSE, FALSE, FALSE);
- if (h != NULL)
- {
- /* Zap symbol defined in an as-needed lib that wasn't linked.
- This is a symptom of a larger problem: Absolute symbols
- defined in shared libraries can't be overridden, because we
- lose the link to the bfd which is via the symbol section. */
- h->root.type = bfd_link_hash_new;
- }
- bh = &h->root;
- if (! (_bfd_generic_link_add_one_symbol
- (info, abfd, "_DYNAMIC", BSF_GLOBAL, s, 0, NULL, FALSE,
- get_elf_backend_data (abfd)->collect, &bh)))
- return FALSE;
- h = (struct elf_link_hash_entry *) bh;
- h->def_regular = 1;
- h->type = STT_OBJECT;
-
- if (! info->executable
- && ! bfd_elf_link_record_dynamic_symbol (info, h))
+ if (!_bfd_elf_define_linkage_sym (abfd, info, s, "_DYNAMIC"))
return FALSE;
s = bfd_make_section_with_flags (abfd, ".hash",
|| ! bfd_set_section_alignment (abfd, s, bed->plt_alignment))
return FALSE;
- if (bed->want_plt_sym)
- {
- /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
- .plt section. */
- struct elf_link_hash_entry *h;
- struct bfd_link_hash_entry *bh = NULL;
-
- if (! (_bfd_generic_link_add_one_symbol
- (info, abfd, "_PROCEDURE_LINKAGE_TABLE_", BSF_GLOBAL, s, 0, NULL,
- FALSE, get_elf_backend_data (abfd)->collect, &bh)))
- return FALSE;
- h = (struct elf_link_hash_entry *) bh;
- h->def_regular = 1;
- h->type = STT_OBJECT;
-
- if (! info->executable
- && ! bfd_elf_link_record_dynamic_symbol (info, h))
- return FALSE;
- }
+ /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
+ .plt section. */
+ if (bed->want_plt_sym
+ && !_bfd_elf_define_linkage_sym (abfd, info, s,
+ "_PROCEDURE_LINKAGE_TABLE_"))
+ return FALSE;
s = bfd_make_section_with_flags (abfd,
(bed->default_use_rela_p
if (dynsymcount != 0)
++dynsymcount;
- return elf_hash_table (info)->dynsymcount = dynsymcount;
+ elf_hash_table (info)->dynsymcount = dynsymcount;
+ return dynsymcount;
}
/* This function is called when we want to define a new symbol. It
/* Sweep symbols in swept sections. Called via elf_link_hash_traverse. */
+struct elf_gc_sweep_symbol_info {
+ struct bfd_link_info *info;
+ void (*hide_symbol) (struct bfd_link_info *, struct elf_link_hash_entry *,
+ bfd_boolean);
+};
+
static bfd_boolean
-elf_gc_sweep_symbol (struct elf_link_hash_entry *h, void *idxptr)
+elf_gc_sweep_symbol (struct elf_link_hash_entry *h, void *data)
{
- int *idx = idxptr;
-
if (h->root.type == bfd_link_hash_warning)
h = (struct elf_link_hash_entry *) h->root.u.i.link;
- if (h->dynindx != -1
- && ((h->root.type != bfd_link_hash_defined
- && h->root.type != bfd_link_hash_defweak)
- || h->root.u.def.section->gc_mark))
- h->dynindx = (*idx)++;
+ if ((h->root.type == bfd_link_hash_defined
+ || h->root.type == bfd_link_hash_defweak)
+ && !h->root.u.def.section->gc_mark
+ && !(h->root.u.def.section->owner->flags & DYNAMIC))
+ {
+ struct elf_gc_sweep_symbol_info *inf = data;
+ (*inf->hide_symbol) (inf->info, h, TRUE);
+ }
return TRUE;
}
(bfd *, struct bfd_link_info *, asection *, const Elf_Internal_Rela *);
static bfd_boolean
-elf_gc_sweep (struct bfd_link_info *info, gc_sweep_hook_fn gc_sweep_hook)
+elf_gc_sweep (bfd *abfd, struct bfd_link_info *info)
{
bfd *sub;
+ const struct elf_backend_data *bed = get_elf_backend_data (abfd);
+ gc_sweep_hook_fn gc_sweep_hook = bed->gc_sweep_hook;
+ unsigned long section_sym_count;
+ struct elf_gc_sweep_symbol_info sweep_info;
for (sub = info->input_bfds; sub != NULL; sub = sub->link_next)
{
/* Remove the symbols that were in the swept sections from the dynamic
symbol table. GCFIXME: Anyone know how to get them out of the
static symbol table as well? */
- {
- int i = 0;
-
- elf_link_hash_traverse (elf_hash_table (info), elf_gc_sweep_symbol, &i);
-
- /* There is an unused NULL entry at the head of the table which
- we must account for in our count. Unless there weren't any
- symbols, which means we'll have no table at all. */
- if (i != 0)
- ++i;
-
- elf_hash_table (info)->dynsymcount = i;
- }
+ sweep_info.info = info;
+ sweep_info.hide_symbol = bed->elf_backend_hide_symbol;
+ elf_link_hash_traverse (elf_hash_table (info), elf_gc_sweep_symbol,
+ &sweep_info);
+ _bfd_elf_link_renumber_dynsyms (abfd, info, §ion_sym_count);
return TRUE;
}
}
/* ... and mark SEC_EXCLUDE for those that go. */
- if (!elf_gc_sweep (info, get_elf_backend_data (abfd)->gc_sweep_hook))
- return FALSE;
-
- return TRUE;
+ return elf_gc_sweep (abfd, info);
}
\f
/* Called from check_relocs to record the existence of a VTINHERIT reloc. */