bfd/
* elf64-ppc.h (ppc64_elf_edit_toc): Declare. * elf64-ppc.c (struct ppc_link_hash_entry <adjust_done>): Update comment. (struct adjust_toc_info): New. (adjust_toc_syms, ppc64_elf_edit_toc): New functions. ld/ * emultempl/ppc64elf.em (no_tls_opt): Rename from notlsopt. (no_opd_opt, no_toc_opt): New static vars. (ppc_before_allocation): Don't edit opt if no_opd_opt. Call ppc64_elf_edit_toc. (OPTION_NO_OPD_OPT, OPTION_NO_TOC_OPT): Define. (PARSE_AND_LIST_LONGOPTS): Add no-opd-optimize and no-toc-optimize. (PARSE_AND_LIST_OPTIONS): Describe new options. (PARSE_AND_LIST_ARGS_CASES): Handle them.
This commit is contained in:
parent
9306ca4a20
commit
c5614fa460
5 changed files with 503 additions and 10 deletions
|
@ -1,3 +1,11 @@
|
|||
2004-11-04 Alan Modra <amodra@bigpond.net.au>
|
||||
|
||||
* elf64-ppc.h (ppc64_elf_edit_toc): Declare.
|
||||
* elf64-ppc.c (struct ppc_link_hash_entry <adjust_done>): Update
|
||||
comment.
|
||||
(struct adjust_toc_info): New.
|
||||
(adjust_toc_syms, ppc64_elf_edit_toc): New functions.
|
||||
|
||||
2004-11-03 Bob Wilson <bob.wilson@acm.org>
|
||||
|
||||
* elf.c (assign_file_positions_for_segments): Set next_file_pos even
|
||||
|
|
445
bfd/elf64-ppc.c
445
bfd/elf64-ppc.c
|
@ -3206,9 +3206,9 @@ struct ppc_link_hash_entry
|
|||
unsigned int is_func:1;
|
||||
unsigned int is_func_descriptor:1;
|
||||
|
||||
/* Whether global opd sym has been adjusted or not.
|
||||
After ppc64_elf_edit_opd has run, this flag should be set for all
|
||||
globals defined in any opd section. */
|
||||
/* Whether global opd/toc sym has been adjusted or not.
|
||||
After ppc64_elf_edit_opd/ppc64_elf_edit_toc has run, this flag
|
||||
should be set for all globals defined in any opd/toc section. */
|
||||
unsigned int adjust_done:1;
|
||||
|
||||
/* Set if we twiddled this symbol to weak at some stage. */
|
||||
|
@ -6645,6 +6645,445 @@ ppc64_elf_tls_optimize (bfd *obfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
/* Called via elf_link_hash_traverse from ppc64_elf_edit_toc to adjust
|
||||
the values of any global symbols in a toc section that has been
|
||||
edited. Globals in toc sections should be a rarity, so this function
|
||||
sets a flag if any are found in toc sections other than the one just
|
||||
edited, so that futher hash table traversals can be avoided. */
|
||||
|
||||
struct adjust_toc_info
|
||||
{
|
||||
asection *toc;
|
||||
unsigned long *skip;
|
||||
bfd_boolean global_toc_syms;
|
||||
};
|
||||
|
||||
static bfd_boolean
|
||||
adjust_toc_syms (struct elf_link_hash_entry *h, void *inf)
|
||||
{
|
||||
struct ppc_link_hash_entry *eh;
|
||||
struct adjust_toc_info *toc_inf = (struct adjust_toc_info *) inf;
|
||||
|
||||
if (h->root.type == bfd_link_hash_indirect)
|
||||
return TRUE;
|
||||
|
||||
if (h->root.type == bfd_link_hash_warning)
|
||||
h = (struct elf_link_hash_entry *) h->root.u.i.link;
|
||||
|
||||
if (h->root.type != bfd_link_hash_defined
|
||||
&& h->root.type != bfd_link_hash_defweak)
|
||||
return TRUE;
|
||||
|
||||
eh = (struct ppc_link_hash_entry *) h;
|
||||
if (eh->adjust_done)
|
||||
return TRUE;
|
||||
|
||||
if (eh->elf.root.u.def.section == toc_inf->toc)
|
||||
{
|
||||
unsigned long skip = toc_inf->skip[eh->elf.root.u.def.value >> 3];
|
||||
if (skip != (unsigned long) -1)
|
||||
eh->elf.root.u.def.value -= skip;
|
||||
else
|
||||
{
|
||||
(*_bfd_error_handler)
|
||||
(_("%s defined in removed toc entry"), eh->elf.root.root.string);
|
||||
eh->elf.root.u.def.section = &bfd_abs_section;
|
||||
eh->elf.root.u.def.value = 0;
|
||||
}
|
||||
eh->adjust_done = 1;
|
||||
}
|
||||
else if (strcmp (eh->elf.root.u.def.section->name, ".toc") == 0)
|
||||
toc_inf->global_toc_syms = TRUE;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Examine all relocs referencing .toc sections in order to remove
|
||||
unused .toc entries. */
|
||||
|
||||
bfd_boolean
|
||||
ppc64_elf_edit_toc (bfd *obfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
|
||||
{
|
||||
bfd *ibfd;
|
||||
struct adjust_toc_info toc_inf;
|
||||
|
||||
toc_inf.global_toc_syms = TRUE;
|
||||
for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link_next)
|
||||
{
|
||||
asection *toc, *sec;
|
||||
Elf_Internal_Shdr *symtab_hdr;
|
||||
Elf_Internal_Sym *local_syms;
|
||||
struct elf_link_hash_entry **sym_hashes;
|
||||
Elf_Internal_Rela *relstart, *rel, *wrel;
|
||||
unsigned long *skip, *drop;
|
||||
unsigned char *used;
|
||||
unsigned char *keep, last, some_unused;
|
||||
|
||||
toc = bfd_get_section_by_name (ibfd, ".toc");
|
||||
if (toc == NULL
|
||||
|| toc->sec_info_type == ELF_INFO_TYPE_JUST_SYMS
|
||||
|| elf_discarded_section (toc))
|
||||
continue;
|
||||
|
||||
local_syms = NULL;
|
||||
symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
|
||||
sym_hashes = elf_sym_hashes (ibfd);
|
||||
|
||||
/* Look at sections dropped from the final link. */
|
||||
skip = NULL;
|
||||
relstart = NULL;
|
||||
for (sec = ibfd->sections; sec != NULL; sec = sec->next)
|
||||
{
|
||||
if (sec->reloc_count == 0
|
||||
|| !elf_discarded_section (sec)
|
||||
|| get_opd_info (sec)
|
||||
|| (sec->flags & SEC_ALLOC) == 0
|
||||
|| (sec->flags & SEC_DEBUGGING) != 0)
|
||||
continue;
|
||||
|
||||
relstart = _bfd_elf_link_read_relocs (ibfd, sec, NULL, NULL, FALSE);
|
||||
if (relstart == NULL)
|
||||
goto error_ret;
|
||||
|
||||
/* Run through the relocs to see which toc entries might be
|
||||
unused. */
|
||||
for (rel = relstart; rel < relstart + sec->reloc_count; ++rel)
|
||||
{
|
||||
enum elf_ppc64_reloc_type r_type;
|
||||
unsigned long r_symndx;
|
||||
asection *sym_sec;
|
||||
struct elf_link_hash_entry *h;
|
||||
Elf_Internal_Sym *sym;
|
||||
bfd_vma val;
|
||||
|
||||
r_type = ELF64_R_TYPE (rel->r_info);
|
||||
switch (r_type)
|
||||
{
|
||||
default:
|
||||
continue;
|
||||
|
||||
case R_PPC64_TOC16:
|
||||
case R_PPC64_TOC16_LO:
|
||||
case R_PPC64_TOC16_HI:
|
||||
case R_PPC64_TOC16_HA:
|
||||
case R_PPC64_TOC16_DS:
|
||||
case R_PPC64_TOC16_LO_DS:
|
||||
break;
|
||||
}
|
||||
|
||||
r_symndx = ELF64_R_SYM (rel->r_info);
|
||||
if (!get_sym_h (&h, &sym, &sym_sec, NULL, &local_syms,
|
||||
r_symndx, ibfd))
|
||||
goto error_ret;
|
||||
|
||||
if (sym_sec != toc)
|
||||
continue;
|
||||
|
||||
if (h != NULL)
|
||||
val = h->root.u.def.value;
|
||||
else
|
||||
val = sym->st_value;
|
||||
val += rel->r_addend;
|
||||
|
||||
if (val >= toc->size)
|
||||
continue;
|
||||
|
||||
/* Anything in the toc ought to be aligned to 8 bytes.
|
||||
If not, don't mark as unused. */
|
||||
if (val & 7)
|
||||
continue;
|
||||
|
||||
if (skip == NULL)
|
||||
{
|
||||
skip = bfd_zmalloc (sizeof (*skip) * (toc->size + 7) / 8);
|
||||
if (skip == NULL)
|
||||
goto error_ret;
|
||||
}
|
||||
|
||||
skip[val >> 3] = 1;
|
||||
}
|
||||
|
||||
if (elf_section_data (sec)->relocs != relstart)
|
||||
free (relstart);
|
||||
}
|
||||
|
||||
if (skip == NULL)
|
||||
continue;
|
||||
|
||||
used = bfd_zmalloc (sizeof (*used) * (toc->size + 7) / 8);
|
||||
if (used == NULL)
|
||||
{
|
||||
error_ret:
|
||||
if (local_syms != NULL
|
||||
&& symtab_hdr->contents != (unsigned char *) local_syms)
|
||||
free (local_syms);
|
||||
if (sec != NULL
|
||||
&& relstart != NULL
|
||||
&& elf_section_data (sec)->relocs != relstart)
|
||||
free (relstart);
|
||||
if (skip != NULL)
|
||||
free (skip);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* Now check all kept sections that might reference the toc. */
|
||||
for (sec = ibfd->sections;
|
||||
sec != NULL;
|
||||
/* Check the toc itself last. */
|
||||
sec = (sec == toc ? NULL
|
||||
: sec->next == toc && sec->next->next ? sec->next->next
|
||||
: sec->next == NULL ? toc
|
||||
: sec->next))
|
||||
{
|
||||
int repeat;
|
||||
|
||||
if (sec->reloc_count == 0
|
||||
|| elf_discarded_section (sec)
|
||||
|| get_opd_info (sec)
|
||||
|| (sec->flags & SEC_ALLOC) == 0
|
||||
|| (sec->flags & SEC_DEBUGGING) != 0)
|
||||
continue;
|
||||
|
||||
relstart = _bfd_elf_link_read_relocs (ibfd, sec, NULL, NULL, TRUE);
|
||||
if (relstart == NULL)
|
||||
goto error_ret;
|
||||
|
||||
/* Mark toc entries referenced as used. */
|
||||
repeat = 0;
|
||||
do
|
||||
for (rel = relstart; rel < relstart + sec->reloc_count; ++rel)
|
||||
{
|
||||
enum elf_ppc64_reloc_type r_type;
|
||||
unsigned long r_symndx;
|
||||
asection *sym_sec;
|
||||
struct elf_link_hash_entry *h;
|
||||
Elf_Internal_Sym *sym;
|
||||
bfd_vma val;
|
||||
|
||||
r_type = ELF64_R_TYPE (rel->r_info);
|
||||
switch (r_type)
|
||||
{
|
||||
case R_PPC64_TOC16:
|
||||
case R_PPC64_TOC16_LO:
|
||||
case R_PPC64_TOC16_HI:
|
||||
case R_PPC64_TOC16_HA:
|
||||
case R_PPC64_TOC16_DS:
|
||||
case R_PPC64_TOC16_LO_DS:
|
||||
/* In case we're taking addresses of toc entries. */
|
||||
case R_PPC64_ADDR64:
|
||||
break;
|
||||
|
||||
default:
|
||||
continue;
|
||||
}
|
||||
|
||||
r_symndx = ELF64_R_SYM (rel->r_info);
|
||||
if (!get_sym_h (&h, &sym, &sym_sec, NULL, &local_syms,
|
||||
r_symndx, ibfd))
|
||||
{
|
||||
free (used);
|
||||
goto error_ret;
|
||||
}
|
||||
|
||||
if (sym_sec != toc)
|
||||
continue;
|
||||
|
||||
if (h != NULL)
|
||||
val = h->root.u.def.value;
|
||||
else
|
||||
val = sym->st_value;
|
||||
val += rel->r_addend;
|
||||
|
||||
if (val >= toc->size)
|
||||
continue;
|
||||
|
||||
/* For the toc section, we only mark as used if
|
||||
this entry itself isn't unused. */
|
||||
if (sec == toc
|
||||
&& !used[val >> 3]
|
||||
&& (used[rel->r_offset >> 3]
|
||||
|| !skip[rel->r_offset >> 3]))
|
||||
/* Do all the relocs again, to catch reference
|
||||
chains. */
|
||||
repeat = 1;
|
||||
|
||||
used[val >> 3] = 1;
|
||||
}
|
||||
while (repeat);
|
||||
}
|
||||
|
||||
/* Merge the used and skip arrays. Assume that TOC
|
||||
doublewords not appearing as either used or unused belong
|
||||
to to an entry more than one doubleword in size. */
|
||||
for (drop = skip, keep = used, last = 0, some_unused = 0;
|
||||
drop < skip + (toc->size + 7) / 8;
|
||||
++drop, ++keep)
|
||||
{
|
||||
if (*keep)
|
||||
{
|
||||
*drop = 0;
|
||||
last = 0;
|
||||
}
|
||||
else if (*drop)
|
||||
{
|
||||
some_unused = 1;
|
||||
last = 1;
|
||||
}
|
||||
else
|
||||
*drop = last;
|
||||
}
|
||||
|
||||
free (used);
|
||||
|
||||
if (some_unused)
|
||||
{
|
||||
bfd_byte *contents, *src;
|
||||
unsigned long off;
|
||||
|
||||
/* Shuffle the toc contents, and at the same time convert the
|
||||
skip array from booleans into offsets. */
|
||||
if (!bfd_malloc_and_get_section (ibfd, toc, &contents))
|
||||
goto error_ret;
|
||||
|
||||
elf_section_data (toc)->this_hdr.contents = contents;
|
||||
|
||||
for (src = contents, off = 0, drop = skip;
|
||||
src < contents + toc->size;
|
||||
src += 8, ++drop)
|
||||
{
|
||||
if (*drop)
|
||||
{
|
||||
*drop = (unsigned long) -1;
|
||||
off += 8;
|
||||
}
|
||||
else if (off != 0)
|
||||
{
|
||||
*drop = off;
|
||||
memcpy (src - off, src, 8);
|
||||
}
|
||||
}
|
||||
toc->rawsize = toc->size;
|
||||
toc->size = src - contents - off;
|
||||
|
||||
/* Read toc relocs. */
|
||||
relstart = _bfd_elf_link_read_relocs (ibfd, toc, NULL, NULL, TRUE);
|
||||
if (relstart == NULL)
|
||||
goto error_ret;
|
||||
|
||||
/* Remove unused toc relocs, and adjust those we keep. */
|
||||
wrel = relstart;
|
||||
for (rel = relstart; rel < relstart + toc->reloc_count; ++rel)
|
||||
if (skip[rel->r_offset >> 3] != (unsigned long) -1)
|
||||
{
|
||||
wrel->r_offset = rel->r_offset - skip[rel->r_offset >> 3];
|
||||
wrel->r_info = rel->r_info;
|
||||
wrel->r_addend = rel->r_addend;
|
||||
++wrel;
|
||||
}
|
||||
toc->reloc_count = wrel - relstart;
|
||||
|
||||
/* Adjust addends for relocs against the toc section sym. */
|
||||
for (sec = ibfd->sections; sec != NULL; sec = sec->next)
|
||||
{
|
||||
if (sec->reloc_count == 0
|
||||
|| elf_discarded_section (sec))
|
||||
continue;
|
||||
|
||||
relstart = _bfd_elf_link_read_relocs (ibfd, sec, NULL, NULL,
|
||||
TRUE);
|
||||
if (relstart == NULL)
|
||||
goto error_ret;
|
||||
|
||||
for (rel = relstart; rel < relstart + sec->reloc_count; ++rel)
|
||||
{
|
||||
enum elf_ppc64_reloc_type r_type;
|
||||
unsigned long r_symndx;
|
||||
asection *sym_sec;
|
||||
struct elf_link_hash_entry *h;
|
||||
Elf_Internal_Sym *sym;
|
||||
|
||||
r_type = ELF64_R_TYPE (rel->r_info);
|
||||
switch (r_type)
|
||||
{
|
||||
default:
|
||||
continue;
|
||||
|
||||
case R_PPC64_TOC16:
|
||||
case R_PPC64_TOC16_LO:
|
||||
case R_PPC64_TOC16_HI:
|
||||
case R_PPC64_TOC16_HA:
|
||||
case R_PPC64_TOC16_DS:
|
||||
case R_PPC64_TOC16_LO_DS:
|
||||
case R_PPC64_ADDR64:
|
||||
break;
|
||||
}
|
||||
|
||||
r_symndx = ELF64_R_SYM (rel->r_info);
|
||||
if (!get_sym_h (&h, &sym, &sym_sec, NULL, &local_syms,
|
||||
r_symndx, ibfd))
|
||||
goto error_ret;
|
||||
|
||||
if (sym_sec != toc || h != NULL || sym->st_value != 0)
|
||||
continue;
|
||||
|
||||
rel->r_addend -= skip[rel->r_addend >> 3];
|
||||
}
|
||||
}
|
||||
|
||||
/* We shouldn't have local or global symbols defined in the TOC,
|
||||
but handle them anyway. */
|
||||
if (local_syms != NULL)
|
||||
{
|
||||
Elf_Internal_Sym *sym;
|
||||
|
||||
for (sym = local_syms;
|
||||
sym < local_syms + symtab_hdr->sh_info;
|
||||
++sym)
|
||||
if (sym->st_shndx != SHN_UNDEF
|
||||
&& (sym->st_shndx < SHN_LORESERVE
|
||||
|| sym->st_shndx > SHN_HIRESERVE)
|
||||
&& sym->st_value != 0
|
||||
&& bfd_section_from_elf_index (ibfd, sym->st_shndx) == toc)
|
||||
{
|
||||
if (skip[sym->st_value >> 3] != (unsigned long) -1)
|
||||
sym->st_value -= skip[sym->st_value >> 3];
|
||||
else
|
||||
{
|
||||
(*_bfd_error_handler)
|
||||
(_("%s defined in removed toc entry"),
|
||||
bfd_elf_local_sym_name (ibfd, sym));
|
||||
sym->st_value = 0;
|
||||
sym->st_shndx = SHN_ABS;
|
||||
}
|
||||
symtab_hdr->contents = (unsigned char *) local_syms;
|
||||
}
|
||||
}
|
||||
|
||||
/* Finally, adjust any global syms defined in the toc. */
|
||||
if (toc_inf.global_toc_syms)
|
||||
{
|
||||
toc_inf.toc = toc;
|
||||
toc_inf.skip = skip;
|
||||
toc_inf.global_toc_syms = FALSE;
|
||||
elf_link_hash_traverse (elf_hash_table (info), adjust_toc_syms,
|
||||
&toc_inf);
|
||||
}
|
||||
}
|
||||
|
||||
if (local_syms != NULL
|
||||
&& symtab_hdr->contents != (unsigned char *) local_syms)
|
||||
{
|
||||
if (!info->keep_memory)
|
||||
free (local_syms);
|
||||
else
|
||||
symtab_hdr->contents = (unsigned char *) local_syms;
|
||||
}
|
||||
free (skip);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/* Allocate space in .plt, .got and associated reloc sections for
|
||||
dynamic relocs. */
|
||||
|
||||
|
|
|
@ -25,6 +25,8 @@ asection *ppc64_elf_tls_setup
|
|||
(bfd *, struct bfd_link_info *);
|
||||
bfd_boolean ppc64_elf_tls_optimize
|
||||
(bfd *, struct bfd_link_info *);
|
||||
bfd_boolean ppc64_elf_edit_toc
|
||||
(bfd *, struct bfd_link_info *);
|
||||
bfd_vma ppc64_elf_toc
|
||||
(bfd *);
|
||||
int ppc64_elf_setup_section_lists
|
||||
|
|
13
ld/ChangeLog
13
ld/ChangeLog
|
@ -1,9 +1,20 @@
|
|||
2004-11-04 Alan Modra <amodra@bigpond.net.au>
|
||||
|
||||
* emultempl/ppc64elf.em (no_tls_opt): Rename from notlsopt.
|
||||
(no_opd_opt, no_toc_opt): New static vars.
|
||||
(ppc_before_allocation): Don't edit opt if no_opd_opt. Call
|
||||
ppc64_elf_edit_toc.
|
||||
(OPTION_NO_OPD_OPT, OPTION_NO_TOC_OPT): Define.
|
||||
(PARSE_AND_LIST_LONGOPTS): Add no-opd-optimize and no-toc-optimize.
|
||||
(PARSE_AND_LIST_OPTIONS): Describe new options.
|
||||
(PARSE_AND_LIST_ARGS_CASES): Handle them.
|
||||
|
||||
2004-10-27 Nick Clifton <nickc@redhat.com>
|
||||
|
||||
* emultempl/alphaelf.em (alpha_after_parse): Add extra, NULL,
|
||||
parameter to invocation of lang_section_start.
|
||||
* emultempl/aix.em (_handle_option): Likewise.
|
||||
|
||||
|
||||
* Makefile.am (eelf64alpha.c, eelf64alpha_fbsd.c,
|
||||
eelf64alpha_nbsd.c): Add dependency upon emultempl/alphaelf.em.
|
||||
* Makefile.in: Regenerate.
|
||||
|
|
|
@ -44,7 +44,13 @@ static bfd_signed_vma group_size = 1;
|
|||
static int dotsyms = 1;
|
||||
|
||||
/* Whether to run tls optimization. */
|
||||
static int notlsopt = 0;
|
||||
static int no_tls_opt = 0;
|
||||
|
||||
/* Whether to run opd optimization. */
|
||||
static int no_opd_opt = 0;
|
||||
|
||||
/* Whether to run toc optimization. */
|
||||
static int no_toc_opt = 0;
|
||||
|
||||
/* Whether to emit symbols for stubs. */
|
||||
static int emit_stub_syms = 0;
|
||||
|
@ -92,13 +98,14 @@ ppc_before_allocation (void)
|
|||
{
|
||||
if (stub_file != NULL)
|
||||
{
|
||||
if (!ppc64_elf_edit_opd (output_bfd, &link_info, non_overlapping_opd))
|
||||
if (!no_opd_opt
|
||||
&& !ppc64_elf_edit_opd (output_bfd, &link_info, non_overlapping_opd))
|
||||
{
|
||||
einfo ("%X%P: can not edit opd %E\n");
|
||||
einfo ("%X%P: can not edit %s %E\n", "opd");
|
||||
return;
|
||||
}
|
||||
|
||||
if (ppc64_elf_tls_setup (output_bfd, &link_info) && !notlsopt)
|
||||
if (ppc64_elf_tls_setup (output_bfd, &link_info) && !no_tls_opt)
|
||||
{
|
||||
/* Size the sections. This is premature, but we want to know the
|
||||
TLS segment layout so that certain optimizations can be done. */
|
||||
|
@ -115,6 +122,14 @@ ppc_before_allocation (void)
|
|||
elf_tdata (output_bfd)->program_header_size = 0;
|
||||
lang_reset_memory_regions ();
|
||||
}
|
||||
|
||||
if (!no_toc_opt
|
||||
&& !link_info.relocatable
|
||||
&& !ppc64_elf_edit_toc (output_bfd, &link_info))
|
||||
{
|
||||
einfo ("%X%P: can not edit %s %E\n", "toc");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
gld${EMULATION_NAME}_before_allocation ();
|
||||
|
@ -467,7 +482,9 @@ PARSE_AND_LIST_PROLOGUE='
|
|||
#define OPTION_DOTSYMS (OPTION_STUBSYMS + 1)
|
||||
#define OPTION_NO_DOTSYMS (OPTION_DOTSYMS + 1)
|
||||
#define OPTION_NO_TLS_OPT (OPTION_NO_DOTSYMS + 1)
|
||||
#define OPTION_NON_OVERLAPPING_OPD (OPTION_NO_TLS_OPT + 1)
|
||||
#define OPTION_NO_OPD_OPT (OPTION_NO_TLS_OPT + 1)
|
||||
#define OPTION_NO_TOC_OPT (OPTION_NO_OPD_OPT + 1)
|
||||
#define OPTION_NON_OVERLAPPING_OPD (OPTION_NO_TOC_OPT + 1)
|
||||
'
|
||||
|
||||
PARSE_AND_LIST_LONGOPTS='
|
||||
|
@ -476,6 +493,8 @@ PARSE_AND_LIST_LONGOPTS='
|
|||
{ "dotsyms", no_argument, NULL, OPTION_DOTSYMS },
|
||||
{ "no-dotsyms", no_argument, NULL, OPTION_NO_DOTSYMS },
|
||||
{ "no-tls-optimize", no_argument, NULL, OPTION_NO_TLS_OPT },
|
||||
{ "no-opd-optimize", no_argument, NULL, OPTION_NO_OPD_OPT },
|
||||
{ "no-toc-optimize", no_argument, NULL, OPTION_NO_TOC_OPT },
|
||||
{ "non-overlapping-opd", no_argument, NULL, OPTION_NON_OVERLAPPING_OPD },
|
||||
'
|
||||
|
||||
|
@ -505,6 +524,12 @@ PARSE_AND_LIST_OPTIONS='
|
|||
--no-tls-optimize Don'\''t try to optimize TLS accesses.\n"
|
||||
));
|
||||
fprintf (file, _("\
|
||||
--no-opd-optimize Don'\''t optimize the OPD section.\n"
|
||||
));
|
||||
fprintf (file, _("\
|
||||
--no-toc-optimize Don'\''t optimize the TOC section.\n"
|
||||
));
|
||||
fprintf (file, _("\
|
||||
--non-overlapping-opd Canonicalize .opd, so that there are no overlapping\n\
|
||||
.opd entries.\n"
|
||||
));
|
||||
|
@ -533,7 +558,15 @@ PARSE_AND_LIST_ARGS_CASES='
|
|||
break;
|
||||
|
||||
case OPTION_NO_TLS_OPT:
|
||||
notlsopt = 1;
|
||||
no_tls_opt = 1;
|
||||
break;
|
||||
|
||||
case OPTION_NO_OPD_OPT:
|
||||
no_opd_opt = 1;
|
||||
break;
|
||||
|
||||
case OPTION_NO_TOC_OPT:
|
||||
no_toc_opt = 1;
|
||||
break;
|
||||
|
||||
case OPTION_NON_OVERLAPPING_OPD:
|
||||
|
|
Loading…
Reference in a new issue