Compare commits

...

1 Commits

Author SHA1 Message Date
H.J. Lu
2159c3f1e6 Properly handle relocs against absolute symbols
Relocations against absolute symbols in shared object should be resolved
at link-time if symbols are bounded locally.  For PC-relative relocation
against absolute symbols, they should be converted to non-PC-relative
relocation in target backend.  If conversion can't be performed, target
backend should detect it and issue an error.  This patch only fixes x86
backends.

bfd/

	PR ld/19818
	* bfd-in.h (bfd_elf_record_link_assignment): Add a bfd_boolean.
	* bfd-in2.h: Regenerated.
	* elf-bfd.h (elf_link_hash_entry): Add def_linker and
	def_linker_abs.
	(RESOLVED_TO_ABS_IN_PIC): New macro.
	* elf32-i386.c (RESOLVED_TO_ZERO_OR_ABS): New macro.
	(elf_i386_allocate_dynrelocs): Replace
	UNDEFINED_WEAK_RESOLVED_TO_ZERO with RESOLVED_TO_ZERO_OR_ABS.
	Discard space for non-pc-relative relocs against symbols which
	are always resolved at link-time.
	(elf_i386_convert_load): Replace UNDEFINED_WEAK_RESOLVED_TO_ZERO
	with RESOLVED_TO_ZERO_OR_ABS.
	(elf_i386_relocate_section): Replace
	UNDEFINED_WEAK_RESOLVED_TO_ZERO with RESOLVED_TO_ZERO_OR_ABS.
	Properly handle R_386_32 relocation against absolute symbol.
	* elf64-x86-64.c (RESOLVED_TO_ZERO_OR_ABS): New macro.
	(elf_x86_64_need_pic): Updated to check absolute symbol.
	(elf_x86_64_check_relocs): Don't check R_X86_64_32 nor
	R_X86_64_32S in shared object here.  Use elf_x86_64_need_pic.
	(elf_x86_64_allocate_dynrelocs): Replace
	UNDEFINED_WEAK_RESOLVED_TO_ZERO with RESOLVED_TO_ZERO_OR_ABS.
	Discard space for non-pc-relative relocs against symbols which
	are always resolved at link-time.
	(elf_x86_64_convert_load): Replace UNDEFINED_WEAK_RESOLVED_TO_ZERO
	with RESOLVED_TO_ZERO_OR_ABS.  Check def_linker for linker
	defined symbol.
	(elf_x86_64_relocate_section): Replace
	UNDEFINED_WEAK_RESOLVED_TO_ZERO with RESOLVED_TO_ZERO_OR_ABS.
	Properly handle R_X86_64_PC32, R_X86_64_32, R_X86_64_32S amd
	R_X86_64_64 relocations against absolute symbol.
	* elflink.c (bfd_elf_record_link_assignment): Updated.  Set
	def_linker and defsym.

ld/

	PR ld/19818
	* emultempl/elf32.em (gld${EMULATION_NAME}_find_exp_assignment):
	Pass "exp->assign.defsym || !expld.rel_from_abs" to
	bfd_elf_record_link_assignment.
	(gld${EMULATION_NAME}_before_allocation): Set def_linker for
	"__ehdr_start".
	* testsuite/ld-i386/i386.exp: Run PR ld/19818 tests.
	* testsuite/ld-x86-64/x86-64.exp: Likewise.
	* testsuite/ld-elf/pr19818a.d: New file.
	* testsuite/ld-elf/pr19818a.s: Likewise.
	* testsuite/ld-elf/pr19818b.d: Likewise.
	* testsuite/ld-elf/pr19818b.s: Likewise.
	* testsuite/ld-i386/pr19818-1.t: Likewise.
	* testsuite/ld-i386/pr19818-1a.d: Likewise.
	* testsuite/ld-i386/pr19818-1a.s: Likewise.
	* testsuite/ld-i386/pr19818-1b.d: Likewise.
	* testsuite/ld-i386/pr19818-1b.s: Likewise.
	* testsuite/ld-i386/pr19818-1c.d: Likewise.
	* testsuite/ld-i386/pr19818-1c.s: Likewise.
	* testsuite/ld-i386/pr19818-1d.d: Likewise.
	* testsuite/ld-i386/pr19818-1e.d: Likewise.
	* testsuite/ld-i386/pr19818-1f.d: Likewise.
	* testsuite/ld-i386/pr19818-1g.d: Likewise.
	* testsuite/ld-i386/pr19818-1h.d: Likewise.
	* testsuite/ld-i386/pr19818-1i.d: Likewise.
	* testsuite/ld-i386/pr19818-1j.d: Likewise.
	* testsuite/ld-i386/pr19818-1k.d: Likewise.
	* testsuite/ld-i386/pr19818-1l.d: Likewise.
	* testsuite/ld-i386/pr19818-2.s: Likewise.
	* testsuite/ld-i386/pr19818-2a.d: Likewise.
	* testsuite/ld-i386/pr19818-2b.d: Likewise.
	* testsuite/ld-i386/pr19818-2c.d: Likewise.
	* testsuite/ld-i386/pr19818-2d.d: Likewise.
	* testsuite/ld-i386/pr19818-2e.d: Likewise.
	* testsuite/ld-i386/pr19818-2f.d: Likewise.
	* testsuite/ld-i386/pr19818-2g.d: Likewise.
	* testsuite/ld-i386/pr19818-2h.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1.t: Likewise.
	* testsuite/ld-x86-64/pr19818-1a.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1a.s: Likewise.
	* testsuite/ld-x86-64/pr19818-1b.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1b.s: Likewise.
	* testsuite/ld-x86-64/pr19818-1c.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1c.s: Likewise.
	* testsuite/ld-x86-64/pr19818-1d.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1e.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1f.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1g.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1h.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1i.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1j.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1k.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1l.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1m.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1n.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1o.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1p.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1q.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1r.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1s.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1t.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1u.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1v.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1w.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1x.d: Likewise.
	* testsuite/ld-x86-64/pr19818-1y.d: Likewise.
	* testsuite/ld-x86-64/pr19818-2.s: Likewise.
	* testsuite/ld-x86-64/pr19818-2a.d: Likewise.
	* testsuite/ld-x86-64/pr19818-2b.d: Likewise.
	* testsuite/ld-x86-64/pr19818-2c.d: Likewise.
	* testsuite/ld-x86-64/pr19818-2d.d: Likewise.
	* testsuite/ld-x86-64/pr19818-3.s: Likewise.
	* testsuite/ld-x86-64/pr19818-3a.d: Likewise.
	* testsuite/ld-x86-64/pr19818-3b.d: Likewise.
	* testsuite/ld-x86-64/pr19818-3c.d: Likewise.
	* testsuite/ld-x86-64/pr19818-3d.d: Likewise.
	* testsuite/ld-x86-64/pr19818-4.s: Likewise.
	* testsuite/ld-x86-64/pr19818-4a.d: Likewise.
	* testsuite/ld-x86-64/pr19818-4b.d: Likewise.
	* testsuite/ld-x86-64/pr19818-5.s: Likewise.
	* testsuite/ld-x86-64/pr19818-5a.d: Likewise.
	* testsuite/ld-x86-64/pr19818-5b.d: Likewise.
2016-03-14 05:38:24 -07:00
83 changed files with 913 additions and 176 deletions

View File

