#include "objalloc.h"
#include "elf/aarch64.h"
#include "elfxx-aarch64.h"
+#include "cpu-aarch64.h"
#define ARCH_SIZE NN
PC relative address inline. */
/* MOV[NZ]: ((S+A-P) >> 0) & 0xffff */
- HOWTO64 (AARCH64_R (MOVW_PREL_G0), /* type */
+ HOWTO (AARCH64_R (MOVW_PREL_G0), /* type */
0, /* rightshift */
2, /* size (0 = byte, 1 = short, 2 = long) */
17, /* bitsize */
TRUE), /* pcrel_offset */
/* MOVK: ((S+A-P) >> 0) & 0xffff [no overflow check] */
- HOWTO64 (AARCH64_R (MOVW_PREL_G0_NC), /* type */
+ HOWTO (AARCH64_R (MOVW_PREL_G0_NC), /* type */
0, /* rightshift */
2, /* size (0 = byte, 1 = short, 2 = long) */
16, /* bitsize */
TRUE), /* pcrel_offset */
/* MOV[NZ]: ((S+A-P) >> 16) & 0xffff */
- HOWTO64 (AARCH64_R (MOVW_PREL_G1), /* type */
+ HOWTO (AARCH64_R (MOVW_PREL_G1), /* type */
16, /* rightshift */
2, /* size (0 = byte, 1 = short, 2 = long) */
17, /* bitsize */
+ offset);
r_type = elfNN_aarch64_bfd_reloc_from_type (input_bfd, r_type);
- value = _bfd_aarch64_elf_resolve_relocation (r_type, place, value, 0, FALSE);
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, r_type, place,
+ value, 0, FALSE);
return _bfd_aarch64_elf_put_addend (input_bfd,
input_section->contents + offset, r_type,
howto, value) == bfd_reloc_ok;
/* FALLTHROUGH */
case BFD_RELOC_AARCH64_CALL26:
case BFD_RELOC_AARCH64_JUMP26:
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
signed_addend,
weak_undef_p);
return _bfd_aarch64_elf_put_addend (input_bfd, hit_data, bfd_r_type,
addend = (globals->root.sgot->output_section->vma
+ globals->root.sgot->output_offset);
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
addend, weak_undef_p);
return _bfd_aarch64_elf_put_addend (input_bfd, hit_data, bfd_r_type, howto, value);
case BFD_RELOC_AARCH64_ADD_LO12:
signed_addend = 0;
}
}
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
signed_addend, weak_undef_p);
*unresolved_reloc_p = FALSE;
break;
case BFD_RELOC_AARCH64_MOVW_G2_S:
case BFD_RELOC_AARCH64_MOVW_G3:
case BFD_RELOC_AARCH64_TSTBR14:
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
signed_addend, weak_undef_p);
break;
if (aarch64_relocation_aginst_gp_p (bfd_r_type))
addend = (globals->root.sgot->output_section->vma
+ globals->root.sgot->output_offset);
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
addend, weak_undef_p);
}
else
if (aarch64_relocation_aginst_gp_p (bfd_r_type))
addend = base_got->output_section->vma + base_got->output_offset;
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
addend, weak_undef_p);
}
+ globals->root.sgot->output_section->vma
+ globals->root.sgot->output_offset);
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
0, weak_undef_p);
*unresolved_reloc_p = FALSE;
break;
return bfd_reloc_notsupported;
value = symbol_got_offset (input_bfd, h, r_symndx);
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
0, weak_undef_p);
*unresolved_reloc_p = FALSE;
break;
case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1:
case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1_NC:
case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G2:
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
- signed_addend - dtpoff_base (info),
- weak_undef_p);
- break;
+ {
+ if (!(weak_undef_p || elf_hash_table (info)->tls_sec))
+ {
+ int howto_index = bfd_r_type - BFD_RELOC_AARCH64_RELOC_START;
+ _bfd_error_handler
+ /* xgettext:c-format */
+ (_("%pB: TLS relocation %s against undefined symbol `%s'"),
+ input_bfd, elfNN_aarch64_howto_table[howto_index].name,
+ h->root.root.string);
+ bfd_set_error (bfd_error_bad_value);
+ return bfd_reloc_notsupported;
+ }
+
+ bfd_vma def_value
+ = weak_undef_p ? 0 : signed_addend - dtpoff_base (info);
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
+ def_value, weak_undef_p);
+ break;
+ }
case BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_HI12:
case BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12:
case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1:
case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1_NC:
case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G2:
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
- signed_addend - tpoff_base (info),
- weak_undef_p);
- *unresolved_reloc_p = FALSE;
- break;
+ {
+ if (!(weak_undef_p || elf_hash_table (info)->tls_sec))
+ {
+ int howto_index = bfd_r_type - BFD_RELOC_AARCH64_RELOC_START;
+ _bfd_error_handler
+ /* xgettext:c-format */
+ (_("%pB: TLS relocation %s against undefined symbol `%s'"),
+ input_bfd, elfNN_aarch64_howto_table[howto_index].name,
+ h->root.root.string);
+ bfd_set_error (bfd_error_bad_value);
+ return bfd_reloc_notsupported;
+ }
+
+ bfd_vma def_value
+ = weak_undef_p ? 0 : signed_addend - tpoff_base (info);
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
+ def_value, weak_undef_p);
+ *unresolved_reloc_p = FALSE;
+ break;
+ }
case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12:
case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
+ globals->root.sgotplt->output_offset
+ globals->sgotplt_jump_table_size);
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
0, weak_undef_p);
*unresolved_reloc_p = FALSE;
break;
value -= (globals->root.sgot->output_section->vma
+ globals->root.sgot->output_offset);
- value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
+ value = _bfd_aarch64_elf_resolve_relocation (input_bfd, bfd_r_type,
+ place, value,
0, weak_undef_p);
*unresolved_reloc_p = FALSE;
break;
name = (bfd_elf_string_from_elf_section
(input_bfd, symtab_hdr->sh_link, sym->st_name));
if (name == NULL || *name == '\0')
- name = bfd_section_name (input_bfd, sec);
+ name = bfd_section_name (sec);
}
if (r_symndx != 0
for (sec = ibfd->sections; sec != NULL; sec = sec->next)
{
- if ((bfd_get_section_flags (ibfd, sec)
+ if ((bfd_section_flags (sec)
& (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
== (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
only_data_sections = FALSE;
(bed->dynamic_sec_flags
| SEC_READONLY));
if (s == NULL
- || ! bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
+ || !bfd_set_section_alignment (s, bed->s->log_file_align))
return FALSE;
htab->srelgot = s;
s = bfd_make_section_anyway_with_flags (abfd, ".got", flags);
if (s == NULL
- || !bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
+ || !bfd_set_section_alignment (s, bed->s->log_file_align))
return FALSE;
htab->sgot = s;
htab->sgot->size += GOT_ENTRY_SIZE;
{
s = bfd_make_section_anyway_with_flags (abfd, ".got.plt", flags);
if (s == NULL
- || !bfd_set_section_alignment (abfd, s,
- bed->s->log_file_align))
+ || !bfd_set_section_alignment (s, bed->s->log_file_align))
return FALSE;
htab->sgotplt = s;
}
BFD_AARCH64_SPECIAL_SYM_TYPE_ANY);
}
-/* This is a copy of elf_find_function () from elf.c except that
+/* This is a version of _bfd_elf_find_function() from dwarf2.c except that
AArch64 mapping symbols are ignored when looking for function names. */
static bfd_boolean
-aarch64_elf_find_function (bfd *abfd ATTRIBUTE_UNUSED,
- asymbol **symbols,
- asection *section,
- bfd_vma offset,
- const char **filename_ptr,
- const char **functionname_ptr)
+aarch64_elf_find_function (bfd * abfd,
+ asymbol ** symbols,
+ asection * section,
+ bfd_vma offset,
+ const char ** filename_ptr,
+ const char ** functionname_ptr)
{
const char *filename = NULL;
asymbol *func = NULL;
bfd_vma low_func = 0;
asymbol **p;
+ if (symbols == NULL)
+ return FALSE;
+
+ if (bfd_get_flavour (abfd) != bfd_target_elf_flavour)
+ return FALSE;
+
for (p = symbols; *p != NULL; p++)
{
elf_symbol_type *q;
(q->symbol.name, BFD_AARCH64_SPECIAL_SYM_TYPE_ANY)))
continue;
/* Fall through. */
- if (bfd_get_section (&q->symbol) == section
+ if (bfd_asymbol_section (&q->symbol) == section
&& q->symbol.value >= low_func && q->symbol.value <= offset)
{
func = (asymbol *) q;
if (_bfd_dwarf2_find_nearest_line (abfd, symbols, NULL, section, offset,
filename_ptr, functionname_ptr,
line_ptr, discriminator_ptr,
- dwarf_debug_sections, 0,
+ dwarf_debug_sections,
&elf_tdata (abfd)->dwarf2_find_line_info))
{
if (!*functionname_ptr)
}
-static void
-elfNN_aarch64_post_process_headers (bfd *abfd,
- struct bfd_link_info *link_info)
+static bfd_boolean
+elfNN_aarch64_init_file_header (bfd *abfd, struct bfd_link_info *link_info)
{
Elf_Internal_Ehdr *i_ehdrp; /* ELF file header, internal form. */
+ if (!_bfd_elf_init_file_header (abfd, link_info))
+ return FALSE;
+
i_ehdrp = elf_elfheader (abfd);
i_ehdrp->e_ident[EI_ABIVERSION] = AARCH64_ELF_ABI_VERSION;
-
- _bfd_elf_post_process_headers (abfd, link_info);
+ return TRUE;
}
static enum elf_reloc_type_class
return TRUE;
}
-/* Allocate space in .plt, .got and associated reloc sections for
- local dynamic relocs. */
-
-static bfd_boolean
-elfNN_aarch64_allocate_local_dynrelocs (void **slot, void *inf)
-{
- struct elf_link_hash_entry *h
- = (struct elf_link_hash_entry *) *slot;
-
- if (h->type != STT_GNU_IFUNC
- || !h->def_regular
- || !h->ref_regular
- || !h->forced_local
- || h->root.type != bfd_link_hash_defined)
- abort ();
-
- return elfNN_aarch64_allocate_dynrelocs (h, inf);
-}
-
/* Allocate space in .plt, .got and associated reloc sections for
local ifunc dynamic relocs. */
elf_link_hash_traverse (&htab->root, elfNN_aarch64_allocate_ifunc_dynrelocs,
info);
- /* Allocate .plt and .got entries, and space for local symbols. */
- htab_traverse (htab->loc_hash_table,
- elfNN_aarch64_allocate_local_dynrelocs,
- info);
-
/* Allocate .plt and .got entries, and space for local ifunc symbols. */
htab_traverse (htab->loc_hash_table,
elfNN_aarch64_allocate_local_ifunc_dynrelocs,
/* Strip this section if we don't need it; see the
comment below. */
}
- else if (CONST_STRNEQ (bfd_get_section_name (dynobj, s), ".rela"))
+ else if (CONST_STRNEQ (bfd_section_name (s), ".rela"))
{
if (s->size != 0 && s != htab->root.srelplt)
relocs = TRUE;
if ((aprop && !(aprop->u.number & GNU_PROPERTY_AARCH64_FEATURE_1_BTI))
|| !aprop)
{
- _bfd_error_handler (_("%pB: warning: BTI turned on by --force-bti when "
+ _bfd_error_handler (_("%pB: warning: BTI turned on by -z force-bti when "
"all inputs do not have BTI in NOTE section."),
abfd);
}
if ((bprop && !(bprop->u.number & GNU_PROPERTY_AARCH64_FEATURE_1_BTI))
|| !bprop)
{
- _bfd_error_handler (_("%pB: warning: BTI turned on by --force-bti when "
+ _bfd_error_handler (_("%pB: warning: BTI turned on by -z force-bti when "
"all inputs do not have BTI in NOTE section."),
bbfd);
}
#define elf_backend_plt_sym_val \
elfNN_aarch64_plt_sym_val
-#define elf_backend_post_process_headers \
- elfNN_aarch64_post_process_headers
+#define elf_backend_init_file_header \
+ elfNN_aarch64_init_file_header
#define elf_backend_relocate_section \
elfNN_aarch64_relocate_section