@@ -649,7 +649,7 @@ enum notice_asneeded_action {
extern bfd_boolean bfd_elf_record_link_assignment extern bfd_boolean bfd_elf_record_link_assignment
(bfd *, struct bfd_link_info *, const char *, bfd_boolean, (bfd *, struct bfd_link_info *, const char *, bfd_boolean,
bfd_boolean); bfd_boolean, bfd_boolean);
extern struct bfd_link_needed_list *bfd_elf_get_needed_list extern struct bfd_link_needed_list *bfd_elf_get_needed_list
(bfd *, struct bfd_link_info *); (bfd *, struct bfd_link_info *);
extern bfd_boolean bfd_elf_get_bfd_needed_list extern bfd_boolean bfd_elf_get_bfd_needed_list

View File

@@ -656,7 +656,7 @@ enum notice_asneeded_action {
extern bfd_boolean bfd_elf_record_link_assignment extern bfd_boolean bfd_elf_record_link_assignment
(bfd *, struct bfd_link_info *, const char *, bfd_boolean, (bfd *, struct bfd_link_info *, const char *, bfd_boolean,
bfd_boolean); bfd_boolean, bfd_boolean);
extern struct bfd_link_needed_list *bfd_elf_get_needed_list extern struct bfd_link_needed_list *bfd_elf_get_needed_list
(bfd *, struct bfd_link_info *); (bfd *, struct bfd_link_info *);
extern bfd_boolean bfd_elf_get_bfd_needed_list extern bfd_boolean bfd_elf_get_bfd_needed_list
@@ -1501,7 +1501,7 @@ typedef struct bfd_section
information. */ information. */
bfd_vma lma; bfd_vma lma;
/* The size of the section in octets, as it will be output. /* The size of the section in *octets*, as it will be output.
Contains a value even if the section has no contents (e.g., the Contains a value even if the section has no contents (e.g., the
size of <<.bss>>). */ size of <<.bss>>). */
bfd_size_type size; bfd_size_type size;

View File

@@ -212,6 +212,10 @@ struct elf_link_hash_entry
/* Symbol is defined by a shared library with non-default visibility /* Symbol is defined by a shared library with non-default visibility
in a read/write section. */ in a read/write section. */
unsigned int protected_def : 1; unsigned int protected_def : 1;
/* Symbol is defiend by linker. */
unsigned int def_linker : 1;
/* Symbol is defiend by linker and absolue. */
unsigned int def_linker_abs : 1;
/* String table index in .dynstr if this is a dynamic symbol. */ /* String table index in .dynstr if this is a dynamic symbol. */
unsigned long dynstr_index; unsigned long dynstr_index;
@@ -2645,6 +2649,16 @@ extern asection _bfd_elf_large_com_section;
(!(H)->unique_global \ (!(H)->unique_global \
&& ((INFO)->symbolic || ((INFO)->dynamic && !(H)->dynamic))) && ((INFO)->symbolic || ((INFO)->dynamic && !(H)->dynamic)))
/* Will a relocation be resolved to absolute symbol in shared object. */
#define RESOLVED_TO_ABS_IN_PIC(INFO, H) \
((bfd_link_pie (INFO) \
|| (bfd_link_dll (INFO) \
&& (ELF_ST_VISIBILITY ((H)->other) != STV_DEFAULT \
|| SYMBOLIC_BIND ((INFO), (H))))) \
&& (H)->def_regular \
&& (!(H)->def_linker || (H)->def_linker_abs) \
&& bfd_is_abs_section ((H)->root.u.def.section))
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

View File

@@ -751,6 +751,12 @@ static const struct elf_i386_backend_data elf_i386_arch_bed =
|| (EH)->has_non_got_reloc \ || (EH)->has_non_got_reloc \
|| !(INFO)->dynamic_undefined_weak)) || !(INFO)->dynamic_undefined_weak))
/* Will a relocation be resolved to absolute value in shared object or
to zero? */
#define RESOLVED_TO_ZERO_OR_ABS(INFO, EH) \
(UNDEFINED_WEAK_RESOLVED_TO_ZERO ((INFO), (EH)) \
|| RESOLVED_TO_ABS_IN_PIC ((INFO), &(EH)->elf))
/* i386 ELF linker hash entry. */ /* i386 ELF linker hash entry. */
struct elf_i386_link_hash_entry struct elf_i386_link_hash_entry
@@ -2397,7 +2403,7 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
struct elf_i386_link_hash_entry *eh; struct elf_i386_link_hash_entry *eh;
struct elf_dyn_relocs *p; struct elf_dyn_relocs *p;
unsigned plt_entry_size; unsigned plt_entry_size;
bfd_boolean resolved_to_zero; bfd_boolean resolved_to_zero_or_abs;
if (h->root.type == bfd_link_hash_indirect) if (h->root.type == bfd_link_hash_indirect)
return TRUE; return TRUE;
@@ -2411,7 +2417,7 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
plt_entry_size = GET_PLT_ENTRY_SIZE (info->output_bfd); plt_entry_size = GET_PLT_ENTRY_SIZE (info->output_bfd);
resolved_to_zero = UNDEFINED_WEAK_RESOLVED_TO_ZERO (info, eh); resolved_to_zero_or_abs = RESOLVED_TO_ZERO_OR_ABS (info, eh);
/* Clear the reference count of function pointer relocations if /* Clear the reference count of function pointer relocations if
symbol isn't a normal function. */ symbol isn't a normal function. */
@@ -2467,11 +2473,11 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
use_plt_got = eh->plt_got.refcount > 0; use_plt_got = eh->plt_got.refcount > 0;
/* Make sure this symbol is output as a dynamic symbol. /* Make sure this symbol is output as a dynamic symbol. Absolute
Undefined weak syms won't yet be marked as dynamic. */ and undefined weak symbols won't yet be marked as dynamic. */
if (h->dynindx == -1 if (h->dynindx == -1
&& !h->forced_local && !h->forced_local
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
{ {
if (! bfd_elf_link_record_dynamic_symbol (info, h)) if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
@@ -2528,9 +2534,9 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
script. */ script. */
htab->elf.sgotplt->size += 4; htab->elf.sgotplt->size += 4;
/* There should be no PLT relocation against resolved /* There should be no PLT relocation against absolute
undefined weak symbol in executable. */ and resolved undefined weak symbols in executable. */
if (!resolved_to_zero) if (!resolved_to_zero_or_abs)
{ {
/* We also need to make an entry in the .rel.plt /* We also need to make an entry in the .rel.plt
section. */ section. */
@@ -2589,11 +2595,11 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
bfd_boolean dyn; bfd_boolean dyn;
int tls_type = elf_i386_hash_entry(h)->tls_type; int tls_type = elf_i386_hash_entry(h)->tls_type;
/* Make sure this symbol is output as a dynamic symbol. /* Make sure this symbol is output as a dynamic symbol. Absolute
Undefined weak syms won't yet be marked as dynamic. */ and undefined weak symbols won't yet be marked as dynamic. */
if (h->dynindx == -1 if (h->dynindx == -1
&& !h->forced_local && !h->forced_local
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
{ {
if (! bfd_elf_link_record_dynamic_symbol (info, h)) if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
@@ -2621,8 +2627,8 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
R_386_TLS_IE resp. R_386_TLS_GOTIE needs one dynamic relocation, R_386_TLS_IE resp. R_386_TLS_GOTIE needs one dynamic relocation,
(but if both R_386_TLS_IE_32 and R_386_TLS_IE is present, we (but if both R_386_TLS_IE_32 and R_386_TLS_IE is present, we
need two), R_386_TLS_GD needs one if local symbol and two if need two), R_386_TLS_GD needs one if local symbol and two if
global. No dynamic relocation against resolved undefined weak global. No dynamic relocation against resolved absolute and
symbol in executable. */ undefined weak symbols in executable. */
if (tls_type == GOT_TLS_IE_BOTH) if (tls_type == GOT_TLS_IE_BOTH)
htab->elf.srelgot->size += 2 * sizeof (Elf32_External_Rel); htab->elf.srelgot->size += 2 * sizeof (Elf32_External_Rel);
else if ((GOT_TLS_GD_P (tls_type) && h->dynindx == -1) else if ((GOT_TLS_GD_P (tls_type) && h->dynindx == -1)
@@ -2632,7 +2638,7 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
htab->elf.srelgot->size += 2 * sizeof (Elf32_External_Rel); htab->elf.srelgot->size += 2 * sizeof (Elf32_External_Rel);
else if (! GOT_TLS_GDESC_P (tls_type) else if (! GOT_TLS_GDESC_P (tls_type)
&& ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT && ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
|| h->root.type != bfd_link_hash_undefweak) || h->root.type != bfd_link_hash_undefweak)
&& (bfd_link_pic (info) && (bfd_link_pic (info)
|| WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h))) || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h)))
@@ -2654,6 +2660,8 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
if (bfd_link_pic (info)) if (bfd_link_pic (info))
{ {
struct elf_dyn_relocs **pp;
/* The only reloc that uses pc_count is R_386_PC32, which will /* The only reloc that uses pc_count is R_386_PC32, which will
appear on a call or on something like ".long foo - .". We appear on a call or on something like ".long foo - .". We
want calls to protected symbols to resolve directly to the want calls to protected symbols to resolve directly to the
@@ -2662,8 +2670,6 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
should avoid writing assembly like ".long foo - .". */ should avoid writing assembly like ".long foo - .". */
if (SYMBOL_CALLS_LOCAL (info, h)) if (SYMBOL_CALLS_LOCAL (info, h))
{ {
struct elf_dyn_relocs **pp;
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; ) for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
{ {
p->count -= p->pc_count; p->count -= p->pc_count;
@@ -2677,7 +2683,6 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
if (get_elf_i386_backend_data (info->output_bfd)->is_vxworks) if (get_elf_i386_backend_data (info->output_bfd)->is_vxworks)
{ {
struct elf_dyn_relocs **pp;
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; ) for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
{ {
if (strcmp (p->sec->output_section->name, ".tls_vars") == 0) if (strcmp (p->sec->output_section->name, ".tls_vars") == 0)
@@ -2689,47 +2694,60 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
/* Also discard relocs on undefined weak syms with non-default /* Also discard relocs on undefined weak syms with non-default
visibility or in PIE. */ visibility or in PIE. */
if (eh->dyn_relocs != NULL if (eh->dyn_relocs != NULL)
&& h->root.type == bfd_link_hash_undefweak)
{ {
/* Undefined weak symbol is never bound locally in shared if (h->root.type == bfd_link_hash_undefweak)
library. */
if (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT
|| resolved_to_zero)
{ {
if (h->non_got_ref) /* Undefined weak symbol is never bound locally in shared
library. */
if (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT
|| resolved_to_zero_or_abs)
{ {
/* Keep dynamic non-GOT/non-PLT relocation so that we if (h->non_got_ref)
can branch to 0 without PLT. */
struct elf_dyn_relocs **pp;
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
if (p->pc_count == 0)
*pp = p->next;
else
{
/* Remove non-R_386_PC32 relocation. */
p->count = p->pc_count;
pp = &p->next;
}
if (eh->dyn_relocs != NULL)
{ {
/* Make sure undefined weak symbols are output /* Keep dynamic non-GOT/non-PLT relocation so that we
as dynamic symbols in PIEs for dynamic non-GOT can branch to 0 without PLT. */
non-PLT reloations. */ for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
if (! bfd_elf_link_record_dynamic_symbol (info, h)) if (p->pc_count == 0)
return FALSE; *pp = p->next;
else
{
/* Remove non-R_386_PC32 relocation. */
p->count = p->pc_count;
pp = &p->next;
}
if (eh->dyn_relocs != NULL)
{
/* Make sure undefined weak symbols are output
as dynamic symbols in PIEs for dynamic non-GOT
non-PLT reloations. */
if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE;
}
} }
else
eh->dyn_relocs = NULL;
}
else if (h->dynindx == -1
&& !h->forced_local)
{
if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE;
} }
else
eh->dyn_relocs = NULL;
} }
else if (h->dynindx == -1 else if (resolved_to_zero_or_abs)
&& !h->forced_local)
{ {
if (! bfd_elf_link_record_dynamic_symbol (info, h)) /* Discard space for non-pc-relative relocs against
return FALSE; absolute symbols which are always resolved at
link-time. */
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
{
if (p->pc_count == 0)
*pp = p->next;
else
pp = &p->next;
}
} }
} }
} }
@@ -2743,7 +2761,7 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
if ((!h->non_got_ref if ((!h->non_got_ref
|| eh->func_pointer_refcount > 0 || eh->func_pointer_refcount > 0
|| (h->root.type == bfd_link_hash_undefweak || (h->root.type == bfd_link_hash_undefweak
&& !resolved_to_zero)) && !resolved_to_zero_or_abs))
&& ((h->def_dynamic && ((h->def_dynamic
&& !h->def_regular) && !h->def_regular)
|| (htab->elf.dynamic_sections_created || (htab->elf.dynamic_sections_created
@@ -2751,10 +2769,11 @@ elf_i386_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
|| h->root.type == bfd_link_hash_undefined)))) || h->root.type == bfd_link_hash_undefined))))
{ {
/* Make sure this symbol is output as a dynamic symbol. /* Make sure this symbol is output as a dynamic symbol.
Undefined weak syms won't yet be marked as dynamic. */ Absolute and undefined weak symbols won't yet be marked
as dynamic. */
if (h->dynindx == -1 if (h->dynindx == -1
&& !h->forced_local && !h->forced_local
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
{ {
if (! bfd_elf_link_record_dynamic_symbol (info, h)) if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
@@ -3020,8 +3039,7 @@ elf_i386_convert_load (bfd *abfd, asection *sec,
/* Undefined weak symbol is only bound locally in executable /* Undefined weak symbol is only bound locally in executable
and its reference is resolved as 0. */ and its reference is resolved as 0. */
if (UNDEFINED_WEAK_RESOLVED_TO_ZERO (link_info, if (RESOLVED_TO_ZERO_OR_ABS (link_info, elf_i386_hash_entry (h)))
elf_i386_hash_entry (h)))
{ {
if (opcode == 0xff) if (opcode == 0xff)
{ {
@@ -3771,7 +3789,7 @@ elf_i386_relocate_section (bfd *output_bfd,
int tls_type; int tls_type;
bfd_vma st_size; bfd_vma st_size;
asection *resolved_plt; asection *resolved_plt;
bfd_boolean resolved_to_zero; bfd_boolean resolved_to_zero_or_abs;
r_type = ELF32_R_TYPE (rel->r_info); r_type = ELF32_R_TYPE (rel->r_info);
if (r_type == R_386_GNU_VTINHERIT if (r_type == R_386_GNU_VTINHERIT
@@ -4113,8 +4131,8 @@ elf_i386_relocate_section (bfd *output_bfd,
} }
eh = (struct elf_i386_link_hash_entry *) h; eh = (struct elf_i386_link_hash_entry *) h;
resolved_to_zero = (eh != NULL resolved_to_zero_or_abs = (eh != NULL
&& UNDEFINED_WEAK_RESOLVED_TO_ZERO (info, eh)); && RESOLVED_TO_ZERO_OR_ABS (info, eh));
switch (r_type) switch (r_type)
{ {
@@ -4370,24 +4388,31 @@ r_386_got32:
unresolved_reloc = FALSE; unresolved_reloc = FALSE;
break; break;
case R_386_32:
/* R_386_32 relocation against absolute symbol or undefined
weak symbol in executable is resolved at link-time. */
if (resolved_to_zero_or_abs)
break;
goto direct;
case R_386_SIZE32: case R_386_SIZE32:
/* Set to symbol size. */ /* Set to symbol size. */
relocation = st_size; relocation = st_size;
/* Fall through. */ /* Fall through. */
case R_386_32:
case R_386_PC32: case R_386_PC32:
direct:
if ((input_section->flags & SEC_ALLOC) == 0 if ((input_section->flags & SEC_ALLOC) == 0
|| is_vxworks_tls) || is_vxworks_tls)
break; break;
/* Copy dynamic function pointer relocations. Don't generate /* Copy dynamic function pointer relocations. Don't generate
dynamic relocations against resolved undefined weak symbols dynamic relocations against absolute nor resolved undefined
in PIE, except for R_386_PC32. */ weak symbols in PIE, except for R_386_PC32. */
if ((bfd_link_pic (info) if ((bfd_link_pic (info)
&& (h == NULL && (h == NULL
|| ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT || ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
&& (!resolved_to_zero && (!resolved_to_zero_or_abs
|| r_type == R_386_PC32)) || r_type == R_386_PC32))
|| h->root.type != bfd_link_hash_undefweak)) || h->root.type != bfd_link_hash_undefweak))
&& ((r_type != R_386_PC32 && r_type != R_386_SIZE32) && ((r_type != R_386_PC32 && r_type != R_386_SIZE32)
@@ -4399,7 +4424,7 @@ r_386_got32:
&& (!h->non_got_ref && (!h->non_got_ref
|| eh->func_pointer_refcount > 0 || eh->func_pointer_refcount > 0
|| (h->root.type == bfd_link_hash_undefweak || (h->root.type == bfd_link_hash_undefweak
&& !resolved_to_zero)) && !resolved_to_zero_or_abs))
&& ((h->def_dynamic && !h->def_regular) && ((h->def_dynamic && !h->def_regular)
/* Undefined weak symbol is bound locally when /* Undefined weak symbol is bound locally when
PIC is false. */ PIC is false. */

View File

@@ -756,6 +756,12 @@ static const struct elf_x86_64_backend_data elf_x86_64_bnd_arch_bed =
|| (EH)->has_non_got_reloc \ || (EH)->has_non_got_reloc \
|| !(INFO)->dynamic_undefined_weak)) || !(INFO)->dynamic_undefined_weak))
/* Will a relocation be resolved to absolute value in shared object or
to zero? */
#define RESOLVED_TO_ZERO_OR_ABS(INFO, EH) \
(UNDEFINED_WEAK_RESOLVED_TO_ZERO ((INFO), (EH)) \
|| RESOLVED_TO_ABS_IN_PIC ((INFO), &(EH)->elf))
/* x86-64 ELF linker hash entry. */ /* x86-64 ELF linker hash entry. */
struct elf_x86_64_link_hash_entry struct elf_x86_64_link_hash_entry
@@ -1581,6 +1587,58 @@ elf_x86_64_tls_transition (struct bfd_link_info *info, bfd *abfd,
return TRUE; return TRUE;
} }
static bfd_boolean
elf_x86_64_need_pic (bfd *input_bfd, struct elf_link_hash_entry *h,
Elf_Internal_Shdr *symtab_hdr,
Elf_Internal_Sym *isym, reloc_howto_type *howto)
{
const char *name;
const char *fmt = _("%B: relocation %s against %s `%s' can not be used when making a shared object%s");
const char *v;
const char *pic = "";
if (h)
{
name = h->root.root.string;
switch (ELF_ST_VISIBILITY (h->other))
{
case STV_HIDDEN:
v = _("hidden symbol");
break;
case STV_INTERNAL:
v = _("internal symbol");
break;
case STV_PROTECTED:
v = _("protected symbol");
break;
default:
if (h->def_regular
&& (!h->def_linker || h->def_linker_abs)
&& bfd_is_abs_section (h->root.u.def.section))
v = _("absolute symbol");
else
{
v = _("symbol");
pic = _("; recompile with -fPIC");
}
break;
}
if (!h->def_regular)
fmt = _("%B: relocation %s against undefined %s `%s' can not be used when making a shared object%s");
}
else
{
name = bfd_elf_sym_name (input_bfd, symtab_hdr, isym, NULL);
v = _("symbol");
pic = _("; recompile with -fPIC");
}
(*_bfd_error_handler) (fmt, input_bfd, howto->name, v, name, pic);
bfd_set_error (bfd_error_bad_value);
return FALSE;
}
/* Rename some of the generic section flags to better document how they /* Rename some of the generic section flags to better document how they
are used here. */ are used here. */
#define need_convert_load sec_flg0 #define need_convert_load sec_flg0
@@ -1964,12 +2022,8 @@ elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
size_reloc = TRUE; size_reloc = TRUE;
goto do_size; goto do_size;
case R_X86_64_32:
if (!ABI_64_P (abfd))
goto pointer;
case R_X86_64_8: case R_X86_64_8:
case R_X86_64_16: case R_X86_64_16:
case R_X86_64_32S:
/* Let's help debug shared library creation. These relocs /* Let's help debug shared library creation. These relocs
cannot be used in shared libs. Don't error out for cannot be used in shared libs. Don't error out for
sections we don't care about, such as debug sections or sections we don't care about, such as debug sections or
@@ -1977,17 +2031,8 @@ elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
if (bfd_link_pic (info) if (bfd_link_pic (info)
&& (sec->flags & SEC_ALLOC) != 0 && (sec->flags & SEC_ALLOC) != 0
&& (sec->flags & SEC_READONLY) != 0) && (sec->flags & SEC_READONLY) != 0)
{ return elf_x86_64_need_pic (abfd, h, symtab_hdr, isym,
if (h) &x86_64_elf_howto_table[r_type]);
name = h->root.root.string;
else
name = bfd_elf_sym_name (abfd, symtab_hdr, isym, NULL);
(*_bfd_error_handler)
(_("%B: relocation %s against `%s' can not be used when making a shared object; recompile with -fPIC"),
abfd, x86_64_elf_howto_table[r_type].name, name);
bfd_set_error (bfd_error_bad_value);
return FALSE;
}
/* Fall through. */ /* Fall through. */
case R_X86_64_PC8: case R_X86_64_PC8:
@@ -1995,8 +2040,9 @@ elf_x86_64_check_relocs (bfd *abfd, struct bfd_link_info *info,
case R_X86_64_PC32: case R_X86_64_PC32:
case R_X86_64_PC32_BND: case R_X86_64_PC32_BND:
case R_X86_64_PC64: case R_X86_64_PC64:
case R_X86_64_32:
case R_X86_64_32S:
case R_X86_64_64: case R_X86_64_64:
pointer:
if (eh != NULL && (sec->flags & SEC_CODE) != 0) if (eh != NULL && (sec->flags & SEC_CODE) != 0)
eh->has_non_got_reloc = 1; eh->has_non_got_reloc = 1;
/* STT_GNU_IFUNC symbol must go through PLT even if it is /* STT_GNU_IFUNC symbol must go through PLT even if it is
@@ -2610,7 +2656,7 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
struct elf_dyn_relocs *p; struct elf_dyn_relocs *p;
const struct elf_backend_data *bed; const struct elf_backend_data *bed;
unsigned int plt_entry_size; unsigned int plt_entry_size;
bfd_boolean resolved_to_zero; bfd_boolean resolved_to_zero_or_abs;
if (h->root.type == bfd_link_hash_indirect) if (h->root.type == bfd_link_hash_indirect)
return TRUE; return TRUE;
@@ -2624,7 +2670,7 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
bed = get_elf_backend_data (info->output_bfd); bed = get_elf_backend_data (info->output_bfd);
plt_entry_size = GET_PLT_ENTRY_SIZE (info->output_bfd); plt_entry_size = GET_PLT_ENTRY_SIZE (info->output_bfd);
resolved_to_zero = UNDEFINED_WEAK_RESOLVED_TO_ZERO (info, eh); resolved_to_zero_or_abs = RESOLVED_TO_ZERO_OR_ABS (info, eh);
/* We can't use the GOT PLT if pointer equality is needed since /* We can't use the GOT PLT if pointer equality is needed since
finish_dynamic_symbol won't clear symbol value and the dynamic finish_dynamic_symbol won't clear symbol value and the dynamic
@@ -2699,11 +2745,11 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
use_plt_got = eh->plt_got.refcount > 0; use_plt_got = eh->plt_got.refcount > 0;
/* Make sure this symbol is output as a dynamic symbol. /* Make sure this symbol is output as a dynamic symbol. Absolute
Undefined weak syms won't yet be marked as dynamic. */ and undefined weak symbols won't yet be marked as dynamic. */
if (h->dynindx == -1 if (h->dynindx == -1
&& !h->forced_local && !h->forced_local
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
{ {
if (! bfd_elf_link_record_dynamic_symbol (info, h)) if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
@@ -2777,9 +2823,9 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
script. */ script. */
htab->elf.sgotplt->size += GOT_ENTRY_SIZE; htab->elf.sgotplt->size += GOT_ENTRY_SIZE;
/* There should be no PLT relocation against resolved /* There should be no PLT relocation against absolute
undefined weak symbol in executable. */ and resolved undefined weak symbols in executable. */
if (!resolved_to_zero) if (!resolved_to_zero_or_abs)
{ {
/* We also need to make an entry in the .rela.plt /* We also need to make an entry in the .rela.plt
section. */ section. */
@@ -2819,11 +2865,11 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
bfd_boolean dyn; bfd_boolean dyn;
int tls_type = elf_x86_64_hash_entry (h)->tls_type; int tls_type = elf_x86_64_hash_entry (h)->tls_type;
/* Make sure this symbol is output as a dynamic symbol. /* Make sure this symbol is output as a dynamic symbol. Absolute
Undefined weak syms won't yet be marked as dynamic. */ and undefined weak symbols won't yet be marked as dynamic. */
if (h->dynindx == -1 if (h->dynindx == -1
&& !h->forced_local && !h->forced_local
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
{ {
if (! bfd_elf_link_record_dynamic_symbol (info, h)) if (! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
@@ -2848,8 +2894,8 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
dyn = htab->elf.dynamic_sections_created; dyn = htab->elf.dynamic_sections_created;
/* R_X86_64_TLSGD needs one dynamic relocation if local symbol /* R_X86_64_TLSGD needs one dynamic relocation if local symbol
and two if global. R_X86_64_GOTTPOFF needs one dynamic and two if global. R_X86_64_GOTTPOFF needs one dynamic
relocation. No dynamic relocation against resolved undefined relocation. No dynamic relocation against absolute and resolved
weak symbol in executable. */ undefined weak symbols in executable. */
if ((GOT_TLS_GD_P (tls_type) && h->dynindx == -1) if ((GOT_TLS_GD_P (tls_type) && h->dynindx == -1)
|| tls_type == GOT_TLS_IE) || tls_type == GOT_TLS_IE)
htab->elf.srelgot->size += bed->s->sizeof_rela; htab->elf.srelgot->size += bed->s->sizeof_rela;
@@ -2857,7 +2903,7 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
htab->elf.srelgot->size += 2 * bed->s->sizeof_rela; htab->elf.srelgot->size += 2 * bed->s->sizeof_rela;
else if (! GOT_TLS_GDESC_P (tls_type) else if (! GOT_TLS_GDESC_P (tls_type)
&& ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT && ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
|| h->root.type != bfd_link_hash_undefweak) || h->root.type != bfd_link_hash_undefweak)
&& (bfd_link_pic (info) && (bfd_link_pic (info)
|| WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h))) || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h)))
@@ -2882,6 +2928,8 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
if (bfd_link_pic (info)) if (bfd_link_pic (info))
{ {
struct elf_dyn_relocs **pp;
/* Relocs that use pc_count are those that appear on a call /* Relocs that use pc_count are those that appear on a call
insn, or certain REL relocs that can generated via assembly. insn, or certain REL relocs that can generated via assembly.
We want calls to protected symbols to resolve directly to the We want calls to protected symbols to resolve directly to the
@@ -2890,8 +2938,6 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
should avoid writing weird assembly. */ should avoid writing weird assembly. */
if (SYMBOL_CALLS_LOCAL (info, h)) if (SYMBOL_CALLS_LOCAL (info, h))
{ {
struct elf_dyn_relocs **pp;
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; ) for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
{ {
p->count -= p->pc_count; p->count -= p->pc_count;
@@ -2912,29 +2958,41 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
/* Undefined weak symbol is never bound locally in shared /* Undefined weak symbol is never bound locally in shared
library. */ library. */
if (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT if (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT
|| resolved_to_zero) || resolved_to_zero_or_abs)
eh->dyn_relocs = NULL; eh->dyn_relocs = NULL;
else if (h->dynindx == -1 else if (h->dynindx == -1
&& ! h->forced_local && ! h->forced_local
&& ! bfd_elf_link_record_dynamic_symbol (info, h)) && ! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
} }
/* For PIE, discard space for pc-relative relocs against else if (h->def_regular)
symbols which turn out to need copy relocs. */
else if (bfd_link_executable (info)
&& (h->needs_copy || eh->needs_copy)
&& h->def_dynamic
&& !h->def_regular)
{ {
struct elf_dyn_relocs **pp; /* Discard space for non-pc-relative relocs against
absolute symbols which are always resolved at
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; ) link-time. */
{ if (resolved_to_zero_or_abs)
if (p->pc_count != 0) for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
*pp = p->next; {
else if (p->pc_count == 0)
pp = &p->next; *pp = p->next;
} else
pp = &p->next;
}
}
else
{
/* For PIE, discard space for pc-relative relocs against
symbols which turn out to need copy relocs. */
if (bfd_link_executable (info)
&& (h->needs_copy || eh->needs_copy)
&& h->def_dynamic)
for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
{
if (p->pc_count != 0)
*pp = p->next;
else
pp = &p->next;
}
} }
} }
} }
@@ -2948,7 +3006,7 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
if ((!h->non_got_ref if ((!h->non_got_ref
|| eh->func_pointer_refcount > 0 || eh->func_pointer_refcount > 0
|| (h->root.type == bfd_link_hash_undefweak || (h->root.type == bfd_link_hash_undefweak
&& !resolved_to_zero)) && !resolved_to_zero_or_abs))
&& ((h->def_dynamic && ((h->def_dynamic
&& !h->def_regular) && !h->def_regular)
|| (htab->elf.dynamic_sections_created || (htab->elf.dynamic_sections_created
@@ -2956,10 +3014,11 @@ elf_x86_64_allocate_dynrelocs (struct elf_link_hash_entry *h, void * inf)
|| h->root.type == bfd_link_hash_undefined)))) || h->root.type == bfd_link_hash_undefined))))
{ {
/* Make sure this symbol is output as a dynamic symbol. /* Make sure this symbol is output as a dynamic symbol.
Undefined weak syms won't yet be marked as dynamic. */ Absolute and undefined weak symbols won't yet be marked
as dynamic. */
if (h->dynindx == -1 if (h->dynindx == -1
&& ! h->forced_local && ! h->forced_local
&& ! resolved_to_zero && ! resolved_to_zero_or_abs
&& ! bfd_elf_link_record_dynamic_symbol (info, h)) && ! bfd_elf_link_record_dynamic_symbol (info, h))
return FALSE; return FALSE;
@@ -3225,8 +3284,8 @@ elf_x86_64_convert_load (bfd *abfd, asection *sec,
It is OK convert mov with R_X86_64_GOTPCREL to It is OK convert mov with R_X86_64_GOTPCREL to
R_X86_64_PC32. */ R_X86_64_PC32. */
if ((relocx || opcode == 0x8b) if ((relocx || opcode == 0x8b)
&& UNDEFINED_WEAK_RESOLVED_TO_ZERO (link_info, && RESOLVED_TO_ZERO_OR_ABS (link_info,
elf_x86_64_hash_entry (h))) elf_x86_64_hash_entry (h)))
{ {
if (opcode == 0xff) if (opcode == 0xff)
{ {
@@ -3256,12 +3315,9 @@ elf_x86_64_convert_load (bfd *abfd, asection *sec,
&& h != htab->elf.hdynamic && h != htab->elf.hdynamic
&& SYMBOL_REFERENCES_LOCAL (link_info, h)) && SYMBOL_REFERENCES_LOCAL (link_info, h))
{ {
/* bfd_link_hash_new or bfd_link_hash_undefined is /* This is set by an assignment in a linker script in
set by an assignment in a linker script in
bfd_elf_record_link_assignment. */ bfd_elf_record_link_assignment. */
if (h->def_regular if (h->def_linker)
&& (h->root.type == bfd_link_hash_new
|| h->root.type == bfd_link_hash_undefined))
{ {
/* Skip since R_X86_64_32/R_X86_64_32S may overflow. */ /* Skip since R_X86_64_32/R_X86_64_32S may overflow. */
if (require_reloc_pc32) if (require_reloc_pc32)
@@ -4034,42 +4090,6 @@ is_32bit_relative_branch (bfd_byte *contents, bfd_vma offset)
&& (contents [offset - 1] & 0xf0) == 0x80)); && (contents [offset - 1] & 0xf0) == 0x80));
} }
static bfd_boolean
elf_x86_64_need_pic (bfd *input_bfd, struct elf_link_hash_entry *h,
reloc_howto_type *howto)
{
const char *fmt;
const char *v;
const char *pic = "";
switch (ELF_ST_VISIBILITY (h->other))
{
case STV_HIDDEN:
v = _("hidden symbol");
break;
case STV_INTERNAL:
v = _("internal symbol");
break;
case STV_PROTECTED:
v = _("protected symbol");
break;
default:
v = _("symbol");
pic = _("; recompile with -fPIC");
break;
}
if (h->def_regular)
fmt = _("%B: relocation %s against %s `%s' can not be used when making a shared object%s");
else
fmt = _("%B: relocation %s against undefined %s `%s' can not be used when making a shared object%s");
(*_bfd_error_handler) (fmt, input_bfd, howto->name,
v, h->root.root.string, pic);
bfd_set_error (bfd_error_bad_value);
return FALSE;
}
/* Relocate an x86_64 ELF section. */ /* Relocate an x86_64 ELF section. */
static bfd_boolean static bfd_boolean
@@ -4122,7 +4142,7 @@ elf_x86_64_relocate_section (bfd *output_bfd,
int tls_type; int tls_type;
asection *base_got, *resolved_plt; asection *base_got, *resolved_plt;
bfd_vma st_size; bfd_vma st_size;
bfd_boolean resolved_to_zero; bfd_boolean resolved_to_zero_or_abs;
r_type = ELF32_R_TYPE (rel->r_info); r_type = ELF32_R_TYPE (rel->r_info);
if (r_type == (int) R_X86_64_GNU_VTINHERIT if (r_type == (int) R_X86_64_GNU_VTINHERIT
@@ -4433,8 +4453,8 @@ elf_x86_64_relocate_section (bfd *output_bfd,
} }
} }
resolved_to_zero = (eh != NULL resolved_to_zero_or_abs = (eh != NULL
&& UNDEFINED_WEAK_RESOLVED_TO_ZERO (info, eh)); && RESOLVED_TO_ZERO_OR_ABS (info, eh));
/* When generating a shared object, the relocations handled here are /* When generating a shared object, the relocations handled here are
copied into the output file to be resolved at run time. */ copied into the output file to be resolved at run time. */
@@ -4705,6 +4725,43 @@ elf_x86_64_relocate_section (bfd *output_bfd,
unresolved_reloc = FALSE; unresolved_reloc = FALSE;
break; break;
case R_X86_64_PC32:
/* R_X86_64_PC32 against absolute symbol can't be resolved
for shared object at link-time since the load address is
unknown. */
if (resolved_to_zero_or_abs
&& h->root.type != bfd_link_hash_undefweak
&& bfd_link_pic (info))
return elf_x86_64_need_pic (input_bfd, h, symtab_hdr, sym,
howto);
goto pc_relative;
case R_X86_64_32:
case R_X86_64_32S:
/* R_X86_64_32/R_X86_64_32S relocations against undefined weak
symbol in executable is resolved to zero. They against
absolute symbol are always resolved at link-time. */
if (resolved_to_zero_or_abs)
break;
if ((ABI_64_P (output_bfd)
|| r_type == R_X86_64_32S)
&& (input_section->flags & SEC_ALLOC) != 0
&& (input_section->flags & SEC_READONLY) != 0
&& bfd_link_pic (info))
return elf_x86_64_need_pic (input_bfd, h, symtab_hdr, sym,
howto);
goto direct;
case R_X86_64_64:
/* R_X86_64_64 relocation against absolute symbol or undefined
weak symbol in executable is resolved at link-time. */
if (resolved_to_zero_or_abs)
break;
goto direct;
case R_X86_64_SIZE32: case R_X86_64_SIZE32:
case R_X86_64_SIZE64: case R_X86_64_SIZE64:
/* Set to symbol size. */ /* Set to symbol size. */
@@ -4713,16 +4770,17 @@ elf_x86_64_relocate_section (bfd *output_bfd,
case R_X86_64_PC8: case R_X86_64_PC8:
case R_X86_64_PC16: case R_X86_64_PC16:
case R_X86_64_PC32:
case R_X86_64_PC32_BND: case R_X86_64_PC32_BND:
pc_relative:
/* Don't complain about -fPIC if the symbol is undefined when /* Don't complain about -fPIC if the symbol is undefined when
building executable unless it is unresolved weak symbol. */ building executable unless it is absolute or unresolved weak
symbol. */
if ((input_section->flags & SEC_ALLOC) != 0 if ((input_section->flags & SEC_ALLOC) != 0
&& (input_section->flags & SEC_READONLY) != 0 && (input_section->flags & SEC_READONLY) != 0
&& h != NULL && h != NULL
&& ((bfd_link_executable (info) && ((bfd_link_executable (info)
&& h->root.type == bfd_link_hash_undefweak && h->root.type == bfd_link_hash_undefweak
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
|| (bfd_link_pic (info) || (bfd_link_pic (info)
&& !(bfd_link_pie (info) && !(bfd_link_pie (info)
&& h->root.type == bfd_link_hash_undefined)))) && h->root.type == bfd_link_hash_undefined))))
@@ -4750,15 +4808,14 @@ elf_x86_64_relocate_section (bfd *output_bfd,
} }
if (fail) if (fail)
return elf_x86_64_need_pic (input_bfd, h, howto); return elf_x86_64_need_pic (input_bfd, h, symtab_hdr,
sym, howto);
} }
/* Fall through. */ /* Fall through. */
case R_X86_64_8: case R_X86_64_8:
case R_X86_64_16: case R_X86_64_16:
case R_X86_64_32:
case R_X86_64_PC64: case R_X86_64_PC64:
case R_X86_64_64:
/* FIXME: The ABI says the linker should make sure the value is /* FIXME: The ABI says the linker should make sure the value is
the same when it's zeroextended to 64 bit. */ the same when it's zeroextended to 64 bit. */
@@ -4770,7 +4827,7 @@ direct:
if the symbol needs copy reloc or the symbol is undefined if the symbol needs copy reloc or the symbol is undefined
when building executable. Copy dynamic function pointer when building executable. Copy dynamic function pointer
relocations. Don't generate dynamic relocations against relocations. Don't generate dynamic relocations against
resolved undefined weak symbols in PIE. */ absolute nor resolved undefined weak symbols in PIE. */
if ((bfd_link_pic (info) if ((bfd_link_pic (info)
&& !(bfd_link_pie (info) && !(bfd_link_pie (info)
&& h != NULL && h != NULL
@@ -4780,7 +4837,7 @@ direct:
&& IS_X86_64_PCREL_TYPE (r_type)) && IS_X86_64_PCREL_TYPE (r_type))
&& (h == NULL && (h == NULL
|| ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT || ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
|| h->root.type != bfd_link_hash_undefweak)) || h->root.type != bfd_link_hash_undefweak))
&& ((! IS_X86_64_PCREL_TYPE (r_type) && ((! IS_X86_64_PCREL_TYPE (r_type)
&& r_type != R_X86_64_SIZE32 && r_type != R_X86_64_SIZE32
@@ -4793,7 +4850,7 @@ direct:
&& (!h->non_got_ref && (!h->non_got_ref
|| eh->func_pointer_refcount > 0 || eh->func_pointer_refcount > 0
|| (h->root.type == bfd_link_hash_undefweak || (h->root.type == bfd_link_hash_undefweak
&& !resolved_to_zero)) && !resolved_to_zero_or_abs))
&& ((h->def_dynamic && !h->def_regular) && ((h->def_dynamic && !h->def_regular)
/* Undefined weak symbol is bound locally when /* Undefined weak symbol is bound locally when
PIC is false. */ PIC is false. */
@@ -4835,8 +4892,9 @@ direct:
if ((r_type != R_X86_64_PC64 && r_type != R_X86_64_64) if ((r_type != R_X86_64_PC64 && r_type != R_X86_64_64)
&& bfd_link_executable (info) && bfd_link_executable (info)
&& h->root.type == bfd_link_hash_undefweak && h->root.type == bfd_link_hash_undefweak
&& !resolved_to_zero) && !resolved_to_zero_or_abs)
return elf_x86_64_need_pic (input_bfd, h, howto); return elf_x86_64_need_pic (input_bfd, h,
symtab_hdr, sym, howto);
outrel.r_info = htab->r_info (h->dynindx, r_type); outrel.r_info = htab->r_info (h->dynindx, r_type);
outrel.r_addend = rel->r_addend; outrel.r_addend = rel->r_addend;
} }

View File

@@ -543,7 +543,8 @@ bfd_elf_record_link_assignment (bfd *output_bfd,
struct bfd_link_info *info, struct bfd_link_info *info,
const char *name, const char *name,
bfd_boolean provide, bfd_boolean provide,
bfd_boolean hidden) bfd_boolean hidden,
bfd_boolean abssym)
{ {
struct elf_link_hash_entry *h, *hv; struct elf_link_hash_entry *h, *hv;
struct elf_link_hash_table *htab; struct elf_link_hash_table *htab;
@@ -628,6 +629,8 @@ bfd_elf_record_link_assignment (bfd *output_bfd,
h->verinfo.verdef = NULL; h->verinfo.verdef = NULL;
h->def_regular = 1; h->def_regular = 1;
h->def_linker = 1;
h->def_linker_abs = abssym;
if (hidden) if (hidden)
{ {

View File

@@ -1354,10 +1354,14 @@ gld${EMULATION_NAME}_find_exp_assignment (etree_type *exp)
will do no harm. */ will do no harm. */
if (strcmp (exp->assign.dst, ".") != 0) if (strcmp (exp->assign.dst, ".") != 0)
{ {
/* Symbol defined --defsym command-line option or absolute
symbol defined in linker script have absolute value. */
if (!bfd_elf_record_link_assignment (link_info.output_bfd, if (!bfd_elf_record_link_assignment (link_info.output_bfd,
&link_info, &link_info,
exp->assign.dst, provide, exp->assign.dst, provide,
exp->assign.hidden)) exp->assign.hidden,
(exp->assign.defsym
|| !expld.rel_from_abs)))
einfo ("%P%F: failed to record assignment to %s: %E\n", einfo ("%P%F: failed to record assignment to %s: %E\n",
exp->assign.dst); exp->assign.dst);
} }
@@ -1506,6 +1510,7 @@ gld${EMULATION_NAME}_before_allocation (void)
library. */ library. */
ehdr_start = h; ehdr_start = h;
ehdr_start_save = h->root; ehdr_start_save = h->root;
h->def_linker = 1;
h->root.type = bfd_link_hash_defined; h->root.type = bfd_link_hash_defined;
h->root.u.def.section = bfd_abs_section_ptr; h->root.u.def.section = bfd_abs_section_ptr;
h->root.u.def.value = 0; h->root.u.def.value = 0;

View File

@@ -0,0 +1,6 @@
#source: pr19818a.s
#ld: -pie --defsym foo=0x7fffffff
#readelf: -r --wide
#target: *-*-linux* *-*-gnu* *-*-solaris*
There are no relocations in this file.

View File

@@ -0,0 +1,12 @@
.text
.global start /* Used by SH targets. */
start:
.global _start
_start:
.global __start
__start:
.global main /* Used by HPPA targets. */
main:
.dc.a 0
.data
.dc.a foo

View File

@@ -0,0 +1,7 @@
#source: pr19818a.s
#source: pr19818b.s
#ld: -pie
#readelf: -r --wide
#target: *-*-linux* *-*-gnu* *-*-solaris*
There are no relocations in this file.

View File

@@ -0,0 +1,2 @@
.globl foo
foo = 0x7fffffff

View File

@@ -364,6 +364,26 @@ run_dump_test "pr19609-2c"
run_dump_test "undefweaka" run_dump_test "undefweaka"
run_dump_test "undefweakb" run_dump_test "undefweakb"
run_dump_test "pr19539" run_dump_test "pr19539"
run_dump_test "pr19818-1a"
run_dump_test "pr19818-1b"
run_dump_test "pr19818-1c"
run_dump_test "pr19818-1a"
run_dump_test "pr19818-1e"
run_dump_test "pr19818-1f"
run_dump_test "pr19818-1g"
run_dump_test "pr19818-1h"
run_dump_test "pr19818-1i"
run_dump_test "pr19818-1j"
run_dump_test "pr19818-1k"
run_dump_test "pr19818-1l"
run_dump_test "pr19818-2a"
run_dump_test "pr19818-2b"
run_dump_test "pr19818-2c"
run_dump_test "pr19818-2d"
run_dump_test "pr19818-2e"
run_dump_test "pr19818-2f"
run_dump_test "pr19818-2g"
run_dump_test "pr19818-2h"
if { !([istarget "i?86-*-linux*"] if { !([istarget "i?86-*-linux*"]
|| [istarget "i?86-*-gnu*"] || [istarget "i?86-*-gnu*"]

View File

@@ -0,0 +1 @@
foo = 0xffffffff;

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --32
#ld: -pie -m elf_i386 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,4 @@
.text
.global _start
_start:
movl $foo, %eax

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --32
#ld: -pie -m elf_i386 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,2 @@
.globl foo
foo = 0xffffffff

View File

@@ -0,0 +1,7 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --32
#ld: -pie -m elf_i386
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,3 @@
.globl foo
.hidden foo
foo = 0xffffffff

View File

@@ -0,0 +1,14 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --32
#ld: -pie -m elf_i386
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --32
#ld: -shared -Bsymbolic -m elf_i386 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --32
#ld: -shared -Bsymbolic -m elf_i386 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,7 @@
#source: pr19818-1a.s
#source: pr19818-1c.s
#as: --32
#ld: -shared -m elf_i386
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,14 @@
#source: pr19818-1a.s
#source: pr19818-1c.s
#as: --32
#ld: -shared -m elf_i386
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,8 @@
#source: pr19818-1a.s
#as: --32
#ld: -shared -m elf_i386 --defsym foo=0xffffffff -z nocombreloc
#readelf: -r --wide
Relocation section '.rel.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Sym. Value Symbol's Name
[0-9a-f]+ +[0-9a-f]+ +R_386_32 +ffffffff +foo

View File

@@ -0,0 +1,9 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --32
#ld: -shared -m elf_i386 -z nocombreloc
#readelf: -r --wide
Relocation section '.rel.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Sym. Value Symbol's Name
[0-9a-f]+ +[0-9a-f]+ +R_386_32 +ffffffff +foo

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --32
#ld: -pie -m elf_i386 -T pr19818-1.t
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --32
#ld: -pie -m elf_i386 -T pr19818-1.t
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,4 @@
.text
.global _start
_start:
movl foo@GOT(%ebx), %eax

View File

@@ -0,0 +1,6 @@
#source: pr19818-2.s
#as: --32 -mrelax-relocations=no
#ld: -pie -m elf_i386 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-2.s
#as: --32
#ld: -pie -m elf_i386 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: c7 c0 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,7 @@
#source: pr19818-2.s
#source: pr19818-1b.s
#as: --32
#ld: -pie -m elf_i386
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,14 @@
#source: pr19818-2.s
#source: pr19818-1b.s
#as: --32
#ld: -pie -m elf_i386
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: c7 c0 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,6 @@
#source: pr19818-2.s
#as: --32 -mrelax-relocations=no
#ld: -shared -Bsymbolic -m elf_i386 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-2.s
#as: --32
#ld: -shared -Bsymbolic -m elf_i386 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: c7 c0 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,7 @@
#source: pr19818-2.s
#source: pr19818-1c.s
#as: --32
#ld: -shared -m elf_i386
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,14 @@
#source: pr19818-2.s
#source: pr19818-1c.s
#as: --32
#ld: -shared -m elf_i386
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: c7 c0 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1 @@
foo = 0xffffffff;

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --64
#ld: -pie -m elf_x86_64 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,4 @@
.text
.global _start
_start:
movl $foo, %eax

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --64
#ld: -pie -m elf_x86_64 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,2 @@
.globl foo
foo = 0xffffffff

View File

@@ -0,0 +1,7 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --64
#ld: -pie -m elf_x86_64
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,3 @@
.globl foo
.hidden foo
foo = 0xffffffff

View File

@@ -0,0 +1,14 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --64
#ld: -pie -m elf_x86_64
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --x32
#ld: -pie -m elf32_x86_64 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --x32
#ld: -pie -m elf32_x86_64 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,7 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --x32
#ld: -pie -m elf32_x86_64
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,14 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --x32
#ld: -pie -m elf32_x86_64
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --64
#ld: -shared -Bsymbolic -m elf_x86_64 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --64
#ld: -shared -Bsymbolic -m elf_x86_64 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,7 @@
#source: pr19818-1a.s
#source: pr19818-1c.s
#as: --64
#ld: -shared -m elf_x86_64
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,14 @@
#source: pr19818-1a.s
#source: pr19818-1c.s
#as: --64
#ld: -shared -m elf_x86_64
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --x32
#ld: -shared -Bsymbolic -m elf32_x86_64 --defsym foo=0xffffffff
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --x32
#ld: -shared -Bsymbolic -m elf32_x86_64 --defsym foo=0xffffffff
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,7 @@
#source: pr19818-1a.s
#source: pr19818-1c.s
#as: --x32
#ld: -shared -m elf32_x86_64
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,14 @@
#source: pr19818-1a.s
#source: pr19818-1c.s
#as: --x32
#ld: -shared -m elf32_x86_64
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,4 @@
#source: pr19818-1a.s
#as: --64 -mrelax-relocations=no
#ld: -shared -m elf_x86_64 --defsym foo=0xffffffff
#error: .*relocation R_X86_64_32 against absolute symbol `foo' can not be used when making a shared object

View File

@@ -0,0 +1,5 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --64 -mrelax-relocations=no
#ld: -shared -m elf_x86_64
#error: .*relocation R_X86_64_32 against absolute symbol `foo' can not be used when making a shared object

View File

@@ -0,0 +1,8 @@
#source: pr19818-1a.s
#as: --x32 -mrelax-relocations=no
#ld: -shared -m elf32_x86_64 --defsym foo=0xffffffff -z nocombreloc
#readelf: -r --wide
Relocation section '.rela.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Sym. Value Symbol's Name \+ Addend
[0-9a-f]+ +[0-9a-f]+ +R_X86_64_32 +ffffffff +foo \+ 0

View File

@@ -0,0 +1,9 @@
#source: pr19818-1a.s
#source: pr19818-1b.s
#as: --x32 -mrelax-relocations=no
#ld: -shared -m elf32_x86_64 -z nocombreloc
#readelf: -r --wide
Relocation section '.rela.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Sym. Value Symbol's Name \+ Addend
[0-9a-f]+ +[0-9a-f]+ +R_X86_64_32 +ffffffff +foo \+ 0

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --64
#ld: -pie -m elf_x86_64 -T pr19818-1.t
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --64
#ld: -pie -m elf_x86_64 -T pr19818-1.t
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,6 @@
#source: pr19818-1a.s
#as: --x32
#ld: -pie -m elf32_x86_64 -T pr19818-1.t
#readelf: -r --wide
There are no relocations in this file.

View File

@@ -0,0 +1,13 @@
#source: pr19818-1a.s
#as: --x32
#ld: -pie -m elf32_x86_64 -T pr19818-1.t
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ff ff ff ff mov \$0xffffffff,%eax
#pass

View File

@@ -0,0 +1,4 @@
#source: pr19818-1a.s
#as: --64
#ld: -pie -melf_x86_64 --defsym foo=0x100000000
#error: .*relocation truncated to fit: R_X86_64_32 .*

View File

@@ -0,0 +1,4 @@
.text
.global _start
_start:
leal foo(%rip), %eax

View File

@@ -0,0 +1,4 @@
#source: pr19818-2.s
#as: --64 -mrelax-relocations=no
#ld: -pie -m elf_x86_64 --defsym foo=0xffffffff
#error: .*relocation R_X86_64_PC32 against absolute symbol `foo' can not be used when making a shared object

View File

@@ -0,0 +1,5 @@
#source: pr19818-2.s
#source: pr19818-1b.s
#as: --64 -mrelax-relocations=no
#ld: -pie -m elf_x86_64
#error: .*relocation R_X86_64_PC32 against absolute symbol `foo' can not be used when making a shared object

View File

@@ -0,0 +1,4 @@
#source: pr19818-2.s
#as: --x32 -mrelax-relocations=no
#ld: -pie -m elf32_x86_64 --defsym foo=0xffffffff
#error: .*relocation R_X86_64_PC32 against absolute symbol `foo' can not be used when making a shared object

View File

@@ -0,0 +1,5 @@
#source: pr19818-2.s
#source: pr19818-1b.s
#as: --x32 -mrelax-relocations=no
#ld: -pie -m elf32_x86_64
#error: .*relocation R_X86_64_PC32 against absolute symbol `foo' can not be used when making a shared object

View File

@@ -0,0 +1,4 @@
.text
.global _start
_start:
movabs $foo, %rax

View File

@@ -0,0 +1,8 @@
#source: pr19818-3.s
#as: --64 -mrelax-relocations=no
#ld: -shared -m elf_x86_64 --defsym foo=0xffffffff -z nocombreloc
#readelf: -r --wide
Relocation section '.rela.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Symbol's Value Symbol's Name \+ Addend
[0-9a-f]+ +[0-9a-f]+ +R_X86_64_64 +0+ffffffff +foo \+ 0

View File

@@ -0,0 +1,9 @@
#source: pr19818-3.s
#source: pr19818-1b.s
#as: --64 -mrelax-relocations=no
#ld: -shared -m elf_x86_64 -z nocombreloc
#readelf: -r --wide
Relocation section '.rela.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Symbol's Value Symbol's Name \+ Addend
[0-9a-f]+ +[0-9a-f]+ +R_X86_64_64 +0+ffffffff +foo \+ 0

View File

@@ -0,0 +1,8 @@
#source: pr19818-3.s
#as: --x32 -mrelax-relocations=no
#ld: -shared -m elf32_x86_64 --defsym foo=0xffffffff -z nocombreloc
#readelf: -r --wide
Relocation section '.rela.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Sym. Value Symbol's Name \+ Addend
[0-9a-f]+ +[0-9a-f]+ +R_X86_64_32 +ffffffff +foo \+ 0

View File

@@ -0,0 +1,9 @@
#source: pr19818-3.s
#source: pr19818-1b.s
#as: --x32 -mrelax-relocations=no
#ld: -shared -m elf32_x86_64 -z nocombreloc
#readelf: -r --wide
Relocation section '.rela.text' at offset 0x[0-9a-f]+ contains 1 entries:
Offset Info Type Sym. Value Symbol's Name \+ Addend
[0-9a-f]+ +[0-9a-f]+ +R_X86_64_32 +ffffffff +foo \+ 0

View File

@@ -0,0 +1,5 @@
.globl foo
.type foo, @object
.data
foo:
.long 0

View File

@@ -0,0 +1,5 @@
#source: pr19818-4.s
#source: pr19818-1a.s
#as: --64
#ld: -pie -melf_x86_64
#error: .*relocation R_X86_64_32 against symbol `foo' can not be used when making a shared object; recompile with -fPIC

View File

@@ -0,0 +1,14 @@
#source: pr19818-4.s
#source: pr19818-1a.s
#as: --x32
#ld: -pie -melf32_x86_64
#objdump: -dw
.*: +file format .*
Disassembly of section .text:
[a-f0-9]+ <_start>:
[ ]*[a-f0-9]+: b8 ([0-9a-f]{2} ){4} mov \$0x[a-f0-9]+,%eax
#pass

View File

@@ -0,0 +1,8 @@
.globl _start
.type _start, @function
_start:
movq $foo, %rax
.size _start, .-_start
.data
foo:
.quad 0

View File

@@ -0,0 +1,4 @@
#source: pr19818-5.s
#as: --64
#ld: -pie -melf_x86_64
#error: .*relocation R_X86_64_32S against symbol `.data' can not be used when making a shared object; recompile with -fPIC

View File

@@ -0,0 +1,4 @@
#source: pr19818-5.s
#as: --x32
#ld: -pie -melf32_x86_64
#error: .*relocation R_X86_64_32S against symbol `.data' can not be used when making a shared object; recompile with -fPIC

View File

@@ -247,6 +247,43 @@ run_dump_test "largecomm-1e"
run_dump_test "largecomm-1f" run_dump_test "largecomm-1f"
run_dump_test "pr19539a" run_dump_test "pr19539a"
run_dump_test "pr19539b" run_dump_test "pr19539b"
run_dump_test "pr19818-1a"
run_dump_test "pr19818-1b"
run_dump_test "pr19818-1c"
run_dump_test "pr19818-1d"
run_dump_test "pr19818-1e"
run_dump_test "pr19818-1f"
run_dump_test "pr19818-1g"
run_dump_test "pr19818-1h"
run_dump_test "pr19818-1i"
run_dump_test "pr19818-1j"
run_dump_test "pr19818-1k"
run_dump_test "pr19818-1l"
run_dump_test "pr19818-1m"
run_dump_test "pr19818-1n"
run_dump_test "pr19818-1o"
run_dump_test "pr19818-1p"
run_dump_test "pr19818-1q"
run_dump_test "pr19818-1r"
run_dump_test "pr19818-1s"
run_dump_test "pr19818-1t"
run_dump_test "pr19818-1u"
run_dump_test "pr19818-1v"
run_dump_test "pr19818-1w"
run_dump_test "pr19818-1x"
run_dump_test "pr19818-1y"
run_dump_test "pr19818-2a"
run_dump_test "pr19818-2b"
run_dump_test "pr19818-2c"
run_dump_test "pr19818-2d"
run_dump_test "pr19818-3a"
run_dump_test "pr19818-3b"
run_dump_test "pr19818-3c"
run_dump_test "pr19818-3d"
run_dump_test "pr19818-4a"
run_dump_test "pr19818-4b"
run_dump_test "pr19818-5a"
run_dump_test "pr19818-5b"
if { ![istarget "x86_64-*-linux*"] && ![istarget "x86_64-*-nacl*"]} { if { ![istarget "x86_64-*-linux*"] && ![istarget "x86_64-*-nacl*"]} {
return return