[GAS][AARCH64]Add BFD_RELOC_AARCH64_MOVW_GOTOFF_G1 Support.
[deliverable/binutils-gdb.git] / bfd / elfnn-aarch64.c
CommitLineData
cec5225b 1/* AArch64-specific support for NN-bit ELF.
b90efa5b 2 Copyright (C) 2009-2015 Free Software Foundation, Inc.
a06ea964
NC
3 Contributed by ARM Ltd.
4
5 This file is part of BFD, the Binary File Descriptor library.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; see the file COPYING3. If not,
19 see <http://www.gnu.org/licenses/>. */
20
21/* Notes on implementation:
22
23 Thread Local Store (TLS)
24
25 Overview:
26
27 The implementation currently supports both traditional TLS and TLS
28 descriptors, but only general dynamic (GD).
29
30 For traditional TLS the assembler will present us with code
31 fragments of the form:
32
33 adrp x0, :tlsgd:foo
34 R_AARCH64_TLSGD_ADR_PAGE21(foo)
35 add x0, :tlsgd_lo12:foo
36 R_AARCH64_TLSGD_ADD_LO12_NC(foo)
37 bl __tls_get_addr
38 nop
39
40 For TLS descriptors the assembler will present us with code
41 fragments of the form:
42
418009c2 43 adrp x0, :tlsdesc:foo R_AARCH64_TLSDESC_ADR_PAGE21(foo)
a06ea964
NC
44 ldr x1, [x0, #:tlsdesc_lo12:foo] R_AARCH64_TLSDESC_LD64_LO12(foo)
45 add x0, x0, #:tlsdesc_lo12:foo R_AARCH64_TLSDESC_ADD_LO12(foo)
46 .tlsdesccall foo
47 blr x1 R_AARCH64_TLSDESC_CALL(foo)
48
49 The relocations R_AARCH64_TLSGD_{ADR_PREL21,ADD_LO12_NC} against foo
50 indicate that foo is thread local and should be accessed via the
51 traditional TLS mechanims.
52
a6bb11b2 53 The relocations R_AARCH64_TLSDESC_{ADR_PAGE21,LD64_LO12_NC,ADD_LO12_NC}
a06ea964
NC
54 against foo indicate that 'foo' is thread local and should be accessed
55 via a TLS descriptor mechanism.
56
57 The precise instruction sequence is only relevant from the
58 perspective of linker relaxation which is currently not implemented.
59
60 The static linker must detect that 'foo' is a TLS object and
61 allocate a double GOT entry. The GOT entry must be created for both
62 global and local TLS symbols. Note that this is different to none
63 TLS local objects which do not need a GOT entry.
64
65 In the traditional TLS mechanism, the double GOT entry is used to
66 provide the tls_index structure, containing module and offset
a6bb11b2 67 entries. The static linker places the relocation R_AARCH64_TLS_DTPMOD
a06ea964
NC
68 on the module entry. The loader will subsequently fixup this
69 relocation with the module identity.
70
71 For global traditional TLS symbols the static linker places an
a6bb11b2 72 R_AARCH64_TLS_DTPREL relocation on the offset entry. The loader
a06ea964
NC
73 will subsequently fixup the offset. For local TLS symbols the static
74 linker fixes up offset.
75
76 In the TLS descriptor mechanism the double GOT entry is used to
77 provide the descriptor. The static linker places the relocation
78 R_AARCH64_TLSDESC on the first GOT slot. The loader will
79 subsequently fix this up.
80
81 Implementation:
82
83 The handling of TLS symbols is implemented across a number of
84 different backend functions. The following is a top level view of
85 what processing is performed where.
86
87 The TLS implementation maintains state information for each TLS
88 symbol. The state information for local and global symbols is kept
89 in different places. Global symbols use generic BFD structures while
90 local symbols use backend specific structures that are allocated and
91 maintained entirely by the backend.
92
93 The flow:
94
cec5225b 95 elfNN_aarch64_check_relocs()
a06ea964
NC
96
97 This function is invoked for each relocation.
98
99 The TLS relocations R_AARCH64_TLSGD_{ADR_PREL21,ADD_LO12_NC} and
a6bb11b2 100 R_AARCH64_TLSDESC_{ADR_PAGE21,LD64_LO12_NC,ADD_LO12_NC} are
a06ea964
NC
101 spotted. One time creation of local symbol data structures are
102 created when the first local symbol is seen.
103
104 The reference count for a symbol is incremented. The GOT type for
105 each symbol is marked as general dynamic.
106
cec5225b 107 elfNN_aarch64_allocate_dynrelocs ()
a06ea964
NC
108
109 For each global with positive reference count we allocate a double
110 GOT slot. For a traditional TLS symbol we allocate space for two
111 relocation entries on the GOT, for a TLS descriptor symbol we
112 allocate space for one relocation on the slot. Record the GOT offset
113 for this symbol.
114
cec5225b 115 elfNN_aarch64_size_dynamic_sections ()
a06ea964
NC
116
117 Iterate all input BFDS, look for in the local symbol data structure
118 constructed earlier for local TLS symbols and allocate them double
119 GOT slots along with space for a single GOT relocation. Update the
120 local symbol structure to record the GOT offset allocated.
121
cec5225b 122 elfNN_aarch64_relocate_section ()
a06ea964 123
cec5225b 124 Calls elfNN_aarch64_final_link_relocate ()
a06ea964
NC
125
126 Emit the relevant TLS relocations against the GOT for each TLS
127 symbol. For local TLS symbols emit the GOT offset directly. The GOT
128 relocations are emitted once the first time a TLS symbol is
129 encountered. The implementation uses the LSB of the GOT offset to
130 flag that the relevant GOT relocations for a symbol have been
131 emitted. All of the TLS code that uses the GOT offset needs to take
132 care to mask out this flag bit before using the offset.
133
cec5225b 134 elfNN_aarch64_final_link_relocate ()
a06ea964
NC
135
136 Fixup the R_AARCH64_TLSGD_{ADR_PREL21, ADD_LO12_NC} relocations. */
137
138#include "sysdep.h"
139#include "bfd.h"
140#include "libiberty.h"
141#include "libbfd.h"
142#include "bfd_stdint.h"
143#include "elf-bfd.h"
144#include "bfdlink.h"
1419bbe5 145#include "objalloc.h"
a06ea964 146#include "elf/aarch64.h"
caed7120 147#include "elfxx-aarch64.h"
a06ea964 148
cec5225b
YZ
149#define ARCH_SIZE NN
150
151#if ARCH_SIZE == 64
152#define AARCH64_R(NAME) R_AARCH64_ ## NAME
153#define AARCH64_R_STR(NAME) "R_AARCH64_" #NAME
a6bb11b2
YZ
154#define HOWTO64(...) HOWTO (__VA_ARGS__)
155#define HOWTO32(...) EMPTY_HOWTO (0)
cec5225b
YZ
156#define LOG_FILE_ALIGN 3
157#endif
158
159#if ARCH_SIZE == 32
160#define AARCH64_R(NAME) R_AARCH64_P32_ ## NAME
161#define AARCH64_R_STR(NAME) "R_AARCH64_P32_" #NAME
a6bb11b2
YZ
162#define HOWTO64(...) EMPTY_HOWTO (0)
163#define HOWTO32(...) HOWTO (__VA_ARGS__)
cec5225b
YZ
164#define LOG_FILE_ALIGN 2
165#endif
166
a6bb11b2 167#define IS_AARCH64_TLS_RELOC(R_TYPE) \
4c0a9a6f
JW
168 ((R_TYPE) == BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC \
169 || (R_TYPE) == BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21 \
3c12b054 170 || (R_TYPE) == BFD_RELOC_AARCH64_TLSGD_ADR_PREL21 \
a6bb11b2 171 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 \
a6bb11b2 172 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_LD32_GOTTPREL_LO12_NC \
4c0a9a6f 173 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC \
a6bb11b2 174 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19 \
4c0a9a6f
JW
175 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC \
176 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_MOVW_GOTTPREL_G1 \
6ffe9a1b 177 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_HI12 \
40fbed84 178 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_LO12 \
753999c1 179 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_LO12_NC \
73f925cc 180 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC \
f69e4920 181 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21 \
77a69ff8 182 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADR_PREL21 \
07c9aa07
JW
183 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST16_DTPREL_LO12 \
184 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST16_DTPREL_LO12_NC \
185 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST32_DTPREL_LO12 \
186 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST32_DTPREL_LO12_NC \
187 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST64_DTPREL_LO12 \
188 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST64_DTPREL_LO12_NC \
189 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST8_DTPREL_LO12 \
190 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_LDST8_DTPREL_LO12_NC \
6ffe9a1b
JW
191 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G0 \
192 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G0_NC \
193 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1 \
194 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1_NC \
195 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G2 \
a6bb11b2 196 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_HI12 \
4c0a9a6f 197 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12 \
a6bb11b2 198 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12_NC \
a6bb11b2
YZ
199 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0 \
200 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0_NC \
4c0a9a6f
JW
201 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1 \
202 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1_NC \
203 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G2 \
a6bb11b2
YZ
204 || (R_TYPE) == BFD_RELOC_AARCH64_TLS_DTPMOD \
205 || (R_TYPE) == BFD_RELOC_AARCH64_TLS_DTPREL \
206 || (R_TYPE) == BFD_RELOC_AARCH64_TLS_TPREL \
a06ea964
NC
207 || IS_AARCH64_TLSDESC_RELOC ((R_TYPE)))
208
9331eea1 209#define IS_AARCH64_TLS_RELAX_RELOC(R_TYPE) \
4af68b9c
JW
210 ((R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC \
211 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21 \
212 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21 \
213 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_CALL \
214 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_LD_PREL19 \
215 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_LDNN_LO12_NC \
216 || (R_TYPE) == BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21 \
9331eea1
JW
217 || (R_TYPE) == BFD_RELOC_AARCH64_TLSGD_ADR_PREL21 \
218 || (R_TYPE) == BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC \
219 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 \
220 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19 \
221 || (R_TYPE) == BFD_RELOC_AARCH64_TLSIE_LDNN_GOTTPREL_LO12_NC \
259364ad
JW
222 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC \
223 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21 \
4af68b9c 224 || (R_TYPE) == BFD_RELOC_AARCH64_TLSLD_ADR_PREL21)
9331eea1 225
a6bb11b2 226#define IS_AARCH64_TLSDESC_RELOC(R_TYPE) \
4c0a9a6f
JW
227 ((R_TYPE) == BFD_RELOC_AARCH64_TLSDESC \
228 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADD \
229 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC \
a6bb11b2 230 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21 \
389b8029 231 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21 \
4c0a9a6f 232 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_CALL \
a6bb11b2 233 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_LD32_LO12_NC \
4c0a9a6f 234 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_LD64_LO12_NC \
a6bb11b2 235 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_LDR \
4c0a9a6f
JW
236 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_LD_PREL19 \
237 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC \
238 || (R_TYPE) == BFD_RELOC_AARCH64_TLSDESC_OFF_G1)
a06ea964
NC
239
240#define ELIMINATE_COPY_RELOCS 0
241
a06ea964 242/* Return size of a relocation entry. HTAB is the bfd's
cec5225b
YZ
243 elf_aarch64_link_hash_entry. */
244#define RELOC_SIZE(HTAB) (sizeof (ElfNN_External_Rela))
a06ea964 245
cec5225b
YZ
246/* GOT Entry size - 8 bytes in ELF64 and 4 bytes in ELF32. */
247#define GOT_ENTRY_SIZE (ARCH_SIZE / 8)
a06ea964
NC
248#define PLT_ENTRY_SIZE (32)
249#define PLT_SMALL_ENTRY_SIZE (16)
250#define PLT_TLSDESC_ENTRY_SIZE (32)
251
a06ea964
NC
252/* Encoding of the nop instruction */
253#define INSN_NOP 0xd503201f
254
255#define aarch64_compute_jump_table_size(htab) \
256 (((htab)->root.srelplt == NULL) ? 0 \
257 : (htab)->root.srelplt->reloc_count * GOT_ENTRY_SIZE)
258
259/* The first entry in a procedure linkage table looks like this
260 if the distance between the PLTGOT and the PLT is < 4GB use
261 these PLT entries. Note that the dynamic linker gets &PLTGOT[2]
262 in x16 and needs to work out PLTGOT[1] by using an address of
cec5225b
YZ
263 [x16,#-GOT_ENTRY_SIZE]. */
264static const bfd_byte elfNN_aarch64_small_plt0_entry[PLT_ENTRY_SIZE] =
a06ea964
NC
265{
266 0xf0, 0x7b, 0xbf, 0xa9, /* stp x16, x30, [sp, #-16]! */
267 0x10, 0x00, 0x00, 0x90, /* adrp x16, (GOT+16) */
caed7120 268#if ARCH_SIZE == 64
a06ea964
NC
269 0x11, 0x0A, 0x40, 0xf9, /* ldr x17, [x16, #PLT_GOT+0x10] */
270 0x10, 0x42, 0x00, 0x91, /* add x16, x16,#PLT_GOT+0x10 */
caed7120
YZ
271#else
272 0x11, 0x0A, 0x40, 0xb9, /* ldr w17, [x16, #PLT_GOT+0x8] */
273 0x10, 0x22, 0x00, 0x11, /* add w16, w16,#PLT_GOT+0x8 */
274#endif
a06ea964
NC
275 0x20, 0x02, 0x1f, 0xd6, /* br x17 */
276 0x1f, 0x20, 0x03, 0xd5, /* nop */
277 0x1f, 0x20, 0x03, 0xd5, /* nop */
278 0x1f, 0x20, 0x03, 0xd5, /* nop */
279};
280
281/* Per function entry in a procedure linkage table looks like this
282 if the distance between the PLTGOT and the PLT is < 4GB use
283 these PLT entries. */
cec5225b 284static const bfd_byte elfNN_aarch64_small_plt_entry[PLT_SMALL_ENTRY_SIZE] =
a06ea964
NC
285{
286 0x10, 0x00, 0x00, 0x90, /* adrp x16, PLTGOT + n * 8 */
caed7120 287#if ARCH_SIZE == 64
a06ea964
NC
288 0x11, 0x02, 0x40, 0xf9, /* ldr x17, [x16, PLTGOT + n * 8] */
289 0x10, 0x02, 0x00, 0x91, /* add x16, x16, :lo12:PLTGOT + n * 8 */
caed7120
YZ
290#else
291 0x11, 0x02, 0x40, 0xb9, /* ldr w17, [x16, PLTGOT + n * 4] */
292 0x10, 0x02, 0x00, 0x11, /* add w16, w16, :lo12:PLTGOT + n * 4 */
293#endif
a06ea964
NC
294 0x20, 0x02, 0x1f, 0xd6, /* br x17. */
295};
296
297static const bfd_byte
cec5225b 298elfNN_aarch64_tlsdesc_small_plt_entry[PLT_TLSDESC_ENTRY_SIZE] =
a06ea964
NC
299{
300 0xe2, 0x0f, 0xbf, 0xa9, /* stp x2, x3, [sp, #-16]! */
301 0x02, 0x00, 0x00, 0x90, /* adrp x2, 0 */
302 0x03, 0x00, 0x00, 0x90, /* adrp x3, 0 */
caed7120
YZ
303#if ARCH_SIZE == 64
304 0x42, 0x00, 0x40, 0xf9, /* ldr x2, [x2, #0] */
a06ea964 305 0x63, 0x00, 0x00, 0x91, /* add x3, x3, 0 */
caed7120
YZ
306#else
307 0x42, 0x00, 0x40, 0xb9, /* ldr w2, [x2, #0] */
308 0x63, 0x00, 0x00, 0x11, /* add w3, w3, 0 */
309#endif
310 0x40, 0x00, 0x1f, 0xd6, /* br x2 */
a06ea964
NC
311 0x1f, 0x20, 0x03, 0xd5, /* nop */
312 0x1f, 0x20, 0x03, 0xd5, /* nop */
313};
314
cec5225b
YZ
315#define elf_info_to_howto elfNN_aarch64_info_to_howto
316#define elf_info_to_howto_rel elfNN_aarch64_info_to_howto
a06ea964
NC
317
318#define AARCH64_ELF_ABI_VERSION 0
a06ea964
NC
319
320/* In case we're on a 32-bit machine, construct a 64-bit "-1" value. */
321#define ALL_ONES (~ (bfd_vma) 0)
322
a6bb11b2
YZ
323/* Indexed by the bfd interal reloc enumerators.
324 Therefore, the table needs to be synced with BFD_RELOC_AARCH64_*
325 in reloc.c. */
a06ea964 326
a6bb11b2 327static reloc_howto_type elfNN_aarch64_howto_table[] =
a06ea964 328{
a6bb11b2 329 EMPTY_HOWTO (0),
a06ea964 330
a6bb11b2 331 /* Basic data relocations. */
a06ea964 332
a6bb11b2
YZ
333#if ARCH_SIZE == 64
334 HOWTO (R_AARCH64_NULL, /* type */
a06ea964 335 0, /* rightshift */
6346d5ca 336 3, /* size (0 = byte, 1 = short, 2 = long) */
a6bb11b2 337 0, /* bitsize */
a06ea964
NC
338 FALSE, /* pc_relative */
339 0, /* bitpos */
340 complain_overflow_dont, /* complain_on_overflow */
341 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 342 "R_AARCH64_NULL", /* name */
a06ea964
NC
343 FALSE, /* partial_inplace */
344 0, /* src_mask */
a6bb11b2 345 0, /* dst_mask */
a06ea964 346 FALSE), /* pcrel_offset */
a6bb11b2
YZ
347#else
348 HOWTO (R_AARCH64_NONE, /* type */
a06ea964 349 0, /* rightshift */
6346d5ca 350 3, /* size (0 = byte, 1 = short, 2 = long) */
a06ea964
NC
351 0, /* bitsize */
352 FALSE, /* pc_relative */
353 0, /* bitpos */
354 complain_overflow_dont, /* complain_on_overflow */
355 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 356 "R_AARCH64_NONE", /* name */
a06ea964
NC
357 FALSE, /* partial_inplace */
358 0, /* src_mask */
359 0, /* dst_mask */
360 FALSE), /* pcrel_offset */
a6bb11b2 361#endif
a06ea964
NC
362
363 /* .xword: (S+A) */
a6bb11b2 364 HOWTO64 (AARCH64_R (ABS64), /* type */
a06ea964
NC
365 0, /* rightshift */
366 4, /* size (4 = long long) */
367 64, /* bitsize */
368 FALSE, /* pc_relative */
369 0, /* bitpos */
370 complain_overflow_unsigned, /* complain_on_overflow */
371 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 372 AARCH64_R_STR (ABS64), /* name */
a06ea964
NC
373 FALSE, /* partial_inplace */
374 ALL_ONES, /* src_mask */
375 ALL_ONES, /* dst_mask */
376 FALSE), /* pcrel_offset */
377
378 /* .word: (S+A) */
a6bb11b2 379 HOWTO (AARCH64_R (ABS32), /* type */
a06ea964
NC
380 0, /* rightshift */
381 2, /* size (0 = byte, 1 = short, 2 = long) */
382 32, /* bitsize */
383 FALSE, /* pc_relative */
384 0, /* bitpos */
385 complain_overflow_unsigned, /* complain_on_overflow */
386 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 387 AARCH64_R_STR (ABS32), /* name */
a06ea964
NC
388 FALSE, /* partial_inplace */
389 0xffffffff, /* src_mask */
390 0xffffffff, /* dst_mask */
391 FALSE), /* pcrel_offset */
392
393 /* .half: (S+A) */
a6bb11b2 394 HOWTO (AARCH64_R (ABS16), /* type */
a06ea964
NC
395 0, /* rightshift */
396 1, /* size (0 = byte, 1 = short, 2 = long) */
397 16, /* bitsize */
398 FALSE, /* pc_relative */
399 0, /* bitpos */
400 complain_overflow_unsigned, /* complain_on_overflow */
401 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 402 AARCH64_R_STR (ABS16), /* name */
a06ea964
NC
403 FALSE, /* partial_inplace */
404 0xffff, /* src_mask */
405 0xffff, /* dst_mask */
406 FALSE), /* pcrel_offset */
407
408 /* .xword: (S+A-P) */
a6bb11b2 409 HOWTO64 (AARCH64_R (PREL64), /* type */
a06ea964
NC
410 0, /* rightshift */
411 4, /* size (4 = long long) */
412 64, /* bitsize */
413 TRUE, /* pc_relative */
414 0, /* bitpos */
415 complain_overflow_signed, /* complain_on_overflow */
416 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 417 AARCH64_R_STR (PREL64), /* name */
a06ea964
NC
418 FALSE, /* partial_inplace */
419 ALL_ONES, /* src_mask */
420 ALL_ONES, /* dst_mask */
421 TRUE), /* pcrel_offset */
422
423 /* .word: (S+A-P) */
a6bb11b2 424 HOWTO (AARCH64_R (PREL32), /* type */
a06ea964
NC
425 0, /* rightshift */
426 2, /* size (0 = byte, 1 = short, 2 = long) */
427 32, /* bitsize */
428 TRUE, /* pc_relative */
429 0, /* bitpos */
430 complain_overflow_signed, /* complain_on_overflow */
431 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 432 AARCH64_R_STR (PREL32), /* name */
a06ea964
NC
433 FALSE, /* partial_inplace */
434 0xffffffff, /* src_mask */
435 0xffffffff, /* dst_mask */
436 TRUE), /* pcrel_offset */
437
438 /* .half: (S+A-P) */
a6bb11b2 439 HOWTO (AARCH64_R (PREL16), /* type */
a06ea964
NC
440 0, /* rightshift */
441 1, /* size (0 = byte, 1 = short, 2 = long) */
442 16, /* bitsize */
443 TRUE, /* pc_relative */
444 0, /* bitpos */
445 complain_overflow_signed, /* complain_on_overflow */
446 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 447 AARCH64_R_STR (PREL16), /* name */
a06ea964
NC
448 FALSE, /* partial_inplace */
449 0xffff, /* src_mask */
450 0xffff, /* dst_mask */
451 TRUE), /* pcrel_offset */
452
453 /* Group relocations to create a 16, 32, 48 or 64 bit
454 unsigned data or abs address inline. */
455
456 /* MOVZ: ((S+A) >> 0) & 0xffff */
a6bb11b2 457 HOWTO (AARCH64_R (MOVW_UABS_G0), /* type */
a06ea964
NC
458 0, /* rightshift */
459 2, /* size (0 = byte, 1 = short, 2 = long) */
460 16, /* bitsize */
461 FALSE, /* pc_relative */
462 0, /* bitpos */
463 complain_overflow_unsigned, /* complain_on_overflow */
464 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 465 AARCH64_R_STR (MOVW_UABS_G0), /* name */
a06ea964
NC
466 FALSE, /* partial_inplace */
467 0xffff, /* src_mask */
468 0xffff, /* dst_mask */
469 FALSE), /* pcrel_offset */
470
471 /* MOVK: ((S+A) >> 0) & 0xffff [no overflow check] */
a6bb11b2 472 HOWTO (AARCH64_R (MOVW_UABS_G0_NC), /* type */
a06ea964
NC
473 0, /* rightshift */
474 2, /* size (0 = byte, 1 = short, 2 = long) */
475 16, /* bitsize */
476 FALSE, /* pc_relative */
477 0, /* bitpos */
478 complain_overflow_dont, /* complain_on_overflow */
479 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 480 AARCH64_R_STR (MOVW_UABS_G0_NC), /* name */
a06ea964
NC
481 FALSE, /* partial_inplace */
482 0xffff, /* src_mask */
483 0xffff, /* dst_mask */
484 FALSE), /* pcrel_offset */
485
486 /* MOVZ: ((S+A) >> 16) & 0xffff */
a6bb11b2 487 HOWTO (AARCH64_R (MOVW_UABS_G1), /* type */
a06ea964
NC
488 16, /* rightshift */
489 2, /* size (0 = byte, 1 = short, 2 = long) */
490 16, /* bitsize */
491 FALSE, /* pc_relative */
492 0, /* bitpos */
493 complain_overflow_unsigned, /* complain_on_overflow */
494 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 495 AARCH64_R_STR (MOVW_UABS_G1), /* name */
a06ea964
NC
496 FALSE, /* partial_inplace */
497 0xffff, /* src_mask */
498 0xffff, /* dst_mask */
499 FALSE), /* pcrel_offset */
500
501 /* MOVK: ((S+A) >> 16) & 0xffff [no overflow check] */
a6bb11b2 502 HOWTO64 (AARCH64_R (MOVW_UABS_G1_NC), /* type */
a06ea964
NC
503 16, /* rightshift */
504 2, /* size (0 = byte, 1 = short, 2 = long) */
505 16, /* bitsize */
506 FALSE, /* pc_relative */
507 0, /* bitpos */
508 complain_overflow_dont, /* complain_on_overflow */
509 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 510 AARCH64_R_STR (MOVW_UABS_G1_NC), /* name */
a06ea964
NC
511 FALSE, /* partial_inplace */
512 0xffff, /* src_mask */
513 0xffff, /* dst_mask */
514 FALSE), /* pcrel_offset */
515
516 /* MOVZ: ((S+A) >> 32) & 0xffff */
a6bb11b2 517 HOWTO64 (AARCH64_R (MOVW_UABS_G2), /* type */
a06ea964
NC
518 32, /* rightshift */
519 2, /* size (0 = byte, 1 = short, 2 = long) */
520 16, /* bitsize */
521 FALSE, /* pc_relative */
522 0, /* bitpos */
523 complain_overflow_unsigned, /* complain_on_overflow */
524 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 525 AARCH64_R_STR (MOVW_UABS_G2), /* name */
a06ea964
NC
526 FALSE, /* partial_inplace */
527 0xffff, /* src_mask */
528 0xffff, /* dst_mask */
529 FALSE), /* pcrel_offset */
530
531 /* MOVK: ((S+A) >> 32) & 0xffff [no overflow check] */
a6bb11b2 532 HOWTO64 (AARCH64_R (MOVW_UABS_G2_NC), /* type */
a06ea964
NC
533 32, /* rightshift */
534 2, /* size (0 = byte, 1 = short, 2 = long) */
535 16, /* bitsize */
536 FALSE, /* pc_relative */
537 0, /* bitpos */
538 complain_overflow_dont, /* complain_on_overflow */
539 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 540 AARCH64_R_STR (MOVW_UABS_G2_NC), /* name */
a06ea964
NC
541 FALSE, /* partial_inplace */
542 0xffff, /* src_mask */
543 0xffff, /* dst_mask */
544 FALSE), /* pcrel_offset */
545
546 /* MOVZ: ((S+A) >> 48) & 0xffff */
a6bb11b2 547 HOWTO64 (AARCH64_R (MOVW_UABS_G3), /* type */
a06ea964
NC
548 48, /* rightshift */
549 2, /* size (0 = byte, 1 = short, 2 = long) */
550 16, /* bitsize */
551 FALSE, /* pc_relative */
552 0, /* bitpos */
553 complain_overflow_unsigned, /* complain_on_overflow */
554 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 555 AARCH64_R_STR (MOVW_UABS_G3), /* name */
a06ea964
NC
556 FALSE, /* partial_inplace */
557 0xffff, /* src_mask */
558 0xffff, /* dst_mask */
559 FALSE), /* pcrel_offset */
560
561 /* Group relocations to create high part of a 16, 32, 48 or 64 bit
562 signed data or abs address inline. Will change instruction
563 to MOVN or MOVZ depending on sign of calculated value. */
564
565 /* MOV[ZN]: ((S+A) >> 0) & 0xffff */
a6bb11b2 566 HOWTO (AARCH64_R (MOVW_SABS_G0), /* type */
a06ea964
NC
567 0, /* rightshift */
568 2, /* size (0 = byte, 1 = short, 2 = long) */
569 16, /* bitsize */
570 FALSE, /* pc_relative */
571 0, /* bitpos */
572 complain_overflow_signed, /* complain_on_overflow */
573 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 574 AARCH64_R_STR (MOVW_SABS_G0), /* name */
a06ea964
NC
575 FALSE, /* partial_inplace */
576 0xffff, /* src_mask */
577 0xffff, /* dst_mask */
578 FALSE), /* pcrel_offset */
579
580 /* MOV[ZN]: ((S+A) >> 16) & 0xffff */
a6bb11b2 581 HOWTO64 (AARCH64_R (MOVW_SABS_G1), /* type */
a06ea964
NC
582 16, /* rightshift */
583 2, /* size (0 = byte, 1 = short, 2 = long) */
584 16, /* bitsize */
585 FALSE, /* pc_relative */
586 0, /* bitpos */
587 complain_overflow_signed, /* complain_on_overflow */
588 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 589 AARCH64_R_STR (MOVW_SABS_G1), /* name */
a06ea964
NC
590 FALSE, /* partial_inplace */
591 0xffff, /* src_mask */
592 0xffff, /* dst_mask */
593 FALSE), /* pcrel_offset */
594
595 /* MOV[ZN]: ((S+A) >> 32) & 0xffff */
a6bb11b2 596 HOWTO64 (AARCH64_R (MOVW_SABS_G2), /* type */
a06ea964
NC
597 32, /* rightshift */
598 2, /* size (0 = byte, 1 = short, 2 = long) */
599 16, /* bitsize */
600 FALSE, /* pc_relative */
601 0, /* bitpos */
602 complain_overflow_signed, /* complain_on_overflow */
603 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 604 AARCH64_R_STR (MOVW_SABS_G2), /* name */
a06ea964
NC
605 FALSE, /* partial_inplace */
606 0xffff, /* src_mask */
607 0xffff, /* dst_mask */
608 FALSE), /* pcrel_offset */
609
610/* Relocations to generate 19, 21 and 33 bit PC-relative load/store
611 addresses: PG(x) is (x & ~0xfff). */
612
613 /* LD-lit: ((S+A-P) >> 2) & 0x7ffff */
a6bb11b2 614 HOWTO (AARCH64_R (LD_PREL_LO19), /* type */
a06ea964
NC
615 2, /* rightshift */
616 2, /* size (0 = byte, 1 = short, 2 = long) */
617 19, /* bitsize */
618 TRUE, /* pc_relative */
619 0, /* bitpos */
620 complain_overflow_signed, /* complain_on_overflow */
621 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 622 AARCH64_R_STR (LD_PREL_LO19), /* name */
a06ea964
NC
623 FALSE, /* partial_inplace */
624 0x7ffff, /* src_mask */
625 0x7ffff, /* dst_mask */
626 TRUE), /* pcrel_offset */
627
628 /* ADR: (S+A-P) & 0x1fffff */
a6bb11b2 629 HOWTO (AARCH64_R (ADR_PREL_LO21), /* type */
a06ea964
NC
630 0, /* rightshift */
631 2, /* size (0 = byte, 1 = short, 2 = long) */
632 21, /* bitsize */
633 TRUE, /* pc_relative */
634 0, /* bitpos */
635 complain_overflow_signed, /* complain_on_overflow */
636 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 637 AARCH64_R_STR (ADR_PREL_LO21), /* name */
a06ea964
NC
638 FALSE, /* partial_inplace */
639 0x1fffff, /* src_mask */
640 0x1fffff, /* dst_mask */
641 TRUE), /* pcrel_offset */
642
643 /* ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff */
a6bb11b2 644 HOWTO (AARCH64_R (ADR_PREL_PG_HI21), /* type */
a06ea964
NC
645 12, /* rightshift */
646 2, /* size (0 = byte, 1 = short, 2 = long) */
647 21, /* bitsize */
648 TRUE, /* pc_relative */
649 0, /* bitpos */
650 complain_overflow_signed, /* complain_on_overflow */
651 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 652 AARCH64_R_STR (ADR_PREL_PG_HI21), /* name */
a06ea964
NC
653 FALSE, /* partial_inplace */
654 0x1fffff, /* src_mask */
655 0x1fffff, /* dst_mask */
656 TRUE), /* pcrel_offset */
657
658 /* ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff [no overflow check] */
a6bb11b2 659 HOWTO64 (AARCH64_R (ADR_PREL_PG_HI21_NC), /* type */
a06ea964
NC
660 12, /* rightshift */
661 2, /* size (0 = byte, 1 = short, 2 = long) */
662 21, /* bitsize */
663 TRUE, /* pc_relative */
664 0, /* bitpos */
665 complain_overflow_dont, /* complain_on_overflow */
666 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 667 AARCH64_R_STR (ADR_PREL_PG_HI21_NC), /* name */
a06ea964
NC
668 FALSE, /* partial_inplace */
669 0x1fffff, /* src_mask */
670 0x1fffff, /* dst_mask */
671 TRUE), /* pcrel_offset */
672
673 /* ADD: (S+A) & 0xfff [no overflow check] */
a6bb11b2 674 HOWTO (AARCH64_R (ADD_ABS_LO12_NC), /* type */
a06ea964
NC
675 0, /* rightshift */
676 2, /* size (0 = byte, 1 = short, 2 = long) */
677 12, /* bitsize */
678 FALSE, /* pc_relative */
679 10, /* bitpos */
680 complain_overflow_dont, /* complain_on_overflow */
681 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 682 AARCH64_R_STR (ADD_ABS_LO12_NC), /* name */
a06ea964
NC
683 FALSE, /* partial_inplace */
684 0x3ffc00, /* src_mask */
685 0x3ffc00, /* dst_mask */
686 FALSE), /* pcrel_offset */
687
688 /* LD/ST8: (S+A) & 0xfff */
a6bb11b2 689 HOWTO (AARCH64_R (LDST8_ABS_LO12_NC), /* type */
a06ea964
NC
690 0, /* rightshift */
691 2, /* size (0 = byte, 1 = short, 2 = long) */
692 12, /* bitsize */
693 FALSE, /* pc_relative */
694 0, /* bitpos */
695 complain_overflow_dont, /* complain_on_overflow */
696 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 697 AARCH64_R_STR (LDST8_ABS_LO12_NC), /* name */
a06ea964
NC
698 FALSE, /* partial_inplace */
699 0xfff, /* src_mask */
700 0xfff, /* dst_mask */
701 FALSE), /* pcrel_offset */
702
703 /* Relocations for control-flow instructions. */
704
705 /* TBZ/NZ: ((S+A-P) >> 2) & 0x3fff */
a6bb11b2 706 HOWTO (AARCH64_R (TSTBR14), /* type */
a06ea964
NC
707 2, /* rightshift */
708 2, /* size (0 = byte, 1 = short, 2 = long) */
709 14, /* bitsize */
710 TRUE, /* pc_relative */
711 0, /* bitpos */
712 complain_overflow_signed, /* complain_on_overflow */
713 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 714 AARCH64_R_STR (TSTBR14), /* name */
a06ea964
NC
715 FALSE, /* partial_inplace */
716 0x3fff, /* src_mask */
717 0x3fff, /* dst_mask */
718 TRUE), /* pcrel_offset */
719
720 /* B.cond: ((S+A-P) >> 2) & 0x7ffff */
a6bb11b2 721 HOWTO (AARCH64_R (CONDBR19), /* type */
a06ea964
NC
722 2, /* rightshift */
723 2, /* size (0 = byte, 1 = short, 2 = long) */
724 19, /* bitsize */
725 TRUE, /* pc_relative */
726 0, /* bitpos */
727 complain_overflow_signed, /* complain_on_overflow */
728 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 729 AARCH64_R_STR (CONDBR19), /* name */
a06ea964
NC
730 FALSE, /* partial_inplace */
731 0x7ffff, /* src_mask */
732 0x7ffff, /* dst_mask */
733 TRUE), /* pcrel_offset */
734
a06ea964 735 /* B: ((S+A-P) >> 2) & 0x3ffffff */
a6bb11b2 736 HOWTO (AARCH64_R (JUMP26), /* type */
a06ea964
NC
737 2, /* rightshift */
738 2, /* size (0 = byte, 1 = short, 2 = long) */
739 26, /* bitsize */
740 TRUE, /* pc_relative */
741 0, /* bitpos */
742 complain_overflow_signed, /* complain_on_overflow */
743 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 744 AARCH64_R_STR (JUMP26), /* name */
a06ea964
NC
745 FALSE, /* partial_inplace */
746 0x3ffffff, /* src_mask */
747 0x3ffffff, /* dst_mask */
748 TRUE), /* pcrel_offset */
749
750 /* BL: ((S+A-P) >> 2) & 0x3ffffff */
a6bb11b2 751 HOWTO (AARCH64_R (CALL26), /* type */
a06ea964
NC
752 2, /* rightshift */
753 2, /* size (0 = byte, 1 = short, 2 = long) */
754 26, /* bitsize */
755 TRUE, /* pc_relative */
756 0, /* bitpos */
757 complain_overflow_signed, /* complain_on_overflow */
758 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 759 AARCH64_R_STR (CALL26), /* name */
a06ea964
NC
760 FALSE, /* partial_inplace */
761 0x3ffffff, /* src_mask */
762 0x3ffffff, /* dst_mask */
763 TRUE), /* pcrel_offset */
764
765 /* LD/ST16: (S+A) & 0xffe */
a6bb11b2 766 HOWTO (AARCH64_R (LDST16_ABS_LO12_NC), /* type */
a06ea964
NC
767 1, /* rightshift */
768 2, /* size (0 = byte, 1 = short, 2 = long) */
769 12, /* bitsize */
770 FALSE, /* pc_relative */
771 0, /* bitpos */
772 complain_overflow_dont, /* complain_on_overflow */
773 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 774 AARCH64_R_STR (LDST16_ABS_LO12_NC), /* name */
a06ea964
NC
775 FALSE, /* partial_inplace */
776 0xffe, /* src_mask */
777 0xffe, /* dst_mask */
778 FALSE), /* pcrel_offset */
779
780 /* LD/ST32: (S+A) & 0xffc */
a6bb11b2 781 HOWTO (AARCH64_R (LDST32_ABS_LO12_NC), /* type */
a06ea964
NC
782 2, /* rightshift */
783 2, /* size (0 = byte, 1 = short, 2 = long) */
784 12, /* bitsize */
785 FALSE, /* pc_relative */
786 0, /* bitpos */
787 complain_overflow_dont, /* complain_on_overflow */
788 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 789 AARCH64_R_STR (LDST32_ABS_LO12_NC), /* name */
a06ea964
NC
790 FALSE, /* partial_inplace */
791 0xffc, /* src_mask */
792 0xffc, /* dst_mask */
793 FALSE), /* pcrel_offset */
794
795 /* LD/ST64: (S+A) & 0xff8 */
a6bb11b2 796 HOWTO (AARCH64_R (LDST64_ABS_LO12_NC), /* type */
a06ea964
NC
797 3, /* rightshift */
798 2, /* size (0 = byte, 1 = short, 2 = long) */
799 12, /* bitsize */
800 FALSE, /* pc_relative */
801 0, /* bitpos */
802 complain_overflow_dont, /* complain_on_overflow */
803 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 804 AARCH64_R_STR (LDST64_ABS_LO12_NC), /* name */
a06ea964
NC
805 FALSE, /* partial_inplace */
806 0xff8, /* src_mask */
807 0xff8, /* dst_mask */
808 FALSE), /* pcrel_offset */
809
a06ea964 810 /* LD/ST128: (S+A) & 0xff0 */
a6bb11b2 811 HOWTO (AARCH64_R (LDST128_ABS_LO12_NC), /* type */
a06ea964
NC
812 4, /* rightshift */
813 2, /* size (0 = byte, 1 = short, 2 = long) */
814 12, /* bitsize */
815 FALSE, /* pc_relative */
816 0, /* bitpos */
817 complain_overflow_dont, /* complain_on_overflow */
818 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 819 AARCH64_R_STR (LDST128_ABS_LO12_NC), /* name */
a06ea964
NC
820 FALSE, /* partial_inplace */
821 0xff0, /* src_mask */
822 0xff0, /* dst_mask */
823 FALSE), /* pcrel_offset */
824
f41aef5f
RE
825 /* Set a load-literal immediate field to bits
826 0x1FFFFC of G(S)-P */
a6bb11b2 827 HOWTO (AARCH64_R (GOT_LD_PREL19), /* type */
f41aef5f
RE
828 2, /* rightshift */
829 2, /* size (0 = byte,1 = short,2 = long) */
830 19, /* bitsize */
831 TRUE, /* pc_relative */
832 0, /* bitpos */
833 complain_overflow_signed, /* complain_on_overflow */
834 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 835 AARCH64_R_STR (GOT_LD_PREL19), /* name */
f41aef5f
RE
836 FALSE, /* partial_inplace */
837 0xffffe0, /* src_mask */
838 0xffffe0, /* dst_mask */
839 TRUE), /* pcrel_offset */
840
a06ea964
NC
841 /* Get to the page for the GOT entry for the symbol
842 (G(S) - P) using an ADRP instruction. */
a6bb11b2 843 HOWTO (AARCH64_R (ADR_GOT_PAGE), /* type */
a06ea964
NC
844 12, /* rightshift */
845 2, /* size (0 = byte, 1 = short, 2 = long) */
846 21, /* bitsize */
847 TRUE, /* pc_relative */
848 0, /* bitpos */
849 complain_overflow_dont, /* complain_on_overflow */
850 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 851 AARCH64_R_STR (ADR_GOT_PAGE), /* name */
a06ea964
NC
852 FALSE, /* partial_inplace */
853 0x1fffff, /* src_mask */
854 0x1fffff, /* dst_mask */
855 TRUE), /* pcrel_offset */
856
a6bb11b2
YZ
857 /* LD64: GOT offset G(S) & 0xff8 */
858 HOWTO64 (AARCH64_R (LD64_GOT_LO12_NC), /* type */
a06ea964
NC
859 3, /* rightshift */
860 2, /* size (0 = byte, 1 = short, 2 = long) */
861 12, /* bitsize */
862 FALSE, /* pc_relative */
863 0, /* bitpos */
864 complain_overflow_dont, /* complain_on_overflow */
865 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 866 AARCH64_R_STR (LD64_GOT_LO12_NC), /* name */
a06ea964
NC
867 FALSE, /* partial_inplace */
868 0xff8, /* src_mask */
869 0xff8, /* dst_mask */
a6bb11b2 870 FALSE), /* pcrel_offset */
a06ea964 871
a6bb11b2
YZ
872 /* LD32: GOT offset G(S) & 0xffc */
873 HOWTO32 (AARCH64_R (LD32_GOT_LO12_NC), /* type */
874 2, /* rightshift */
875 2, /* size (0 = byte, 1 = short, 2 = long) */
876 12, /* bitsize */
877 FALSE, /* pc_relative */
878 0, /* bitpos */
879 complain_overflow_dont, /* complain_on_overflow */
880 bfd_elf_generic_reloc, /* special_function */
881 AARCH64_R_STR (LD32_GOT_LO12_NC), /* name */
882 FALSE, /* partial_inplace */
883 0xffc, /* src_mask */
884 0xffc, /* dst_mask */
885 FALSE), /* pcrel_offset */
a06ea964 886
654248e7
RL
887 /* Higher 16 bits of GOT offset for the symbol. */
888 HOWTO64 (AARCH64_R (MOVW_GOTOFF_G1), /* type */
889 16, /* rightshift */
890 2, /* size (0 = byte, 1 = short, 2 = long) */
891 16, /* bitsize */
892 FALSE, /* pc_relative */
893 0, /* bitpos */
894 complain_overflow_unsigned, /* complain_on_overflow */
895 bfd_elf_generic_reloc, /* special_function */
896 AARCH64_R_STR (MOVW_GOTOFF_G1), /* name */
897 FALSE, /* partial_inplace */
898 0xffff, /* src_mask */
899 0xffff, /* dst_mask */
900 FALSE), /* pcrel_offset */
901
87f5fbcc
RL
902 /* LD64: GOT offset for the symbol. */
903 HOWTO64 (AARCH64_R (LD64_GOTOFF_LO15), /* type */
904 3, /* rightshift */
905 2, /* size (0 = byte, 1 = short, 2 = long) */
906 12, /* bitsize */
907 FALSE, /* pc_relative */
908 0, /* bitpos */
909 complain_overflow_unsigned, /* complain_on_overflow */
910 bfd_elf_generic_reloc, /* special_function */
911 AARCH64_R_STR (LD64_GOTOFF_LO15), /* name */
912 FALSE, /* partial_inplace */
913 0x7ff8, /* src_mask */
914 0x7ff8, /* dst_mask */
915 FALSE), /* pcrel_offset */
916
3d715ce4
JW
917 /* LD32: GOT offset to the page address of GOT table.
918 (G(S) - PAGE (_GLOBAL_OFFSET_TABLE_)) & 0x5ffc. */
919 HOWTO32 (AARCH64_R (LD32_GOTPAGE_LO14), /* type */
920 2, /* rightshift */
921 2, /* size (0 = byte, 1 = short, 2 = long) */
922 12, /* bitsize */
923 FALSE, /* pc_relative */
924 0, /* bitpos */
925 complain_overflow_unsigned, /* complain_on_overflow */
926 bfd_elf_generic_reloc, /* special_function */
927 AARCH64_R_STR (LD32_GOTPAGE_LO14), /* name */
928 FALSE, /* partial_inplace */
929 0x5ffc, /* src_mask */
930 0x5ffc, /* dst_mask */
931 FALSE), /* pcrel_offset */
932
a921b5bd
JW
933 /* LD64: GOT offset to the page address of GOT table.
934 (G(S) - PAGE (_GLOBAL_OFFSET_TABLE_)) & 0x7ff8. */
935 HOWTO64 (AARCH64_R (LD64_GOTPAGE_LO15), /* type */
936 3, /* rightshift */
937 2, /* size (0 = byte, 1 = short, 2 = long) */
938 12, /* bitsize */
939 FALSE, /* pc_relative */
940 0, /* bitpos */
941 complain_overflow_unsigned, /* complain_on_overflow */
942 bfd_elf_generic_reloc, /* special_function */
943 AARCH64_R_STR (LD64_GOTPAGE_LO15), /* name */
944 FALSE, /* partial_inplace */
945 0x7ff8, /* src_mask */
946 0x7ff8, /* dst_mask */
947 FALSE), /* pcrel_offset */
948
a06ea964
NC
949 /* Get to the page for the GOT entry for the symbol
950 (G(S) - P) using an ADRP instruction. */
a6bb11b2 951 HOWTO (AARCH64_R (TLSGD_ADR_PAGE21), /* type */
a06ea964
NC
952 12, /* rightshift */
953 2, /* size (0 = byte, 1 = short, 2 = long) */
954 21, /* bitsize */
955 TRUE, /* pc_relative */
956 0, /* bitpos */
957 complain_overflow_dont, /* complain_on_overflow */
958 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 959 AARCH64_R_STR (TLSGD_ADR_PAGE21), /* name */
a06ea964
NC
960 FALSE, /* partial_inplace */
961 0x1fffff, /* src_mask */
962 0x1fffff, /* dst_mask */
963 TRUE), /* pcrel_offset */
964
3c12b054
MS
965 HOWTO (AARCH64_R (TLSGD_ADR_PREL21), /* type */
966 0, /* rightshift */
967 2, /* size (0 = byte, 1 = short, 2 = long) */
968 21, /* bitsize */
969 TRUE, /* pc_relative */
970 0, /* bitpos */
971 complain_overflow_dont, /* complain_on_overflow */
972 bfd_elf_generic_reloc, /* special_function */
973 AARCH64_R_STR (TLSGD_ADR_PREL21), /* name */
974 FALSE, /* partial_inplace */
975 0x1fffff, /* src_mask */
976 0x1fffff, /* dst_mask */
977 TRUE), /* pcrel_offset */
978
a06ea964 979 /* ADD: GOT offset G(S) & 0xff8 [no overflow check] */
a6bb11b2 980 HOWTO (AARCH64_R (TLSGD_ADD_LO12_NC), /* type */
a06ea964
NC
981 0, /* rightshift */
982 2, /* size (0 = byte, 1 = short, 2 = long) */
983 12, /* bitsize */
984 FALSE, /* pc_relative */
985 0, /* bitpos */
986 complain_overflow_dont, /* complain_on_overflow */
987 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 988 AARCH64_R_STR (TLSGD_ADD_LO12_NC), /* name */
a06ea964
NC
989 FALSE, /* partial_inplace */
990 0xfff, /* src_mask */
991 0xfff, /* dst_mask */
992 FALSE), /* pcrel_offset */
993
a6bb11b2 994 HOWTO64 (AARCH64_R (TLSIE_MOVW_GOTTPREL_G1), /* type */
a06ea964
NC
995 16, /* rightshift */
996 2, /* size (0 = byte, 1 = short, 2 = long) */
997 16, /* bitsize */
998 FALSE, /* pc_relative */
999 0, /* bitpos */
1000 complain_overflow_dont, /* complain_on_overflow */
1001 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1002 AARCH64_R_STR (TLSIE_MOVW_GOTTPREL_G1), /* name */
a06ea964
NC
1003 FALSE, /* partial_inplace */
1004 0xffff, /* src_mask */
1005 0xffff, /* dst_mask */
1006 FALSE), /* pcrel_offset */
1007
a6bb11b2 1008 HOWTO64 (AARCH64_R (TLSIE_MOVW_GOTTPREL_G0_NC), /* type */
a06ea964
NC
1009 0, /* rightshift */
1010 2, /* size (0 = byte, 1 = short, 2 = long) */
49d8f92c 1011 16, /* bitsize */
a06ea964
NC
1012 FALSE, /* pc_relative */
1013 0, /* bitpos */
1014 complain_overflow_dont, /* complain_on_overflow */
1015 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1016 AARCH64_R_STR (TLSIE_MOVW_GOTTPREL_G0_NC), /* name */
a06ea964
NC
1017 FALSE, /* partial_inplace */
1018 0xffff, /* src_mask */
1019 0xffff, /* dst_mask */
1020 FALSE), /* pcrel_offset */
1021
a6bb11b2 1022 HOWTO (AARCH64_R (TLSIE_ADR_GOTTPREL_PAGE21), /* type */
a06ea964
NC
1023 12, /* rightshift */
1024 2, /* size (0 = byte, 1 = short, 2 = long) */
1025 21, /* bitsize */
1026 FALSE, /* pc_relative */
1027 0, /* bitpos */
1028 complain_overflow_dont, /* complain_on_overflow */
1029 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1030 AARCH64_R_STR (TLSIE_ADR_GOTTPREL_PAGE21), /* name */
a06ea964
NC
1031 FALSE, /* partial_inplace */
1032 0x1fffff, /* src_mask */
1033 0x1fffff, /* dst_mask */
1034 FALSE), /* pcrel_offset */
1035
a6bb11b2 1036 HOWTO64 (AARCH64_R (TLSIE_LD64_GOTTPREL_LO12_NC), /* type */
a06ea964
NC
1037 3, /* rightshift */
1038 2, /* size (0 = byte, 1 = short, 2 = long) */
1039 12, /* bitsize */
1040 FALSE, /* pc_relative */
1041 0, /* bitpos */
1042 complain_overflow_dont, /* complain_on_overflow */
1043 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1044 AARCH64_R_STR (TLSIE_LD64_GOTTPREL_LO12_NC), /* name */
a06ea964
NC
1045 FALSE, /* partial_inplace */
1046 0xff8, /* src_mask */
1047 0xff8, /* dst_mask */
1048 FALSE), /* pcrel_offset */
1049
a6bb11b2
YZ
1050 HOWTO32 (AARCH64_R (TLSIE_LD32_GOTTPREL_LO12_NC), /* type */
1051 2, /* rightshift */
1052 2, /* size (0 = byte, 1 = short, 2 = long) */
1053 12, /* bitsize */
1054 FALSE, /* pc_relative */
1055 0, /* bitpos */
1056 complain_overflow_dont, /* complain_on_overflow */
1057 bfd_elf_generic_reloc, /* special_function */
1058 AARCH64_R_STR (TLSIE_LD32_GOTTPREL_LO12_NC), /* name */
1059 FALSE, /* partial_inplace */
1060 0xffc, /* src_mask */
1061 0xffc, /* dst_mask */
1062 FALSE), /* pcrel_offset */
1063
1064 HOWTO (AARCH64_R (TLSIE_LD_GOTTPREL_PREL19), /* type */
bb3f9ed8 1065 2, /* rightshift */
a06ea964 1066 2, /* size (0 = byte, 1 = short, 2 = long) */
043bf05a 1067 19, /* bitsize */
a06ea964
NC
1068 FALSE, /* pc_relative */
1069 0, /* bitpos */
1070 complain_overflow_dont, /* complain_on_overflow */
1071 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1072 AARCH64_R_STR (TLSIE_LD_GOTTPREL_PREL19), /* name */
a06ea964
NC
1073 FALSE, /* partial_inplace */
1074 0x1ffffc, /* src_mask */
1075 0x1ffffc, /* dst_mask */
1076 FALSE), /* pcrel_offset */
1077
49df5539
JW
1078 /* ADD: bit[23:12] of byte offset to module TLS base address. */
1079 HOWTO (AARCH64_R (TLSLD_ADD_DTPREL_HI12), /* type */
1080 12, /* rightshift */
1081 2, /* size (0 = byte, 1 = short, 2 = long) */
1082 12, /* bitsize */
1083 FALSE, /* pc_relative */
1084 0, /* bitpos */
1085 complain_overflow_unsigned, /* complain_on_overflow */
1086 bfd_elf_generic_reloc, /* special_function */
1087 AARCH64_R_STR (TLSLD_ADD_DTPREL_HI12), /* name */
1088 FALSE, /* partial_inplace */
1089 0xfff, /* src_mask */
1090 0xfff, /* dst_mask */
1091 FALSE), /* pcrel_offset */
1092
70151fb5
JW
1093 /* Unsigned 12 bit byte offset to module TLS base address. */
1094 HOWTO (AARCH64_R (TLSLD_ADD_DTPREL_LO12), /* type */
1095 0, /* rightshift */
1096 2, /* size (0 = byte, 1 = short, 2 = long) */
1097 12, /* bitsize */
1098 FALSE, /* pc_relative */
1099 0, /* bitpos */
1100 complain_overflow_unsigned, /* complain_on_overflow */
1101 bfd_elf_generic_reloc, /* special_function */
1102 AARCH64_R_STR (TLSLD_ADD_DTPREL_LO12), /* name */
1103 FALSE, /* partial_inplace */
1104 0xfff, /* src_mask */
1105 0xfff, /* dst_mask */
1106 FALSE), /* pcrel_offset */
13289c10
JW
1107
1108 /* No overflow check version of BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_LO12. */
1109 HOWTO (AARCH64_R (TLSLD_ADD_DTPREL_LO12_NC), /* type */
1110 0, /* rightshift */
1111 2, /* size (0 = byte, 1 = short, 2 = long) */
1112 12, /* bitsize */
1113 FALSE, /* pc_relative */
1114 0, /* bitpos */
1115 complain_overflow_dont, /* complain_on_overflow */
1116 bfd_elf_generic_reloc, /* special_function */
1117 AARCH64_R_STR (TLSLD_ADD_DTPREL_LO12_NC), /* name */
1118 FALSE, /* partial_inplace */
1119 0xfff, /* src_mask */
1120 0xfff, /* dst_mask */
1121 FALSE), /* pcrel_offset */
70151fb5 1122
a12fad50
JW
1123 /* ADD: GOT offset G(S) & 0xff8 [no overflow check] */
1124 HOWTO (AARCH64_R (TLSLD_ADD_LO12_NC), /* type */
1125 0, /* rightshift */
1126 2, /* size (0 = byte, 1 = short, 2 = long) */
1127 12, /* bitsize */
1128 FALSE, /* pc_relative */
1129 0, /* bitpos */
1130 complain_overflow_dont, /* complain_on_overflow */
1131 bfd_elf_generic_reloc, /* special_function */
1132 AARCH64_R_STR (TLSLD_ADD_LO12_NC), /* name */
1133 FALSE, /* partial_inplace */
1134 0xfff, /* src_mask */
1135 0xfff, /* dst_mask */
1136 FALSE), /* pcrel_offset */
1137
1107e076
JW
1138 /* Get to the page for the GOT entry for the symbol
1139 (G(S) - P) using an ADRP instruction. */
1140 HOWTO (AARCH64_R (TLSLD_ADR_PAGE21), /* type */
1141 12, /* rightshift */
1142 2, /* size (0 = byte, 1 = short, 2 = long) */
1143 21, /* bitsize */
1144 TRUE, /* pc_relative */
1145 0, /* bitpos */
1146 complain_overflow_signed, /* complain_on_overflow */
1147 bfd_elf_generic_reloc, /* special_function */
1148 AARCH64_R_STR (TLSLD_ADR_PAGE21), /* name */
1149 FALSE, /* partial_inplace */
1150 0x1fffff, /* src_mask */
1151 0x1fffff, /* dst_mask */
1152 TRUE), /* pcrel_offset */
1153
6c37fedc
JW
1154 HOWTO (AARCH64_R (TLSLD_ADR_PREL21), /* type */
1155 0, /* rightshift */
1156 2, /* size (0 = byte, 1 = short, 2 = long) */
1157 21, /* bitsize */
1158 TRUE, /* pc_relative */
1159 0, /* bitpos */
1160 complain_overflow_signed, /* complain_on_overflow */
1161 bfd_elf_generic_reloc, /* special_function */
1162 AARCH64_R_STR (TLSLD_ADR_PREL21), /* name */
1163 FALSE, /* partial_inplace */
1164 0x1fffff, /* src_mask */
1165 0x1fffff, /* dst_mask */
1166 TRUE), /* pcrel_offset */
1167
4c562523
JW
1168 /* LD/ST16: bit[11:1] of byte offset to module TLS base address. */
1169 HOWTO64 (AARCH64_R (TLSLD_LDST16_DTPREL_LO12), /* type */
1170 1, /* rightshift */
1171 2, /* size (0 = byte, 1 = short, 2 = long) */
1172 11, /* bitsize */
1173 FALSE, /* pc_relative */
1174 10, /* bitpos */
1175 complain_overflow_unsigned, /* complain_on_overflow */
1176 bfd_elf_generic_reloc, /* special_function */
1177 AARCH64_R_STR (TLSLD_LDST16_DTPREL_LO12), /* name */
1178 FALSE, /* partial_inplace */
1179 0x1ffc00, /* src_mask */
1180 0x1ffc00, /* dst_mask */
1181 FALSE), /* pcrel_offset */
1182
1183 /* Same as BFD_RELOC_AARCH64_TLSLD_LDST16_DTPREL_LO12, but no overflow check. */
1184 HOWTO64 (AARCH64_R (TLSLD_LDST16_DTPREL_LO12_NC), /* type */
1185 1, /* rightshift */
1186 2, /* size (0 = byte, 1 = short, 2 = long) */
1187 11, /* bitsize */
1188 FALSE, /* pc_relative */
1189 10, /* bitpos */
1190 complain_overflow_dont, /* complain_on_overflow */
1191 bfd_elf_generic_reloc, /* special_function */
1192 AARCH64_R_STR (TLSLD_LDST16_DTPREL_LO12_NC), /* name */
1193 FALSE, /* partial_inplace */
1194 0x1ffc00, /* src_mask */
1195 0x1ffc00, /* dst_mask */
1196 FALSE), /* pcrel_offset */
1197
1198 /* LD/ST32: bit[11:2] of byte offset to module TLS base address. */
1199 HOWTO64 (AARCH64_R (TLSLD_LDST32_DTPREL_LO12), /* type */
1200 2, /* rightshift */
1201 2, /* size (0 = byte, 1 = short, 2 = long) */
1202 10, /* bitsize */
1203 FALSE, /* pc_relative */
1204 10, /* bitpos */
1205 complain_overflow_unsigned, /* complain_on_overflow */
1206 bfd_elf_generic_reloc, /* special_function */
1207 AARCH64_R_STR (TLSLD_LDST32_DTPREL_LO12), /* name */
1208 FALSE, /* partial_inplace */
1209 0x3ffc00, /* src_mask */
1210 0x3ffc00, /* dst_mask */
1211 FALSE), /* pcrel_offset */
1212
1213 /* Same as BFD_RELOC_AARCH64_TLSLD_LDST32_DTPREL_LO12, but no overflow check. */
1214 HOWTO64 (AARCH64_R (TLSLD_LDST32_DTPREL_LO12_NC), /* type */
1215 2, /* rightshift */
1216 2, /* size (0 = byte, 1 = short, 2 = long) */
1217 10, /* bitsize */
1218 FALSE, /* pc_relative */
1219 10, /* bitpos */
1220 complain_overflow_dont, /* complain_on_overflow */
1221 bfd_elf_generic_reloc, /* special_function */
1222 AARCH64_R_STR (TLSLD_LDST32_DTPREL_LO12_NC), /* name */
1223 FALSE, /* partial_inplace */
1224 0xffc00, /* src_mask */
1225 0xffc00, /* dst_mask */
1226 FALSE), /* pcrel_offset */
1227
1228 /* LD/ST64: bit[11:3] of byte offset to module TLS base address. */
1229 HOWTO64 (AARCH64_R (TLSLD_LDST64_DTPREL_LO12), /* type */
1230 3, /* rightshift */
1231 2, /* size (0 = byte, 1 = short, 2 = long) */
1232 9, /* bitsize */
1233 FALSE, /* pc_relative */
1234 10, /* bitpos */
1235 complain_overflow_unsigned, /* complain_on_overflow */
1236 bfd_elf_generic_reloc, /* special_function */
1237 AARCH64_R_STR (TLSLD_LDST64_DTPREL_LO12), /* name */
1238 FALSE, /* partial_inplace */
1239 0x3ffc00, /* src_mask */
1240 0x3ffc00, /* dst_mask */
1241 FALSE), /* pcrel_offset */
1242
1243 /* Same as BFD_RELOC_AARCH64_TLSLD_LDST64_DTPREL_LO12, but no overflow check. */
1244 HOWTO64 (AARCH64_R (TLSLD_LDST64_DTPREL_LO12_NC), /* type */
1245 3, /* rightshift */
1246 2, /* size (0 = byte, 1 = short, 2 = long) */
1247 9, /* bitsize */
1248 FALSE, /* pc_relative */
1249 10, /* bitpos */
1250 complain_overflow_dont, /* complain_on_overflow */
1251 bfd_elf_generic_reloc, /* special_function */
1252 AARCH64_R_STR (TLSLD_LDST64_DTPREL_LO12_NC), /* name */
1253 FALSE, /* partial_inplace */
1254 0x7fc00, /* src_mask */
1255 0x7fc00, /* dst_mask */
1256 FALSE), /* pcrel_offset */
1257
1258 /* LD/ST8: bit[11:0] of byte offset to module TLS base address. */
1259 HOWTO64 (AARCH64_R (TLSLD_LDST8_DTPREL_LO12), /* type */
1260 0, /* rightshift */
1261 2, /* size (0 = byte, 1 = short, 2 = long) */
1262 12, /* bitsize */
1263 FALSE, /* pc_relative */
1264 10, /* bitpos */
1265 complain_overflow_unsigned, /* complain_on_overflow */
1266 bfd_elf_generic_reloc, /* special_function */
1267 AARCH64_R_STR (TLSLD_LDST8_DTPREL_LO12), /* name */
1268 FALSE, /* partial_inplace */
1269 0x3ffc00, /* src_mask */
1270 0x3ffc00, /* dst_mask */
1271 FALSE), /* pcrel_offset */
1272
1273 /* Same as BFD_RELOC_AARCH64_TLSLD_LDST8_DTPREL_LO12, but no overflow check. */
1274 HOWTO64 (AARCH64_R (TLSLD_LDST8_DTPREL_LO12_NC), /* type */
1275 0, /* rightshift */
1276 2, /* size (0 = byte, 1 = short, 2 = long) */
1277 12, /* bitsize */
1278 FALSE, /* pc_relative */
1279 10, /* bitpos */
1280 complain_overflow_dont, /* complain_on_overflow */
1281 bfd_elf_generic_reloc, /* special_function */
1282 AARCH64_R_STR (TLSLD_LDST8_DTPREL_LO12_NC), /* name */
1283 FALSE, /* partial_inplace */
1284 0x3ffc00, /* src_mask */
1285 0x3ffc00, /* dst_mask */
1286 FALSE), /* pcrel_offset */
1287
49df5539
JW
1288 /* MOVZ: bit[15:0] of byte offset to module TLS base address. */
1289 HOWTO (AARCH64_R (TLSLD_MOVW_DTPREL_G0), /* type */
1290 0, /* rightshift */
1291 2, /* size (0 = byte, 1 = short, 2 = long) */
1292 16, /* bitsize */
1293 FALSE, /* pc_relative */
1294 0, /* bitpos */
1295 complain_overflow_unsigned, /* complain_on_overflow */
1296 bfd_elf_generic_reloc, /* special_function */
1297 AARCH64_R_STR (TLSLD_MOVW_DTPREL_G0), /* name */
1298 FALSE, /* partial_inplace */
1299 0xffff, /* src_mask */
1300 0xffff, /* dst_mask */
1301 FALSE), /* pcrel_offset */
1302
1303 /* No overflow check version of BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G0. */
1304 HOWTO (AARCH64_R (TLSLD_MOVW_DTPREL_G0_NC), /* type */
1305 0, /* rightshift */
1306 2, /* size (0 = byte, 1 = short, 2 = long) */
1307 16, /* bitsize */
1308 FALSE, /* pc_relative */
1309 0, /* bitpos */
1310 complain_overflow_dont, /* complain_on_overflow */
1311 bfd_elf_generic_reloc, /* special_function */
1312 AARCH64_R_STR (TLSLD_MOVW_DTPREL_G0_NC), /* name */
1313 FALSE, /* partial_inplace */
1314 0xffff, /* src_mask */
1315 0xffff, /* dst_mask */
1316 FALSE), /* pcrel_offset */
1317
1318 /* MOVZ: bit[31:16] of byte offset to module TLS base address. */
1319 HOWTO (AARCH64_R (TLSLD_MOVW_DTPREL_G1), /* type */
1320 16, /* rightshift */
1321 2, /* size (0 = byte, 1 = short, 2 = long) */
1322 16, /* bitsize */
1323 FALSE, /* pc_relative */
1324 0, /* bitpos */
1325 complain_overflow_unsigned, /* complain_on_overflow */
1326 bfd_elf_generic_reloc, /* special_function */
1327 AARCH64_R_STR (TLSLD_MOVW_DTPREL_G1), /* name */
1328 FALSE, /* partial_inplace */
1329 0xffff, /* src_mask */
1330 0xffff, /* dst_mask */
1331 FALSE), /* pcrel_offset */
1332
1333 /* No overflow check version of BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1. */
1334 HOWTO64 (AARCH64_R (TLSLD_MOVW_DTPREL_G1_NC), /* type */
1335 16, /* rightshift */
1336 2, /* size (0 = byte, 1 = short, 2 = long) */
1337 16, /* bitsize */
1338 FALSE, /* pc_relative */
1339 0, /* bitpos */
1340 complain_overflow_dont, /* complain_on_overflow */
1341 bfd_elf_generic_reloc, /* special_function */
1342 AARCH64_R_STR (TLSLD_MOVW_DTPREL_G1_NC), /* name */
1343 FALSE, /* partial_inplace */
1344 0xffff, /* src_mask */
1345 0xffff, /* dst_mask */
1346 FALSE), /* pcrel_offset */
1347
1348 /* MOVZ: bit[47:32] of byte offset to module TLS base address. */
1349 HOWTO64 (AARCH64_R (TLSLD_MOVW_DTPREL_G2), /* type */
1350 32, /* rightshift */
1351 2, /* size (0 = byte, 1 = short, 2 = long) */
1352 16, /* bitsize */
1353 FALSE, /* pc_relative */
1354 0, /* bitpos */
1355 complain_overflow_unsigned, /* complain_on_overflow */
1356 bfd_elf_generic_reloc, /* special_function */
1357 AARCH64_R_STR (TLSLD_MOVW_DTPREL_G2), /* name */
1358 FALSE, /* partial_inplace */
1359 0xffff, /* src_mask */
1360 0xffff, /* dst_mask */
1361 FALSE), /* pcrel_offset */
1362
a6bb11b2 1363 HOWTO64 (AARCH64_R (TLSLE_MOVW_TPREL_G2), /* type */
bb3f9ed8 1364 32, /* rightshift */
a06ea964 1365 2, /* size (0 = byte, 1 = short, 2 = long) */
07875fbc 1366 16, /* bitsize */
a06ea964
NC
1367 FALSE, /* pc_relative */
1368 0, /* bitpos */
0172429c 1369 complain_overflow_unsigned, /* complain_on_overflow */
a06ea964 1370 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1371 AARCH64_R_STR (TLSLE_MOVW_TPREL_G2), /* name */
a06ea964
NC
1372 FALSE, /* partial_inplace */
1373 0xffff, /* src_mask */
1374 0xffff, /* dst_mask */
1375 FALSE), /* pcrel_offset */
1376
a6bb11b2 1377 HOWTO (AARCH64_R (TLSLE_MOVW_TPREL_G1), /* type */
bb3f9ed8 1378 16, /* rightshift */
a06ea964 1379 2, /* size (0 = byte, 1 = short, 2 = long) */
07875fbc 1380 16, /* bitsize */
a06ea964
NC
1381 FALSE, /* pc_relative */
1382 0, /* bitpos */
1383 complain_overflow_dont, /* complain_on_overflow */
1384 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1385 AARCH64_R_STR (TLSLE_MOVW_TPREL_G1), /* name */
a06ea964
NC
1386 FALSE, /* partial_inplace */
1387 0xffff, /* src_mask */
1388 0xffff, /* dst_mask */
1389 FALSE), /* pcrel_offset */
1390
a6bb11b2 1391 HOWTO64 (AARCH64_R (TLSLE_MOVW_TPREL_G1_NC), /* type */
bb3f9ed8 1392 16, /* rightshift */
a06ea964 1393 2, /* size (0 = byte, 1 = short, 2 = long) */
07875fbc 1394 16, /* bitsize */
a06ea964
NC
1395 FALSE, /* pc_relative */
1396 0, /* bitpos */
1397 complain_overflow_dont, /* complain_on_overflow */
1398 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1399 AARCH64_R_STR (TLSLE_MOVW_TPREL_G1_NC), /* name */
a06ea964
NC
1400 FALSE, /* partial_inplace */
1401 0xffff, /* src_mask */
1402 0xffff, /* dst_mask */
1403 FALSE), /* pcrel_offset */
1404
a6bb11b2 1405 HOWTO (AARCH64_R (TLSLE_MOVW_TPREL_G0), /* type */
a06ea964
NC
1406 0, /* rightshift */
1407 2, /* size (0 = byte, 1 = short, 2 = long) */
07875fbc 1408 16, /* bitsize */
a06ea964
NC
1409 FALSE, /* pc_relative */
1410 0, /* bitpos */
1411 complain_overflow_dont, /* complain_on_overflow */
1412 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1413 AARCH64_R_STR (TLSLE_MOVW_TPREL_G0), /* name */
a06ea964
NC
1414 FALSE, /* partial_inplace */
1415 0xffff, /* src_mask */
1416 0xffff, /* dst_mask */
1417 FALSE), /* pcrel_offset */
1418
a6bb11b2 1419 HOWTO (AARCH64_R (TLSLE_MOVW_TPREL_G0_NC), /* type */
a06ea964
NC
1420 0, /* rightshift */
1421 2, /* size (0 = byte, 1 = short, 2 = long) */
07875fbc 1422 16, /* bitsize */
a06ea964
NC
1423 FALSE, /* pc_relative */
1424 0, /* bitpos */
1425 complain_overflow_dont, /* complain_on_overflow */
1426 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1427 AARCH64_R_STR (TLSLE_MOVW_TPREL_G0_NC), /* name */
a06ea964
NC
1428 FALSE, /* partial_inplace */
1429 0xffff, /* src_mask */
1430 0xffff, /* dst_mask */
1431 FALSE), /* pcrel_offset */
1432
a6bb11b2 1433 HOWTO (AARCH64_R (TLSLE_ADD_TPREL_HI12), /* type */
bb3f9ed8 1434 12, /* rightshift */
a06ea964
NC
1435 2, /* size (0 = byte, 1 = short, 2 = long) */
1436 12, /* bitsize */
1437 FALSE, /* pc_relative */
1438 0, /* bitpos */
bab91cce 1439 complain_overflow_unsigned, /* complain_on_overflow */
a06ea964 1440 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1441 AARCH64_R_STR (TLSLE_ADD_TPREL_HI12), /* name */
a06ea964
NC
1442 FALSE, /* partial_inplace */
1443 0xfff, /* src_mask */
1444 0xfff, /* dst_mask */
1445 FALSE), /* pcrel_offset */
1446
a6bb11b2 1447 HOWTO (AARCH64_R (TLSLE_ADD_TPREL_LO12), /* type */
a06ea964
NC
1448 0, /* rightshift */
1449 2, /* size (0 = byte, 1 = short, 2 = long) */
1450 12, /* bitsize */
1451 FALSE, /* pc_relative */
1452 0, /* bitpos */
36e6c140 1453 complain_overflow_unsigned, /* complain_on_overflow */
a06ea964 1454 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1455 AARCH64_R_STR (TLSLE_ADD_TPREL_LO12), /* name */
a06ea964
NC
1456 FALSE, /* partial_inplace */
1457 0xfff, /* src_mask */
1458 0xfff, /* dst_mask */
1459 FALSE), /* pcrel_offset */
1460
a6bb11b2 1461 HOWTO (AARCH64_R (TLSLE_ADD_TPREL_LO12_NC), /* type */
a06ea964
NC
1462 0, /* rightshift */
1463 2, /* size (0 = byte, 1 = short, 2 = long) */
1464 12, /* bitsize */
1465 FALSE, /* pc_relative */
1466 0, /* bitpos */
1467 complain_overflow_dont, /* complain_on_overflow */
1468 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1469 AARCH64_R_STR (TLSLE_ADD_TPREL_LO12_NC), /* name */
a06ea964
NC
1470 FALSE, /* partial_inplace */
1471 0xfff, /* src_mask */
1472 0xfff, /* dst_mask */
1473 FALSE), /* pcrel_offset */
a06ea964 1474
a6bb11b2 1475 HOWTO (AARCH64_R (TLSDESC_LD_PREL19), /* type */
bb3f9ed8 1476 2, /* rightshift */
a06ea964 1477 2, /* size (0 = byte, 1 = short, 2 = long) */
1ada945d 1478 19, /* bitsize */
a06ea964
NC
1479 TRUE, /* pc_relative */
1480 0, /* bitpos */
1481 complain_overflow_dont, /* complain_on_overflow */
1482 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1483 AARCH64_R_STR (TLSDESC_LD_PREL19), /* name */
a06ea964 1484 FALSE, /* partial_inplace */
1ada945d
MS
1485 0x0ffffe0, /* src_mask */
1486 0x0ffffe0, /* dst_mask */
a06ea964
NC
1487 TRUE), /* pcrel_offset */
1488
a6bb11b2 1489 HOWTO (AARCH64_R (TLSDESC_ADR_PREL21), /* type */
a06ea964
NC
1490 0, /* rightshift */
1491 2, /* size (0 = byte, 1 = short, 2 = long) */
1492 21, /* bitsize */
1493 TRUE, /* pc_relative */
1494 0, /* bitpos */
1495 complain_overflow_dont, /* complain_on_overflow */
1496 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1497 AARCH64_R_STR (TLSDESC_ADR_PREL21), /* name */
a06ea964
NC
1498 FALSE, /* partial_inplace */
1499 0x1fffff, /* src_mask */
1500 0x1fffff, /* dst_mask */
1501 TRUE), /* pcrel_offset */
1502
1503 /* Get to the page for the GOT entry for the symbol
1504 (G(S) - P) using an ADRP instruction. */
a6bb11b2 1505 HOWTO (AARCH64_R (TLSDESC_ADR_PAGE21), /* type */
a06ea964
NC
1506 12, /* rightshift */
1507 2, /* size (0 = byte, 1 = short, 2 = long) */
1508 21, /* bitsize */
1509 TRUE, /* pc_relative */
1510 0, /* bitpos */
1511 complain_overflow_dont, /* complain_on_overflow */
1512 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1513 AARCH64_R_STR (TLSDESC_ADR_PAGE21), /* name */
a06ea964
NC
1514 FALSE, /* partial_inplace */
1515 0x1fffff, /* src_mask */
1516 0x1fffff, /* dst_mask */
1517 TRUE), /* pcrel_offset */
1518
a6bb11b2
YZ
1519 /* LD64: GOT offset G(S) & 0xff8. */
1520 HOWTO64 (AARCH64_R (TLSDESC_LD64_LO12_NC), /* type */
a06ea964
NC
1521 3, /* rightshift */
1522 2, /* size (0 = byte, 1 = short, 2 = long) */
1523 12, /* bitsize */
1524 FALSE, /* pc_relative */
1525 0, /* bitpos */
1526 complain_overflow_dont, /* complain_on_overflow */
1527 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1528 AARCH64_R_STR (TLSDESC_LD64_LO12_NC), /* name */
a06ea964 1529 FALSE, /* partial_inplace */
a6bb11b2
YZ
1530 0xff8, /* src_mask */
1531 0xff8, /* dst_mask */
1532 FALSE), /* pcrel_offset */
1533
1534 /* LD32: GOT offset G(S) & 0xffc. */
1535 HOWTO32 (AARCH64_R (TLSDESC_LD32_LO12_NC), /* type */
1536 2, /* rightshift */
1537 2, /* size (0 = byte, 1 = short, 2 = long) */
1538 12, /* bitsize */
1539 FALSE, /* pc_relative */
1540 0, /* bitpos */
1541 complain_overflow_dont, /* complain_on_overflow */
1542 bfd_elf_generic_reloc, /* special_function */
1543 AARCH64_R_STR (TLSDESC_LD32_LO12_NC), /* name */
1544 FALSE, /* partial_inplace */
1545 0xffc, /* src_mask */
1546 0xffc, /* dst_mask */
a06ea964
NC
1547 FALSE), /* pcrel_offset */
1548
1549 /* ADD: GOT offset G(S) & 0xfff. */
a6bb11b2 1550 HOWTO (AARCH64_R (TLSDESC_ADD_LO12_NC), /* type */
a06ea964
NC
1551 0, /* rightshift */
1552 2, /* size (0 = byte, 1 = short, 2 = long) */
1553 12, /* bitsize */
1554 FALSE, /* pc_relative */
1555 0, /* bitpos */
1556 complain_overflow_dont, /* complain_on_overflow */
1557 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1558 AARCH64_R_STR (TLSDESC_ADD_LO12_NC), /* name */
a06ea964
NC
1559 FALSE, /* partial_inplace */
1560 0xfff, /* src_mask */
1561 0xfff, /* dst_mask */
1562 FALSE), /* pcrel_offset */
1563
a6bb11b2 1564 HOWTO64 (AARCH64_R (TLSDESC_OFF_G1), /* type */
bb3f9ed8 1565 16, /* rightshift */
a06ea964
NC
1566 2, /* size (0 = byte, 1 = short, 2 = long) */
1567 12, /* bitsize */
1568 FALSE, /* pc_relative */
1569 0, /* bitpos */
1570 complain_overflow_dont, /* complain_on_overflow */
1571 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1572 AARCH64_R_STR (TLSDESC_OFF_G1), /* name */
a06ea964
NC
1573 FALSE, /* partial_inplace */
1574 0xffff, /* src_mask */
1575 0xffff, /* dst_mask */
1576 FALSE), /* pcrel_offset */
1577
a6bb11b2 1578 HOWTO64 (AARCH64_R (TLSDESC_OFF_G0_NC), /* type */
a06ea964
NC
1579 0, /* rightshift */
1580 2, /* size (0 = byte, 1 = short, 2 = long) */
1581 12, /* bitsize */
1582 FALSE, /* pc_relative */
1583 0, /* bitpos */
1584 complain_overflow_dont, /* complain_on_overflow */
1585 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1586 AARCH64_R_STR (TLSDESC_OFF_G0_NC), /* name */
a06ea964
NC
1587 FALSE, /* partial_inplace */
1588 0xffff, /* src_mask */
1589 0xffff, /* dst_mask */
1590 FALSE), /* pcrel_offset */
1591
a6bb11b2 1592 HOWTO64 (AARCH64_R (TLSDESC_LDR), /* type */
a06ea964
NC
1593 0, /* rightshift */
1594 2, /* size (0 = byte, 1 = short, 2 = long) */
1595 12, /* bitsize */
1596 FALSE, /* pc_relative */
1597 0, /* bitpos */
1598 complain_overflow_dont, /* complain_on_overflow */
1599 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1600 AARCH64_R_STR (TLSDESC_LDR), /* name */
a06ea964
NC
1601 FALSE, /* partial_inplace */
1602 0x0, /* src_mask */
1603 0x0, /* dst_mask */
1604 FALSE), /* pcrel_offset */
1605
a6bb11b2 1606 HOWTO64 (AARCH64_R (TLSDESC_ADD), /* type */
a06ea964
NC
1607 0, /* rightshift */
1608 2, /* size (0 = byte, 1 = short, 2 = long) */
1609 12, /* bitsize */
1610 FALSE, /* pc_relative */
1611 0, /* bitpos */
1612 complain_overflow_dont, /* complain_on_overflow */
1613 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1614 AARCH64_R_STR (TLSDESC_ADD), /* name */
a06ea964
NC
1615 FALSE, /* partial_inplace */
1616 0x0, /* src_mask */
1617 0x0, /* dst_mask */
1618 FALSE), /* pcrel_offset */
1619
a6bb11b2 1620 HOWTO (AARCH64_R (TLSDESC_CALL), /* type */
a06ea964
NC
1621 0, /* rightshift */
1622 2, /* size (0 = byte, 1 = short, 2 = long) */
7366006f 1623 0, /* bitsize */
a06ea964
NC
1624 FALSE, /* pc_relative */
1625 0, /* bitpos */
1626 complain_overflow_dont, /* complain_on_overflow */
1627 bfd_elf_generic_reloc, /* special_function */
a6bb11b2 1628 AARCH64_R_STR (TLSDESC_CALL), /* name */
a06ea964
NC
1629 FALSE, /* partial_inplace */
1630 0x0, /* src_mask */
1631 0x0, /* dst_mask */
1632 FALSE), /* pcrel_offset */
a6bb11b2
YZ
1633
1634 HOWTO (AARCH64_R (COPY), /* type */
1635 0, /* rightshift */
1636 2, /* size (0 = byte, 1 = short, 2 = long) */
1637 64, /* bitsize */
1638 FALSE, /* pc_relative */
1639 0, /* bitpos */
1640 complain_overflow_bitfield, /* complain_on_overflow */
1641 bfd_elf_generic_reloc, /* special_function */
1642 AARCH64_R_STR (COPY), /* name */
1643 TRUE, /* partial_inplace */
1644 0xffffffff, /* src_mask */
1645 0xffffffff, /* dst_mask */
1646 FALSE), /* pcrel_offset */
1647
1648 HOWTO (AARCH64_R (GLOB_DAT), /* type */
1649 0, /* rightshift */
1650 2, /* size (0 = byte, 1 = short, 2 = long) */
1651 64, /* bitsize */
1652 FALSE, /* pc_relative */
1653 0, /* bitpos */
1654 complain_overflow_bitfield, /* complain_on_overflow */
1655 bfd_elf_generic_reloc, /* special_function */
1656 AARCH64_R_STR (GLOB_DAT), /* name */
1657 TRUE, /* partial_inplace */
1658 0xffffffff, /* src_mask */
1659 0xffffffff, /* dst_mask */
1660 FALSE), /* pcrel_offset */
1661
1662 HOWTO (AARCH64_R (JUMP_SLOT), /* type */
1663 0, /* rightshift */
1664 2, /* size (0 = byte, 1 = short, 2 = long) */
1665 64, /* bitsize */
1666 FALSE, /* pc_relative */
1667 0, /* bitpos */
1668 complain_overflow_bitfield, /* complain_on_overflow */
1669 bfd_elf_generic_reloc, /* special_function */
1670 AARCH64_R_STR (JUMP_SLOT), /* name */
1671 TRUE, /* partial_inplace */
1672 0xffffffff, /* src_mask */
1673 0xffffffff, /* dst_mask */
1674 FALSE), /* pcrel_offset */
1675
1676 HOWTO (AARCH64_R (RELATIVE), /* type */
1677 0, /* rightshift */
1678 2, /* size (0 = byte, 1 = short, 2 = long) */
1679 64, /* bitsize */
1680 FALSE, /* pc_relative */
1681 0, /* bitpos */
1682 complain_overflow_bitfield, /* complain_on_overflow */
1683 bfd_elf_generic_reloc, /* special_function */
1684 AARCH64_R_STR (RELATIVE), /* name */
1685 TRUE, /* partial_inplace */
1686 ALL_ONES, /* src_mask */
1687 ALL_ONES, /* dst_mask */
1688 FALSE), /* pcrel_offset */
1689
1690 HOWTO (AARCH64_R (TLS_DTPMOD), /* type */
1691 0, /* rightshift */
1692 2, /* size (0 = byte, 1 = short, 2 = long) */
1693 64, /* bitsize */
1694 FALSE, /* pc_relative */
1695 0, /* bitpos */
1696 complain_overflow_dont, /* complain_on_overflow */
1697 bfd_elf_generic_reloc, /* special_function */
da0781dc
YZ
1698#if ARCH_SIZE == 64
1699 AARCH64_R_STR (TLS_DTPMOD64), /* name */
1700#else
a6bb11b2 1701 AARCH64_R_STR (TLS_DTPMOD), /* name */
da0781dc 1702#endif
a6bb11b2
YZ
1703 FALSE, /* partial_inplace */
1704 0, /* src_mask */
1705 ALL_ONES, /* dst_mask */
1706 FALSE), /* pc_reloffset */
1707
1708 HOWTO (AARCH64_R (TLS_DTPREL), /* type */
1709 0, /* rightshift */
1710 2, /* size (0 = byte, 1 = short, 2 = long) */
1711 64, /* bitsize */
1712 FALSE, /* pc_relative */
1713 0, /* bitpos */
1714 complain_overflow_dont, /* complain_on_overflow */
1715 bfd_elf_generic_reloc, /* special_function */
da0781dc
YZ
1716#if ARCH_SIZE == 64
1717 AARCH64_R_STR (TLS_DTPREL64), /* name */
1718#else
a6bb11b2 1719 AARCH64_R_STR (TLS_DTPREL), /* name */
da0781dc 1720#endif
a6bb11b2
YZ
1721 FALSE, /* partial_inplace */
1722 0, /* src_mask */
1723 ALL_ONES, /* dst_mask */
1724 FALSE), /* pcrel_offset */
1725
1726 HOWTO (AARCH64_R (TLS_TPREL), /* type */
1727 0, /* rightshift */
1728 2, /* size (0 = byte, 1 = short, 2 = long) */
1729 64, /* bitsize */
1730 FALSE, /* pc_relative */
1731 0, /* bitpos */
1732 complain_overflow_dont, /* complain_on_overflow */
1733 bfd_elf_generic_reloc, /* special_function */
da0781dc
YZ
1734#if ARCH_SIZE == 64
1735 AARCH64_R_STR (TLS_TPREL64), /* name */
1736#else
a6bb11b2 1737 AARCH64_R_STR (TLS_TPREL), /* name */
da0781dc 1738#endif
a6bb11b2
YZ
1739 FALSE, /* partial_inplace */
1740 0, /* src_mask */
1741 ALL_ONES, /* dst_mask */
1742 FALSE), /* pcrel_offset */
1743
1744 HOWTO (AARCH64_R (TLSDESC), /* type */
1745 0, /* rightshift */
1746 2, /* size (0 = byte, 1 = short, 2 = long) */
1747 64, /* bitsize */
1748 FALSE, /* pc_relative */
1749 0, /* bitpos */
1750 complain_overflow_dont, /* complain_on_overflow */
1751 bfd_elf_generic_reloc, /* special_function */
1752 AARCH64_R_STR (TLSDESC), /* name */
1753 FALSE, /* partial_inplace */
1754 0, /* src_mask */
1755 ALL_ONES, /* dst_mask */
1756 FALSE), /* pcrel_offset */
1757
1758 HOWTO (AARCH64_R (IRELATIVE), /* type */
1759 0, /* rightshift */
1760 2, /* size (0 = byte, 1 = short, 2 = long) */
1761 64, /* bitsize */
1762 FALSE, /* pc_relative */
1763 0, /* bitpos */
1764 complain_overflow_bitfield, /* complain_on_overflow */
1765 bfd_elf_generic_reloc, /* special_function */
1766 AARCH64_R_STR (IRELATIVE), /* name */
1767 FALSE, /* partial_inplace */
1768 0, /* src_mask */
1769 ALL_ONES, /* dst_mask */
1770 FALSE), /* pcrel_offset */
1771
1772 EMPTY_HOWTO (0),
a06ea964
NC
1773};
1774
a6bb11b2
YZ
1775static reloc_howto_type elfNN_aarch64_howto_none =
1776 HOWTO (R_AARCH64_NONE, /* type */
1777 0, /* rightshift */
6346d5ca 1778 3, /* size (0 = byte, 1 = short, 2 = long) */
a6bb11b2
YZ
1779 0, /* bitsize */
1780 FALSE, /* pc_relative */
1781 0, /* bitpos */
1782 complain_overflow_dont,/* complain_on_overflow */
1783 bfd_elf_generic_reloc, /* special_function */
1784 "R_AARCH64_NONE", /* name */
1785 FALSE, /* partial_inplace */
1786 0, /* src_mask */
1787 0, /* dst_mask */
1788 FALSE); /* pcrel_offset */
1789
1790/* Given HOWTO, return the bfd internal relocation enumerator. */
1791
1792static bfd_reloc_code_real_type
1793elfNN_aarch64_bfd_reloc_from_howto (reloc_howto_type *howto)
1794{
1795 const int size
1796 = (int) ARRAY_SIZE (elfNN_aarch64_howto_table);
1797 const ptrdiff_t offset
1798 = howto - elfNN_aarch64_howto_table;
1799
1800 if (offset > 0 && offset < size - 1)
1801 return BFD_RELOC_AARCH64_RELOC_START + offset;
1802
1803 if (howto == &elfNN_aarch64_howto_none)
1804 return BFD_RELOC_AARCH64_NONE;
1805
1806 return BFD_RELOC_AARCH64_RELOC_START;
1807}
1808
1809/* Given R_TYPE, return the bfd internal relocation enumerator. */
1810
1811static bfd_reloc_code_real_type
1812elfNN_aarch64_bfd_reloc_from_type (unsigned int r_type)
1813{
1814 static bfd_boolean initialized_p = FALSE;
1815 /* Indexed by R_TYPE, values are offsets in the howto_table. */
1816 static unsigned int offsets[R_AARCH64_end];
1817
1818 if (initialized_p == FALSE)
1819 {
1820 unsigned int i;
1821
1822 for (i = 1; i < ARRAY_SIZE (elfNN_aarch64_howto_table) - 1; ++i)
1823 if (elfNN_aarch64_howto_table[i].type != 0)
1824 offsets[elfNN_aarch64_howto_table[i].type] = i;
1825
1826 initialized_p = TRUE;
1827 }
1828
1829 if (r_type == R_AARCH64_NONE || r_type == R_AARCH64_NULL)
1830 return BFD_RELOC_AARCH64_NONE;
1831
5860e3f8
NC
1832 /* PR 17512: file: b371e70a. */
1833 if (r_type >= R_AARCH64_end)
1834 {
1835 _bfd_error_handler (_("Invalid AArch64 reloc number: %d"), r_type);
1836 bfd_set_error (bfd_error_bad_value);
1837 return BFD_RELOC_AARCH64_NONE;
1838 }
1839
a6bb11b2
YZ
1840 return BFD_RELOC_AARCH64_RELOC_START + offsets[r_type];
1841}
1842
1843struct elf_aarch64_reloc_map
1844{
1845 bfd_reloc_code_real_type from;
1846 bfd_reloc_code_real_type to;
1847};
1848
1849/* Map bfd generic reloc to AArch64-specific reloc. */
1850static const struct elf_aarch64_reloc_map elf_aarch64_reloc_map[] =
1851{
1852 {BFD_RELOC_NONE, BFD_RELOC_AARCH64_NONE},
1853
1854 /* Basic data relocations. */
1855 {BFD_RELOC_CTOR, BFD_RELOC_AARCH64_NN},
1856 {BFD_RELOC_64, BFD_RELOC_AARCH64_64},
1857 {BFD_RELOC_32, BFD_RELOC_AARCH64_32},
1858 {BFD_RELOC_16, BFD_RELOC_AARCH64_16},
1859 {BFD_RELOC_64_PCREL, BFD_RELOC_AARCH64_64_PCREL},
1860 {BFD_RELOC_32_PCREL, BFD_RELOC_AARCH64_32_PCREL},
1861 {BFD_RELOC_16_PCREL, BFD_RELOC_AARCH64_16_PCREL},
1862};
1863
1864/* Given the bfd internal relocation enumerator in CODE, return the
1865 corresponding howto entry. */
1866
1867static reloc_howto_type *
1868elfNN_aarch64_howto_from_bfd_reloc (bfd_reloc_code_real_type code)
1869{
1870 unsigned int i;
1871
1872 /* Convert bfd generic reloc to AArch64-specific reloc. */
1873 if (code < BFD_RELOC_AARCH64_RELOC_START
1874 || code > BFD_RELOC_AARCH64_RELOC_END)
1875 for (i = 0; i < ARRAY_SIZE (elf_aarch64_reloc_map); i++)
1876 if (elf_aarch64_reloc_map[i].from == code)
1877 {
1878 code = elf_aarch64_reloc_map[i].to;
1879 break;
1880 }
1881
1882 if (code > BFD_RELOC_AARCH64_RELOC_START
1883 && code < BFD_RELOC_AARCH64_RELOC_END)
1884 if (elfNN_aarch64_howto_table[code - BFD_RELOC_AARCH64_RELOC_START].type)
1885 return &elfNN_aarch64_howto_table[code - BFD_RELOC_AARCH64_RELOC_START];
1886
54757ed1
AP
1887 if (code == BFD_RELOC_AARCH64_NONE)
1888 return &elfNN_aarch64_howto_none;
1889
a6bb11b2
YZ
1890 return NULL;
1891}
1892
a06ea964 1893static reloc_howto_type *
cec5225b 1894elfNN_aarch64_howto_from_type (unsigned int r_type)
a06ea964 1895{
a6bb11b2
YZ
1896 bfd_reloc_code_real_type val;
1897 reloc_howto_type *howto;
1898
cec5225b
YZ
1899#if ARCH_SIZE == 32
1900 if (r_type > 256)
1901 {
1902 bfd_set_error (bfd_error_bad_value);
1903 return NULL;
1904 }
1905#endif
1906
a6bb11b2
YZ
1907 if (r_type == R_AARCH64_NONE)
1908 return &elfNN_aarch64_howto_none;
a06ea964 1909
a6bb11b2
YZ
1910 val = elfNN_aarch64_bfd_reloc_from_type (r_type);
1911 howto = elfNN_aarch64_howto_from_bfd_reloc (val);
a06ea964 1912
a6bb11b2
YZ
1913 if (howto != NULL)
1914 return howto;
a06ea964 1915
a06ea964
NC
1916 bfd_set_error (bfd_error_bad_value);
1917 return NULL;
1918}
1919
1920static void
cec5225b 1921elfNN_aarch64_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED, arelent *bfd_reloc,
a06ea964
NC
1922 Elf_Internal_Rela *elf_reloc)
1923{
1924 unsigned int r_type;
1925
cec5225b
YZ
1926 r_type = ELFNN_R_TYPE (elf_reloc->r_info);
1927 bfd_reloc->howto = elfNN_aarch64_howto_from_type (r_type);
a06ea964
NC
1928}
1929
a06ea964 1930static reloc_howto_type *
cec5225b 1931elfNN_aarch64_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
a06ea964
NC
1932 bfd_reloc_code_real_type code)
1933{
a6bb11b2 1934 reloc_howto_type *howto = elfNN_aarch64_howto_from_bfd_reloc (code);
a06ea964 1935
a6bb11b2
YZ
1936 if (howto != NULL)
1937 return howto;
a06ea964
NC
1938
1939 bfd_set_error (bfd_error_bad_value);
1940 return NULL;
1941}
1942
1943static reloc_howto_type *
cec5225b 1944elfNN_aarch64_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
a06ea964
NC
1945 const char *r_name)
1946{
1947 unsigned int i;
1948
a6bb11b2
YZ
1949 for (i = 1; i < ARRAY_SIZE (elfNN_aarch64_howto_table) - 1; ++i)
1950 if (elfNN_aarch64_howto_table[i].name != NULL
1951 && strcasecmp (elfNN_aarch64_howto_table[i].name, r_name) == 0)
1952 return &elfNN_aarch64_howto_table[i];
a06ea964
NC
1953
1954 return NULL;
1955}
1956
6d00b590 1957#define TARGET_LITTLE_SYM aarch64_elfNN_le_vec
cec5225b 1958#define TARGET_LITTLE_NAME "elfNN-littleaarch64"
6d00b590 1959#define TARGET_BIG_SYM aarch64_elfNN_be_vec
cec5225b 1960#define TARGET_BIG_NAME "elfNN-bigaarch64"
a06ea964 1961
a06ea964
NC
1962/* The linker script knows the section names for placement.
1963 The entry_names are used to do simple name mangling on the stubs.
1964 Given a function name, and its type, the stub can be found. The
1965 name can be changed. The only requirement is the %s be present. */
1966#define STUB_ENTRY_NAME "__%s_veneer"
1967
1968/* The name of the dynamic interpreter. This is put in the .interp
1969 section. */
1970#define ELF_DYNAMIC_INTERPRETER "/lib/ld.so.1"
1971
1972#define AARCH64_MAX_FWD_BRANCH_OFFSET \
1973 (((1 << 25) - 1) << 2)
1974#define AARCH64_MAX_BWD_BRANCH_OFFSET \
1975 (-((1 << 25) << 2))
1976
1977#define AARCH64_MAX_ADRP_IMM ((1 << 20) - 1)
1978#define AARCH64_MIN_ADRP_IMM (-(1 << 20))
1979
1980static int
1981aarch64_valid_for_adrp_p (bfd_vma value, bfd_vma place)
1982{
1983 bfd_signed_vma offset = (bfd_signed_vma) (PG (value) - PG (place)) >> 12;
1984 return offset <= AARCH64_MAX_ADRP_IMM && offset >= AARCH64_MIN_ADRP_IMM;
1985}
1986
1987static int
1988aarch64_valid_branch_p (bfd_vma value, bfd_vma place)
1989{
1990 bfd_signed_vma offset = (bfd_signed_vma) (value - place);
1991 return (offset <= AARCH64_MAX_FWD_BRANCH_OFFSET
1992 && offset >= AARCH64_MAX_BWD_BRANCH_OFFSET);
1993}
1994
1995static const uint32_t aarch64_adrp_branch_stub [] =
1996{
1997 0x90000010, /* adrp ip0, X */
1998 /* R_AARCH64_ADR_HI21_PCREL(X) */
1999 0x91000210, /* add ip0, ip0, :lo12:X */
2000 /* R_AARCH64_ADD_ABS_LO12_NC(X) */
2001 0xd61f0200, /* br ip0 */
2002};
2003
2004static const uint32_t aarch64_long_branch_stub[] =
2005{
cec5225b 2006#if ARCH_SIZE == 64
a06ea964 2007 0x58000090, /* ldr ip0, 1f */
cec5225b
YZ
2008#else
2009 0x18000090, /* ldr wip0, 1f */
2010#endif
a06ea964
NC
2011 0x10000011, /* adr ip1, #0 */
2012 0x8b110210, /* add ip0, ip0, ip1 */
2013 0xd61f0200, /* br ip0 */
cec5225b
YZ
2014 0x00000000, /* 1: .xword or .word
2015 R_AARCH64_PRELNN(X) + 12
a06ea964
NC
2016 */
2017 0x00000000,
2018};
2019
68fcca92
JW
2020static const uint32_t aarch64_erratum_835769_stub[] =
2021{
2022 0x00000000, /* Placeholder for multiply accumulate. */
2023 0x14000000, /* b <label> */
2024};
2025
4106101c
MS
2026static const uint32_t aarch64_erratum_843419_stub[] =
2027{
2028 0x00000000, /* Placeholder for LDR instruction. */
2029 0x14000000, /* b <label> */
2030};
2031
a06ea964
NC
2032/* Section name for stubs is the associated section name plus this
2033 string. */
2034#define STUB_SUFFIX ".stub"
2035
cec5225b 2036enum elf_aarch64_stub_type
a06ea964
NC
2037{
2038 aarch64_stub_none,
2039 aarch64_stub_adrp_branch,
2040 aarch64_stub_long_branch,
68fcca92 2041 aarch64_stub_erratum_835769_veneer,
4106101c 2042 aarch64_stub_erratum_843419_veneer,
a06ea964
NC
2043};
2044
cec5225b 2045struct elf_aarch64_stub_hash_entry
a06ea964
NC
2046{
2047 /* Base hash table entry structure. */
2048 struct bfd_hash_entry root;
2049
2050 /* The stub section. */
2051 asection *stub_sec;
2052
2053 /* Offset within stub_sec of the beginning of this stub. */
2054 bfd_vma stub_offset;
2055
2056 /* Given the symbol's value and its section we can determine its final
2057 value when building the stubs (so the stub knows where to jump). */
2058 bfd_vma target_value;
2059 asection *target_section;
2060
cec5225b 2061 enum elf_aarch64_stub_type stub_type;
a06ea964
NC
2062
2063 /* The symbol table entry, if any, that this was derived from. */
cec5225b 2064 struct elf_aarch64_link_hash_entry *h;
a06ea964
NC
2065
2066 /* Destination symbol type */
2067 unsigned char st_type;
2068
2069 /* Where this stub is being called from, or, in the case of combined
2070 stub sections, the first input section in the group. */
2071 asection *id_sec;
2072
2073 /* The name for the local symbol at the start of this stub. The
2074 stub name in the hash table has to be unique; this does not, so
2075 it can be friendlier. */
2076 char *output_name;
68fcca92
JW
2077
2078 /* The instruction which caused this stub to be generated (only valid for
2079 erratum 835769 workaround stubs at present). */
2080 uint32_t veneered_insn;
4106101c
MS
2081
2082 /* In an erratum 843419 workaround stub, the ADRP instruction offset. */
2083 bfd_vma adrp_offset;
a06ea964
NC
2084};
2085
2086/* Used to build a map of a section. This is required for mixed-endian
2087 code/data. */
2088
cec5225b 2089typedef struct elf_elf_section_map
a06ea964
NC
2090{
2091 bfd_vma vma;
2092 char type;
2093}
cec5225b 2094elf_aarch64_section_map;
a06ea964
NC
2095
2096
2097typedef struct _aarch64_elf_section_data
2098{
2099 struct bfd_elf_section_data elf;
2100 unsigned int mapcount;
2101 unsigned int mapsize;
cec5225b 2102 elf_aarch64_section_map *map;
a06ea964
NC
2103}
2104_aarch64_elf_section_data;
2105
cec5225b 2106#define elf_aarch64_section_data(sec) \
a06ea964
NC
2107 ((_aarch64_elf_section_data *) elf_section_data (sec))
2108
4e8516b2
AP
2109/* The size of the thread control block which is defined to be two pointers. */
2110#define TCB_SIZE (ARCH_SIZE/8)*2
a06ea964
NC
2111
2112struct elf_aarch64_local_symbol
2113{
2114 unsigned int got_type;
2115 bfd_signed_vma got_refcount;
2116 bfd_vma got_offset;
2117
2118 /* Offset of the GOTPLT entry reserved for the TLS descriptor. The
2119 offset is from the end of the jump table and reserved entries
2120 within the PLTGOT.
2121
2122 The magic value (bfd_vma) -1 indicates that an offset has not be
2123 allocated. */
2124 bfd_vma tlsdesc_got_jump_table_offset;
2125};
2126
2127struct elf_aarch64_obj_tdata
2128{
2129 struct elf_obj_tdata root;
2130
2131 /* local symbol descriptors */
2132 struct elf_aarch64_local_symbol *locals;
2133
2134 /* Zero to warn when linking objects with incompatible enum sizes. */
2135 int no_enum_size_warning;
2136
2137 /* Zero to warn when linking objects with incompatible wchar_t sizes. */
2138 int no_wchar_size_warning;
2139};
2140
2141#define elf_aarch64_tdata(bfd) \
2142 ((struct elf_aarch64_obj_tdata *) (bfd)->tdata.any)
2143
cec5225b 2144#define elf_aarch64_locals(bfd) (elf_aarch64_tdata (bfd)->locals)
a06ea964
NC
2145
2146#define is_aarch64_elf(bfd) \
2147 (bfd_get_flavour (bfd) == bfd_target_elf_flavour \
2148 && elf_tdata (bfd) != NULL \
2149 && elf_object_id (bfd) == AARCH64_ELF_DATA)
2150
2151static bfd_boolean
cec5225b 2152elfNN_aarch64_mkobject (bfd *abfd)
a06ea964
NC
2153{
2154 return bfd_elf_allocate_object (abfd, sizeof (struct elf_aarch64_obj_tdata),
2155 AARCH64_ELF_DATA);
2156}
2157
cec5225b
YZ
2158#define elf_aarch64_hash_entry(ent) \
2159 ((struct elf_aarch64_link_hash_entry *)(ent))
a06ea964
NC
2160
2161#define GOT_UNKNOWN 0
2162#define GOT_NORMAL 1
2163#define GOT_TLS_GD 2
2164#define GOT_TLS_IE 4
2165#define GOT_TLSDESC_GD 8
2166
2167#define GOT_TLS_GD_ANY_P(type) ((type & GOT_TLS_GD) || (type & GOT_TLSDESC_GD))
2168
2169/* AArch64 ELF linker hash entry. */
cec5225b 2170struct elf_aarch64_link_hash_entry
a06ea964
NC
2171{
2172 struct elf_link_hash_entry root;
2173
2174 /* Track dynamic relocs copied for this symbol. */
2175 struct elf_dyn_relocs *dyn_relocs;
2176
a06ea964
NC
2177 /* Since PLT entries have variable size, we need to record the
2178 index into .got.plt instead of recomputing it from the PLT
2179 offset. */
2180 bfd_signed_vma plt_got_offset;
2181
2182 /* Bit mask representing the type of GOT entry(s) if any required by
2183 this symbol. */
2184 unsigned int got_type;
2185
2186 /* A pointer to the most recently used stub hash entry against this
2187 symbol. */
cec5225b 2188 struct elf_aarch64_stub_hash_entry *stub_cache;
a06ea964
NC
2189
2190 /* Offset of the GOTPLT entry reserved for the TLS descriptor. The offset
2191 is from the end of the jump table and reserved entries within the PLTGOT.
2192
2193 The magic value (bfd_vma) -1 indicates that an offset has not
2194 be allocated. */
2195 bfd_vma tlsdesc_got_jump_table_offset;
2196};
2197
2198static unsigned int
cec5225b 2199elfNN_aarch64_symbol_got_type (struct elf_link_hash_entry *h,
a06ea964
NC
2200 bfd *abfd,
2201 unsigned long r_symndx)
2202{
2203 if (h)
cec5225b 2204 return elf_aarch64_hash_entry (h)->got_type;
a06ea964 2205
cec5225b 2206 if (! elf_aarch64_locals (abfd))
a06ea964
NC
2207 return GOT_UNKNOWN;
2208
cec5225b 2209 return elf_aarch64_locals (abfd)[r_symndx].got_type;
a06ea964
NC
2210}
2211
a06ea964 2212/* Get the AArch64 elf linker hash table from a link_info structure. */
cec5225b
YZ
2213#define elf_aarch64_hash_table(info) \
2214 ((struct elf_aarch64_link_hash_table *) ((info)->hash))
a06ea964
NC
2215
2216#define aarch64_stub_hash_lookup(table, string, create, copy) \
cec5225b 2217 ((struct elf_aarch64_stub_hash_entry *) \
a06ea964
NC
2218 bfd_hash_lookup ((table), (string), (create), (copy)))
2219
2220/* AArch64 ELF linker hash table. */
cec5225b 2221struct elf_aarch64_link_hash_table
a06ea964
NC
2222{
2223 /* The main hash table. */
2224 struct elf_link_hash_table root;
2225
2226 /* Nonzero to force PIC branch veneers. */
2227 int pic_veneer;
2228
68fcca92
JW
2229 /* Fix erratum 835769. */
2230 int fix_erratum_835769;
2231
4106101c
MS
2232 /* Fix erratum 843419. */
2233 int fix_erratum_843419;
2234
2235 /* Enable ADRP->ADR rewrite for erratum 843419 workaround. */
2236 int fix_erratum_843419_adr;
2237
a06ea964
NC
2238 /* The number of bytes in the initial entry in the PLT. */
2239 bfd_size_type plt_header_size;
2240
2241 /* The number of bytes in the subsequent PLT etries. */
2242 bfd_size_type plt_entry_size;
2243
2244 /* Short-cuts to get to dynamic linker sections. */
2245 asection *sdynbss;
2246 asection *srelbss;
2247
2248 /* Small local sym cache. */
2249 struct sym_cache sym_cache;
2250
2251 /* For convenience in allocate_dynrelocs. */
2252 bfd *obfd;
2253
2254 /* The amount of space used by the reserved portion of the sgotplt
2255 section, plus whatever space is used by the jump slots. */
2256 bfd_vma sgotplt_jump_table_size;
2257
2258 /* The stub hash table. */
2259 struct bfd_hash_table stub_hash_table;
2260
2261 /* Linker stub bfd. */
2262 bfd *stub_bfd;
2263
2264 /* Linker call-backs. */
2265 asection *(*add_stub_section) (const char *, asection *);
2266 void (*layout_sections_again) (void);
2267
2268 /* Array to keep track of which stub sections have been created, and
2269 information on stub grouping. */
2270 struct map_stub
2271 {
2272 /* This is the section to which stubs in the group will be
2273 attached. */
2274 asection *link_sec;
2275 /* The stub section. */
2276 asection *stub_sec;
2277 } *stub_group;
2278
cec5225b 2279 /* Assorted information used by elfNN_aarch64_size_stubs. */
a06ea964 2280 unsigned int bfd_count;
7292b3ac 2281 unsigned int top_index;
a06ea964
NC
2282 asection **input_list;
2283
2284 /* The offset into splt of the PLT entry for the TLS descriptor
2285 resolver. Special values are 0, if not necessary (or not found
2286 to be necessary yet), and -1 if needed but not determined
2287 yet. */
2288 bfd_vma tlsdesc_plt;
2289
2290 /* The GOT offset for the lazy trampoline. Communicated to the
2291 loader via DT_TLSDESC_GOT. The magic value (bfd_vma) -1
2292 indicates an offset is not allocated. */
2293 bfd_vma dt_tlsdesc_got;
1419bbe5
WN
2294
2295 /* Used by local STT_GNU_IFUNC symbols. */
2296 htab_t loc_hash_table;
2297 void * loc_hash_memory;
a06ea964
NC
2298};
2299
a06ea964
NC
2300/* Create an entry in an AArch64 ELF linker hash table. */
2301
2302static struct bfd_hash_entry *
cec5225b 2303elfNN_aarch64_link_hash_newfunc (struct bfd_hash_entry *entry,
a06ea964
NC
2304 struct bfd_hash_table *table,
2305 const char *string)
2306{
cec5225b
YZ
2307 struct elf_aarch64_link_hash_entry *ret =
2308 (struct elf_aarch64_link_hash_entry *) entry;
a06ea964
NC
2309
2310 /* Allocate the structure if it has not already been allocated by a
2311 subclass. */
2312 if (ret == NULL)
2313 ret = bfd_hash_allocate (table,
cec5225b 2314 sizeof (struct elf_aarch64_link_hash_entry));
a06ea964
NC
2315 if (ret == NULL)
2316 return (struct bfd_hash_entry *) ret;
2317
2318 /* Call the allocation method of the superclass. */
cec5225b 2319 ret = ((struct elf_aarch64_link_hash_entry *)
a06ea964
NC
2320 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
2321 table, string));
2322 if (ret != NULL)
2323 {
2324 ret->dyn_relocs = NULL;
a06ea964
NC
2325 ret->got_type = GOT_UNKNOWN;
2326 ret->plt_got_offset = (bfd_vma) - 1;
2327 ret->stub_cache = NULL;
2328 ret->tlsdesc_got_jump_table_offset = (bfd_vma) - 1;
2329 }
2330
2331 return (struct bfd_hash_entry *) ret;
2332}
2333
2334/* Initialize an entry in the stub hash table. */
2335
2336static struct bfd_hash_entry *
2337stub_hash_newfunc (struct bfd_hash_entry *entry,
2338 struct bfd_hash_table *table, const char *string)
2339{
2340 /* Allocate the structure if it has not already been allocated by a
2341 subclass. */
2342 if (entry == NULL)
2343 {
2344 entry = bfd_hash_allocate (table,
2345 sizeof (struct
cec5225b 2346 elf_aarch64_stub_hash_entry));
a06ea964
NC
2347 if (entry == NULL)
2348 return entry;
2349 }
2350
2351 /* Call the allocation method of the superclass. */
2352 entry = bfd_hash_newfunc (entry, table, string);
2353 if (entry != NULL)
2354 {
cec5225b 2355 struct elf_aarch64_stub_hash_entry *eh;
a06ea964
NC
2356
2357 /* Initialize the local fields. */
cec5225b 2358 eh = (struct elf_aarch64_stub_hash_entry *) entry;
4106101c 2359 eh->adrp_offset = 0;
a06ea964
NC
2360 eh->stub_sec = NULL;
2361 eh->stub_offset = 0;
2362 eh->target_value = 0;
2363 eh->target_section = NULL;
2364 eh->stub_type = aarch64_stub_none;
2365 eh->h = NULL;
2366 eh->id_sec = NULL;
2367 }
2368
2369 return entry;
2370}
2371
1419bbe5
WN
2372/* Compute a hash of a local hash entry. We use elf_link_hash_entry
2373 for local symbol so that we can handle local STT_GNU_IFUNC symbols
2374 as global symbol. We reuse indx and dynstr_index for local symbol
2375 hash since they aren't used by global symbols in this backend. */
2376
2377static hashval_t
2378elfNN_aarch64_local_htab_hash (const void *ptr)
2379{
2380 struct elf_link_hash_entry *h
2381 = (struct elf_link_hash_entry *) ptr;
2382 return ELF_LOCAL_SYMBOL_HASH (h->indx, h->dynstr_index);
2383}
2384
2385/* Compare local hash entries. */
2386
2387static int
2388elfNN_aarch64_local_htab_eq (const void *ptr1, const void *ptr2)
2389{
2390 struct elf_link_hash_entry *h1
2391 = (struct elf_link_hash_entry *) ptr1;
2392 struct elf_link_hash_entry *h2
2393 = (struct elf_link_hash_entry *) ptr2;
2394
2395 return h1->indx == h2->indx && h1->dynstr_index == h2->dynstr_index;
2396}
2397
2398/* Find and/or create a hash entry for local symbol. */
2399
2400static struct elf_link_hash_entry *
2401elfNN_aarch64_get_local_sym_hash (struct elf_aarch64_link_hash_table *htab,
2402 bfd *abfd, const Elf_Internal_Rela *rel,
2403 bfd_boolean create)
2404{
2405 struct elf_aarch64_link_hash_entry e, *ret;
2406 asection *sec = abfd->sections;
2407 hashval_t h = ELF_LOCAL_SYMBOL_HASH (sec->id,
2408 ELFNN_R_SYM (rel->r_info));
2409 void **slot;
2410
2411 e.root.indx = sec->id;
2412 e.root.dynstr_index = ELFNN_R_SYM (rel->r_info);
2413 slot = htab_find_slot_with_hash (htab->loc_hash_table, &e, h,
2414 create ? INSERT : NO_INSERT);
2415
2416 if (!slot)
2417 return NULL;
2418
2419 if (*slot)
2420 {
2421 ret = (struct elf_aarch64_link_hash_entry *) *slot;
2422 return &ret->root;
2423 }
2424
2425 ret = (struct elf_aarch64_link_hash_entry *)
2426 objalloc_alloc ((struct objalloc *) htab->loc_hash_memory,
2427 sizeof (struct elf_aarch64_link_hash_entry));
2428 if (ret)
2429 {
2430 memset (ret, 0, sizeof (*ret));
2431 ret->root.indx = sec->id;
2432 ret->root.dynstr_index = ELFNN_R_SYM (rel->r_info);
2433 ret->root.dynindx = -1;
2434 *slot = ret;
2435 }
2436 return &ret->root;
2437}
a06ea964
NC
2438
2439/* Copy the extra info we tack onto an elf_link_hash_entry. */
2440
2441static void
cec5225b 2442elfNN_aarch64_copy_indirect_symbol (struct bfd_link_info *info,
a06ea964
NC
2443 struct elf_link_hash_entry *dir,
2444 struct elf_link_hash_entry *ind)
2445{
cec5225b 2446 struct elf_aarch64_link_hash_entry *edir, *eind;
a06ea964 2447
cec5225b
YZ
2448 edir = (struct elf_aarch64_link_hash_entry *) dir;
2449 eind = (struct elf_aarch64_link_hash_entry *) ind;
a06ea964
NC
2450
2451 if (eind->dyn_relocs != NULL)
2452 {
2453 if (edir->dyn_relocs != NULL)
2454 {
2455 struct elf_dyn_relocs **pp;
2456 struct elf_dyn_relocs *p;
2457
2458 /* Add reloc counts against the indirect sym to the direct sym
2459 list. Merge any entries against the same section. */
2460 for (pp = &eind->dyn_relocs; (p = *pp) != NULL;)
2461 {
2462 struct elf_dyn_relocs *q;
2463
2464 for (q = edir->dyn_relocs; q != NULL; q = q->next)
2465 if (q->sec == p->sec)
2466 {
2467 q->pc_count += p->pc_count;
2468 q->count += p->count;
2469 *pp = p->next;
2470 break;
2471 }
2472 if (q == NULL)
2473 pp = &p->next;
2474 }
2475 *pp = edir->dyn_relocs;
2476 }
2477
2478 edir->dyn_relocs = eind->dyn_relocs;
2479 eind->dyn_relocs = NULL;
2480 }
2481
a06ea964
NC
2482 if (ind->root.type == bfd_link_hash_indirect)
2483 {
2484 /* Copy over PLT info. */
2485 if (dir->got.refcount <= 0)
2486 {
2487 edir->got_type = eind->got_type;
2488 eind->got_type = GOT_UNKNOWN;
2489 }
2490 }
2491
2492 _bfd_elf_link_hash_copy_indirect (info, dir, ind);
2493}
2494
68faa637
AM
2495/* Destroy an AArch64 elf linker hash table. */
2496
2497static void
d495ab0d 2498elfNN_aarch64_link_hash_table_free (bfd *obfd)
68faa637
AM
2499{
2500 struct elf_aarch64_link_hash_table *ret
d495ab0d 2501 = (struct elf_aarch64_link_hash_table *) obfd->link.hash;
68faa637
AM
2502
2503 if (ret->loc_hash_table)
2504 htab_delete (ret->loc_hash_table);
2505 if (ret->loc_hash_memory)
2506 objalloc_free ((struct objalloc *) ret->loc_hash_memory);
2507
2508 bfd_hash_table_free (&ret->stub_hash_table);
d495ab0d 2509 _bfd_elf_link_hash_table_free (obfd);
68faa637
AM
2510}
2511
a06ea964
NC
2512/* Create an AArch64 elf linker hash table. */
2513
2514static struct bfd_link_hash_table *
cec5225b 2515elfNN_aarch64_link_hash_table_create (bfd *abfd)
a06ea964 2516{
cec5225b
YZ
2517 struct elf_aarch64_link_hash_table *ret;
2518 bfd_size_type amt = sizeof (struct elf_aarch64_link_hash_table);
a06ea964 2519
7bf52ea2 2520 ret = bfd_zmalloc (amt);
a06ea964
NC
2521 if (ret == NULL)
2522 return NULL;
2523
2524 if (!_bfd_elf_link_hash_table_init
cec5225b
YZ
2525 (&ret->root, abfd, elfNN_aarch64_link_hash_newfunc,
2526 sizeof (struct elf_aarch64_link_hash_entry), AARCH64_ELF_DATA))
a06ea964
NC
2527 {
2528 free (ret);
2529 return NULL;
2530 }
2531
a06ea964
NC
2532 ret->plt_header_size = PLT_ENTRY_SIZE;
2533 ret->plt_entry_size = PLT_SMALL_ENTRY_SIZE;
a06ea964 2534 ret->obfd = abfd;
a06ea964
NC
2535 ret->dt_tlsdesc_got = (bfd_vma) - 1;
2536
2537 if (!bfd_hash_table_init (&ret->stub_hash_table, stub_hash_newfunc,
cec5225b 2538 sizeof (struct elf_aarch64_stub_hash_entry)))
a06ea964 2539 {
d495ab0d 2540 _bfd_elf_link_hash_table_free (abfd);
a06ea964
NC
2541 return NULL;
2542 }
2543
1419bbe5
WN
2544 ret->loc_hash_table = htab_try_create (1024,
2545 elfNN_aarch64_local_htab_hash,
2546 elfNN_aarch64_local_htab_eq,
2547 NULL);
2548 ret->loc_hash_memory = objalloc_create ();
2549 if (!ret->loc_hash_table || !ret->loc_hash_memory)
2550 {
d495ab0d 2551 elfNN_aarch64_link_hash_table_free (abfd);
1419bbe5
WN
2552 return NULL;
2553 }
d495ab0d 2554 ret->root.root.hash_table_free = elfNN_aarch64_link_hash_table_free;
1419bbe5 2555
a06ea964
NC
2556 return &ret->root.root;
2557}
2558
a06ea964
NC
2559static bfd_boolean
2560aarch64_relocate (unsigned int r_type, bfd *input_bfd, asection *input_section,
2561 bfd_vma offset, bfd_vma value)
2562{
2563 reloc_howto_type *howto;
2564 bfd_vma place;
2565
cec5225b 2566 howto = elfNN_aarch64_howto_from_type (r_type);
a06ea964
NC
2567 place = (input_section->output_section->vma + input_section->output_offset
2568 + offset);
caed7120
YZ
2569
2570 r_type = elfNN_aarch64_bfd_reloc_from_type (r_type);
2571 value = _bfd_aarch64_elf_resolve_relocation (r_type, place, value, 0, FALSE);
2572 return _bfd_aarch64_elf_put_addend (input_bfd,
2573 input_section->contents + offset, r_type,
2574 howto, value);
a06ea964
NC
2575}
2576
cec5225b 2577static enum elf_aarch64_stub_type
a06ea964
NC
2578aarch64_select_branch_stub (bfd_vma value, bfd_vma place)
2579{
2580 if (aarch64_valid_for_adrp_p (value, place))
2581 return aarch64_stub_adrp_branch;
2582 return aarch64_stub_long_branch;
2583}
2584
2585/* Determine the type of stub needed, if any, for a call. */
2586
cec5225b 2587static enum elf_aarch64_stub_type
a06ea964
NC
2588aarch64_type_of_stub (struct bfd_link_info *info,
2589 asection *input_sec,
2590 const Elf_Internal_Rela *rel,
f678ded7 2591 asection *sym_sec,
a06ea964 2592 unsigned char st_type,
cec5225b 2593 struct elf_aarch64_link_hash_entry *hash,
a06ea964
NC
2594 bfd_vma destination)
2595{
2596 bfd_vma location;
2597 bfd_signed_vma branch_offset;
2598 unsigned int r_type;
cec5225b
YZ
2599 struct elf_aarch64_link_hash_table *globals;
2600 enum elf_aarch64_stub_type stub_type = aarch64_stub_none;
a06ea964
NC
2601 bfd_boolean via_plt_p;
2602
f678ded7
JW
2603 if (st_type != STT_FUNC
2604 && (sym_sec != bfd_abs_section_ptr))
a06ea964
NC
2605 return stub_type;
2606
cec5225b 2607 globals = elf_aarch64_hash_table (info);
a06ea964
NC
2608 via_plt_p = (globals->root.splt != NULL && hash != NULL
2609 && hash->root.plt.offset != (bfd_vma) - 1);
07f9ddfe 2610 /* Make sure call to plt stub can fit into the branch range. */
a06ea964 2611 if (via_plt_p)
07f9ddfe
JW
2612 destination = (globals->root.splt->output_section->vma
2613 + globals->root.splt->output_offset
2614 + hash->root.plt.offset);
a06ea964
NC
2615
2616 /* Determine where the call point is. */
2617 location = (input_sec->output_offset
2618 + input_sec->output_section->vma + rel->r_offset);
2619
2620 branch_offset = (bfd_signed_vma) (destination - location);
2621
cec5225b 2622 r_type = ELFNN_R_TYPE (rel->r_info);
a06ea964
NC
2623
2624 /* We don't want to redirect any old unconditional jump in this way,
2625 only one which is being used for a sibcall, where it is
2626 acceptable for the IP0 and IP1 registers to be clobbered. */
a6bb11b2 2627 if ((r_type == AARCH64_R (CALL26) || r_type == AARCH64_R (JUMP26))
a06ea964
NC
2628 && (branch_offset > AARCH64_MAX_FWD_BRANCH_OFFSET
2629 || branch_offset < AARCH64_MAX_BWD_BRANCH_OFFSET))
2630 {
2631 stub_type = aarch64_stub_long_branch;
2632 }
2633
2634 return stub_type;
2635}
2636
2637/* Build a name for an entry in the stub hash table. */
2638
2639static char *
cec5225b 2640elfNN_aarch64_stub_name (const asection *input_section,
a06ea964 2641 const asection *sym_sec,
cec5225b 2642 const struct elf_aarch64_link_hash_entry *hash,
a06ea964
NC
2643 const Elf_Internal_Rela *rel)
2644{
2645 char *stub_name;
2646 bfd_size_type len;
2647
2648 if (hash)
2649 {
2650 len = 8 + 1 + strlen (hash->root.root.root.string) + 1 + 16 + 1;
2651 stub_name = bfd_malloc (len);
2652 if (stub_name != NULL)
2653 snprintf (stub_name, len, "%08x_%s+%" BFD_VMA_FMT "x",
2654 (unsigned int) input_section->id,
2655 hash->root.root.root.string,
2656 rel->r_addend);
2657 }
2658 else
2659 {
2660 len = 8 + 1 + 8 + 1 + 8 + 1 + 16 + 1;
2661 stub_name = bfd_malloc (len);
2662 if (stub_name != NULL)
2663 snprintf (stub_name, len, "%08x_%x:%x+%" BFD_VMA_FMT "x",
2664 (unsigned int) input_section->id,
2665 (unsigned int) sym_sec->id,
cec5225b 2666 (unsigned int) ELFNN_R_SYM (rel->r_info),
a06ea964
NC
2667 rel->r_addend);
2668 }
2669
2670 return stub_name;
2671}
2672
2673/* Look up an entry in the stub hash. Stub entries are cached because
2674 creating the stub name takes a bit of time. */
2675
cec5225b
YZ
2676static struct elf_aarch64_stub_hash_entry *
2677elfNN_aarch64_get_stub_entry (const asection *input_section,
a06ea964
NC
2678 const asection *sym_sec,
2679 struct elf_link_hash_entry *hash,
2680 const Elf_Internal_Rela *rel,
cec5225b 2681 struct elf_aarch64_link_hash_table *htab)
a06ea964 2682{
cec5225b
YZ
2683 struct elf_aarch64_stub_hash_entry *stub_entry;
2684 struct elf_aarch64_link_hash_entry *h =
2685 (struct elf_aarch64_link_hash_entry *) hash;
a06ea964
NC
2686 const asection *id_sec;
2687
2688 if ((input_section->flags & SEC_CODE) == 0)
2689 return NULL;
2690
2691 /* If this input section is part of a group of sections sharing one
2692 stub section, then use the id of the first section in the group.
2693 Stub names need to include a section id, as there may well be
2694 more than one stub used to reach say, printf, and we need to
2695 distinguish between them. */
2696 id_sec = htab->stub_group[input_section->id].link_sec;
2697
2698 if (h != NULL && h->stub_cache != NULL
2699 && h->stub_cache->h == h && h->stub_cache->id_sec == id_sec)
2700 {
2701 stub_entry = h->stub_cache;
2702 }
2703 else
2704 {
2705 char *stub_name;
2706
cec5225b 2707 stub_name = elfNN_aarch64_stub_name (id_sec, sym_sec, h, rel);
a06ea964
NC
2708 if (stub_name == NULL)
2709 return NULL;
2710
2711 stub_entry = aarch64_stub_hash_lookup (&htab->stub_hash_table,
2712 stub_name, FALSE, FALSE);
2713 if (h != NULL)
2714 h->stub_cache = stub_entry;
2715
2716 free (stub_name);
2717 }
2718
2719 return stub_entry;
2720}
2721
a06ea964 2722
66585675
MS
2723/* Create a stub section. */
2724
2725static asection *
2726_bfd_aarch64_create_stub_section (asection *section,
2727 struct elf_aarch64_link_hash_table *htab)
2728{
2729 size_t namelen;
2730 bfd_size_type len;
2731 char *s_name;
2732
2733 namelen = strlen (section->name);
2734 len = namelen + sizeof (STUB_SUFFIX);
2735 s_name = bfd_alloc (htab->stub_bfd, len);
2736 if (s_name == NULL)
2737 return NULL;
2738
2739 memcpy (s_name, section->name, namelen);
2740 memcpy (s_name + namelen, STUB_SUFFIX, sizeof (STUB_SUFFIX));
2741 return (*htab->add_stub_section) (s_name, section);
2742}
2743
2744
fc6d53be
MS
2745/* Find or create a stub section for a link section.
2746
2747 Fix or create the stub section used to collect stubs attached to
2748 the specified link section. */
2749
2750static asection *
2751_bfd_aarch64_get_stub_for_link_section (asection *link_section,
2752 struct elf_aarch64_link_hash_table *htab)
2753{
2754 if (htab->stub_group[link_section->id].stub_sec == NULL)
2755 htab->stub_group[link_section->id].stub_sec
2756 = _bfd_aarch64_create_stub_section (link_section, htab);
2757 return htab->stub_group[link_section->id].stub_sec;
2758}
2759
2760
ef857521
MS
2761/* Find or create a stub section in the stub group for an input
2762 section. */
2763
2764static asection *
2765_bfd_aarch64_create_or_find_stub_sec (asection *section,
2766 struct elf_aarch64_link_hash_table *htab)
a06ea964 2767{
fc6d53be
MS
2768 asection *link_sec = htab->stub_group[section->id].link_sec;
2769 return _bfd_aarch64_get_stub_for_link_section (link_sec, htab);
ef857521
MS
2770}
2771
2772
2773/* Add a new stub entry in the stub group associated with an input
2774 section to the stub hash. Not all fields of the new stub entry are
2775 initialised. */
2776
2777static struct elf_aarch64_stub_hash_entry *
2778_bfd_aarch64_add_stub_entry_in_group (const char *stub_name,
2779 asection *section,
2780 struct elf_aarch64_link_hash_table *htab)
2781{
2782 asection *link_sec;
2783 asection *stub_sec;
2784 struct elf_aarch64_stub_hash_entry *stub_entry;
2785
2786 link_sec = htab->stub_group[section->id].link_sec;
2787 stub_sec = _bfd_aarch64_create_or_find_stub_sec (section, htab);
2788
a06ea964
NC
2789 /* Enter this entry into the linker stub hash table. */
2790 stub_entry = aarch64_stub_hash_lookup (&htab->stub_hash_table, stub_name,
2791 TRUE, FALSE);
2792 if (stub_entry == NULL)
2793 {
2794 (*_bfd_error_handler) (_("%s: cannot create stub entry %s"),
2795 section->owner, stub_name);
2796 return NULL;
2797 }
2798
2799 stub_entry->stub_sec = stub_sec;
2800 stub_entry->stub_offset = 0;
2801 stub_entry->id_sec = link_sec;
2802
2803 return stub_entry;
2804}
2805
4106101c
MS
2806/* Add a new stub entry in the final stub section to the stub hash.
2807 Not all fields of the new stub entry are initialised. */
2808
2809static struct elf_aarch64_stub_hash_entry *
2810_bfd_aarch64_add_stub_entry_after (const char *stub_name,
2811 asection *link_section,
2812 struct elf_aarch64_link_hash_table *htab)
2813{
2814 asection *stub_sec;
2815 struct elf_aarch64_stub_hash_entry *stub_entry;
2816
2817 stub_sec = _bfd_aarch64_get_stub_for_link_section (link_section, htab);
2818 stub_entry = aarch64_stub_hash_lookup (&htab->stub_hash_table, stub_name,
2819 TRUE, FALSE);
2820 if (stub_entry == NULL)
2821 {
2822 (*_bfd_error_handler) (_("cannot create stub entry %s"), stub_name);
2823 return NULL;
2824 }
2825
2826 stub_entry->stub_sec = stub_sec;
2827 stub_entry->stub_offset = 0;
2828 stub_entry->id_sec = link_section;
2829
2830 return stub_entry;
2831}
2832
2833
a06ea964
NC
2834static bfd_boolean
2835aarch64_build_one_stub (struct bfd_hash_entry *gen_entry,
2836 void *in_arg ATTRIBUTE_UNUSED)
2837{
cec5225b 2838 struct elf_aarch64_stub_hash_entry *stub_entry;
a06ea964
NC
2839 asection *stub_sec;
2840 bfd *stub_bfd;
2841 bfd_byte *loc;
2842 bfd_vma sym_value;
68fcca92
JW
2843 bfd_vma veneered_insn_loc;
2844 bfd_vma veneer_entry_loc;
2845 bfd_signed_vma branch_offset = 0;
a06ea964
NC
2846 unsigned int template_size;
2847 const uint32_t *template;
2848 unsigned int i;
2849
2850 /* Massage our args to the form they really have. */
cec5225b 2851 stub_entry = (struct elf_aarch64_stub_hash_entry *) gen_entry;
a06ea964
NC
2852
2853 stub_sec = stub_entry->stub_sec;
2854
2855 /* Make a note of the offset within the stubs for this entry. */
2856 stub_entry->stub_offset = stub_sec->size;
2857 loc = stub_sec->contents + stub_entry->stub_offset;
2858
2859 stub_bfd = stub_sec->owner;
2860
2861 /* This is the address of the stub destination. */
2862 sym_value = (stub_entry->target_value
2863 + stub_entry->target_section->output_offset
2864 + stub_entry->target_section->output_section->vma);
2865
2866 if (stub_entry->stub_type == aarch64_stub_long_branch)
2867 {
2868 bfd_vma place = (stub_entry->stub_offset + stub_sec->output_section->vma
2869 + stub_sec->output_offset);
2870
2871 /* See if we can relax the stub. */
2872 if (aarch64_valid_for_adrp_p (sym_value, place))
2873 stub_entry->stub_type = aarch64_select_branch_stub (sym_value, place);
2874 }
2875
2876 switch (stub_entry->stub_type)
2877 {
2878 case aarch64_stub_adrp_branch:
2879 template = aarch64_adrp_branch_stub;
2880 template_size = sizeof (aarch64_adrp_branch_stub);
2881 break;
2882 case aarch64_stub_long_branch:
2883 template = aarch64_long_branch_stub;
2884 template_size = sizeof (aarch64_long_branch_stub);
2885 break;
68fcca92
JW
2886 case aarch64_stub_erratum_835769_veneer:
2887 template = aarch64_erratum_835769_stub;
2888 template_size = sizeof (aarch64_erratum_835769_stub);
2889 break;
4106101c
MS
2890 case aarch64_stub_erratum_843419_veneer:
2891 template = aarch64_erratum_843419_stub;
2892 template_size = sizeof (aarch64_erratum_843419_stub);
2893 break;
a06ea964 2894 default:
8e2fe09f 2895 abort ();
a06ea964
NC
2896 }
2897
2898 for (i = 0; i < (template_size / sizeof template[0]); i++)
2899 {
2900 bfd_putl32 (template[i], loc);
2901 loc += 4;
2902 }
2903
2904 template_size = (template_size + 7) & ~7;
2905 stub_sec->size += template_size;
2906
2907 switch (stub_entry->stub_type)
2908 {
2909 case aarch64_stub_adrp_branch:
a6bb11b2 2910 if (aarch64_relocate (AARCH64_R (ADR_PREL_PG_HI21), stub_bfd, stub_sec,
a06ea964
NC
2911 stub_entry->stub_offset, sym_value))
2912 /* The stub would not have been relaxed if the offset was out
2913 of range. */
2914 BFD_FAIL ();
2915
93ca8569
TB
2916 if (aarch64_relocate (AARCH64_R (ADD_ABS_LO12_NC), stub_bfd, stub_sec,
2917 stub_entry->stub_offset + 4, sym_value))
2918 BFD_FAIL ();
a06ea964
NC
2919 break;
2920
2921 case aarch64_stub_long_branch:
2922 /* We want the value relative to the address 12 bytes back from the
2923 value itself. */
93ca8569
TB
2924 if (aarch64_relocate (AARCH64_R (PRELNN), stub_bfd, stub_sec,
2925 stub_entry->stub_offset + 16, sym_value + 12))
2926 BFD_FAIL ();
a06ea964 2927 break;
68fcca92
JW
2928
2929 case aarch64_stub_erratum_835769_veneer:
2930 veneered_insn_loc = stub_entry->target_section->output_section->vma
2931 + stub_entry->target_section->output_offset
2932 + stub_entry->target_value;
2933 veneer_entry_loc = stub_entry->stub_sec->output_section->vma
2934 + stub_entry->stub_sec->output_offset
2935 + stub_entry->stub_offset;
2936 branch_offset = veneered_insn_loc - veneer_entry_loc;
2937 branch_offset >>= 2;
2938 branch_offset &= 0x3ffffff;
2939 bfd_putl32 (stub_entry->veneered_insn,
2940 stub_sec->contents + stub_entry->stub_offset);
2941 bfd_putl32 (template[1] | branch_offset,
2942 stub_sec->contents + stub_entry->stub_offset + 4);
2943 break;
2944
4106101c
MS
2945 case aarch64_stub_erratum_843419_veneer:
2946 if (aarch64_relocate (AARCH64_R (JUMP26), stub_bfd, stub_sec,
2947 stub_entry->stub_offset + 4, sym_value + 4))
2948 BFD_FAIL ();
2949 break;
2950
a06ea964 2951 default:
8e2fe09f 2952 abort ();
a06ea964
NC
2953 }
2954
2955 return TRUE;
2956}
2957
2958/* As above, but don't actually build the stub. Just bump offset so
2959 we know stub section sizes. */
2960
2961static bfd_boolean
2962aarch64_size_one_stub (struct bfd_hash_entry *gen_entry,
2963 void *in_arg ATTRIBUTE_UNUSED)
2964{
cec5225b 2965 struct elf_aarch64_stub_hash_entry *stub_entry;
a06ea964
NC
2966 int size;
2967
2968 /* Massage our args to the form they really have. */
cec5225b 2969 stub_entry = (struct elf_aarch64_stub_hash_entry *) gen_entry;
a06ea964
NC
2970
2971 switch (stub_entry->stub_type)
2972 {
2973 case aarch64_stub_adrp_branch:
2974 size = sizeof (aarch64_adrp_branch_stub);
2975 break;
2976 case aarch64_stub_long_branch:
2977 size = sizeof (aarch64_long_branch_stub);
2978 break;
68fcca92
JW
2979 case aarch64_stub_erratum_835769_veneer:
2980 size = sizeof (aarch64_erratum_835769_stub);
2981 break;
4106101c
MS
2982 case aarch64_stub_erratum_843419_veneer:
2983 size = sizeof (aarch64_erratum_843419_stub);
2984 break;
a06ea964 2985 default:
8e2fe09f 2986 abort ();
a06ea964
NC
2987 }
2988
2989 size = (size + 7) & ~7;
2990 stub_entry->stub_sec->size += size;
2991 return TRUE;
2992}
2993
2994/* External entry points for sizing and building linker stubs. */
2995
2996/* Set up various things so that we can make a list of input sections
2997 for each output section included in the link. Returns -1 on error,
2998 0 when no stubs will be needed, and 1 on success. */
2999
3000int
cec5225b 3001elfNN_aarch64_setup_section_lists (bfd *output_bfd,
a06ea964
NC
3002 struct bfd_link_info *info)
3003{
3004 bfd *input_bfd;
3005 unsigned int bfd_count;
7292b3ac 3006 unsigned int top_id, top_index;
a06ea964
NC
3007 asection *section;
3008 asection **input_list, **list;
3009 bfd_size_type amt;
cec5225b
YZ
3010 struct elf_aarch64_link_hash_table *htab =
3011 elf_aarch64_hash_table (info);
a06ea964
NC
3012
3013 if (!is_elf_hash_table (htab))
3014 return 0;
3015
3016 /* Count the number of input BFDs and find the top input section id. */
3017 for (input_bfd = info->input_bfds, bfd_count = 0, top_id = 0;
c72f2fb2 3018 input_bfd != NULL; input_bfd = input_bfd->link.next)
a06ea964
NC
3019 {
3020 bfd_count += 1;
3021 for (section = input_bfd->sections;
3022 section != NULL; section = section->next)
3023 {
3024 if (top_id < section->id)
3025 top_id = section->id;
3026 }
3027 }
3028 htab->bfd_count = bfd_count;
3029
3030 amt = sizeof (struct map_stub) * (top_id + 1);
3031 htab->stub_group = bfd_zmalloc (amt);
3032 if (htab->stub_group == NULL)
3033 return -1;
3034
3035 /* We can't use output_bfd->section_count here to find the top output
3036 section index as some sections may have been removed, and
3037 _bfd_strip_section_from_output doesn't renumber the indices. */
3038 for (section = output_bfd->sections, top_index = 0;
3039 section != NULL; section = section->next)
3040 {
3041 if (top_index < section->index)
3042 top_index = section->index;
3043 }
3044
3045 htab->top_index = top_index;
3046 amt = sizeof (asection *) * (top_index + 1);
3047 input_list = bfd_malloc (amt);
3048 htab->input_list = input_list;
3049 if (input_list == NULL)
3050 return -1;
3051
3052 /* For sections we aren't interested in, mark their entries with a
3053 value we can check later. */
3054 list = input_list + top_index;
3055 do
3056 *list = bfd_abs_section_ptr;
3057 while (list-- != input_list);
3058
3059 for (section = output_bfd->sections;
3060 section != NULL; section = section->next)
3061 {
3062 if ((section->flags & SEC_CODE) != 0)
3063 input_list[section->index] = NULL;
3064 }
3065
3066 return 1;
3067}
3068
cec5225b 3069/* Used by elfNN_aarch64_next_input_section and group_sections. */
a06ea964
NC
3070#define PREV_SEC(sec) (htab->stub_group[(sec)->id].link_sec)
3071
3072/* The linker repeatedly calls this function for each input section,
3073 in the order that input sections are linked into output sections.
3074 Build lists of input sections to determine groupings between which
3075 we may insert linker stubs. */
3076
3077void
cec5225b 3078elfNN_aarch64_next_input_section (struct bfd_link_info *info, asection *isec)
a06ea964 3079{
cec5225b
YZ
3080 struct elf_aarch64_link_hash_table *htab =
3081 elf_aarch64_hash_table (info);
a06ea964
NC
3082
3083 if (isec->output_section->index <= htab->top_index)
3084 {
3085 asection **list = htab->input_list + isec->output_section->index;
3086
3087 if (*list != bfd_abs_section_ptr)
3088 {
3089 /* Steal the link_sec pointer for our list. */
3090 /* This happens to make the list in reverse order,
3091 which is what we want. */
3092 PREV_SEC (isec) = *list;
3093 *list = isec;
3094 }
3095 }
3096}
3097
3098/* See whether we can group stub sections together. Grouping stub
3099 sections may result in fewer stubs. More importantly, we need to
3100 put all .init* and .fini* stubs at the beginning of the .init or
3101 .fini output sections respectively, because glibc splits the
3102 _init and _fini functions into multiple parts. Putting a stub in
3103 the middle of a function is not a good idea. */
3104
3105static void
cec5225b 3106group_sections (struct elf_aarch64_link_hash_table *htab,
a06ea964
NC
3107 bfd_size_type stub_group_size,
3108 bfd_boolean stubs_always_before_branch)
3109{
3110 asection **list = htab->input_list + htab->top_index;
3111
3112 do
3113 {
3114 asection *tail = *list;
3115
3116 if (tail == bfd_abs_section_ptr)
3117 continue;
3118
3119 while (tail != NULL)
3120 {
3121 asection *curr;
3122 asection *prev;
3123 bfd_size_type total;
3124
3125 curr = tail;
3126 total = tail->size;
3127 while ((prev = PREV_SEC (curr)) != NULL
3128 && ((total += curr->output_offset - prev->output_offset)
3129 < stub_group_size))
3130 curr = prev;
3131
3132 /* OK, the size from the start of CURR to the end is less
3133 than stub_group_size and thus can be handled by one stub
3134 section. (Or the tail section is itself larger than
3135 stub_group_size, in which case we may be toast.)
3136 We should really be keeping track of the total size of
3137 stubs added here, as stubs contribute to the final output
3138 section size. */
3139 do
3140 {
3141 prev = PREV_SEC (tail);
3142 /* Set up this stub group. */
3143 htab->stub_group[tail->id].link_sec = curr;
3144 }
3145 while (tail != curr && (tail = prev) != NULL);
3146
3147 /* But wait, there's more! Input sections up to stub_group_size
3148 bytes before the stub section can be handled by it too. */
3149 if (!stubs_always_before_branch)
3150 {
3151 total = 0;
3152 while (prev != NULL
3153 && ((total += tail->output_offset - prev->output_offset)
3154 < stub_group_size))
3155 {
3156 tail = prev;
3157 prev = PREV_SEC (tail);
3158 htab->stub_group[tail->id].link_sec = curr;
3159 }
3160 }
3161 tail = prev;
3162 }
3163 }
3164 while (list-- != htab->input_list);
3165
3166 free (htab->input_list);
3167}
3168
3169#undef PREV_SEC
3170
68fcca92
JW
3171#define AARCH64_BITS(x, pos, n) (((x) >> (pos)) & ((1 << (n)) - 1))
3172
3173#define AARCH64_RT(insn) AARCH64_BITS (insn, 0, 5)
3174#define AARCH64_RT2(insn) AARCH64_BITS (insn, 10, 5)
3175#define AARCH64_RA(insn) AARCH64_BITS (insn, 10, 5)
3176#define AARCH64_RD(insn) AARCH64_BITS (insn, 0, 5)
3177#define AARCH64_RN(insn) AARCH64_BITS (insn, 5, 5)
3178#define AARCH64_RM(insn) AARCH64_BITS (insn, 16, 5)
3179
3180#define AARCH64_MAC(insn) (((insn) & 0xff000000) == 0x9b000000)
3181#define AARCH64_BIT(insn, n) AARCH64_BITS (insn, n, 1)
3182#define AARCH64_OP31(insn) AARCH64_BITS (insn, 21, 3)
3183#define AARCH64_ZR 0x1f
3184
3185/* All ld/st ops. See C4-182 of the ARM ARM. The encoding space for
3186 LD_PCREL, LDST_RO, LDST_UI and LDST_UIMM cover prefetch ops. */
3187
3188#define AARCH64_LD(insn) (AARCH64_BIT (insn, 22) == 1)
3189#define AARCH64_LDST(insn) (((insn) & 0x0a000000) == 0x08000000)
3190#define AARCH64_LDST_EX(insn) (((insn) & 0x3f000000) == 0x08000000)
3191#define AARCH64_LDST_PCREL(insn) (((insn) & 0x3b000000) == 0x18000000)
3192#define AARCH64_LDST_NAP(insn) (((insn) & 0x3b800000) == 0x28000000)
3193#define AARCH64_LDSTP_PI(insn) (((insn) & 0x3b800000) == 0x28800000)
3194#define AARCH64_LDSTP_O(insn) (((insn) & 0x3b800000) == 0x29000000)
3195#define AARCH64_LDSTP_PRE(insn) (((insn) & 0x3b800000) == 0x29800000)
3196#define AARCH64_LDST_UI(insn) (((insn) & 0x3b200c00) == 0x38000000)
3197#define AARCH64_LDST_PIIMM(insn) (((insn) & 0x3b200c00) == 0x38000400)
3198#define AARCH64_LDST_U(insn) (((insn) & 0x3b200c00) == 0x38000800)
3199#define AARCH64_LDST_PREIMM(insn) (((insn) & 0x3b200c00) == 0x38000c00)
3200#define AARCH64_LDST_RO(insn) (((insn) & 0x3b200c00) == 0x38200800)
3201#define AARCH64_LDST_UIMM(insn) (((insn) & 0x3b000000) == 0x39000000)
3202#define AARCH64_LDST_SIMD_M(insn) (((insn) & 0xbfbf0000) == 0x0c000000)
3203#define AARCH64_LDST_SIMD_M_PI(insn) (((insn) & 0xbfa00000) == 0x0c800000)
3204#define AARCH64_LDST_SIMD_S(insn) (((insn) & 0xbf9f0000) == 0x0d000000)
3205#define AARCH64_LDST_SIMD_S_PI(insn) (((insn) & 0xbf800000) == 0x0d800000)
3206
3d14faea
MS
3207/* Classify an INSN if it is indeed a load/store.
3208
3209 Return TRUE if INSN is a LD/ST instruction otherwise return FALSE.
3210
3211 For scalar LD/ST instructions PAIR is FALSE, RT is returned and RT2
3212 is set equal to RT.
3213
3214 For LD/ST pair instructions PAIR is TRUE, RT and RT2 are returned.
3215
3216 */
68fcca92
JW
3217
3218static bfd_boolean
3d14faea 3219aarch64_mem_op_p (uint32_t insn, unsigned int *rt, unsigned int *rt2,
68fcca92
JW
3220 bfd_boolean *pair, bfd_boolean *load)
3221{
3222 uint32_t opcode;
3223 unsigned int r;
3224 uint32_t opc = 0;
3225 uint32_t v = 0;
3226 uint32_t opc_v = 0;
3227
3228 /* Bail out quickly if INSN doesn't fall into the the load-store
3229 encoding space. */
3230 if (!AARCH64_LDST (insn))
3231 return FALSE;
3232
3233 *pair = FALSE;
3234 *load = FALSE;
3235 if (AARCH64_LDST_EX (insn))
3236 {
3237 *rt = AARCH64_RT (insn);
3d14faea 3238 *rt2 = *rt;
68fcca92
JW
3239 if (AARCH64_BIT (insn, 21) == 1)
3240 {
3241 *pair = TRUE;
3d14faea 3242 *rt2 = AARCH64_RT2 (insn);
68fcca92
JW
3243 }
3244 *load = AARCH64_LD (insn);
3245 return TRUE;
3246 }
3247 else if (AARCH64_LDST_NAP (insn)
3248 || AARCH64_LDSTP_PI (insn)
3249 || AARCH64_LDSTP_O (insn)
3250 || AARCH64_LDSTP_PRE (insn))
3251 {
3252 *pair = TRUE;
3253 *rt = AARCH64_RT (insn);
3d14faea 3254 *rt2 = AARCH64_RT2 (insn);
68fcca92
JW
3255 *load = AARCH64_LD (insn);
3256 return TRUE;
3257 }
3258 else if (AARCH64_LDST_PCREL (insn)
3259 || AARCH64_LDST_UI (insn)
3260 || AARCH64_LDST_PIIMM (insn)
3261 || AARCH64_LDST_U (insn)
3262 || AARCH64_LDST_PREIMM (insn)
3263 || AARCH64_LDST_RO (insn)
3264 || AARCH64_LDST_UIMM (insn))
3265 {
3266 *rt = AARCH64_RT (insn);
3d14faea 3267 *rt2 = *rt;
68fcca92
JW
3268 if (AARCH64_LDST_PCREL (insn))
3269 *load = TRUE;
3270 opc = AARCH64_BITS (insn, 22, 2);
3271 v = AARCH64_BIT (insn, 26);
3272 opc_v = opc | (v << 2);
3273 *load = (opc_v == 1 || opc_v == 2 || opc_v == 3
3274 || opc_v == 5 || opc_v == 7);
3275 return TRUE;
3276 }
3277 else if (AARCH64_LDST_SIMD_M (insn)
3278 || AARCH64_LDST_SIMD_M_PI (insn))
3279 {
3280 *rt = AARCH64_RT (insn);
3281 *load = AARCH64_BIT (insn, 22);
3282 opcode = (insn >> 12) & 0xf;
3283 switch (opcode)
3284 {
3285 case 0:
3286 case 2:
3d14faea 3287 *rt2 = *rt + 3;
68fcca92
JW
3288 break;
3289
3290 case 4:
3291 case 6:
3d14faea 3292 *rt2 = *rt + 2;
68fcca92
JW
3293 break;
3294
3295 case 7:
3d14faea 3296 *rt2 = *rt;
68fcca92
JW
3297 break;
3298
3299 case 8:
3300 case 10:
3d14faea 3301 *rt2 = *rt + 1;
68fcca92
JW
3302 break;
3303
3304 default:
3305 return FALSE;
3306 }
3307 return TRUE;
3308 }
3309 else if (AARCH64_LDST_SIMD_S (insn)
3310 || AARCH64_LDST_SIMD_S_PI (insn))
3311 {
3312 *rt = AARCH64_RT (insn);
3313 r = (insn >> 21) & 1;
3314 *load = AARCH64_BIT (insn, 22);
3315 opcode = (insn >> 13) & 0x7;
3316 switch (opcode)
3317 {
3318 case 0:
3319 case 2:
3320 case 4:
3d14faea 3321 *rt2 = *rt + r;
68fcca92
JW
3322 break;
3323
3324 case 1:
3325 case 3:
3326 case 5:
3d14faea 3327 *rt2 = *rt + (r == 0 ? 2 : 3);
68fcca92
JW
3328 break;
3329
3330 case 6:
3d14faea 3331 *rt2 = *rt + r;
68fcca92
JW
3332 break;
3333
3334 case 7:
3d14faea 3335 *rt2 = *rt + (r == 0 ? 2 : 3);
68fcca92
JW
3336 break;
3337
3338 default:
3339 return FALSE;
3340 }
3341 return TRUE;
3342 }
3343
3344 return FALSE;
3345}
3346
3347/* Return TRUE if INSN is multiply-accumulate. */
3348
3349static bfd_boolean
3350aarch64_mlxl_p (uint32_t insn)
3351{
3352 uint32_t op31 = AARCH64_OP31 (insn);
3353
3354 if (AARCH64_MAC (insn)
3355 && (op31 == 0 || op31 == 1 || op31 == 5)
3356 /* Exclude MUL instructions which are encoded as a multiple accumulate
3357 with RA = XZR. */
3358 && AARCH64_RA (insn) != AARCH64_ZR)
3359 return TRUE;
3360
3361 return FALSE;
3362}
3363
3364/* Some early revisions of the Cortex-A53 have an erratum (835769) whereby
3365 it is possible for a 64-bit multiply-accumulate instruction to generate an
3366 incorrect result. The details are quite complex and hard to
3367 determine statically, since branches in the code may exist in some
3368 circumstances, but all cases end with a memory (load, store, or
3369 prefetch) instruction followed immediately by the multiply-accumulate
3370 operation. We employ a linker patching technique, by moving the potentially
3371 affected multiply-accumulate instruction into a patch region and replacing
3372 the original instruction with a branch to the patch. This function checks
3373 if INSN_1 is the memory operation followed by a multiply-accumulate
3374 operation (INSN_2). Return TRUE if an erratum sequence is found, FALSE
3375 if INSN_1 and INSN_2 are safe. */
3376
3377static bfd_boolean
3378aarch64_erratum_sequence (uint32_t insn_1, uint32_t insn_2)
3379{
3380 uint32_t rt;
3d14faea 3381 uint32_t rt2;
68fcca92
JW
3382 uint32_t rn;
3383 uint32_t rm;
3384 uint32_t ra;
3385 bfd_boolean pair;
3386 bfd_boolean load;
3387
3388 if (aarch64_mlxl_p (insn_2)
3d14faea 3389 && aarch64_mem_op_p (insn_1, &rt, &rt2, &pair, &load))
68fcca92
JW
3390 {
3391 /* Any SIMD memory op is independent of the subsequent MLA
3392 by definition of the erratum. */
3393 if (AARCH64_BIT (insn_1, 26))
3394 return TRUE;
3395
3396 /* If not SIMD, check for integer memory ops and MLA relationship. */
3397 rn = AARCH64_RN (insn_2);
3398 ra = AARCH64_RA (insn_2);
3399 rm = AARCH64_RM (insn_2);
3400
3401 /* If this is a load and there's a true(RAW) dependency, we are safe
3402 and this is not an erratum sequence. */
3403 if (load &&
3404 (rt == rn || rt == rm || rt == ra
3d14faea 3405 || (pair && (rt2 == rn || rt2 == rm || rt2 == ra))))
68fcca92
JW
3406 return FALSE;
3407
3408 /* We conservatively put out stubs for all other cases (including
3409 writebacks). */
3410 return TRUE;
3411 }
3412
3413 return FALSE;
3414}
3415
520c7b56
JW
3416/* Used to order a list of mapping symbols by address. */
3417
3418static int
3419elf_aarch64_compare_mapping (const void *a, const void *b)
3420{
3421 const elf_aarch64_section_map *amap = (const elf_aarch64_section_map *) a;
3422 const elf_aarch64_section_map *bmap = (const elf_aarch64_section_map *) b;
3423
3424 if (amap->vma > bmap->vma)
3425 return 1;
3426 else if (amap->vma < bmap->vma)
3427 return -1;
3428 else if (amap->type > bmap->type)
3429 /* Ensure results do not depend on the host qsort for objects with
3430 multiple mapping symbols at the same address by sorting on type
3431 after vma. */
3432 return 1;
3433 else if (amap->type < bmap->type)
3434 return -1;
3435 else
3436 return 0;
3437}
3438
2144188d 3439
35fee8b7
MS
3440static char *
3441_bfd_aarch64_erratum_835769_stub_name (unsigned num_fixes)
3442{
3443 char *stub_name = (char *) bfd_malloc
3444 (strlen ("__erratum_835769_veneer_") + 16);
3445 sprintf (stub_name,"__erratum_835769_veneer_%d", num_fixes);
3446 return stub_name;
3447}
3448
4106101c 3449/* Scan for Cortex-A53 erratum 835769 sequence.
2144188d
MS
3450
3451 Return TRUE else FALSE on abnormal termination. */
3452
68fcca92 3453static bfd_boolean
5421cc6e
MS
3454_bfd_aarch64_erratum_835769_scan (bfd *input_bfd,
3455 struct bfd_link_info *info,
3456 unsigned int *num_fixes_p)
68fcca92
JW
3457{
3458 asection *section;
3459 struct elf_aarch64_link_hash_table *htab = elf_aarch64_hash_table (info);
68fcca92 3460 unsigned int num_fixes = *num_fixes_p;
68fcca92
JW
3461
3462 if (htab == NULL)
2144188d 3463 return TRUE;
68fcca92
JW
3464
3465 for (section = input_bfd->sections;
3466 section != NULL;
3467 section = section->next)
3468 {
3469 bfd_byte *contents = NULL;
3470 struct _aarch64_elf_section_data *sec_data;
3471 unsigned int span;
3472
3473 if (elf_section_type (section) != SHT_PROGBITS
3474 || (elf_section_flags (section) & SHF_EXECINSTR) == 0
3475 || (section->flags & SEC_EXCLUDE) != 0
3476 || (section->sec_info_type == SEC_INFO_TYPE_JUST_SYMS)
3477 || (section->output_section == bfd_abs_section_ptr))
3478 continue;
3479
3480 if (elf_section_data (section)->this_hdr.contents != NULL)
3481 contents = elf_section_data (section)->this_hdr.contents;
3482 else if (! bfd_malloc_and_get_section (input_bfd, section, &contents))
2144188d 3483 return FALSE;
68fcca92
JW
3484
3485 sec_data = elf_aarch64_section_data (section);
520c7b56
JW
3486
3487 qsort (sec_data->map, sec_data->mapcount,
3488 sizeof (elf_aarch64_section_map), elf_aarch64_compare_mapping);
3489
68fcca92
JW
3490 for (span = 0; span < sec_data->mapcount; span++)
3491 {
3492 unsigned int span_start = sec_data->map[span].vma;
3493 unsigned int span_end = ((span == sec_data->mapcount - 1)
3494 ? sec_data->map[0].vma + section->size
3495 : sec_data->map[span + 1].vma);
3496 unsigned int i;
3497 char span_type = sec_data->map[span].type;
3498
3499 if (span_type == 'd')
3500 continue;
3501
3502 for (i = span_start; i + 4 < span_end; i += 4)
3503 {
3504 uint32_t insn_1 = bfd_getl32 (contents + i);
3505 uint32_t insn_2 = bfd_getl32 (contents + i + 4);
3506
3507 if (aarch64_erratum_sequence (insn_1, insn_2))
3508 {
5421cc6e 3509 struct elf_aarch64_stub_hash_entry *stub_entry;
35fee8b7
MS
3510 char *stub_name = _bfd_aarch64_erratum_835769_stub_name (num_fixes);
3511 if (! stub_name)
2144188d 3512 return FALSE;
68fcca92 3513
5421cc6e
MS
3514 stub_entry = _bfd_aarch64_add_stub_entry_in_group (stub_name,
3515 section,
3516 htab);
3517 if (! stub_entry)
3518 return FALSE;
68fcca92 3519
5421cc6e
MS
3520 stub_entry->stub_type = aarch64_stub_erratum_835769_veneer;
3521 stub_entry->target_section = section;
3522 stub_entry->target_value = i + 4;
3523 stub_entry->veneered_insn = insn_2;
3524 stub_entry->output_name = stub_name;
68fcca92
JW
3525 num_fixes++;
3526 }
3527 }
3528 }
3529 if (elf_section_data (section)->this_hdr.contents == NULL)
3530 free (contents);
3531 }
3532
357d1523
MS
3533 *num_fixes_p = num_fixes;
3534
2144188d 3535 return TRUE;
68fcca92
JW
3536}
3537
13f622ec 3538
4106101c
MS
3539/* Test if instruction INSN is ADRP. */
3540
3541static bfd_boolean
3542_bfd_aarch64_adrp_p (uint32_t insn)
3543{
3544 return ((insn & 0x9f000000) == 0x90000000);
3545}
3546
3547
3548/* Helper predicate to look for cortex-a53 erratum 843419 sequence 1. */
3549
3550static bfd_boolean
3551_bfd_aarch64_erratum_843419_sequence_p (uint32_t insn_1, uint32_t insn_2,
3552 uint32_t insn_3)
3553{
3554 uint32_t rt;
3555 uint32_t rt2;
3556 bfd_boolean pair;
3557 bfd_boolean load;
3558
3559 return (aarch64_mem_op_p (insn_2, &rt, &rt2, &pair, &load)
3560 && (!pair
3561 || (pair && !load))
3562 && AARCH64_LDST_UIMM (insn_3)
3563 && AARCH64_RN (insn_3) == AARCH64_RD (insn_1));
3564}
3565
3566
3567/* Test for the presence of Cortex-A53 erratum 843419 instruction sequence.
3568
3569 Return TRUE if section CONTENTS at offset I contains one of the
3570 erratum 843419 sequences, otherwise return FALSE. If a sequence is
3571 seen set P_VENEER_I to the offset of the final LOAD/STORE
3572 instruction in the sequence.
3573 */
3574
3575static bfd_boolean
3576_bfd_aarch64_erratum_843419_p (bfd_byte *contents, bfd_vma vma,
3577 bfd_vma i, bfd_vma span_end,
3578 bfd_vma *p_veneer_i)
3579{
3580 uint32_t insn_1 = bfd_getl32 (contents + i);
3581
3582 if (!_bfd_aarch64_adrp_p (insn_1))
3583 return FALSE;
3584
3585 if (span_end < i + 12)
3586 return FALSE;
3587
3588 uint32_t insn_2 = bfd_getl32 (contents + i + 4);
3589 uint32_t insn_3 = bfd_getl32 (contents + i + 8);
3590
3591 if ((vma & 0xfff) != 0xff8 && (vma & 0xfff) != 0xffc)
3592 return FALSE;
3593
3594 if (_bfd_aarch64_erratum_843419_sequence_p (insn_1, insn_2, insn_3))
3595 {
3596 *p_veneer_i = i + 8;
3597 return TRUE;
3598 }
3599
3600 if (span_end < i + 16)
3601 return FALSE;
3602
3603 uint32_t insn_4 = bfd_getl32 (contents + i + 12);
3604
3605 if (_bfd_aarch64_erratum_843419_sequence_p (insn_1, insn_2, insn_4))
3606 {
3607 *p_veneer_i = i + 12;
3608 return TRUE;
3609 }
3610
3611 return FALSE;
3612}
3613
3614
13f622ec
MS
3615/* Resize all stub sections. */
3616
3617static void
3618_bfd_aarch64_resize_stubs (struct elf_aarch64_link_hash_table *htab)
3619{
3620 asection *section;
3621
3622 /* OK, we've added some stubs. Find out the new size of the
3623 stub sections. */
3624 for (section = htab->stub_bfd->sections;
3625 section != NULL; section = section->next)
3626 {
3627 /* Ignore non-stub sections. */
3628 if (!strstr (section->name, STUB_SUFFIX))
3629 continue;
3630 section->size = 0;
3631 }
3632
3633 bfd_hash_traverse (&htab->stub_hash_table, aarch64_size_one_stub, htab);
13f622ec 3634
61865519
MS
3635 for (section = htab->stub_bfd->sections;
3636 section != NULL; section = section->next)
3637 {
3638 if (!strstr (section->name, STUB_SUFFIX))
3639 continue;
3640
3641 if (section->size)
3642 section->size += 4;
4106101c
MS
3643
3644 /* Ensure all stub sections have a size which is a multiple of
3645 4096. This is important in order to ensure that the insertion
3646 of stub sections does not in itself move existing code around
3647 in such a way that new errata sequences are created. */
3648 if (htab->fix_erratum_843419)
3649 if (section->size)
3650 section->size = BFD_ALIGN (section->size, 0x1000);
3651 }
3652}
3653
3654
3655/* Construct an erratum 843419 workaround stub name.
3656 */
3657
3658static char *
3659_bfd_aarch64_erratum_843419_stub_name (asection *input_section,
3660 bfd_vma offset)
3661{
3662 const bfd_size_type len = 8 + 4 + 1 + 8 + 1 + 16 + 1;
3663 char *stub_name = bfd_malloc (len);
3664
3665 if (stub_name != NULL)
3666 snprintf (stub_name, len, "e843419@%04x_%08x_%" BFD_VMA_FMT "x",
3667 input_section->owner->id,
3668 input_section->id,
3669 offset);
3670 return stub_name;
3671}
3672
3673/* Build a stub_entry structure describing an 843419 fixup.
3674
3675 The stub_entry constructed is populated with the bit pattern INSN
3676 of the instruction located at OFFSET within input SECTION.
3677
3678 Returns TRUE on success. */
3679
3680static bfd_boolean
3681_bfd_aarch64_erratum_843419_fixup (uint32_t insn,
3682 bfd_vma adrp_offset,
3683 bfd_vma ldst_offset,
3684 asection *section,
3685 struct bfd_link_info *info)
3686{
3687 struct elf_aarch64_link_hash_table *htab = elf_aarch64_hash_table (info);
3688 char *stub_name;
3689 struct elf_aarch64_stub_hash_entry *stub_entry;
3690
3691 stub_name = _bfd_aarch64_erratum_843419_stub_name (section, ldst_offset);
3692 stub_entry = aarch64_stub_hash_lookup (&htab->stub_hash_table, stub_name,
3693 FALSE, FALSE);
3694 if (stub_entry)
3695 {
3696 free (stub_name);
3697 return TRUE;
3698 }
3699
3700 /* We always place an 843419 workaround veneer in the stub section
3701 attached to the input section in which an erratum sequence has
3702 been found. This ensures that later in the link process (in
3703 elfNN_aarch64_write_section) when we copy the veneered
3704 instruction from the input section into the stub section the
3705 copied instruction will have had any relocations applied to it.
3706 If we placed workaround veneers in any other stub section then we
3707 could not assume that all relocations have been processed on the
3708 corresponding input section at the point we output the stub
3709 section.
3710 */
3711
3712 stub_entry = _bfd_aarch64_add_stub_entry_after (stub_name, section, htab);
3713 if (stub_entry == NULL)
3714 {
3715 free (stub_name);
3716 return FALSE;
3717 }
3718
3719 stub_entry->adrp_offset = adrp_offset;
3720 stub_entry->target_value = ldst_offset;
3721 stub_entry->target_section = section;
3722 stub_entry->stub_type = aarch64_stub_erratum_843419_veneer;
3723 stub_entry->veneered_insn = insn;
3724 stub_entry->output_name = stub_name;
3725
3726 return TRUE;
3727}
3728
3729
3730/* Scan an input section looking for the signature of erratum 843419.
3731
3732 Scans input SECTION in INPUT_BFD looking for erratum 843419
3733 signatures, for each signature found a stub_entry is created
3734 describing the location of the erratum for subsequent fixup.
3735
3736 Return TRUE on successful scan, FALSE on failure to scan.
3737 */
3738
3739static bfd_boolean
3740_bfd_aarch64_erratum_843419_scan (bfd *input_bfd, asection *section,
3741 struct bfd_link_info *info)
3742{
3743 struct elf_aarch64_link_hash_table *htab = elf_aarch64_hash_table (info);
3744
3745 if (htab == NULL)
3746 return TRUE;
3747
3748 if (elf_section_type (section) != SHT_PROGBITS
3749 || (elf_section_flags (section) & SHF_EXECINSTR) == 0
3750 || (section->flags & SEC_EXCLUDE) != 0
3751 || (section->sec_info_type == SEC_INFO_TYPE_JUST_SYMS)
3752 || (section->output_section == bfd_abs_section_ptr))
3753 return TRUE;
3754
3755 do
3756 {
3757 bfd_byte *contents = NULL;
3758 struct _aarch64_elf_section_data *sec_data;
3759 unsigned int span;
3760
3761 if (elf_section_data (section)->this_hdr.contents != NULL)
3762 contents = elf_section_data (section)->this_hdr.contents;
3763 else if (! bfd_malloc_and_get_section (input_bfd, section, &contents))
3764 return FALSE;
3765
3766 sec_data = elf_aarch64_section_data (section);
3767
3768 qsort (sec_data->map, sec_data->mapcount,
3769 sizeof (elf_aarch64_section_map), elf_aarch64_compare_mapping);
3770
3771 for (span = 0; span < sec_data->mapcount; span++)
3772 {
3773 unsigned int span_start = sec_data->map[span].vma;
3774 unsigned int span_end = ((span == sec_data->mapcount - 1)
3775 ? sec_data->map[0].vma + section->size
3776 : sec_data->map[span + 1].vma);
3777 unsigned int i;
3778 char span_type = sec_data->map[span].type;
3779
3780 if (span_type == 'd')
3781 continue;
3782
3783 for (i = span_start; i + 8 < span_end; i += 4)
3784 {
3785 bfd_vma vma = (section->output_section->vma
3786 + section->output_offset
3787 + i);
3788 bfd_vma veneer_i;
3789
3790 if (_bfd_aarch64_erratum_843419_p
3791 (contents, vma, i, span_end, &veneer_i))
3792 {
3793 uint32_t insn = bfd_getl32 (contents + veneer_i);
3794
3795 if (!_bfd_aarch64_erratum_843419_fixup (insn, i, veneer_i,
3796 section, info))
3797 return FALSE;
3798 }
3799 }
3800 }
3801
3802 if (elf_section_data (section)->this_hdr.contents == NULL)
3803 free (contents);
61865519 3804 }
4106101c
MS
3805 while (0);
3806
3807 return TRUE;
61865519 3808}
13f622ec 3809
4106101c 3810
a06ea964
NC
3811/* Determine and set the size of the stub section for a final link.
3812
3813 The basic idea here is to examine all the relocations looking for
3814 PC-relative calls to a target that is unreachable with a "bl"
3815 instruction. */
3816
3817bfd_boolean
cec5225b 3818elfNN_aarch64_size_stubs (bfd *output_bfd,
a06ea964
NC
3819 bfd *stub_bfd,
3820 struct bfd_link_info *info,
3821 bfd_signed_vma group_size,
3822 asection * (*add_stub_section) (const char *,
3823 asection *),
3824 void (*layout_sections_again) (void))
3825{
3826 bfd_size_type stub_group_size;
3827 bfd_boolean stubs_always_before_branch;
5421cc6e 3828 bfd_boolean stub_changed = FALSE;
cec5225b 3829 struct elf_aarch64_link_hash_table *htab = elf_aarch64_hash_table (info);
68fcca92 3830 unsigned int num_erratum_835769_fixes = 0;
a06ea964
NC
3831
3832 /* Propagate mach to stub bfd, because it may not have been
3833 finalized when we created stub_bfd. */
3834 bfd_set_arch_mach (stub_bfd, bfd_get_arch (output_bfd),
3835 bfd_get_mach (output_bfd));
3836
3837 /* Stash our params away. */
3838 htab->stub_bfd = stub_bfd;
3839 htab->add_stub_section = add_stub_section;
3840 htab->layout_sections_again = layout_sections_again;
3841 stubs_always_before_branch = group_size < 0;
3842 if (group_size < 0)
3843 stub_group_size = -group_size;
3844 else
3845 stub_group_size = group_size;
3846
3847 if (stub_group_size == 1)
3848 {
3849 /* Default values. */
b9eead84 3850 /* AArch64 branch range is +-128MB. The value used is 1MB less. */
a06ea964
NC
3851 stub_group_size = 127 * 1024 * 1024;
3852 }
3853
3854 group_sections (htab, stub_group_size, stubs_always_before_branch);
3855
4106101c
MS
3856 (*htab->layout_sections_again) ();
3857
5421cc6e
MS
3858 if (htab->fix_erratum_835769)
3859 {
3860 bfd *input_bfd;
3861
3862 for (input_bfd = info->input_bfds;
3863 input_bfd != NULL; input_bfd = input_bfd->link.next)
3864 if (!_bfd_aarch64_erratum_835769_scan (input_bfd, info,
3865 &num_erratum_835769_fixes))
3866 return FALSE;
3867
4106101c
MS
3868 _bfd_aarch64_resize_stubs (htab);
3869 (*htab->layout_sections_again) ();
3870 }
3871
3872 if (htab->fix_erratum_843419)
3873 {
3874 bfd *input_bfd;
3875
3876 for (input_bfd = info->input_bfds;
3877 input_bfd != NULL;
3878 input_bfd = input_bfd->link.next)
3879 {
3880 asection *section;
3881
3882 for (section = input_bfd->sections;
3883 section != NULL;
3884 section = section->next)
3885 if (!_bfd_aarch64_erratum_843419_scan (input_bfd, section, info))
3886 return FALSE;
3887 }
3888
3889 _bfd_aarch64_resize_stubs (htab);
3890 (*htab->layout_sections_again) ();
5421cc6e
MS
3891 }
3892
a06ea964
NC
3893 while (1)
3894 {
3895 bfd *input_bfd;
a06ea964 3896
9b9971aa
MS
3897 for (input_bfd = info->input_bfds;
3898 input_bfd != NULL; input_bfd = input_bfd->link.next)
a06ea964
NC
3899 {
3900 Elf_Internal_Shdr *symtab_hdr;
3901 asection *section;
3902 Elf_Internal_Sym *local_syms = NULL;
3903
3904 /* We'll need the symbol table in a second. */
3905 symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
3906 if (symtab_hdr->sh_info == 0)
3907 continue;
3908
3909 /* Walk over each section attached to the input bfd. */
3910 for (section = input_bfd->sections;
3911 section != NULL; section = section->next)
3912 {
3913 Elf_Internal_Rela *internal_relocs, *irelaend, *irela;
3914
3915 /* If there aren't any relocs, then there's nothing more
3916 to do. */
3917 if ((section->flags & SEC_RELOC) == 0
3918 || section->reloc_count == 0
3919 || (section->flags & SEC_CODE) == 0)
3920 continue;
3921
3922 /* If this section is a link-once section that will be
3923 discarded, then don't create any stubs. */
3924 if (section->output_section == NULL
3925 || section->output_section->owner != output_bfd)
3926 continue;
3927
3928 /* Get the relocs. */
3929 internal_relocs
3930 = _bfd_elf_link_read_relocs (input_bfd, section, NULL,
3931 NULL, info->keep_memory);
3932 if (internal_relocs == NULL)
3933 goto error_ret_free_local;
3934
3935 /* Now examine each relocation. */
3936 irela = internal_relocs;
3937 irelaend = irela + section->reloc_count;
3938 for (; irela < irelaend; irela++)
3939 {
3940 unsigned int r_type, r_indx;
cec5225b
YZ
3941 enum elf_aarch64_stub_type stub_type;
3942 struct elf_aarch64_stub_hash_entry *stub_entry;
a06ea964
NC
3943 asection *sym_sec;
3944 bfd_vma sym_value;
3945 bfd_vma destination;
cec5225b 3946 struct elf_aarch64_link_hash_entry *hash;
a06ea964
NC
3947 const char *sym_name;
3948 char *stub_name;
3949 const asection *id_sec;
3950 unsigned char st_type;
3951 bfd_size_type len;
3952
cec5225b
YZ
3953 r_type = ELFNN_R_TYPE (irela->r_info);
3954 r_indx = ELFNN_R_SYM (irela->r_info);
a06ea964
NC
3955
3956 if (r_type >= (unsigned int) R_AARCH64_end)
3957 {
3958 bfd_set_error (bfd_error_bad_value);
3959 error_ret_free_internal:
3960 if (elf_section_data (section)->relocs == NULL)
3961 free (internal_relocs);
3962 goto error_ret_free_local;
3963 }
3964
3965 /* Only look for stubs on unconditional branch and
3966 branch and link instructions. */
a6bb11b2
YZ
3967 if (r_type != (unsigned int) AARCH64_R (CALL26)
3968 && r_type != (unsigned int) AARCH64_R (JUMP26))
a06ea964
NC
3969 continue;
3970
3971 /* Now determine the call target, its name, value,
3972 section. */
3973 sym_sec = NULL;
3974 sym_value = 0;
3975 destination = 0;
3976 hash = NULL;
3977 sym_name = NULL;
3978 if (r_indx < symtab_hdr->sh_info)
3979 {
3980 /* It's a local symbol. */
3981 Elf_Internal_Sym *sym;
3982 Elf_Internal_Shdr *hdr;
3983
3984 if (local_syms == NULL)
3985 {
3986 local_syms
3987 = (Elf_Internal_Sym *) symtab_hdr->contents;
3988 if (local_syms == NULL)
3989 local_syms
3990 = bfd_elf_get_elf_syms (input_bfd, symtab_hdr,
3991 symtab_hdr->sh_info, 0,
3992 NULL, NULL, NULL);
3993 if (local_syms == NULL)
3994 goto error_ret_free_internal;
3995 }
3996
3997 sym = local_syms + r_indx;
3998 hdr = elf_elfsections (input_bfd)[sym->st_shndx];
3999 sym_sec = hdr->bfd_section;
4000 if (!sym_sec)
4001 /* This is an undefined symbol. It can never
4002 be resolved. */
4003 continue;
4004
4005 if (ELF_ST_TYPE (sym->st_info) != STT_SECTION)
4006 sym_value = sym->st_value;
4007 destination = (sym_value + irela->r_addend
4008 + sym_sec->output_offset
4009 + sym_sec->output_section->vma);
4010 st_type = ELF_ST_TYPE (sym->st_info);
4011 sym_name
4012 = bfd_elf_string_from_elf_section (input_bfd,
4013 symtab_hdr->sh_link,
4014 sym->st_name);
4015 }
4016 else
4017 {
4018 int e_indx;
4019
4020 e_indx = r_indx - symtab_hdr->sh_info;
cec5225b 4021 hash = ((struct elf_aarch64_link_hash_entry *)
a06ea964
NC
4022 elf_sym_hashes (input_bfd)[e_indx]);
4023
4024 while (hash->root.root.type == bfd_link_hash_indirect
4025 || hash->root.root.type == bfd_link_hash_warning)
cec5225b 4026 hash = ((struct elf_aarch64_link_hash_entry *)
a06ea964
NC
4027 hash->root.root.u.i.link);
4028
4029 if (hash->root.root.type == bfd_link_hash_defined
4030 || hash->root.root.type == bfd_link_hash_defweak)
4031 {
cec5225b
YZ
4032 struct elf_aarch64_link_hash_table *globals =
4033 elf_aarch64_hash_table (info);
a06ea964
NC
4034 sym_sec = hash->root.root.u.def.section;
4035 sym_value = hash->root.root.u.def.value;
4036 /* For a destination in a shared library,
4037 use the PLT stub as target address to
4038 decide whether a branch stub is
4039 needed. */
4040 if (globals->root.splt != NULL && hash != NULL
4041 && hash->root.plt.offset != (bfd_vma) - 1)
4042 {
4043 sym_sec = globals->root.splt;
4044 sym_value = hash->root.plt.offset;
4045 if (sym_sec->output_section != NULL)
4046 destination = (sym_value
4047 + sym_sec->output_offset
4048 +
4049 sym_sec->output_section->vma);
4050 }
4051 else if (sym_sec->output_section != NULL)
4052 destination = (sym_value + irela->r_addend
4053 + sym_sec->output_offset
4054 + sym_sec->output_section->vma);
4055 }
4056 else if (hash->root.root.type == bfd_link_hash_undefined
4057 || (hash->root.root.type
4058 == bfd_link_hash_undefweak))
4059 {
4060 /* For a shared library, use the PLT stub as
4061 target address to decide whether a long
4062 branch stub is needed.
4063 For absolute code, they cannot be handled. */
cec5225b
YZ
4064 struct elf_aarch64_link_hash_table *globals =
4065 elf_aarch64_hash_table (info);
a06ea964
NC
4066
4067 if (globals->root.splt != NULL && hash != NULL
4068 && hash->root.plt.offset != (bfd_vma) - 1)
4069 {
4070 sym_sec = globals->root.splt;
4071 sym_value = hash->root.plt.offset;
4072 if (sym_sec->output_section != NULL)
4073 destination = (sym_value
4074 + sym_sec->output_offset
4075 +
4076 sym_sec->output_section->vma);
4077 }
4078 else
4079 continue;
4080 }
4081 else
4082 {
4083 bfd_set_error (bfd_error_bad_value);
4084 goto error_ret_free_internal;
4085 }
4086 st_type = ELF_ST_TYPE (hash->root.type);
4087 sym_name = hash->root.root.root.string;
4088 }
4089
4090 /* Determine what (if any) linker stub is needed. */
4091 stub_type = aarch64_type_of_stub
f678ded7 4092 (info, section, irela, sym_sec, st_type, hash, destination);
a06ea964
NC
4093 if (stub_type == aarch64_stub_none)
4094 continue;
4095
4096 /* Support for grouping stub sections. */
4097 id_sec = htab->stub_group[section->id].link_sec;
4098
4099 /* Get the name of this stub. */
cec5225b 4100 stub_name = elfNN_aarch64_stub_name (id_sec, sym_sec, hash,
a06ea964
NC
4101 irela);
4102 if (!stub_name)
4103 goto error_ret_free_internal;
4104
4105 stub_entry =
4106 aarch64_stub_hash_lookup (&htab->stub_hash_table,
4107 stub_name, FALSE, FALSE);
4108 if (stub_entry != NULL)
4109 {
4110 /* The proper stub has already been created. */
4111 free (stub_name);
4112 continue;
4113 }
4114
ef857521
MS
4115 stub_entry = _bfd_aarch64_add_stub_entry_in_group
4116 (stub_name, section, htab);
a06ea964
NC
4117 if (stub_entry == NULL)
4118 {
4119 free (stub_name);
4120 goto error_ret_free_internal;
4121 }
4122
4123 stub_entry->target_value = sym_value;
4124 stub_entry->target_section = sym_sec;
4125 stub_entry->stub_type = stub_type;
4126 stub_entry->h = hash;
4127 stub_entry->st_type = st_type;
4128
4129 if (sym_name == NULL)
4130 sym_name = "unnamed";
4131 len = sizeof (STUB_ENTRY_NAME) + strlen (sym_name);
4132 stub_entry->output_name = bfd_alloc (htab->stub_bfd, len);
4133 if (stub_entry->output_name == NULL)
4134 {
4135 free (stub_name);
4136 goto error_ret_free_internal;
4137 }
4138
4139 snprintf (stub_entry->output_name, len, STUB_ENTRY_NAME,
4140 sym_name);
4141
4142 stub_changed = TRUE;
4143 }
4144
4145 /* We're done with the internal relocs, free them. */
4146 if (elf_section_data (section)->relocs == NULL)
4147 free (internal_relocs);
4148 }
4149 }
4150
4151 if (!stub_changed)
4152 break;
4153
13f622ec 4154 _bfd_aarch64_resize_stubs (htab);
a06ea964
NC
4155
4156 /* Ask the linker to do its stuff. */
4157 (*htab->layout_sections_again) ();
4158 stub_changed = FALSE;
4159 }
4160
4161 return TRUE;
4162
4163error_ret_free_local:
4164 return FALSE;
4165}
4166
4167/* Build all the stubs associated with the current output file. The
4168 stubs are kept in a hash table attached to the main linker hash
4169 table. We also set up the .plt entries for statically linked PIC
4170 functions here. This function is called via aarch64_elf_finish in the
4171 linker. */
4172
4173bfd_boolean
cec5225b 4174elfNN_aarch64_build_stubs (struct bfd_link_info *info)
a06ea964
NC
4175{
4176 asection *stub_sec;
4177 struct bfd_hash_table *table;
cec5225b 4178 struct elf_aarch64_link_hash_table *htab;
a06ea964 4179
cec5225b 4180 htab = elf_aarch64_hash_table (info);
a06ea964
NC
4181
4182 for (stub_sec = htab->stub_bfd->sections;
4183 stub_sec != NULL; stub_sec = stub_sec->next)
4184 {
4185 bfd_size_type size;
4186
4187 /* Ignore non-stub sections. */
4188 if (!strstr (stub_sec->name, STUB_SUFFIX))
4189 continue;
4190
4191 /* Allocate memory to hold the linker stubs. */
4192 size = stub_sec->size;
4193 stub_sec->contents = bfd_zalloc (htab->stub_bfd, size);
4194 if (stub_sec->contents == NULL && size != 0)
4195 return FALSE;
4196 stub_sec->size = 0;
61865519
MS
4197
4198 bfd_putl32 (0x14000000 | (size >> 2), stub_sec->contents);
4199 stub_sec->size += 4;
a06ea964
NC
4200 }
4201
4202 /* Build the stubs as directed by the stub hash table. */
4203 table = &htab->stub_hash_table;
4204 bfd_hash_traverse (table, aarch64_build_one_stub, info);
4205
4206 return TRUE;
4207}
4208
4209
4210/* Add an entry to the code/data map for section SEC. */
4211
4212static void
cec5225b 4213elfNN_aarch64_section_map_add (asection *sec, char type, bfd_vma vma)
a06ea964
NC
4214{
4215 struct _aarch64_elf_section_data *sec_data =
cec5225b 4216 elf_aarch64_section_data (sec);
a06ea964
NC
4217 unsigned int newidx;
4218
4219 if (sec_data->map == NULL)
4220 {
cec5225b 4221 sec_data->map = bfd_malloc (sizeof (elf_aarch64_section_map));
a06ea964
NC
4222 sec_data->mapcount = 0;
4223 sec_data->mapsize = 1;
4224 }
4225
4226 newidx = sec_data->mapcount++;
4227
4228 if (sec_data->mapcount > sec_data->mapsize)
4229 {
4230 sec_data->mapsize *= 2;
4231 sec_data->map = bfd_realloc_or_free
cec5225b 4232 (sec_data->map, sec_data->mapsize * sizeof (elf_aarch64_section_map));
a06ea964
NC
4233 }
4234
4235 if (sec_data->map)
4236 {
4237 sec_data->map[newidx].vma = vma;
4238 sec_data->map[newidx].type = type;
4239 }
4240}
4241
4242
4243/* Initialise maps of insn/data for input BFDs. */
4244void
cec5225b 4245bfd_elfNN_aarch64_init_maps (bfd *abfd)
a06ea964
NC
4246{
4247 Elf_Internal_Sym *isymbuf;
4248 Elf_Internal_Shdr *hdr;
4249 unsigned int i, localsyms;
4250
4251 /* Make sure that we are dealing with an AArch64 elf binary. */
4252 if (!is_aarch64_elf (abfd))
4253 return;
4254
4255 if ((abfd->flags & DYNAMIC) != 0)
68fcca92 4256 return;
a06ea964
NC
4257
4258 hdr = &elf_symtab_hdr (abfd);
4259 localsyms = hdr->sh_info;
4260
4261 /* Obtain a buffer full of symbols for this BFD. The hdr->sh_info field
4262 should contain the number of local symbols, which should come before any
4263 global symbols. Mapping symbols are always local. */
4264 isymbuf = bfd_elf_get_elf_syms (abfd, hdr, localsyms, 0, NULL, NULL, NULL);
4265
4266 /* No internal symbols read? Skip this BFD. */
4267 if (isymbuf == NULL)
4268 return;
4269
4270 for (i = 0; i < localsyms; i++)
4271 {
4272 Elf_Internal_Sym *isym = &isymbuf[i];
4273 asection *sec = bfd_section_from_elf_index (abfd, isym->st_shndx);
4274 const char *name;
4275
4276 if (sec != NULL && ELF_ST_BIND (isym->st_info) == STB_LOCAL)
4277 {
4278 name = bfd_elf_string_from_elf_section (abfd,
4279 hdr->sh_link,
4280 isym->st_name);
4281
4282 if (bfd_is_aarch64_special_symbol_name
4283 (name, BFD_AARCH64_SPECIAL_SYM_TYPE_MAP))
cec5225b 4284 elfNN_aarch64_section_map_add (sec, name[1], isym->st_value);
a06ea964
NC
4285 }
4286 }
4287}
4288
4289/* Set option values needed during linking. */
4290void
cec5225b 4291bfd_elfNN_aarch64_set_options (struct bfd *output_bfd,
a06ea964
NC
4292 struct bfd_link_info *link_info,
4293 int no_enum_warn,
68fcca92 4294 int no_wchar_warn, int pic_veneer,
4106101c
MS
4295 int fix_erratum_835769,
4296 int fix_erratum_843419)
a06ea964 4297{
cec5225b 4298 struct elf_aarch64_link_hash_table *globals;
a06ea964 4299
cec5225b 4300 globals = elf_aarch64_hash_table (link_info);
a06ea964 4301 globals->pic_veneer = pic_veneer;
68fcca92 4302 globals->fix_erratum_835769 = fix_erratum_835769;
4106101c
MS
4303 globals->fix_erratum_843419 = fix_erratum_843419;
4304 globals->fix_erratum_843419_adr = TRUE;
a06ea964
NC
4305
4306 BFD_ASSERT (is_aarch64_elf (output_bfd));
4307 elf_aarch64_tdata (output_bfd)->no_enum_size_warning = no_enum_warn;
4308 elf_aarch64_tdata (output_bfd)->no_wchar_size_warning = no_wchar_warn;
4309}
4310
a06ea964
NC
4311static bfd_vma
4312aarch64_calculate_got_entry_vma (struct elf_link_hash_entry *h,
cec5225b 4313 struct elf_aarch64_link_hash_table
a06ea964
NC
4314 *globals, struct bfd_link_info *info,
4315 bfd_vma value, bfd *output_bfd,
4316 bfd_boolean *unresolved_reloc_p)
4317{
4318 bfd_vma off = (bfd_vma) - 1;
4319 asection *basegot = globals->root.sgot;
4320 bfd_boolean dyn = globals->root.dynamic_sections_created;
4321
4322 if (h != NULL)
4323 {
a6bb11b2 4324 BFD_ASSERT (basegot != NULL);
a06ea964
NC
4325 off = h->got.offset;
4326 BFD_ASSERT (off != (bfd_vma) - 1);
0e1862bb
L
4327 if (!WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, bfd_link_pic (info), h)
4328 || (bfd_link_pic (info)
a06ea964
NC
4329 && SYMBOL_REFERENCES_LOCAL (info, h))
4330 || (ELF_ST_VISIBILITY (h->other)
4331 && h->root.type == bfd_link_hash_undefweak))
4332 {
4333 /* This is actually a static link, or it is a -Bsymbolic link
4334 and the symbol is defined locally. We must initialize this
4335 entry in the global offset table. Since the offset must
a6bb11b2
YZ
4336 always be a multiple of 8 (4 in the case of ILP32), we use
4337 the least significant bit to record whether we have
4338 initialized it already.
a06ea964
NC
4339 When doing a dynamic link, we create a .rel(a).got relocation
4340 entry to initialize the value. This is done in the
4341 finish_dynamic_symbol routine. */
4342 if ((off & 1) != 0)
4343 off &= ~1;
4344 else
4345 {
cec5225b 4346 bfd_put_NN (output_bfd, value, basegot->contents + off);
a06ea964
NC
4347 h->got.offset |= 1;
4348 }
4349 }
4350 else
4351 *unresolved_reloc_p = FALSE;
4352
4353 off = off + basegot->output_section->vma + basegot->output_offset;
4354 }
4355
4356 return off;
4357}
4358
4359/* Change R_TYPE to a more efficient access model where possible,
4360 return the new reloc type. */
4361
a6bb11b2
YZ
4362static bfd_reloc_code_real_type
4363aarch64_tls_transition_without_check (bfd_reloc_code_real_type r_type,
a06ea964
NC
4364 struct elf_link_hash_entry *h)
4365{
4366 bfd_boolean is_local = h == NULL;
a6bb11b2 4367
a06ea964
NC
4368 switch (r_type)
4369 {
a6bb11b2 4370 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
ce336788 4371 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
a6bb11b2
YZ
4372 return (is_local
4373 ? BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1
4374 : BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21);
4375
389b8029
MS
4376 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
4377 return (is_local
4378 ? BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0_NC
4379 : r_type);
4380
1ada945d
MS
4381 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
4382 return (is_local
4383 ? BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1
4384 : BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19);
4385
a6bb11b2 4386 case BFD_RELOC_AARCH64_TLSDESC_LDNN_LO12_NC:
ce336788 4387 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
a6bb11b2
YZ
4388 return (is_local
4389 ? BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0_NC
4390 : BFD_RELOC_AARCH64_TLSIE_LDNN_GOTTPREL_LO12_NC);
4391
4392 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
4393 return is_local ? BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1 : r_type;
4394
4395 case BFD_RELOC_AARCH64_TLSIE_LDNN_GOTTPREL_LO12_NC:
4396 return is_local ? BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0_NC : r_type;
4397
043bf05a
MS
4398 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
4399 return r_type;
4400
3c12b054
MS
4401 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
4402 return (is_local
4403 ? BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_HI12
4404 : BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19);
4405
a6bb11b2
YZ
4406 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
4407 case BFD_RELOC_AARCH64_TLSDESC_CALL:
a06ea964 4408 /* Instructions with these relocations will become NOPs. */
a6bb11b2
YZ
4409 return BFD_RELOC_AARCH64_NONE;
4410
259364ad
JW
4411 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
4412 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
4413 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
4414 return is_local ? BFD_RELOC_AARCH64_NONE : r_type;
4415
a6bb11b2
YZ
4416 default:
4417 break;
a06ea964
NC
4418 }
4419
4420 return r_type;
4421}
4422
4423static unsigned int
a6bb11b2 4424aarch64_reloc_got_type (bfd_reloc_code_real_type r_type)
a06ea964
NC
4425{
4426 switch (r_type)
4427 {
a6bb11b2
YZ
4428 case BFD_RELOC_AARCH64_ADR_GOT_PAGE:
4429 case BFD_RELOC_AARCH64_GOT_LD_PREL19:
7018c030 4430 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
ce336788 4431 case BFD_RELOC_AARCH64_LD32_GOT_LO12_NC:
a2e1db00 4432 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
99ad26cb 4433 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
ce336788 4434 case BFD_RELOC_AARCH64_LD64_GOT_LO12_NC:
a06ea964
NC
4435 return GOT_NORMAL;
4436
ce336788 4437 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
a6bb11b2 4438 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
3c12b054 4439 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
73f925cc 4440 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
f69e4920 4441 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
77a69ff8 4442 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
a06ea964
NC
4443 return GOT_TLS_GD;
4444
a6bb11b2
YZ
4445 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
4446 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
389b8029 4447 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
a6bb11b2 4448 case BFD_RELOC_AARCH64_TLSDESC_CALL:
a6bb11b2 4449 case BFD_RELOC_AARCH64_TLSDESC_LD32_LO12_NC:
ce336788 4450 case BFD_RELOC_AARCH64_TLSDESC_LD64_LO12_NC:
1ada945d 4451 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
a06ea964
NC
4452 return GOT_TLSDESC_GD;
4453
a6bb11b2 4454 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
a6bb11b2 4455 case BFD_RELOC_AARCH64_TLSIE_LD32_GOTTPREL_LO12_NC:
ce336788 4456 case BFD_RELOC_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
043bf05a 4457 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
a06ea964
NC
4458 return GOT_TLS_IE;
4459
a6bb11b2
YZ
4460 default:
4461 break;
a06ea964
NC
4462 }
4463 return GOT_UNKNOWN;
4464}
4465
4466static bfd_boolean
4467aarch64_can_relax_tls (bfd *input_bfd,
4468 struct bfd_link_info *info,
a6bb11b2 4469 bfd_reloc_code_real_type r_type,
a06ea964
NC
4470 struct elf_link_hash_entry *h,
4471 unsigned long r_symndx)
4472{
4473 unsigned int symbol_got_type;
4474 unsigned int reloc_got_type;
4475
9331eea1 4476 if (! IS_AARCH64_TLS_RELAX_RELOC (r_type))
a06ea964
NC
4477 return FALSE;
4478
cec5225b 4479 symbol_got_type = elfNN_aarch64_symbol_got_type (h, input_bfd, r_symndx);
a06ea964
NC
4480 reloc_got_type = aarch64_reloc_got_type (r_type);
4481
4482 if (symbol_got_type == GOT_TLS_IE && GOT_TLS_GD_ANY_P (reloc_got_type))
4483 return TRUE;
4484
0e1862bb 4485 if (bfd_link_pic (info))
a06ea964
NC
4486 return FALSE;
4487
4488 if (h && h->root.type == bfd_link_hash_undefweak)
4489 return FALSE;
4490
4491 return TRUE;
4492}
4493
a6bb11b2
YZ
4494/* Given the relocation code R_TYPE, return the relaxed bfd reloc
4495 enumerator. */
4496
4497static bfd_reloc_code_real_type
a06ea964
NC
4498aarch64_tls_transition (bfd *input_bfd,
4499 struct bfd_link_info *info,
4500 unsigned int r_type,
4501 struct elf_link_hash_entry *h,
4502 unsigned long r_symndx)
4503{
a6bb11b2
YZ
4504 bfd_reloc_code_real_type bfd_r_type
4505 = elfNN_aarch64_bfd_reloc_from_type (r_type);
a06ea964 4506
a6bb11b2
YZ
4507 if (! aarch64_can_relax_tls (input_bfd, info, bfd_r_type, h, r_symndx))
4508 return bfd_r_type;
4509
4510 return aarch64_tls_transition_without_check (bfd_r_type, h);
a06ea964
NC
4511}
4512
4513/* Return the base VMA address which should be subtracted from real addresses
a6bb11b2 4514 when resolving R_AARCH64_TLS_DTPREL relocation. */
a06ea964
NC
4515
4516static bfd_vma
4517dtpoff_base (struct bfd_link_info *info)
4518{
4519 /* If tls_sec is NULL, we should have signalled an error already. */
4520 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4521 return elf_hash_table (info)->tls_sec->vma;
4522}
4523
a06ea964
NC
4524/* Return the base VMA address which should be subtracted from real addresses
4525 when resolving R_AARCH64_TLS_GOTTPREL64 relocations. */
4526
4527static bfd_vma
4528tpoff_base (struct bfd_link_info *info)
4529{
4530 struct elf_link_hash_table *htab = elf_hash_table (info);
4531
4532 /* If tls_sec is NULL, we should have signalled an error already. */
ac21917f 4533 BFD_ASSERT (htab->tls_sec != NULL);
a06ea964
NC
4534
4535 bfd_vma base = align_power ((bfd_vma) TCB_SIZE,
4536 htab->tls_sec->alignment_power);
4537 return htab->tls_sec->vma - base;
4538}
4539
4540static bfd_vma *
4541symbol_got_offset_ref (bfd *input_bfd, struct elf_link_hash_entry *h,
4542 unsigned long r_symndx)
4543{
4544 /* Calculate the address of the GOT entry for symbol
4545 referred to in h. */
4546 if (h != NULL)
4547 return &h->got.offset;
4548 else
4549 {
4550 /* local symbol */
4551 struct elf_aarch64_local_symbol *l;
4552
cec5225b 4553 l = elf_aarch64_locals (input_bfd);
a06ea964
NC
4554 return &l[r_symndx].got_offset;
4555 }
4556}
4557
4558static void
4559symbol_got_offset_mark (bfd *input_bfd, struct elf_link_hash_entry *h,
4560 unsigned long r_symndx)
4561{
4562 bfd_vma *p;
4563 p = symbol_got_offset_ref (input_bfd, h, r_symndx);
4564 *p |= 1;
4565}
4566
4567static int
4568symbol_got_offset_mark_p (bfd *input_bfd, struct elf_link_hash_entry *h,
4569 unsigned long r_symndx)
4570{
4571 bfd_vma value;
4572 value = * symbol_got_offset_ref (input_bfd, h, r_symndx);
4573 return value & 1;
4574}
4575
4576static bfd_vma
4577symbol_got_offset (bfd *input_bfd, struct elf_link_hash_entry *h,
4578 unsigned long r_symndx)
4579{
4580 bfd_vma value;
4581 value = * symbol_got_offset_ref (input_bfd, h, r_symndx);
4582 value &= ~1;
4583 return value;
4584}
4585
4586static bfd_vma *
4587symbol_tlsdesc_got_offset_ref (bfd *input_bfd, struct elf_link_hash_entry *h,
4588 unsigned long r_symndx)
4589{
4590 /* Calculate the address of the GOT entry for symbol
4591 referred to in h. */
4592 if (h != NULL)
4593 {
cec5225b
YZ
4594 struct elf_aarch64_link_hash_entry *eh;
4595 eh = (struct elf_aarch64_link_hash_entry *) h;
a06ea964
NC
4596 return &eh->tlsdesc_got_jump_table_offset;
4597 }
4598 else
4599 {
4600 /* local symbol */
4601 struct elf_aarch64_local_symbol *l;
4602
cec5225b 4603 l = elf_aarch64_locals (input_bfd);
a06ea964
NC
4604 return &l[r_symndx].tlsdesc_got_jump_table_offset;
4605 }
4606}
4607
4608static void
4609symbol_tlsdesc_got_offset_mark (bfd *input_bfd, struct elf_link_hash_entry *h,
4610 unsigned long r_symndx)
4611{
4612 bfd_vma *p;
4613 p = symbol_tlsdesc_got_offset_ref (input_bfd, h, r_symndx);
4614 *p |= 1;
4615}
4616
4617static int
4618symbol_tlsdesc_got_offset_mark_p (bfd *input_bfd,
4619 struct elf_link_hash_entry *h,
4620 unsigned long r_symndx)
4621{
4622 bfd_vma value;
4623 value = * symbol_tlsdesc_got_offset_ref (input_bfd, h, r_symndx);
4624 return value & 1;
4625}
4626
4627static bfd_vma
4628symbol_tlsdesc_got_offset (bfd *input_bfd, struct elf_link_hash_entry *h,
4629 unsigned long r_symndx)
4630{
4631 bfd_vma value;
4632 value = * symbol_tlsdesc_got_offset_ref (input_bfd, h, r_symndx);
4633 value &= ~1;
4634 return value;
4635}
4636
68fcca92
JW
4637/* Data for make_branch_to_erratum_835769_stub(). */
4638
4639struct erratum_835769_branch_to_stub_data
4640{
4106101c 4641 struct bfd_link_info *info;
68fcca92
JW
4642 asection *output_section;
4643 bfd_byte *contents;
4644};
4645
4646/* Helper to insert branches to erratum 835769 stubs in the right
4647 places for a particular section. */
4648
4649static bfd_boolean
4650make_branch_to_erratum_835769_stub (struct bfd_hash_entry *gen_entry,
4651 void *in_arg)
4652{
4653 struct elf_aarch64_stub_hash_entry *stub_entry;
4654 struct erratum_835769_branch_to_stub_data *data;
4655 bfd_byte *contents;
4656 unsigned long branch_insn = 0;
4657 bfd_vma veneered_insn_loc, veneer_entry_loc;
4658 bfd_signed_vma branch_offset;
4659 unsigned int target;
4660 bfd *abfd;
4661
4662 stub_entry = (struct elf_aarch64_stub_hash_entry *) gen_entry;
4663 data = (struct erratum_835769_branch_to_stub_data *) in_arg;
4664
4665 if (stub_entry->target_section != data->output_section
4666 || stub_entry->stub_type != aarch64_stub_erratum_835769_veneer)
4667 return TRUE;
4668
4669 contents = data->contents;
4670 veneered_insn_loc = stub_entry->target_section->output_section->vma
4671 + stub_entry->target_section->output_offset
4672 + stub_entry->target_value;
4673 veneer_entry_loc = stub_entry->stub_sec->output_section->vma
4674 + stub_entry->stub_sec->output_offset
4675 + stub_entry->stub_offset;
4676 branch_offset = veneer_entry_loc - veneered_insn_loc;
4677
4678 abfd = stub_entry->target_section->owner;
4679 if (!aarch64_valid_branch_p (veneer_entry_loc, veneered_insn_loc))
4680 (*_bfd_error_handler)
4681 (_("%B: error: Erratum 835769 stub out "
4682 "of range (input file too large)"), abfd);
4683
4684 target = stub_entry->target_value;
4685 branch_insn = 0x14000000;
4686 branch_offset >>= 2;
4687 branch_offset &= 0x3ffffff;
4688 branch_insn |= branch_offset;
4689 bfd_putl32 (branch_insn, &contents[target]);
4690
4691 return TRUE;
4692}
4693
4106101c
MS
4694
4695static bfd_boolean
4696_bfd_aarch64_erratum_843419_branch_to_stub (struct bfd_hash_entry *gen_entry,
4697 void *in_arg)
4698{
4699 struct elf_aarch64_stub_hash_entry *stub_entry
4700 = (struct elf_aarch64_stub_hash_entry *) gen_entry;
4701 struct erratum_835769_branch_to_stub_data *data
4702 = (struct erratum_835769_branch_to_stub_data *) in_arg;
4703 struct bfd_link_info *info;
4704 struct elf_aarch64_link_hash_table *htab;
4705 bfd_byte *contents;
4706 asection *section;
4707 bfd *abfd;
4708 bfd_vma place;
4709 uint32_t insn;
4710
4711 info = data->info;
4712 contents = data->contents;
4713 section = data->output_section;
4714
4715 htab = elf_aarch64_hash_table (info);
4716
4717 if (stub_entry->target_section != section
4718 || stub_entry->stub_type != aarch64_stub_erratum_843419_veneer)
4719 return TRUE;
4720
4721 insn = bfd_getl32 (contents + stub_entry->target_value);
4722 bfd_putl32 (insn,
4723 stub_entry->stub_sec->contents + stub_entry->stub_offset);
4724
4725 place = (section->output_section->vma + section->output_offset
4726 + stub_entry->adrp_offset);
4727 insn = bfd_getl32 (contents + stub_entry->adrp_offset);
4728
4729 if ((insn & AARCH64_ADRP_OP_MASK) != AARCH64_ADRP_OP)
4730 abort ();
4731
4732 bfd_signed_vma imm =
4733 (_bfd_aarch64_sign_extend
4734 ((bfd_vma) _bfd_aarch64_decode_adrp_imm (insn) << 12, 33)
4735 - (place & 0xfff));
4736
4737 if (htab->fix_erratum_843419_adr
4738 && (imm >= AARCH64_MIN_ADRP_IMM && imm <= AARCH64_MAX_ADRP_IMM))
4739 {
4740 insn = (_bfd_aarch64_reencode_adr_imm (AARCH64_ADR_OP, imm)
4741 | AARCH64_RT (insn));
4742 bfd_putl32 (insn, contents + stub_entry->adrp_offset);
4743 }
4744 else
4745 {
4746 bfd_vma veneered_insn_loc;
4747 bfd_vma veneer_entry_loc;
4748 bfd_signed_vma branch_offset;
4749 uint32_t branch_insn;
4750
4751 veneered_insn_loc = stub_entry->target_section->output_section->vma
4752 + stub_entry->target_section->output_offset
4753 + stub_entry->target_value;
4754 veneer_entry_loc = stub_entry->stub_sec->output_section->vma
4755 + stub_entry->stub_sec->output_offset
4756 + stub_entry->stub_offset;
4757 branch_offset = veneer_entry_loc - veneered_insn_loc;
4758
4759 abfd = stub_entry->target_section->owner;
4760 if (!aarch64_valid_branch_p (veneer_entry_loc, veneered_insn_loc))
4761 (*_bfd_error_handler)
4762 (_("%B: error: Erratum 843419 stub out "
4763 "of range (input file too large)"), abfd);
4764
4765 branch_insn = 0x14000000;
4766 branch_offset >>= 2;
4767 branch_offset &= 0x3ffffff;
4768 branch_insn |= branch_offset;
4769 bfd_putl32 (branch_insn, contents + stub_entry->target_value);
4770 }
4771 return TRUE;
4772}
4773
4774
68fcca92
JW
4775static bfd_boolean
4776elfNN_aarch64_write_section (bfd *output_bfd ATTRIBUTE_UNUSED,
4777 struct bfd_link_info *link_info,
4778 asection *sec,
4779 bfd_byte *contents)
4780
4781{
4782 struct elf_aarch64_link_hash_table *globals =
f872121a 4783 elf_aarch64_hash_table (link_info);
68fcca92
JW
4784
4785 if (globals == NULL)
4786 return FALSE;
4787
4788 /* Fix code to point to erratum 835769 stubs. */
4789 if (globals->fix_erratum_835769)
4790 {
4791 struct erratum_835769_branch_to_stub_data data;
4792
4106101c 4793 data.info = link_info;
68fcca92
JW
4794 data.output_section = sec;
4795 data.contents = contents;
4796 bfd_hash_traverse (&globals->stub_hash_table,
4797 make_branch_to_erratum_835769_stub, &data);
4798 }
4799
4106101c
MS
4800 if (globals->fix_erratum_843419)
4801 {
4802 struct erratum_835769_branch_to_stub_data data;
4803
4804 data.info = link_info;
4805 data.output_section = sec;
4806 data.contents = contents;
4807 bfd_hash_traverse (&globals->stub_hash_table,
4808 _bfd_aarch64_erratum_843419_branch_to_stub, &data);
4809 }
4810
68fcca92
JW
4811 return FALSE;
4812}
4813
a06ea964
NC
4814/* Perform a relocation as part of a final link. */
4815static bfd_reloc_status_type
cec5225b 4816elfNN_aarch64_final_link_relocate (reloc_howto_type *howto,
a06ea964
NC
4817 bfd *input_bfd,
4818 bfd *output_bfd,
4819 asection *input_section,
4820 bfd_byte *contents,
4821 Elf_Internal_Rela *rel,
4822 bfd_vma value,
4823 struct bfd_link_info *info,
4824 asection *sym_sec,
4825 struct elf_link_hash_entry *h,
4826 bfd_boolean *unresolved_reloc_p,
4827 bfd_boolean save_addend,
1419bbe5
WN
4828 bfd_vma *saved_addend,
4829 Elf_Internal_Sym *sym)
a06ea964 4830{
1419bbe5 4831 Elf_Internal_Shdr *symtab_hdr;
a06ea964 4832 unsigned int r_type = howto->type;
a6bb11b2
YZ
4833 bfd_reloc_code_real_type bfd_r_type
4834 = elfNN_aarch64_bfd_reloc_from_howto (howto);
4835 bfd_reloc_code_real_type new_bfd_r_type;
a06ea964
NC
4836 unsigned long r_symndx;
4837 bfd_byte *hit_data = contents + rel->r_offset;
b53b1bed 4838 bfd_vma place, off;
a06ea964 4839 bfd_signed_vma signed_addend;
cec5225b 4840 struct elf_aarch64_link_hash_table *globals;
a06ea964 4841 bfd_boolean weak_undef_p;
b53b1bed 4842 asection *base_got;
a06ea964 4843
cec5225b 4844 globals = elf_aarch64_hash_table (info);
a06ea964 4845
1419bbe5
WN
4846 symtab_hdr = &elf_symtab_hdr (input_bfd);
4847
a06ea964
NC
4848 BFD_ASSERT (is_aarch64_elf (input_bfd));
4849
cec5225b 4850 r_symndx = ELFNN_R_SYM (rel->r_info);
a06ea964
NC
4851
4852 /* It is possible to have linker relaxations on some TLS access
4853 models. Update our information here. */
a6bb11b2
YZ
4854 new_bfd_r_type = aarch64_tls_transition (input_bfd, info, r_type, h, r_symndx);
4855 if (new_bfd_r_type != bfd_r_type)
4856 {
4857 bfd_r_type = new_bfd_r_type;
4858 howto = elfNN_aarch64_howto_from_bfd_reloc (bfd_r_type);
4859 BFD_ASSERT (howto != NULL);
4860 r_type = howto->type;
4861 }
a06ea964
NC
4862
4863 place = input_section->output_section->vma
4864 + input_section->output_offset + rel->r_offset;
4865
4866 /* Get addend, accumulating the addend for consecutive relocs
4867 which refer to the same offset. */
4868 signed_addend = saved_addend ? *saved_addend : 0;
4869 signed_addend += rel->r_addend;
4870
4871 weak_undef_p = (h ? h->root.type == bfd_link_hash_undefweak
4872 : bfd_is_und_section (sym_sec));
a6bb11b2 4873
1419bbe5
WN
4874 /* Since STT_GNU_IFUNC symbol must go through PLT, we handle
4875 it here if it is defined in a non-shared object. */
4876 if (h != NULL
4877 && h->type == STT_GNU_IFUNC
4878 && h->def_regular)
4879 {
4880 asection *plt;
4881 const char *name;
99ad26cb 4882 bfd_vma addend = 0;
1419bbe5
WN
4883
4884 if ((input_section->flags & SEC_ALLOC) == 0
4885 || h->plt.offset == (bfd_vma) -1)
4886 abort ();
4887
4888 /* STT_GNU_IFUNC symbol must go through PLT. */
4889 plt = globals->root.splt ? globals->root.splt : globals->root.iplt;
4890 value = (plt->output_section->vma + plt->output_offset + h->plt.offset);
4891
4892 switch (bfd_r_type)
4893 {
4894 default:
4895 if (h->root.root.string)
4896 name = h->root.root.string;
4897 else
4898 name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
4899 NULL);
4900 (*_bfd_error_handler)
4901 (_("%B: relocation %s against STT_GNU_IFUNC "
4902 "symbol `%s' isn't handled by %s"), input_bfd,
4903 howto->name, name, __FUNCTION__);
4904 bfd_set_error (bfd_error_bad_value);
4905 return FALSE;
4906
4907 case BFD_RELOC_AARCH64_NN:
4908 if (rel->r_addend != 0)
4909 {
4910 if (h->root.root.string)
4911 name = h->root.root.string;
4912 else
4913 name = bfd_elf_sym_name (input_bfd, symtab_hdr,
4914 sym, NULL);
4915 (*_bfd_error_handler)
4916 (_("%B: relocation %s against STT_GNU_IFUNC "
4917 "symbol `%s' has non-zero addend: %d"),
4918 input_bfd, howto->name, name, rel->r_addend);
4919 bfd_set_error (bfd_error_bad_value);
4920 return FALSE;
4921 }
4922
4923 /* Generate dynamic relocation only when there is a
4924 non-GOT reference in a shared object. */
0e1862bb 4925 if (bfd_link_pic (info) && h->non_got_ref)
1419bbe5
WN
4926 {
4927 Elf_Internal_Rela outrel;
4928 asection *sreloc;
4929
4930 /* Need a dynamic relocation to get the real function
4931 address. */
4932 outrel.r_offset = _bfd_elf_section_offset (output_bfd,
4933 info,
4934 input_section,
4935 rel->r_offset);
4936 if (outrel.r_offset == (bfd_vma) -1
4937 || outrel.r_offset == (bfd_vma) -2)
4938 abort ();
4939
4940 outrel.r_offset += (input_section->output_section->vma
4941 + input_section->output_offset);
4942
4943 if (h->dynindx == -1
4944 || h->forced_local
0e1862bb 4945 || bfd_link_executable (info))
1419bbe5
WN
4946 {
4947 /* This symbol is resolved locally. */
4948 outrel.r_info = ELFNN_R_INFO (0, AARCH64_R (IRELATIVE));
4949 outrel.r_addend = (h->root.u.def.value
4950 + h->root.u.def.section->output_section->vma
4951 + h->root.u.def.section->output_offset);
4952 }
4953 else
4954 {
4955 outrel.r_info = ELFNN_R_INFO (h->dynindx, r_type);
4956 outrel.r_addend = 0;
4957 }
4958
4959 sreloc = globals->root.irelifunc;
4960 elf_append_rela (output_bfd, sreloc, &outrel);
4961
4962 /* If this reloc is against an external symbol, we
4963 do not want to fiddle with the addend. Otherwise,
4964 we need to include the symbol value so that it
4965 becomes an addend for the dynamic reloc. For an
4966 internal symbol, we have updated addend. */
4967 return bfd_reloc_ok;
4968 }
4969 /* FALLTHROUGH */
1419bbe5 4970 case BFD_RELOC_AARCH64_CALL26:
ce336788 4971 case BFD_RELOC_AARCH64_JUMP26:
1419bbe5
WN
4972 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
4973 signed_addend,
4974 weak_undef_p);
4975 return _bfd_aarch64_elf_put_addend (input_bfd, hit_data, bfd_r_type,
4976 howto, value);
1419bbe5
WN
4977 case BFD_RELOC_AARCH64_ADR_GOT_PAGE:
4978 case BFD_RELOC_AARCH64_GOT_LD_PREL19:
7018c030 4979 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
ce336788 4980 case BFD_RELOC_AARCH64_LD32_GOT_LO12_NC:
99ad26cb 4981 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
a2e1db00 4982 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
ce336788 4983 case BFD_RELOC_AARCH64_LD64_GOT_LO12_NC:
1419bbe5
WN
4984 base_got = globals->root.sgot;
4985 off = h->got.offset;
4986
4987 if (base_got == NULL)
4988 abort ();
4989
4990 if (off == (bfd_vma) -1)
4991 {
4992 bfd_vma plt_index;
4993
4994 /* We can't use h->got.offset here to save state, or
4995 even just remember the offset, as finish_dynamic_symbol
4996 would use that as offset into .got. */
4997
4998 if (globals->root.splt != NULL)
4999 {
b1ee0cc4
WN
5000 plt_index = ((h->plt.offset - globals->plt_header_size) /
5001 globals->plt_entry_size);
1419bbe5
WN
5002 off = (plt_index + 3) * GOT_ENTRY_SIZE;
5003 base_got = globals->root.sgotplt;
5004 }
5005 else
5006 {
5007 plt_index = h->plt.offset / globals->plt_entry_size;
5008 off = plt_index * GOT_ENTRY_SIZE;
5009 base_got = globals->root.igotplt;
5010 }
5011
5012 if (h->dynindx == -1
5013 || h->forced_local
5014 || info->symbolic)
5015 {
5016 /* This references the local definition. We must
5017 initialize this entry in the global offset table.
5018 Since the offset must always be a multiple of 8,
5019 we use the least significant bit to record
5020 whether we have initialized it already.
5021
5022 When doing a dynamic link, we create a .rela.got
5023 relocation entry to initialize the value. This
5024 is done in the finish_dynamic_symbol routine. */
5025 if ((off & 1) != 0)
5026 off &= ~1;
5027 else
5028 {
5029 bfd_put_NN (output_bfd, value,
5030 base_got->contents + off);
5031 /* Note that this is harmless as -1 | 1 still is -1. */
5032 h->got.offset |= 1;
5033 }
5034 }
5035 value = (base_got->output_section->vma
5036 + base_got->output_offset + off);
5037 }
5038 else
5039 value = aarch64_calculate_got_entry_vma (h, globals, info,
5040 value, output_bfd,
5041 unresolved_reloc_p);
a0becb89
RL
5042
5043 switch (bfd_r_type)
5044 {
5045 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
5046 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
5047 addend = (globals->root.sgot->output_section->vma
5048 + globals->root.sgot->output_offset);
5049 break;
a2e1db00
RL
5050 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
5051 value = (value - globals->root.sgot->output_section->vma
5052 - globals->root.sgot->output_offset);
a0becb89
RL
5053 default:
5054 break;
5055 }
5056
1419bbe5 5057 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
99ad26cb 5058 addend, weak_undef_p);
1419bbe5 5059 return _bfd_aarch64_elf_put_addend (input_bfd, hit_data, bfd_r_type, howto, value);
1419bbe5 5060 case BFD_RELOC_AARCH64_ADD_LO12:
ce336788 5061 case BFD_RELOC_AARCH64_ADR_HI21_PCREL:
1419bbe5
WN
5062 break;
5063 }
5064 }
5065
a6bb11b2 5066 switch (bfd_r_type)
a06ea964 5067 {
a6bb11b2
YZ
5068 case BFD_RELOC_AARCH64_NONE:
5069 case BFD_RELOC_AARCH64_TLSDESC_CALL:
a06ea964
NC
5070 *unresolved_reloc_p = FALSE;
5071 return bfd_reloc_ok;
5072
a6bb11b2 5073 case BFD_RELOC_AARCH64_NN:
a06ea964
NC
5074
5075 /* When generating a shared object or relocatable executable, these
5076 relocations are copied into the output file to be resolved at
5077 run time. */
0e1862bb
L
5078 if (((bfd_link_pic (info) == TRUE)
5079 || globals->root.is_relocatable_executable)
a06ea964
NC
5080 && (input_section->flags & SEC_ALLOC)
5081 && (h == NULL
5082 || ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
5083 || h->root.type != bfd_link_hash_undefweak))
5084 {
5085 Elf_Internal_Rela outrel;
5086 bfd_byte *loc;
5087 bfd_boolean skip, relocate;
5088 asection *sreloc;
5089
5090 *unresolved_reloc_p = FALSE;
5091
a06ea964
NC
5092 skip = FALSE;
5093 relocate = FALSE;
5094
5095 outrel.r_addend = signed_addend;
5096 outrel.r_offset =
5097 _bfd_elf_section_offset (output_bfd, info, input_section,
5098 rel->r_offset);
5099 if (outrel.r_offset == (bfd_vma) - 1)
5100 skip = TRUE;
5101 else if (outrel.r_offset == (bfd_vma) - 2)
5102 {
5103 skip = TRUE;
5104 relocate = TRUE;
5105 }
5106
5107 outrel.r_offset += (input_section->output_section->vma
5108 + input_section->output_offset);
5109
5110 if (skip)
5111 memset (&outrel, 0, sizeof outrel);
5112 else if (h != NULL
5113 && h->dynindx != -1
0e1862bb
L
5114 && (!bfd_link_pic (info)
5115 || !SYMBOLIC_BIND (info, h)
5116 || !h->def_regular))
cec5225b 5117 outrel.r_info = ELFNN_R_INFO (h->dynindx, r_type);
a06ea964
NC
5118 else
5119 {
5120 int symbol;
5121
5122 /* On SVR4-ish systems, the dynamic loader cannot
5123 relocate the text and data segments independently,
5124 so the symbol does not matter. */
5125 symbol = 0;
a6bb11b2 5126 outrel.r_info = ELFNN_R_INFO (symbol, AARCH64_R (RELATIVE));
a06ea964
NC
5127 outrel.r_addend += value;
5128 }
5129
1419bbe5
WN
5130 sreloc = elf_section_data (input_section)->sreloc;
5131 if (sreloc == NULL || sreloc->contents == NULL)
5132 return bfd_reloc_notsupported;
5133
5134 loc = sreloc->contents + sreloc->reloc_count++ * RELOC_SIZE (globals);
cec5225b 5135 bfd_elfNN_swap_reloca_out (output_bfd, &outrel, loc);
a06ea964 5136
1419bbe5 5137 if (sreloc->reloc_count * RELOC_SIZE (globals) > sreloc->size)
a06ea964
NC
5138 {
5139 /* Sanity to check that we have previously allocated
5140 sufficient space in the relocation section for the
5141 number of relocations we actually want to emit. */
5142 abort ();
5143 }
5144
5145 /* If this reloc is against an external symbol, we do not want to
5146 fiddle with the addend. Otherwise, we need to include the symbol
5147 value so that it becomes an addend for the dynamic reloc. */
5148 if (!relocate)
5149 return bfd_reloc_ok;
5150
5151 return _bfd_final_link_relocate (howto, input_bfd, input_section,
5152 contents, rel->r_offset, value,
5153 signed_addend);
5154 }
5155 else
5156 value += signed_addend;
5157 break;
5158
a6bb11b2 5159 case BFD_RELOC_AARCH64_CALL26:
ce336788 5160 case BFD_RELOC_AARCH64_JUMP26:
a06ea964
NC
5161 {
5162 asection *splt = globals->root.splt;
5163 bfd_boolean via_plt_p =
5164 splt != NULL && h != NULL && h->plt.offset != (bfd_vma) - 1;
5165
5166 /* A call to an undefined weak symbol is converted to a jump to
5167 the next instruction unless a PLT entry will be created.
5168 The jump to the next instruction is optimized as a NOP.
5169 Do the same for local undefined symbols. */
5170 if (weak_undef_p && ! via_plt_p)
5171 {
5172 bfd_putl32 (INSN_NOP, hit_data);
5173 return bfd_reloc_ok;
5174 }
5175
5176 /* If the call goes through a PLT entry, make sure to
5177 check distance to the right destination address. */
5178 if (via_plt_p)
07f9ddfe
JW
5179 value = (splt->output_section->vma
5180 + splt->output_offset + h->plt.offset);
5181
5182 /* Check if a stub has to be inserted because the destination
5183 is too far away. */
5184 struct elf_aarch64_stub_hash_entry *stub_entry = NULL;
5185 if (! aarch64_valid_branch_p (value, place))
5186 /* The target is out of reach, so redirect the branch to
5187 the local stub for this function. */
5188 stub_entry = elfNN_aarch64_get_stub_entry (input_section, sym_sec, h,
5189 rel, globals);
5190 if (stub_entry != NULL)
5191 value = (stub_entry->stub_offset
5192 + stub_entry->stub_sec->output_offset
5193 + stub_entry->stub_sec->output_section->vma);
a06ea964 5194 }
caed7120
YZ
5195 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5196 signed_addend, weak_undef_p);
07f9ddfe 5197 *unresolved_reloc_p = FALSE;
a06ea964
NC
5198 break;
5199
dcbd20eb
JW
5200 case BFD_RELOC_AARCH64_16_PCREL:
5201 case BFD_RELOC_AARCH64_32_PCREL:
5202 case BFD_RELOC_AARCH64_64_PCREL:
ce336788
JW
5203 case BFD_RELOC_AARCH64_ADR_HI21_NC_PCREL:
5204 case BFD_RELOC_AARCH64_ADR_HI21_PCREL:
5205 case BFD_RELOC_AARCH64_ADR_LO21_PCREL:
5206 case BFD_RELOC_AARCH64_LD_LO19_PCREL:
0e1862bb 5207 if (bfd_link_pic (info)
dcbd20eb
JW
5208 && (input_section->flags & SEC_ALLOC) != 0
5209 && (input_section->flags & SEC_READONLY) != 0
5210 && h != NULL
5211 && !h->def_regular)
5212 {
5213 int howto_index = bfd_r_type - BFD_RELOC_AARCH64_RELOC_START;
5214
5215 (*_bfd_error_handler)
5216 (_("%B: relocation %s against external symbol `%s' can not be used"
5217 " when making a shared object; recompile with -fPIC"),
5218 input_bfd, elfNN_aarch64_howto_table[howto_index].name,
5219 h->root.root.string);
5220 bfd_set_error (bfd_error_bad_value);
5221 return FALSE;
5222 }
5223
a6bb11b2
YZ
5224 case BFD_RELOC_AARCH64_16:
5225#if ARCH_SIZE == 64
5226 case BFD_RELOC_AARCH64_32:
5227#endif
5228 case BFD_RELOC_AARCH64_ADD_LO12:
a6bb11b2 5229 case BFD_RELOC_AARCH64_BRANCH19:
ce336788 5230 case BFD_RELOC_AARCH64_LDST128_LO12:
a6bb11b2
YZ
5231 case BFD_RELOC_AARCH64_LDST16_LO12:
5232 case BFD_RELOC_AARCH64_LDST32_LO12:
5233 case BFD_RELOC_AARCH64_LDST64_LO12:
ce336788 5234 case BFD_RELOC_AARCH64_LDST8_LO12:
a6bb11b2
YZ
5235 case BFD_RELOC_AARCH64_MOVW_G0:
5236 case BFD_RELOC_AARCH64_MOVW_G0_NC:
ce336788 5237 case BFD_RELOC_AARCH64_MOVW_G0_S:
a6bb11b2
YZ
5238 case BFD_RELOC_AARCH64_MOVW_G1:
5239 case BFD_RELOC_AARCH64_MOVW_G1_NC:
ce336788 5240 case BFD_RELOC_AARCH64_MOVW_G1_S:
a6bb11b2
YZ
5241 case BFD_RELOC_AARCH64_MOVW_G2:
5242 case BFD_RELOC_AARCH64_MOVW_G2_NC:
ce336788 5243 case BFD_RELOC_AARCH64_MOVW_G2_S:
a6bb11b2 5244 case BFD_RELOC_AARCH64_MOVW_G3:
a6bb11b2 5245 case BFD_RELOC_AARCH64_TSTBR14:
caed7120
YZ
5246 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5247 signed_addend, weak_undef_p);
a06ea964
NC
5248 break;
5249
a6bb11b2
YZ
5250 case BFD_RELOC_AARCH64_ADR_GOT_PAGE:
5251 case BFD_RELOC_AARCH64_GOT_LD_PREL19:
7018c030 5252 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
ce336788 5253 case BFD_RELOC_AARCH64_LD32_GOT_LO12_NC:
99ad26cb 5254 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
ce336788 5255 case BFD_RELOC_AARCH64_LD64_GOT_LO12_NC:
a06ea964
NC
5256 if (globals->root.sgot == NULL)
5257 BFD_ASSERT (h != NULL);
5258
5259 if (h != NULL)
5260 {
99ad26cb 5261 bfd_vma addend = 0;
a06ea964
NC
5262 value = aarch64_calculate_got_entry_vma (h, globals, info, value,
5263 output_bfd,
5264 unresolved_reloc_p);
7018c030
JW
5265 if (bfd_r_type == BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15
5266 || bfd_r_type == BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14)
99ad26cb
JW
5267 addend = (globals->root.sgot->output_section->vma
5268 + globals->root.sgot->output_offset);
caed7120 5269 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
99ad26cb 5270 addend, weak_undef_p);
a06ea964 5271 }
b53b1bed
JW
5272 else
5273 {
99ad26cb 5274 bfd_vma addend = 0;
b53b1bed
JW
5275 struct elf_aarch64_local_symbol *locals
5276 = elf_aarch64_locals (input_bfd);
5277
5278 if (locals == NULL)
5279 {
5280 int howto_index = bfd_r_type - BFD_RELOC_AARCH64_RELOC_START;
5281 (*_bfd_error_handler)
5282 (_("%B: Local symbol descriptor table be NULL when applying "
5283 "relocation %s against local symbol"),
5284 input_bfd, elfNN_aarch64_howto_table[howto_index].name);
5285 abort ();
5286 }
5287
5288 off = symbol_got_offset (input_bfd, h, r_symndx);
5289 base_got = globals->root.sgot;
5290 bfd_vma got_entry_addr = (base_got->output_section->vma
5291 + base_got->output_offset + off);
5292
5293 if (!symbol_got_offset_mark_p (input_bfd, h, r_symndx))
5294 {
5295 bfd_put_64 (output_bfd, value, base_got->contents + off);
5296
0e1862bb 5297 if (bfd_link_pic (info))
b53b1bed
JW
5298 {
5299 asection *s;
5300 Elf_Internal_Rela outrel;
5301
5302 /* For local symbol, we have done absolute relocation in static
5303 linking stageh. While for share library, we need to update
5304 the content of GOT entry according to the share objects
5305 loading base address. So we need to generate a
5306 R_AARCH64_RELATIVE reloc for dynamic linker. */
5307 s = globals->root.srelgot;
5308 if (s == NULL)
5309 abort ();
5310
5311 outrel.r_offset = got_entry_addr;
5312 outrel.r_info = ELFNN_R_INFO (0, AARCH64_R (RELATIVE));
5313 outrel.r_addend = value;
5314 elf_append_rela (output_bfd, s, &outrel);
5315 }
5316
5317 symbol_got_offset_mark (input_bfd, h, r_symndx);
5318 }
5319
5320 /* Update the relocation value to GOT entry addr as we have transformed
5321 the direct data access into indirect data access through GOT. */
5322 value = got_entry_addr;
99ad26cb 5323
7018c030
JW
5324 if (bfd_r_type == BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15
5325 || bfd_r_type == BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14)
99ad26cb
JW
5326 addend = base_got->output_section->vma + base_got->output_offset;
5327
5328 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5329 addend, weak_undef_p);
b53b1bed
JW
5330 }
5331
a06ea964
NC
5332 break;
5333
a2e1db00
RL
5334 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
5335 if (h != NULL)
5336 value = aarch64_calculate_got_entry_vma (h, globals, info, value,
5337 output_bfd,
5338 unresolved_reloc_p);
5339 else
5340 {
5341 struct elf_aarch64_local_symbol *locals
5342 = elf_aarch64_locals (input_bfd);
5343
5344 if (locals == NULL)
5345 {
5346 int howto_index = bfd_r_type - BFD_RELOC_AARCH64_RELOC_START;
5347 (*_bfd_error_handler)
5348 (_("%B: Local symbol descriptor table be NULL when applying "
5349 "relocation %s against local symbol"),
5350 input_bfd, elfNN_aarch64_howto_table[howto_index].name);
5351 abort ();
5352 }
5353
5354 off = symbol_got_offset (input_bfd, h, r_symndx);
5355 base_got = globals->root.sgot;
5356 if (base_got == NULL)
5357 abort ();
5358
5359 bfd_vma got_entry_addr = (base_got->output_section->vma
5360 + base_got->output_offset + off);
5361
5362 if (!symbol_got_offset_mark_p (input_bfd, h, r_symndx))
5363 {
5364 bfd_put_64 (output_bfd, value, base_got->contents + off);
5365
5366 if (bfd_link_pic (info))
5367 {
5368 asection *s;
5369 Elf_Internal_Rela outrel;
5370
5371 /* For local symbol, we have done absolute relocation in static
5372 linking stage. While for share library, we need to update
5373 the content of GOT entry according to the share objects
5374 loading base address. So we need to generate a
5375 R_AARCH64_RELATIVE reloc for dynamic linker. */
5376 s = globals->root.srelgot;
5377 if (s == NULL)
5378 abort ();
5379
5380 outrel.r_offset = got_entry_addr;
5381 outrel.r_info = ELFNN_R_INFO (0, AARCH64_R (RELATIVE));
5382 outrel.r_addend = value;
5383 elf_append_rela (output_bfd, s, &outrel);
5384 }
5385
5386 symbol_got_offset_mark (input_bfd, h, r_symndx);
5387 }
5388 }
5389
5390 /* Update the relocation value to GOT entry addr as we have transformed
5391 the direct data access into indirect data access through GOT. */
5392 value = symbol_got_offset (input_bfd, h, r_symndx);
5393 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5394 0, weak_undef_p);
5395 *unresolved_reloc_p = FALSE;
5396 break;
5397
ce336788 5398 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
a6bb11b2 5399 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
3c12b054 5400 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
a6bb11b2 5401 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
a6bb11b2 5402 case BFD_RELOC_AARCH64_TLSIE_LD32_GOTTPREL_LO12_NC:
ce336788 5403 case BFD_RELOC_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
043bf05a 5404 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
73f925cc 5405 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
f69e4920 5406 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
77a69ff8 5407 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
a06ea964
NC
5408 if (globals->root.sgot == NULL)
5409 return bfd_reloc_notsupported;
5410
5411 value = (symbol_got_offset (input_bfd, h, r_symndx)
5412 + globals->root.sgot->output_section->vma
f44a1f8e 5413 + globals->root.sgot->output_offset);
a06ea964 5414
caed7120
YZ
5415 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5416 0, weak_undef_p);
a06ea964
NC
5417 *unresolved_reloc_p = FALSE;
5418 break;
5419
6ffe9a1b 5420 case BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_HI12:
40fbed84 5421 case BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_LO12:
753999c1 5422 case BFD_RELOC_AARCH64_TLSLD_ADD_DTPREL_LO12_NC:
07c9aa07
JW
5423 case BFD_RELOC_AARCH64_TLSLD_LDST16_DTPREL_LO12:
5424 case BFD_RELOC_AARCH64_TLSLD_LDST16_DTPREL_LO12_NC:
5425 case BFD_RELOC_AARCH64_TLSLD_LDST32_DTPREL_LO12:
5426 case BFD_RELOC_AARCH64_TLSLD_LDST32_DTPREL_LO12_NC:
5427 case BFD_RELOC_AARCH64_TLSLD_LDST64_DTPREL_LO12:
5428 case BFD_RELOC_AARCH64_TLSLD_LDST64_DTPREL_LO12_NC:
5429 case BFD_RELOC_AARCH64_TLSLD_LDST8_DTPREL_LO12:
5430 case BFD_RELOC_AARCH64_TLSLD_LDST8_DTPREL_LO12_NC:
6ffe9a1b
JW
5431 case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G0:
5432 case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G0_NC:
5433 case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1:
5434 case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G1_NC:
5435 case BFD_RELOC_AARCH64_TLSLD_MOVW_DTPREL_G2:
40fbed84
JW
5436 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5437 signed_addend - dtpoff_base (info),
5438 weak_undef_p);
5439 break;
5440
a6bb11b2
YZ
5441 case BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_HI12:
5442 case BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12:
5443 case BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12_NC:
5444 case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0:
5445 case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0_NC:
5446 case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1:
5447 case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1_NC:
5448 case BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G2:
caed7120
YZ
5449 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5450 signed_addend - tpoff_base (info),
5451 weak_undef_p);
a06ea964
NC
5452 *unresolved_reloc_p = FALSE;
5453 break;
5454
7bcccb57
MS
5455 case BFD_RELOC_AARCH64_TLSDESC_ADD:
5456 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
a6bb11b2 5457 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
389b8029 5458 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
a6bb11b2 5459 case BFD_RELOC_AARCH64_TLSDESC_LD32_LO12_NC:
7bcccb57 5460 case BFD_RELOC_AARCH64_TLSDESC_LD64_LO12_NC:
a6bb11b2 5461 case BFD_RELOC_AARCH64_TLSDESC_LDR:
1ada945d 5462 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
a06ea964
NC
5463 if (globals->root.sgot == NULL)
5464 return bfd_reloc_notsupported;
a06ea964
NC
5465 value = (symbol_tlsdesc_got_offset (input_bfd, h, r_symndx)
5466 + globals->root.sgotplt->output_section->vma
f44a1f8e 5467 + globals->root.sgotplt->output_offset
a06ea964
NC
5468 + globals->sgotplt_jump_table_size);
5469
caed7120
YZ
5470 value = _bfd_aarch64_elf_resolve_relocation (bfd_r_type, place, value,
5471 0, weak_undef_p);
a06ea964
NC
5472 *unresolved_reloc_p = FALSE;
5473 break;
5474
5475 default:
5476 return bfd_reloc_notsupported;
5477 }
5478
5479 if (saved_addend)
5480 *saved_addend = value;
5481
5482 /* Only apply the final relocation in a sequence. */
5483 if (save_addend)
5484 return bfd_reloc_continue;
5485
caed7120
YZ
5486 return _bfd_aarch64_elf_put_addend (input_bfd, hit_data, bfd_r_type,
5487 howto, value);
a06ea964
NC
5488}
5489
5490/* Handle TLS relaxations. Relaxing is possible for symbols that use
5491 R_AARCH64_TLSDESC_ADR_{PAGE, LD64_LO12_NC, ADD_LO12_NC} during a static
5492 link.
5493
5494 Return bfd_reloc_ok if we're done, bfd_reloc_continue if the caller
5495 is to then call final_link_relocate. Return other values in the
5496 case of error. */
5497
5498static bfd_reloc_status_type
cec5225b 5499elfNN_aarch64_tls_relax (struct elf_aarch64_link_hash_table *globals,
a06ea964
NC
5500 bfd *input_bfd, bfd_byte *contents,
5501 Elf_Internal_Rela *rel, struct elf_link_hash_entry *h)
5502{
5503 bfd_boolean is_local = h == NULL;
cec5225b 5504 unsigned int r_type = ELFNN_R_TYPE (rel->r_info);
a06ea964
NC
5505 unsigned long insn;
5506
5507 BFD_ASSERT (globals && input_bfd && contents && rel);
5508
a6bb11b2 5509 switch (elfNN_aarch64_bfd_reloc_from_type (r_type))
a06ea964 5510 {
a6bb11b2 5511 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
ce336788 5512 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
a06ea964
NC
5513 if (is_local)
5514 {
5515 /* GD->LE relaxation:
5516 adrp x0, :tlsgd:var => movz x0, :tprel_g1:var
5517 or
5518 adrp x0, :tlsdesc:var => movz x0, :tprel_g1:var
5519 */
5520 bfd_putl32 (0xd2a00000, contents + rel->r_offset);
5521 return bfd_reloc_continue;
5522 }
5523 else
5524 {
5525 /* GD->IE relaxation:
5526 adrp x0, :tlsgd:var => adrp x0, :gottprel:var
5527 or
5528 adrp x0, :tlsdesc:var => adrp x0, :gottprel:var
5529 */
a06ea964
NC
5530 return bfd_reloc_continue;
5531 }
5532
389b8029
MS
5533 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
5534 BFD_ASSERT (0);
5535 break;
5536
1ada945d
MS
5537 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
5538 if (is_local)
5539 {
5540 /* Tiny TLSDESC->LE relaxation:
5541 ldr x1, :tlsdesc:var => movz x0, #:tprel_g1:var
5542 adr x0, :tlsdesc:var => movk x0, #:tprel_g0_nc:var
5543 .tlsdesccall var
5544 blr x1 => nop
5545 */
5546 BFD_ASSERT (ELFNN_R_TYPE (rel[1].r_info) == AARCH64_R (TLSDESC_ADR_PREL21));
5547 BFD_ASSERT (ELFNN_R_TYPE (rel[2].r_info) == AARCH64_R (TLSDESC_CALL));
5548
5549 rel[1].r_info = ELFNN_R_INFO (ELFNN_R_SYM (rel->r_info),
5550 AARCH64_R (TLSLE_MOVW_TPREL_G0_NC));
5551 rel[2].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
5552
5553 bfd_putl32 (0xd2a00000, contents + rel->r_offset);
5554 bfd_putl32 (0xf2800000, contents + rel->r_offset + 4);
5555 bfd_putl32 (INSN_NOP, contents + rel->r_offset + 8);
5556 return bfd_reloc_continue;
5557 }
5558 else
5559 {
5560 /* Tiny TLSDESC->IE relaxation:
5561 ldr x1, :tlsdesc:var => ldr x0, :gottprel:var
5562 adr x0, :tlsdesc:var => nop
5563 .tlsdesccall var
5564 blr x1 => nop
5565 */
5566 BFD_ASSERT (ELFNN_R_TYPE (rel[1].r_info) == AARCH64_R (TLSDESC_ADR_PREL21));
5567 BFD_ASSERT (ELFNN_R_TYPE (rel[2].r_info) == AARCH64_R (TLSDESC_CALL));
5568
5569 rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
5570 rel[2].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
5571
5572 bfd_putl32 (0x58000000, contents + rel->r_offset);
5573 bfd_putl32 (INSN_NOP, contents + rel->r_offset + 4);
5574 bfd_putl32 (INSN_NOP, contents + rel->r_offset + 8);
5575 return bfd_reloc_continue;
5576 }
5577
3c12b054
MS
5578 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
5579 if (is_local)
5580 {
5581 /* Tiny GD->LE relaxation:
5582 adr x0, :tlsgd:var => mrs x1, tpidr_el0
5583 bl __tls_get_addr => add x0, x1, #:tprel_hi12:x, lsl #12
5584 nop => add x0, x0, #:tprel_lo12_nc:x
5585 */
5586
5587 /* First kill the tls_get_addr reloc on the bl instruction. */
5588 BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
5589
5590 bfd_putl32 (0xd53bd041, contents + rel->r_offset + 0);
5591 bfd_putl32 (0x91400020, contents + rel->r_offset + 4);
5592 bfd_putl32 (0x91000000, contents + rel->r_offset + 8);
5593
5594 rel[1].r_info = ELFNN_R_INFO (ELFNN_R_SYM (rel->r_info),
5595 AARCH64_R (TLSLE_ADD_TPREL_LO12_NC));
5596 rel[1].r_offset = rel->r_offset + 8;
5597
5598 /* Move the current relocation to the second instruction in
5599 the sequence. */
5600 rel->r_offset += 4;
5601 rel->r_info = ELFNN_R_INFO (ELFNN_R_SYM (rel->r_info),
5602 AARCH64_R (TLSLE_ADD_TPREL_HI12));
5603 return bfd_reloc_continue;
5604 }
5605 else
5606 {
5607 /* Tiny GD->IE relaxation:
5608 adr x0, :tlsgd:var => ldr x0, :gottprel:var
5609 bl __tls_get_addr => mrs x1, tpidr_el0
5610 nop => add x0, x0, x1
5611 */
5612
5613 /* First kill the tls_get_addr reloc on the bl instruction. */
5614 BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
5615 rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
5616
5617 bfd_putl32 (0x58000000, contents + rel->r_offset);
5618 bfd_putl32 (0xd53bd041, contents + rel->r_offset + 4);
5619 bfd_putl32 (0x8b000020, contents + rel->r_offset + 8);
5620 return bfd_reloc_continue;
5621 }
5622
043bf05a
MS
5623 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
5624 return bfd_reloc_continue;
5625
a6bb11b2 5626 case BFD_RELOC_AARCH64_TLSDESC_LDNN_LO12_NC:
a06ea964
NC
5627 if (is_local)
5628 {
5629 /* GD->LE relaxation:
5630 ldr xd, [x0, #:tlsdesc_lo12:var] => movk x0, :tprel_g0_nc:var
5631 */
5632 bfd_putl32 (0xf2800000, contents + rel->r_offset);
5633 return bfd_reloc_continue;
5634 }
5635 else
5636 {
5637 /* GD->IE relaxation:
5638 ldr xd, [x0, #:tlsdesc_lo12:var] => ldr x0, [x0, #:gottprel_lo12:var]
5639 */
5640 insn = bfd_getl32 (contents + rel->r_offset);
fa85fb9a 5641 insn &= 0xffffffe0;
a06ea964
NC
5642 bfd_putl32 (insn, contents + rel->r_offset);
5643 return bfd_reloc_continue;
5644 }
5645
a6bb11b2 5646 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
a06ea964
NC
5647 if (is_local)
5648 {
5649 /* GD->LE relaxation
5650 add x0, #:tlsgd_lo12:var => movk x0, :tprel_g0_nc:var
5651 bl __tls_get_addr => mrs x1, tpidr_el0
5652 nop => add x0, x1, x0
5653 */
5654
5655 /* First kill the tls_get_addr reloc on the bl instruction. */
5656 BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
cec5225b 5657 rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
a06ea964
NC
5658
5659 bfd_putl32 (0xf2800000, contents + rel->r_offset);
5660 bfd_putl32 (0xd53bd041, contents + rel->r_offset + 4);
5661 bfd_putl32 (0x8b000020, contents + rel->r_offset + 8);
5662 return bfd_reloc_continue;
5663 }
5664 else
5665 {
5666 /* GD->IE relaxation
5667 ADD x0, #:tlsgd_lo12:var => ldr x0, [x0, #:gottprel_lo12:var]
5668 BL __tls_get_addr => mrs x1, tpidr_el0
5669 R_AARCH64_CALL26
5670 NOP => add x0, x1, x0
5671 */
5672
a6bb11b2 5673 BFD_ASSERT (ELFNN_R_TYPE (rel[1].r_info) == AARCH64_R (CALL26));
a06ea964
NC
5674
5675 /* Remove the relocation on the BL instruction. */
cec5225b 5676 rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
a06ea964
NC
5677
5678 bfd_putl32 (0xf9400000, contents + rel->r_offset);
5679
5680 /* We choose to fixup the BL and NOP instructions using the
5681 offset from the second relocation to allow flexibility in
5682 scheduling instructions between the ADD and BL. */
5683 bfd_putl32 (0xd53bd041, contents + rel[1].r_offset);
5684 bfd_putl32 (0x8b000020, contents + rel[1].r_offset + 4);
5685 return bfd_reloc_continue;
5686 }
5687
a6bb11b2
YZ
5688 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
5689 case BFD_RELOC_AARCH64_TLSDESC_CALL:
a06ea964
NC
5690 /* GD->IE/LE relaxation:
5691 add x0, x0, #:tlsdesc_lo12:var => nop
5692 blr xd => nop
5693 */
5694 bfd_putl32 (INSN_NOP, contents + rel->r_offset);
5695 return bfd_reloc_ok;
5696
a6bb11b2 5697 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
a06ea964
NC
5698 /* IE->LE relaxation:
5699 adrp xd, :gottprel:var => movz xd, :tprel_g1:var
5700 */
5701 if (is_local)
5702 {
5703 insn = bfd_getl32 (contents + rel->r_offset);
5704 bfd_putl32 (0xd2a00000 | (insn & 0x1f), contents + rel->r_offset);
5705 }
5706 return bfd_reloc_continue;
5707
a6bb11b2 5708 case BFD_RELOC_AARCH64_TLSIE_LDNN_GOTTPREL_LO12_NC:
a06ea964
NC
5709 /* IE->LE relaxation:
5710 ldr xd, [xm, #:gottprel_lo12:var] => movk xd, :tprel_g0_nc:var
5711 */
5712 if (is_local)
5713 {
5714 insn = bfd_getl32 (contents + rel->r_offset);
5715 bfd_putl32 (0xf2800000 | (insn & 0x1f), contents + rel->r_offset);
5716 }
5717 return bfd_reloc_continue;
5718
259364ad
JW
5719 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
5720 /* LD->LE relaxation (tiny):
5721 adr x0, :tlsldm:x => mrs x0, tpidr_el0
5722 bl __tls_get_addr => add x0, x0, TCB_SIZE
5723 */
5724 if (is_local)
5725 {
5726 BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
5727 BFD_ASSERT (ELFNN_R_TYPE (rel[1].r_info) == AARCH64_R (CALL26));
5728 /* No need of CALL26 relocation for tls_get_addr. */
5729 rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
5730 bfd_putl32 (0xd53bd040, contents + rel->r_offset + 0);
5731 bfd_putl32 (0x91004000, contents + rel->r_offset + 4);
5732 return bfd_reloc_ok;
5733 }
5734 return bfd_reloc_continue;
5735
5736 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
5737 /* LD->LE relaxation (small):
5738 adrp x0, :tlsldm:x => mrs x0, tpidr_el0
5739 */
5740 if (is_local)
5741 {
5742 bfd_putl32 (0xd53bd040, contents + rel->r_offset);
5743 return bfd_reloc_ok;
5744 }
5745 return bfd_reloc_continue;
5746
5747 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
5748 /* LD->LE relaxation (small):
5749 add x0, #:tlsldm_lo12:x => add x0, x0, TCB_SIZE
5750 bl __tls_get_addr => nop
5751 */
5752 if (is_local)
5753 {
5754 BFD_ASSERT (rel->r_offset + 4 == rel[1].r_offset);
5755 BFD_ASSERT (ELFNN_R_TYPE (rel[1].r_info) == AARCH64_R (CALL26));
5756 /* No need of CALL26 relocation for tls_get_addr. */
5757 rel[1].r_info = ELFNN_R_INFO (STN_UNDEF, R_AARCH64_NONE);
5758 bfd_putl32 (0x91004000, contents + rel->r_offset + 0);
5759 bfd_putl32 (0xd503201f, contents + rel->r_offset + 4);
5760 return bfd_reloc_ok;
5761 }
5762 return bfd_reloc_continue;
5763
a06ea964
NC
5764 default:
5765 return bfd_reloc_continue;
5766 }
5767
5768 return bfd_reloc_ok;
5769}
5770
5771/* Relocate an AArch64 ELF section. */
5772
5773static bfd_boolean
cec5225b 5774elfNN_aarch64_relocate_section (bfd *output_bfd,
a06ea964
NC
5775 struct bfd_link_info *info,
5776 bfd *input_bfd,
5777 asection *input_section,
5778 bfd_byte *contents,
5779 Elf_Internal_Rela *relocs,
5780 Elf_Internal_Sym *local_syms,
5781 asection **local_sections)
5782{
5783 Elf_Internal_Shdr *symtab_hdr;
5784 struct elf_link_hash_entry **sym_hashes;
5785 Elf_Internal_Rela *rel;
5786 Elf_Internal_Rela *relend;
5787 const char *name;
cec5225b 5788 struct elf_aarch64_link_hash_table *globals;
a06ea964
NC
5789 bfd_boolean save_addend = FALSE;
5790 bfd_vma addend = 0;
5791
cec5225b 5792 globals = elf_aarch64_hash_table (info);
a06ea964
NC
5793
5794 symtab_hdr = &elf_symtab_hdr (input_bfd);
5795 sym_hashes = elf_sym_hashes (input_bfd);
5796
5797 rel = relocs;
5798 relend = relocs + input_section->reloc_count;
5799 for (; rel < relend; rel++)
5800 {
5801 unsigned int r_type;
a6bb11b2
YZ
5802 bfd_reloc_code_real_type bfd_r_type;
5803 bfd_reloc_code_real_type relaxed_bfd_r_type;
a06ea964
NC
5804 reloc_howto_type *howto;
5805 unsigned long r_symndx;
5806 Elf_Internal_Sym *sym;
5807 asection *sec;
5808 struct elf_link_hash_entry *h;
5809 bfd_vma relocation;
5810 bfd_reloc_status_type r;
5811 arelent bfd_reloc;
5812 char sym_type;
5813 bfd_boolean unresolved_reloc = FALSE;
5814 char *error_message = NULL;
5815
cec5225b
YZ
5816 r_symndx = ELFNN_R_SYM (rel->r_info);
5817 r_type = ELFNN_R_TYPE (rel->r_info);
a06ea964 5818
cec5225b 5819 bfd_reloc.howto = elfNN_aarch64_howto_from_type (r_type);
a06ea964
NC
5820 howto = bfd_reloc.howto;
5821
7fcfd62d
NC
5822 if (howto == NULL)
5823 {
5824 (*_bfd_error_handler)
5825 (_("%B: unrecognized relocation (0x%x) in section `%A'"),
5826 input_bfd, input_section, r_type);
5827 return FALSE;
5828 }
a6bb11b2 5829 bfd_r_type = elfNN_aarch64_bfd_reloc_from_howto (howto);
7fcfd62d 5830
a06ea964
NC
5831 h = NULL;
5832 sym = NULL;
5833 sec = NULL;
5834
5835 if (r_symndx < symtab_hdr->sh_info)
5836 {
5837 sym = local_syms + r_symndx;
cec5225b 5838 sym_type = ELFNN_ST_TYPE (sym->st_info);
a06ea964
NC
5839 sec = local_sections[r_symndx];
5840
5841 /* An object file might have a reference to a local
5842 undefined symbol. This is a daft object file, but we
5843 should at least do something about it. */
5844 if (r_type != R_AARCH64_NONE && r_type != R_AARCH64_NULL
5845 && bfd_is_und_section (sec)
5846 && ELF_ST_BIND (sym->st_info) != STB_WEAK)
5847 {
5848 if (!info->callbacks->undefined_symbol
5849 (info, bfd_elf_string_from_elf_section
5850 (input_bfd, symtab_hdr->sh_link, sym->st_name),
5851 input_bfd, input_section, rel->r_offset, TRUE))
5852 return FALSE;
5853 }
5854
a06ea964 5855 relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
1419bbe5
WN
5856
5857 /* Relocate against local STT_GNU_IFUNC symbol. */
0e1862bb 5858 if (!bfd_link_relocatable (info)
1419bbe5
WN
5859 && ELF_ST_TYPE (sym->st_info) == STT_GNU_IFUNC)
5860 {
5861 h = elfNN_aarch64_get_local_sym_hash (globals, input_bfd,
5862 rel, FALSE);
5863 if (h == NULL)
5864 abort ();
5865
5866 /* Set STT_GNU_IFUNC symbol value. */
5867 h->root.u.def.value = sym->st_value;
5868 h->root.u.def.section = sec;
5869 }
a06ea964
NC
5870 }
5871 else
5872 {
62d887d4 5873 bfd_boolean warned, ignored;
a06ea964
NC
5874
5875 RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
5876 r_symndx, symtab_hdr, sym_hashes,
5877 h, sec, relocation,
62d887d4 5878 unresolved_reloc, warned, ignored);
a06ea964
NC
5879
5880 sym_type = h->type;
5881 }
5882
5883 if (sec != NULL && discarded_section (sec))
5884 RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
5885 rel, 1, relend, howto, 0, contents);
5886
0e1862bb 5887 if (bfd_link_relocatable (info))
2e0488d3 5888 continue;
a06ea964
NC
5889
5890 if (h != NULL)
5891 name = h->root.root.string;
5892 else
5893 {
5894 name = (bfd_elf_string_from_elf_section
5895 (input_bfd, symtab_hdr->sh_link, sym->st_name));
5896 if (name == NULL || *name == '\0')
5897 name = bfd_section_name (input_bfd, sec);
5898 }
5899
5900 if (r_symndx != 0
5901 && r_type != R_AARCH64_NONE
5902 && r_type != R_AARCH64_NULL
5903 && (h == NULL
5904 || h->root.type == bfd_link_hash_defined
5905 || h->root.type == bfd_link_hash_defweak)
a6bb11b2 5906 && IS_AARCH64_TLS_RELOC (bfd_r_type) != (sym_type == STT_TLS))
a06ea964
NC
5907 {
5908 (*_bfd_error_handler)
5909 ((sym_type == STT_TLS
5910 ? _("%B(%A+0x%lx): %s used with TLS symbol %s")
5911 : _("%B(%A+0x%lx): %s used with non-TLS symbol %s")),
5912 input_bfd,
5913 input_section, (long) rel->r_offset, howto->name, name);
5914 }
5915
a06ea964
NC
5916 /* We relax only if we can see that there can be a valid transition
5917 from a reloc type to another.
cec5225b 5918 We call elfNN_aarch64_final_link_relocate unless we're completely
a06ea964
NC
5919 done, i.e., the relaxation produced the final output we want. */
5920
a6bb11b2
YZ
5921 relaxed_bfd_r_type = aarch64_tls_transition (input_bfd, info, r_type,
5922 h, r_symndx);
5923 if (relaxed_bfd_r_type != bfd_r_type)
a06ea964 5924 {
a6bb11b2
YZ
5925 bfd_r_type = relaxed_bfd_r_type;
5926 howto = elfNN_aarch64_howto_from_bfd_reloc (bfd_r_type);
5927 BFD_ASSERT (howto != NULL);
5928 r_type = howto->type;
cec5225b 5929 r = elfNN_aarch64_tls_relax (globals, input_bfd, contents, rel, h);
a06ea964
NC
5930 unresolved_reloc = 0;
5931 }
5932 else
5933 r = bfd_reloc_continue;
5934
5935 /* There may be multiple consecutive relocations for the
5936 same offset. In that case we are supposed to treat the
5937 output of each relocation as the addend for the next. */
5938 if (rel + 1 < relend
5939 && rel->r_offset == rel[1].r_offset
cec5225b
YZ
5940 && ELFNN_R_TYPE (rel[1].r_info) != R_AARCH64_NONE
5941 && ELFNN_R_TYPE (rel[1].r_info) != R_AARCH64_NULL)
a06ea964
NC
5942 save_addend = TRUE;
5943 else
5944 save_addend = FALSE;
5945
5946 if (r == bfd_reloc_continue)
cec5225b 5947 r = elfNN_aarch64_final_link_relocate (howto, input_bfd, output_bfd,
a06ea964
NC
5948 input_section, contents, rel,
5949 relocation, info, sec,
5950 h, &unresolved_reloc,
1419bbe5 5951 save_addend, &addend, sym);
a06ea964 5952
a6bb11b2 5953 switch (elfNN_aarch64_bfd_reloc_from_type (r_type))
a06ea964 5954 {
ce336788 5955 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
a6bb11b2 5956 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
3c12b054 5957 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
73f925cc 5958 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
f69e4920 5959 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
77a69ff8 5960 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
a06ea964
NC
5961 if (! symbol_got_offset_mark_p (input_bfd, h, r_symndx))
5962 {
5963 bfd_boolean need_relocs = FALSE;
5964 bfd_byte *loc;
5965 int indx;
5966 bfd_vma off;
5967
5968 off = symbol_got_offset (input_bfd, h, r_symndx);
5969 indx = h && h->dynindx != -1 ? h->dynindx : 0;
5970
5971 need_relocs =
0e1862bb 5972 (bfd_link_pic (info) || indx != 0) &&
a06ea964
NC
5973 (h == NULL
5974 || ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
5975 || h->root.type != bfd_link_hash_undefweak);
5976
5977 BFD_ASSERT (globals->root.srelgot != NULL);
5978
5979 if (need_relocs)
5980 {
5981 Elf_Internal_Rela rela;
a6bb11b2 5982 rela.r_info = ELFNN_R_INFO (indx, AARCH64_R (TLS_DTPMOD));
a06ea964
NC
5983 rela.r_addend = 0;
5984 rela.r_offset = globals->root.sgot->output_section->vma +
5985 globals->root.sgot->output_offset + off;
5986
5987
5988 loc = globals->root.srelgot->contents;
5989 loc += globals->root.srelgot->reloc_count++
5990 * RELOC_SIZE (htab);
cec5225b 5991 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
a06ea964 5992
f69e4920
JW
5993 bfd_reloc_code_real_type real_type =
5994 elfNN_aarch64_bfd_reloc_from_type (r_type);
5995
5996 if (real_type == BFD_RELOC_AARCH64_TLSLD_ADR_PREL21
73f925cc
JW
5997 || real_type == BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21
5998 || real_type == BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC)
77a69ff8
JW
5999 {
6000 /* For local dynamic, don't generate DTPREL in any case.
6001 Initialize the DTPREL slot into zero, so we get module
6002 base address when invoke runtime TLS resolver. */
6003 bfd_put_NN (output_bfd, 0,
6004 globals->root.sgot->contents + off
6005 + GOT_ENTRY_SIZE);
6006 }
6007 else if (indx == 0)
a06ea964 6008 {
cec5225b 6009 bfd_put_NN (output_bfd,
a06ea964
NC
6010 relocation - dtpoff_base (info),
6011 globals->root.sgot->contents + off
6012 + GOT_ENTRY_SIZE);
6013 }
6014 else
6015 {
6016 /* This TLS symbol is global. We emit a
6017 relocation to fixup the tls offset at load
6018 time. */
6019 rela.r_info =
a6bb11b2 6020 ELFNN_R_INFO (indx, AARCH64_R (TLS_DTPREL));
a06ea964
NC
6021 rela.r_addend = 0;
6022 rela.r_offset =
6023 (globals->root.sgot->output_section->vma
6024 + globals->root.sgot->output_offset + off
6025 + GOT_ENTRY_SIZE);
6026
6027 loc = globals->root.srelgot->contents;
6028 loc += globals->root.srelgot->reloc_count++
6029 * RELOC_SIZE (globals);
cec5225b
YZ
6030 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
6031 bfd_put_NN (output_bfd, (bfd_vma) 0,
a06ea964
NC
6032 globals->root.sgot->contents + off
6033 + GOT_ENTRY_SIZE);
6034 }
6035 }
6036 else
6037 {
cec5225b 6038 bfd_put_NN (output_bfd, (bfd_vma) 1,
a06ea964 6039 globals->root.sgot->contents + off);
cec5225b 6040 bfd_put_NN (output_bfd,
a06ea964
NC
6041 relocation - dtpoff_base (info),
6042 globals->root.sgot->contents + off
6043 + GOT_ENTRY_SIZE);
6044 }
6045
6046 symbol_got_offset_mark (input_bfd, h, r_symndx);
6047 }
6048 break;
6049
a6bb11b2
YZ
6050 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
6051 case BFD_RELOC_AARCH64_TLSIE_LDNN_GOTTPREL_LO12_NC:
043bf05a 6052 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
a06ea964
NC
6053 if (! symbol_got_offset_mark_p (input_bfd, h, r_symndx))
6054 {
6055 bfd_boolean need_relocs = FALSE;
6056 bfd_byte *loc;
6057 int indx;
6058 bfd_vma off;
6059
6060 off = symbol_got_offset (input_bfd, h, r_symndx);
6061
6062 indx = h && h->dynindx != -1 ? h->dynindx : 0;
6063
6064 need_relocs =
0e1862bb 6065 (bfd_link_pic (info) || indx != 0) &&
a06ea964
NC
6066 (h == NULL
6067 || ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
6068 || h->root.type != bfd_link_hash_undefweak);
6069
6070 BFD_ASSERT (globals->root.srelgot != NULL);
6071
6072 if (need_relocs)
6073 {
6074 Elf_Internal_Rela rela;
6075
6076 if (indx == 0)
6077 rela.r_addend = relocation - dtpoff_base (info);
6078 else
6079 rela.r_addend = 0;
6080
a6bb11b2 6081 rela.r_info = ELFNN_R_INFO (indx, AARCH64_R (TLS_TPREL));
a06ea964
NC
6082 rela.r_offset = globals->root.sgot->output_section->vma +
6083 globals->root.sgot->output_offset + off;
6084
6085 loc = globals->root.srelgot->contents;
6086 loc += globals->root.srelgot->reloc_count++
6087 * RELOC_SIZE (htab);
6088
cec5225b 6089 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
a06ea964 6090
cec5225b 6091 bfd_put_NN (output_bfd, rela.r_addend,
a06ea964
NC
6092 globals->root.sgot->contents + off);
6093 }
6094 else
cec5225b 6095 bfd_put_NN (output_bfd, relocation - tpoff_base (info),
a06ea964
NC
6096 globals->root.sgot->contents + off);
6097
6098 symbol_got_offset_mark (input_bfd, h, r_symndx);
6099 }
6100 break;
6101
7bcccb57 6102 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
a6bb11b2 6103 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
389b8029 6104 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
a6bb11b2 6105 case BFD_RELOC_AARCH64_TLSDESC_LDNN_LO12_NC:
1ada945d 6106 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
a06ea964
NC
6107 if (! symbol_tlsdesc_got_offset_mark_p (input_bfd, h, r_symndx))
6108 {
6109 bfd_boolean need_relocs = FALSE;
6110 int indx = h && h->dynindx != -1 ? h->dynindx : 0;
6111 bfd_vma off = symbol_tlsdesc_got_offset (input_bfd, h, r_symndx);
6112
6113 need_relocs = (h == NULL
6114 || ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
6115 || h->root.type != bfd_link_hash_undefweak);
6116
6117 BFD_ASSERT (globals->root.srelgot != NULL);
6118 BFD_ASSERT (globals->root.sgot != NULL);
6119
6120 if (need_relocs)
6121 {
6122 bfd_byte *loc;
6123 Elf_Internal_Rela rela;
a6bb11b2
YZ
6124 rela.r_info = ELFNN_R_INFO (indx, AARCH64_R (TLSDESC));
6125
a06ea964
NC
6126 rela.r_addend = 0;
6127 rela.r_offset = (globals->root.sgotplt->output_section->vma
6128 + globals->root.sgotplt->output_offset
6129 + off + globals->sgotplt_jump_table_size);
6130
6131 if (indx == 0)
6132 rela.r_addend = relocation - dtpoff_base (info);
6133
6134 /* Allocate the next available slot in the PLT reloc
6135 section to hold our R_AARCH64_TLSDESC, the next
6136 available slot is determined from reloc_count,
6137 which we step. But note, reloc_count was
6138 artifically moved down while allocating slots for
6139 real PLT relocs such that all of the PLT relocs
6140 will fit above the initial reloc_count and the
6141 extra stuff will fit below. */
6142 loc = globals->root.srelplt->contents;
6143 loc += globals->root.srelplt->reloc_count++
6144 * RELOC_SIZE (globals);
6145
cec5225b 6146 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
a06ea964 6147
cec5225b 6148 bfd_put_NN (output_bfd, (bfd_vma) 0,
a06ea964
NC
6149 globals->root.sgotplt->contents + off +
6150 globals->sgotplt_jump_table_size);
cec5225b 6151 bfd_put_NN (output_bfd, (bfd_vma) 0,
a06ea964
NC
6152 globals->root.sgotplt->contents + off +
6153 globals->sgotplt_jump_table_size +
6154 GOT_ENTRY_SIZE);
6155 }
6156
6157 symbol_tlsdesc_got_offset_mark (input_bfd, h, r_symndx);
6158 }
6159 break;
a6bb11b2
YZ
6160 default:
6161 break;
a06ea964
NC
6162 }
6163
6164 if (!save_addend)
6165 addend = 0;
6166
6167
6168 /* Dynamic relocs are not propagated for SEC_DEBUGGING sections
6169 because such sections are not SEC_ALLOC and thus ld.so will
6170 not process them. */
6171 if (unresolved_reloc
6172 && !((input_section->flags & SEC_DEBUGGING) != 0
6173 && h->def_dynamic)
6174 && _bfd_elf_section_offset (output_bfd, info, input_section,
6175 +rel->r_offset) != (bfd_vma) - 1)
6176 {
6177 (*_bfd_error_handler)
6178 (_
6179 ("%B(%A+0x%lx): unresolvable %s relocation against symbol `%s'"),
6180 input_bfd, input_section, (long) rel->r_offset, howto->name,
6181 h->root.root.string);
6182 return FALSE;
6183 }
6184
6185 if (r != bfd_reloc_ok && r != bfd_reloc_continue)
6186 {
c674f5cd
JW
6187 bfd_reloc_code_real_type real_r_type
6188 = elfNN_aarch64_bfd_reloc_from_type (r_type);
6189
a06ea964
NC
6190 switch (r)
6191 {
6192 case bfd_reloc_overflow:
fdc3b1b1
JW
6193 if (!(*info->callbacks->reloc_overflow)
6194 (info, (h ? &h->root : NULL), name, howto->name, (bfd_vma) 0,
6195 input_bfd, input_section, rel->r_offset))
a06ea964 6196 return FALSE;
c674f5cd
JW
6197 if (real_r_type == BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15
6198 || real_r_type == BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14)
6199 {
6200 (*info->callbacks->warning)
6201 (info,
6202 _("Too many GOT entries for -fpic, "
6203 "please recompile with -fPIC"),
6204 name, input_bfd, input_section, rel->r_offset);
6205 return FALSE;
6206 }
a06ea964
NC
6207 break;
6208
6209 case bfd_reloc_undefined:
6210 if (!((*info->callbacks->undefined_symbol)
6211 (info, name, input_bfd, input_section,
6212 rel->r_offset, TRUE)))
6213 return FALSE;
6214 break;
6215
6216 case bfd_reloc_outofrange:
6217 error_message = _("out of range");
6218 goto common_error;
6219
6220 case bfd_reloc_notsupported:
6221 error_message = _("unsupported relocation");
6222 goto common_error;
6223
6224 case bfd_reloc_dangerous:
6225 /* error_message should already be set. */
6226 goto common_error;
6227
6228 default:
6229 error_message = _("unknown error");
6230 /* Fall through. */
6231
6232 common_error:
6233 BFD_ASSERT (error_message != NULL);
6234 if (!((*info->callbacks->reloc_dangerous)
6235 (info, error_message, input_bfd, input_section,
6236 rel->r_offset)))
6237 return FALSE;
6238 break;
6239 }
6240 }
6241 }
6242
6243 return TRUE;
6244}
6245
6246/* Set the right machine number. */
6247
6248static bfd_boolean
cec5225b 6249elfNN_aarch64_object_p (bfd *abfd)
a06ea964 6250{
cec5225b
YZ
6251#if ARCH_SIZE == 32
6252 bfd_default_set_arch_mach (abfd, bfd_arch_aarch64, bfd_mach_aarch64_ilp32);
6253#else
a06ea964 6254 bfd_default_set_arch_mach (abfd, bfd_arch_aarch64, bfd_mach_aarch64);
cec5225b 6255#endif
a06ea964
NC
6256 return TRUE;
6257}
6258
6259/* Function to keep AArch64 specific flags in the ELF header. */
6260
6261static bfd_boolean
cec5225b 6262elfNN_aarch64_set_private_flags (bfd *abfd, flagword flags)
a06ea964
NC
6263{
6264 if (elf_flags_init (abfd) && elf_elfheader (abfd)->e_flags != flags)
6265 {
6266 }
6267 else
6268 {
6269 elf_elfheader (abfd)->e_flags = flags;
6270 elf_flags_init (abfd) = TRUE;
6271 }
6272
6273 return TRUE;
6274}
6275
a06ea964
NC
6276/* Merge backend specific data from an object file to the output
6277 object file when linking. */
6278
6279static bfd_boolean
cec5225b 6280elfNN_aarch64_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
a06ea964
NC
6281{
6282 flagword out_flags;
6283 flagword in_flags;
6284 bfd_boolean flags_compatible = TRUE;
6285 asection *sec;
6286
6287 /* Check if we have the same endianess. */
6288 if (!_bfd_generic_verify_endian_match (ibfd, obfd))
6289 return FALSE;
6290
6291 if (!is_aarch64_elf (ibfd) || !is_aarch64_elf (obfd))
6292 return TRUE;
6293
6294 /* The input BFD must have had its flags initialised. */
6295 /* The following seems bogus to me -- The flags are initialized in
6296 the assembler but I don't think an elf_flags_init field is
6297 written into the object. */
6298 /* BFD_ASSERT (elf_flags_init (ibfd)); */
6299
6300 in_flags = elf_elfheader (ibfd)->e_flags;
6301 out_flags = elf_elfheader (obfd)->e_flags;
6302
6303 if (!elf_flags_init (obfd))
6304 {
6305 /* If the input is the default architecture and had the default
6306 flags then do not bother setting the flags for the output
6307 architecture, instead allow future merges to do this. If no
6308 future merges ever set these flags then they will retain their
6309 uninitialised values, which surprise surprise, correspond
6310 to the default values. */
6311 if (bfd_get_arch_info (ibfd)->the_default
6312 && elf_elfheader (ibfd)->e_flags == 0)
6313 return TRUE;
6314
6315 elf_flags_init (obfd) = TRUE;
6316 elf_elfheader (obfd)->e_flags = in_flags;
6317
6318 if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
6319 && bfd_get_arch_info (obfd)->the_default)
6320 return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd),
6321 bfd_get_mach (ibfd));
6322
6323 return TRUE;
6324 }
6325
6326 /* Identical flags must be compatible. */
6327 if (in_flags == out_flags)
6328 return TRUE;
6329
6330 /* Check to see if the input BFD actually contains any sections. If
6331 not, its flags may not have been initialised either, but it
6332 cannot actually cause any incompatiblity. Do not short-circuit
6333 dynamic objects; their section list may be emptied by
6334 elf_link_add_object_symbols.
6335
6336 Also check to see if there are no code sections in the input.
6337 In this case there is no need to check for code specific flags.
6338 XXX - do we need to worry about floating-point format compatability
6339 in data sections ? */
6340 if (!(ibfd->flags & DYNAMIC))
6341 {
6342 bfd_boolean null_input_bfd = TRUE;
6343 bfd_boolean only_data_sections = TRUE;
6344
6345 for (sec = ibfd->sections; sec != NULL; sec = sec->next)
6346 {
6347 if ((bfd_get_section_flags (ibfd, sec)
6348 & (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
6349 == (SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS))
6350 only_data_sections = FALSE;
6351
6352 null_input_bfd = FALSE;
6353 break;
6354 }
6355
6356 if (null_input_bfd || only_data_sections)
6357 return TRUE;
6358 }
6359
6360 return flags_compatible;
6361}
6362
6363/* Display the flags field. */
6364
6365static bfd_boolean
cec5225b 6366elfNN_aarch64_print_private_bfd_data (bfd *abfd, void *ptr)
a06ea964
NC
6367{
6368 FILE *file = (FILE *) ptr;
6369 unsigned long flags;
6370
6371 BFD_ASSERT (abfd != NULL && ptr != NULL);
6372
6373 /* Print normal ELF private data. */
6374 _bfd_elf_print_private_bfd_data (abfd, ptr);
6375
6376 flags = elf_elfheader (abfd)->e_flags;
6377 /* Ignore init flag - it may not be set, despite the flags field
6378 containing valid data. */
6379
6380 /* xgettext:c-format */
6381 fprintf (file, _("private flags = %lx:"), elf_elfheader (abfd)->e_flags);
6382
6383 if (flags)
6384 fprintf (file, _("<Unrecognised flag bits set>"));
6385
6386 fputc ('\n', file);
6387
6388 return TRUE;
6389}
6390
6391/* Update the got entry reference counts for the section being removed. */
6392
6393static bfd_boolean
cec5225b 6394elfNN_aarch64_gc_sweep_hook (bfd *abfd,
cb8af559
NC
6395 struct bfd_link_info *info,
6396 asection *sec,
6397 const Elf_Internal_Rela * relocs)
a06ea964 6398{
cec5225b 6399 struct elf_aarch64_link_hash_table *htab;
59c108f7
NC
6400 Elf_Internal_Shdr *symtab_hdr;
6401 struct elf_link_hash_entry **sym_hashes;
cb8af559 6402 struct elf_aarch64_local_symbol *locals;
59c108f7
NC
6403 const Elf_Internal_Rela *rel, *relend;
6404
0e1862bb 6405 if (bfd_link_relocatable (info))
59c108f7
NC
6406 return TRUE;
6407
cec5225b 6408 htab = elf_aarch64_hash_table (info);
59c108f7
NC
6409
6410 if (htab == NULL)
6411 return FALSE;
6412
6413 elf_section_data (sec)->local_dynrel = NULL;
6414
6415 symtab_hdr = &elf_symtab_hdr (abfd);
6416 sym_hashes = elf_sym_hashes (abfd);
6417
cec5225b 6418 locals = elf_aarch64_locals (abfd);
59c108f7
NC
6419
6420 relend = relocs + sec->reloc_count;
6421 for (rel = relocs; rel < relend; rel++)
6422 {
6423 unsigned long r_symndx;
6424 unsigned int r_type;
6425 struct elf_link_hash_entry *h = NULL;
6426
cec5225b 6427 r_symndx = ELFNN_R_SYM (rel->r_info);
8847944f 6428
59c108f7
NC
6429 if (r_symndx >= symtab_hdr->sh_info)
6430 {
8847944f 6431
59c108f7
NC
6432 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
6433 while (h->root.type == bfd_link_hash_indirect
6434 || h->root.type == bfd_link_hash_warning)
6435 h = (struct elf_link_hash_entry *) h->root.u.i.link;
59c108f7
NC
6436 }
6437 else
6438 {
6439 Elf_Internal_Sym *isym;
6440
8847944f 6441 /* A local symbol. */
59c108f7
NC
6442 isym = bfd_sym_from_r_symndx (&htab->sym_cache,
6443 abfd, r_symndx);
1419bbe5
WN
6444
6445 /* Check relocation against local STT_GNU_IFUNC symbol. */
6446 if (isym != NULL
6447 && ELF_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
6448 {
6449 h = elfNN_aarch64_get_local_sym_hash (htab, abfd, rel, FALSE);
6450 if (h == NULL)
6451 abort ();
6452 }
6453 }
6454
6455 if (h)
6456 {
6457 struct elf_aarch64_link_hash_entry *eh;
6458 struct elf_dyn_relocs **pp;
6459 struct elf_dyn_relocs *p;
6460
6461 eh = (struct elf_aarch64_link_hash_entry *) h;
6462
6463 for (pp = &eh->dyn_relocs; (p = *pp) != NULL; pp = &p->next)
6464 if (p->sec == sec)
6465 {
6466 /* Everything must go for SEC. */
6467 *pp = p->next;
6468 break;
6469 }
59c108f7
NC
6470 }
6471
cec5225b 6472 r_type = ELFNN_R_TYPE (rel->r_info);
a6bb11b2 6473 switch (aarch64_tls_transition (abfd,info, r_type, h ,r_symndx))
59c108f7 6474 {
a6bb11b2 6475 case BFD_RELOC_AARCH64_ADR_GOT_PAGE:
7bcccb57 6476 case BFD_RELOC_AARCH64_GOT_LD_PREL19:
7018c030 6477 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
7bcccb57 6478 case BFD_RELOC_AARCH64_LD32_GOT_LO12_NC:
a2e1db00 6479 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
99ad26cb 6480 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
7bcccb57
MS
6481 case BFD_RELOC_AARCH64_LD64_GOT_LO12_NC:
6482 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
6483 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
389b8029 6484 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
7bcccb57
MS
6485 case BFD_RELOC_AARCH64_TLSDESC_LD32_LO12_NC:
6486 case BFD_RELOC_AARCH64_TLSDESC_LD64_LO12_NC:
1ada945d 6487 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
a6bb11b2 6488 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
7bcccb57 6489 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
3c12b054 6490 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
a6bb11b2 6491 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
a6bb11b2 6492 case BFD_RELOC_AARCH64_TLSIE_LD32_GOTTPREL_LO12_NC:
7bcccb57 6493 case BFD_RELOC_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
043bf05a 6494 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
73f925cc 6495 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
f69e4920 6496 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
77a69ff8 6497 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
a6bb11b2 6498 if (h != NULL)
59c108f7
NC
6499 {
6500 if (h->got.refcount > 0)
6501 h->got.refcount -= 1;
1419bbe5
WN
6502
6503 if (h->type == STT_GNU_IFUNC)
6504 {
6505 if (h->plt.refcount > 0)
6506 h->plt.refcount -= 1;
6507 }
59c108f7 6508 }
cb8af559 6509 else if (locals != NULL)
59c108f7 6510 {
cb8af559
NC
6511 if (locals[r_symndx].got_refcount > 0)
6512 locals[r_symndx].got_refcount -= 1;
59c108f7
NC
6513 }
6514 break;
6515
a6bb11b2
YZ
6516 case BFD_RELOC_AARCH64_CALL26:
6517 case BFD_RELOC_AARCH64_JUMP26:
6518 /* If this is a local symbol then we resolve it
6519 directly without creating a PLT entry. */
59c108f7
NC
6520 if (h == NULL)
6521 continue;
6522
6523 if (h->plt.refcount > 0)
6524 h->plt.refcount -= 1;
6525 break;
6526
ce336788
JW
6527 case BFD_RELOC_AARCH64_ADR_HI21_NC_PCREL:
6528 case BFD_RELOC_AARCH64_ADR_HI21_PCREL:
6529 case BFD_RELOC_AARCH64_ADR_LO21_PCREL:
614b09ce
JW
6530 case BFD_RELOC_AARCH64_MOVW_G0_NC:
6531 case BFD_RELOC_AARCH64_MOVW_G1_NC:
6532 case BFD_RELOC_AARCH64_MOVW_G2_NC:
6533 case BFD_RELOC_AARCH64_MOVW_G3:
a6bb11b2 6534 case BFD_RELOC_AARCH64_NN:
0e1862bb 6535 if (h != NULL && bfd_link_executable (info))
59c108f7
NC
6536 {
6537 if (h->plt.refcount > 0)
6538 h->plt.refcount -= 1;
6539 }
6540 break;
cec5225b 6541
59c108f7
NC
6542 default:
6543 break;
6544 }
6545 }
6546
a06ea964
NC
6547 return TRUE;
6548}
6549
6550/* Adjust a symbol defined by a dynamic object and referenced by a
6551 regular object. The current definition is in some section of the
6552 dynamic object, but we're not including those sections. We have to
6553 change the definition to something the rest of the link can
6554 understand. */
6555
6556static bfd_boolean
cec5225b 6557elfNN_aarch64_adjust_dynamic_symbol (struct bfd_link_info *info,
a06ea964
NC
6558 struct elf_link_hash_entry *h)
6559{
cec5225b 6560 struct elf_aarch64_link_hash_table *htab;
a06ea964
NC
6561 asection *s;
6562
6563 /* If this is a function, put it in the procedure linkage table. We
6564 will fill in the contents of the procedure linkage table later,
6565 when we know the address of the .got section. */
1419bbe5 6566 if (h->type == STT_FUNC || h->type == STT_GNU_IFUNC || h->needs_plt)
a06ea964
NC
6567 {
6568 if (h->plt.refcount <= 0
1419bbe5
WN
6569 || (h->type != STT_GNU_IFUNC
6570 && (SYMBOL_CALLS_LOCAL (info, h)
6571 || (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT
6572 && h->root.type == bfd_link_hash_undefweak))))
a06ea964
NC
6573 {
6574 /* This case can occur if we saw a CALL26 reloc in
6575 an input file, but the symbol wasn't referred to
6576 by a dynamic object or all references were
6577 garbage collected. In which case we can end up
6578 resolving. */
6579 h->plt.offset = (bfd_vma) - 1;
6580 h->needs_plt = 0;
6581 }
6582
6583 return TRUE;
6584 }
6585 else
80de0c6d 6586 /* Otherwise, reset to -1. */
a06ea964
NC
6587 h->plt.offset = (bfd_vma) - 1;
6588
6589
6590 /* If this is a weak symbol, and there is a real definition, the
6591 processor independent code will have arranged for us to see the
6592 real definition first, and we can just use the same value. */
6593 if (h->u.weakdef != NULL)
6594 {
6595 BFD_ASSERT (h->u.weakdef->root.type == bfd_link_hash_defined
6596 || h->u.weakdef->root.type == bfd_link_hash_defweak);
6597 h->root.u.def.section = h->u.weakdef->root.u.def.section;
6598 h->root.u.def.value = h->u.weakdef->root.u.def.value;
6599 if (ELIMINATE_COPY_RELOCS || info->nocopyreloc)
6600 h->non_got_ref = h->u.weakdef->non_got_ref;
6601 return TRUE;
6602 }
6603
6604 /* If we are creating a shared library, we must presume that the
6605 only references to the symbol are via the global offset table.
6606 For such cases we need not do anything here; the relocations will
6607 be handled correctly by relocate_section. */
0e1862bb 6608 if (bfd_link_pic (info))
a06ea964
NC
6609 return TRUE;
6610
6611 /* If there are no references to this symbol that do not use the
6612 GOT, we don't need to generate a copy reloc. */
6613 if (!h->non_got_ref)
6614 return TRUE;
6615
6616 /* If -z nocopyreloc was given, we won't generate them either. */
6617 if (info->nocopyreloc)
6618 {
6619 h->non_got_ref = 0;
6620 return TRUE;
6621 }
6622
6623 /* We must allocate the symbol in our .dynbss section, which will
6624 become part of the .bss section of the executable. There will be
6625 an entry for this symbol in the .dynsym section. The dynamic
6626 object will contain position independent code, so all references
6627 from the dynamic object to this symbol will go through the global
6628 offset table. The dynamic linker will use the .dynsym entry to
6629 determine the address it must put in the global offset table, so
6630 both the dynamic object and the regular object will refer to the
6631 same memory location for the variable. */
6632
cec5225b 6633 htab = elf_aarch64_hash_table (info);
a06ea964
NC
6634
6635 /* We must generate a R_AARCH64_COPY reloc to tell the dynamic linker
6636 to copy the initial value out of the dynamic object and into the
6637 runtime process image. */
6638 if ((h->root.u.def.section->flags & SEC_ALLOC) != 0 && h->size != 0)
6639 {
6640 htab->srelbss->size += RELOC_SIZE (htab);
6641 h->needs_copy = 1;
6642 }
6643
6644 s = htab->sdynbss;
6645
6cabe1ea 6646 return _bfd_elf_adjust_dynamic_copy (info, h, s);
a06ea964
NC
6647
6648}
6649
6650static bfd_boolean
cec5225b 6651elfNN_aarch64_allocate_local_symbols (bfd *abfd, unsigned number)
a06ea964
NC
6652{
6653 struct elf_aarch64_local_symbol *locals;
cec5225b 6654 locals = elf_aarch64_locals (abfd);
a06ea964
NC
6655 if (locals == NULL)
6656 {
6657 locals = (struct elf_aarch64_local_symbol *)
6658 bfd_zalloc (abfd, number * sizeof (struct elf_aarch64_local_symbol));
6659 if (locals == NULL)
6660 return FALSE;
cec5225b 6661 elf_aarch64_locals (abfd) = locals;
a06ea964
NC
6662 }
6663 return TRUE;
6664}
6665
cc0efaa8
MS
6666/* Create the .got section to hold the global offset table. */
6667
6668static bfd_boolean
6669aarch64_elf_create_got_section (bfd *abfd, struct bfd_link_info *info)
6670{
6671 const struct elf_backend_data *bed = get_elf_backend_data (abfd);
6672 flagword flags;
6673 asection *s;
6674 struct elf_link_hash_entry *h;
6675 struct elf_link_hash_table *htab = elf_hash_table (info);
6676
6677 /* This function may be called more than once. */
6678 s = bfd_get_linker_section (abfd, ".got");
6679 if (s != NULL)
6680 return TRUE;
6681
6682 flags = bed->dynamic_sec_flags;
6683
6684 s = bfd_make_section_anyway_with_flags (abfd,
6685 (bed->rela_plts_and_copies_p
6686 ? ".rela.got" : ".rel.got"),
6687 (bed->dynamic_sec_flags
6688 | SEC_READONLY));
6689 if (s == NULL
6690 || ! bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
6691 return FALSE;
6692 htab->srelgot = s;
6693
6694 s = bfd_make_section_anyway_with_flags (abfd, ".got", flags);
6695 if (s == NULL
6696 || !bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
6697 return FALSE;
6698 htab->sgot = s;
6699 htab->sgot->size += GOT_ENTRY_SIZE;
6700
6701 if (bed->want_got_sym)
6702 {
6703 /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the .got
6704 (or .got.plt) section. We don't do this in the linker script
6705 because we don't want to define the symbol if we are not creating
6706 a global offset table. */
6707 h = _bfd_elf_define_linkage_sym (abfd, info, s,
6708 "_GLOBAL_OFFSET_TABLE_");
6709 elf_hash_table (info)->hgot = h;
6710 if (h == NULL)
6711 return FALSE;
6712 }
6713
6714 if (bed->want_got_plt)
6715 {
6716 s = bfd_make_section_anyway_with_flags (abfd, ".got.plt", flags);
6717 if (s == NULL
6718 || !bfd_set_section_alignment (abfd, s,
6719 bed->s->log_file_align))
6720 return FALSE;
6721 htab->sgotplt = s;
6722 }
6723
6724 /* The first bit of the global offset table is the header. */
6725 s->size += bed->got_header_size;
6726
6727 return TRUE;
6728}
6729
a06ea964
NC
6730/* Look through the relocs for a section during the first phase. */
6731
6732static bfd_boolean
cec5225b 6733elfNN_aarch64_check_relocs (bfd *abfd, struct bfd_link_info *info,
a06ea964
NC
6734 asection *sec, const Elf_Internal_Rela *relocs)
6735{
6736 Elf_Internal_Shdr *symtab_hdr;
6737 struct elf_link_hash_entry **sym_hashes;
6738 const Elf_Internal_Rela *rel;
6739 const Elf_Internal_Rela *rel_end;
6740 asection *sreloc;
6741
cec5225b 6742 struct elf_aarch64_link_hash_table *htab;
a06ea964 6743
0e1862bb 6744 if (bfd_link_relocatable (info))
a06ea964
NC
6745 return TRUE;
6746
6747 BFD_ASSERT (is_aarch64_elf (abfd));
6748
cec5225b 6749 htab = elf_aarch64_hash_table (info);
a06ea964
NC
6750 sreloc = NULL;
6751
6752 symtab_hdr = &elf_symtab_hdr (abfd);
6753 sym_hashes = elf_sym_hashes (abfd);
a06ea964
NC
6754
6755 rel_end = relocs + sec->reloc_count;
6756 for (rel = relocs; rel < rel_end; rel++)
6757 {
6758 struct elf_link_hash_entry *h;
6759 unsigned long r_symndx;
6760 unsigned int r_type;
a6bb11b2 6761 bfd_reloc_code_real_type bfd_r_type;
1419bbe5 6762 Elf_Internal_Sym *isym;
a06ea964 6763
cec5225b
YZ
6764 r_symndx = ELFNN_R_SYM (rel->r_info);
6765 r_type = ELFNN_R_TYPE (rel->r_info);
a06ea964
NC
6766
6767 if (r_symndx >= NUM_SHDR_ENTRIES (symtab_hdr))
6768 {
6769 (*_bfd_error_handler) (_("%B: bad symbol index: %d"), abfd,
6770 r_symndx);
6771 return FALSE;
6772 }
6773
ed5acf27 6774 if (r_symndx < symtab_hdr->sh_info)
1419bbe5
WN
6775 {
6776 /* A local symbol. */
6777 isym = bfd_sym_from_r_symndx (&htab->sym_cache,
6778 abfd, r_symndx);
6779 if (isym == NULL)
6780 return FALSE;
6781
6782 /* Check relocation against local STT_GNU_IFUNC symbol. */
6783 if (ELF_ST_TYPE (isym->st_info) == STT_GNU_IFUNC)
6784 {
6785 h = elfNN_aarch64_get_local_sym_hash (htab, abfd, rel,
6786 TRUE);
6787 if (h == NULL)
6788 return FALSE;
6789
6790 /* Fake a STT_GNU_IFUNC symbol. */
6791 h->type = STT_GNU_IFUNC;
6792 h->def_regular = 1;
6793 h->ref_regular = 1;
6794 h->forced_local = 1;
6795 h->root.type = bfd_link_hash_defined;
6796 }
6797 else
6798 h = NULL;
6799 }
a06ea964
NC
6800 else
6801 {
6802 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
6803 while (h->root.type == bfd_link_hash_indirect
6804 || h->root.type == bfd_link_hash_warning)
6805 h = (struct elf_link_hash_entry *) h->root.u.i.link;
81fbe831
AM
6806
6807 /* PR15323, ref flags aren't set for references in the same
6808 object. */
6809 h->root.non_ir_ref = 1;
a06ea964
NC
6810 }
6811
6812 /* Could be done earlier, if h were already available. */
a6bb11b2 6813 bfd_r_type = aarch64_tls_transition (abfd, info, r_type, h, r_symndx);
a06ea964 6814
1419bbe5
WN
6815 if (h != NULL)
6816 {
6817 /* Create the ifunc sections for static executables. If we
6818 never see an indirect function symbol nor we are building
6819 a static executable, those sections will be empty and
6820 won't appear in output. */
6821 switch (bfd_r_type)
6822 {
6823 default:
6824 break;
6825
ce336788
JW
6826 case BFD_RELOC_AARCH64_ADD_LO12:
6827 case BFD_RELOC_AARCH64_ADR_GOT_PAGE:
6828 case BFD_RELOC_AARCH64_ADR_HI21_PCREL:
1419bbe5 6829 case BFD_RELOC_AARCH64_CALL26:
ce336788 6830 case BFD_RELOC_AARCH64_GOT_LD_PREL19:
1419bbe5 6831 case BFD_RELOC_AARCH64_JUMP26:
7018c030 6832 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
1419bbe5 6833 case BFD_RELOC_AARCH64_LD32_GOT_LO12_NC:
a2e1db00 6834 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
99ad26cb 6835 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
1419bbe5 6836 case BFD_RELOC_AARCH64_LD64_GOT_LO12_NC:
ce336788 6837 case BFD_RELOC_AARCH64_NN:
1419bbe5
WN
6838 if (htab->root.dynobj == NULL)
6839 htab->root.dynobj = abfd;
6840 if (!_bfd_elf_create_ifunc_sections (htab->root.dynobj, info))
6841 return FALSE;
6842 break;
6843 }
6844
6845 /* It is referenced by a non-shared object. */
6846 h->ref_regular = 1;
6847 h->root.non_ir_ref = 1;
6848 }
6849
a6bb11b2 6850 switch (bfd_r_type)
a06ea964 6851 {
a6bb11b2 6852 case BFD_RELOC_AARCH64_NN:
a06ea964
NC
6853
6854 /* We don't need to handle relocs into sections not going into
6855 the "real" output. */
6856 if ((sec->flags & SEC_ALLOC) == 0)
6857 break;
6858
6859 if (h != NULL)
6860 {
0e1862bb 6861 if (!bfd_link_pic (info))
a06ea964
NC
6862 h->non_got_ref = 1;
6863
6864 h->plt.refcount += 1;
6865 h->pointer_equality_needed = 1;
6866 }
6867
6868 /* No need to do anything if we're not creating a shared
6869 object. */
0e1862bb 6870 if (! bfd_link_pic (info))
a06ea964
NC
6871 break;
6872
6873 {
6874 struct elf_dyn_relocs *p;
6875 struct elf_dyn_relocs **head;
6876
6877 /* We must copy these reloc types into the output file.
6878 Create a reloc section in dynobj and make room for
6879 this reloc. */
6880 if (sreloc == NULL)
6881 {
6882 if (htab->root.dynobj == NULL)
6883 htab->root.dynobj = abfd;
6884
6885 sreloc = _bfd_elf_make_dynamic_reloc_section
0608afa7 6886 (sec, htab->root.dynobj, LOG_FILE_ALIGN, abfd, /*rela? */ TRUE);
a06ea964
NC
6887
6888 if (sreloc == NULL)
6889 return FALSE;
6890 }
6891
6892 /* If this is a global symbol, we count the number of
6893 relocations we need for this symbol. */
6894 if (h != NULL)
6895 {
cec5225b
YZ
6896 struct elf_aarch64_link_hash_entry *eh;
6897 eh = (struct elf_aarch64_link_hash_entry *) h;
a06ea964
NC
6898 head = &eh->dyn_relocs;
6899 }
6900 else
6901 {
6902 /* Track dynamic relocs needed for local syms too.
6903 We really need local syms available to do this
6904 easily. Oh well. */
6905
6906 asection *s;
6907 void **vpp;
a06ea964
NC
6908
6909 isym = bfd_sym_from_r_symndx (&htab->sym_cache,
6910 abfd, r_symndx);
6911 if (isym == NULL)
6912 return FALSE;
6913
6914 s = bfd_section_from_elf_index (abfd, isym->st_shndx);
6915 if (s == NULL)
6916 s = sec;
6917
6918 /* Beware of type punned pointers vs strict aliasing
6919 rules. */
6920 vpp = &(elf_section_data (s)->local_dynrel);
6921 head = (struct elf_dyn_relocs **) vpp;
6922 }
6923
6924 p = *head;
6925 if (p == NULL || p->sec != sec)
6926 {
6927 bfd_size_type amt = sizeof *p;
6928 p = ((struct elf_dyn_relocs *)
6929 bfd_zalloc (htab->root.dynobj, amt));
6930 if (p == NULL)
6931 return FALSE;
6932 p->next = *head;
6933 *head = p;
6934 p->sec = sec;
6935 }
6936
6937 p->count += 1;
6938
6939 }
6940 break;
6941
6942 /* RR: We probably want to keep a consistency check that
6943 there are no dangling GOT_PAGE relocs. */
a6bb11b2 6944 case BFD_RELOC_AARCH64_ADR_GOT_PAGE:
7bcccb57 6945 case BFD_RELOC_AARCH64_GOT_LD_PREL19:
7018c030 6946 case BFD_RELOC_AARCH64_LD32_GOTPAGE_LO14:
7bcccb57 6947 case BFD_RELOC_AARCH64_LD32_GOT_LO12_NC:
a2e1db00 6948 case BFD_RELOC_AARCH64_LD64_GOTOFF_LO15:
99ad26cb 6949 case BFD_RELOC_AARCH64_LD64_GOTPAGE_LO15:
7bcccb57
MS
6950 case BFD_RELOC_AARCH64_LD64_GOT_LO12_NC:
6951 case BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC:
6952 case BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21:
389b8029 6953 case BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21:
7bcccb57
MS
6954 case BFD_RELOC_AARCH64_TLSDESC_LD32_LO12_NC:
6955 case BFD_RELOC_AARCH64_TLSDESC_LD64_LO12_NC:
1ada945d 6956 case BFD_RELOC_AARCH64_TLSDESC_LD_PREL19:
a6bb11b2 6957 case BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC:
7bcccb57 6958 case BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21:
3c12b054 6959 case BFD_RELOC_AARCH64_TLSGD_ADR_PREL21:
a6bb11b2 6960 case BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
a6bb11b2 6961 case BFD_RELOC_AARCH64_TLSIE_LD32_GOTTPREL_LO12_NC:
7bcccb57 6962 case BFD_RELOC_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
043bf05a 6963 case BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19:
73f925cc 6964 case BFD_RELOC_AARCH64_TLSLD_ADD_LO12_NC:
f69e4920 6965 case BFD_RELOC_AARCH64_TLSLD_ADR_PAGE21:
77a69ff8 6966 case BFD_RELOC_AARCH64_TLSLD_ADR_PREL21:
a06ea964
NC
6967 {
6968 unsigned got_type;
6969 unsigned old_got_type;
6970
a6bb11b2 6971 got_type = aarch64_reloc_got_type (bfd_r_type);
a06ea964
NC
6972
6973 if (h)
6974 {
6975 h->got.refcount += 1;
cec5225b 6976 old_got_type = elf_aarch64_hash_entry (h)->got_type;
a06ea964
NC
6977 }
6978 else
6979 {
6980 struct elf_aarch64_local_symbol *locals;
6981
cec5225b 6982 if (!elfNN_aarch64_allocate_local_symbols
a06ea964
NC
6983 (abfd, symtab_hdr->sh_info))
6984 return FALSE;
6985
cec5225b 6986 locals = elf_aarch64_locals (abfd);
a06ea964
NC
6987 BFD_ASSERT (r_symndx < symtab_hdr->sh_info);
6988 locals[r_symndx].got_refcount += 1;
6989 old_got_type = locals[r_symndx].got_type;
6990 }
6991
6992 /* If a variable is accessed with both general dynamic TLS
6993 methods, two slots may be created. */
6994 if (GOT_TLS_GD_ANY_P (old_got_type) && GOT_TLS_GD_ANY_P (got_type))
6995 got_type |= old_got_type;
6996
6997 /* We will already have issued an error message if there
6998 is a TLS/non-TLS mismatch, based on the symbol type.
6999 So just combine any TLS types needed. */
7000 if (old_got_type != GOT_UNKNOWN && old_got_type != GOT_NORMAL
7001 && got_type != GOT_NORMAL)
7002 got_type |= old_got_type;
7003
7004 /* If the symbol is accessed by both IE and GD methods, we
7005 are able to relax. Turn off the GD flag, without
7006 messing up with any other kind of TLS types that may be
7007 involved. */
7008 if ((got_type & GOT_TLS_IE) && GOT_TLS_GD_ANY_P (got_type))
7009 got_type &= ~ (GOT_TLSDESC_GD | GOT_TLS_GD);
7010
7011 if (old_got_type != got_type)
7012 {
7013 if (h != NULL)
cec5225b 7014 elf_aarch64_hash_entry (h)->got_type = got_type;
a06ea964
NC
7015 else
7016 {
7017 struct elf_aarch64_local_symbol *locals;
cec5225b 7018 locals = elf_aarch64_locals (abfd);
a06ea964
NC
7019 BFD_ASSERT (r_symndx < symtab_hdr->sh_info);
7020 locals[r_symndx].got_type = got_type;
7021 }
7022 }
7023
cc0efaa8
MS
7024 if (htab->root.dynobj == NULL)
7025 htab->root.dynobj = abfd;
7026 if (! aarch64_elf_create_got_section (htab->root.dynobj, info))
7027 return FALSE;
a06ea964
NC
7028 break;
7029 }
7030
614b09ce
JW
7031 case BFD_RELOC_AARCH64_MOVW_G0_NC:
7032 case BFD_RELOC_AARCH64_MOVW_G1_NC:
7033 case BFD_RELOC_AARCH64_MOVW_G2_NC:
7034 case BFD_RELOC_AARCH64_MOVW_G3:
0e1862bb 7035 if (bfd_link_pic (info))
614b09ce
JW
7036 {
7037 int howto_index = bfd_r_type - BFD_RELOC_AARCH64_RELOC_START;
7038 (*_bfd_error_handler)
7039 (_("%B: relocation %s against `%s' can not be used when making "
7040 "a shared object; recompile with -fPIC"),
7041 abfd, elfNN_aarch64_howto_table[howto_index].name,
7042 (h) ? h->root.root.string : "a local symbol");
7043 bfd_set_error (bfd_error_bad_value);
7044 return FALSE;
7045 }
7046
a6bb11b2
YZ
7047 case BFD_RELOC_AARCH64_ADR_HI21_NC_PCREL:
7048 case BFD_RELOC_AARCH64_ADR_HI21_PCREL:
7049 case BFD_RELOC_AARCH64_ADR_LO21_PCREL:
0e1862bb 7050 if (h != NULL && bfd_link_executable (info))
a06ea964
NC
7051 {
7052 /* If this reloc is in a read-only section, we might
7053 need a copy reloc. We can't check reliably at this
7054 stage whether the section is read-only, as input
7055 sections have not yet been mapped to output sections.
7056 Tentatively set the flag for now, and correct in
7057 adjust_dynamic_symbol. */
7058 h->non_got_ref = 1;
7059 h->plt.refcount += 1;
7060 h->pointer_equality_needed = 1;
7061 }
7062 /* FIXME:: RR need to handle these in shared libraries
7063 and essentially bomb out as these being non-PIC
7064 relocations in shared libraries. */
7065 break;
7066
a6bb11b2
YZ
7067 case BFD_RELOC_AARCH64_CALL26:
7068 case BFD_RELOC_AARCH64_JUMP26:
a06ea964
NC
7069 /* If this is a local symbol then we resolve it
7070 directly without creating a PLT entry. */
7071 if (h == NULL)
7072 continue;
7073
7074 h->needs_plt = 1;
1419bbe5
WN
7075 if (h->plt.refcount <= 0)
7076 h->plt.refcount = 1;
7077 else
7078 h->plt.refcount += 1;
a06ea964 7079 break;
a6bb11b2
YZ
7080
7081 default:
7082 break;
a06ea964
NC
7083 }
7084 }
a6bb11b2 7085
a06ea964
NC
7086 return TRUE;
7087}
7088
7089/* Treat mapping symbols as special target symbols. */
7090
7091static bfd_boolean
cec5225b 7092elfNN_aarch64_is_target_special_symbol (bfd *abfd ATTRIBUTE_UNUSED,
a06ea964
NC
7093 asymbol *sym)
7094{
7095 return bfd_is_aarch64_special_symbol_name (sym->name,
7096 BFD_AARCH64_SPECIAL_SYM_TYPE_ANY);
7097}
7098
7099/* This is a copy of elf_find_function () from elf.c except that
7100 AArch64 mapping symbols are ignored when looking for function names. */
7101
7102static bfd_boolean
7103aarch64_elf_find_function (bfd *abfd ATTRIBUTE_UNUSED,
a06ea964 7104 asymbol **symbols,
fb167eb2 7105 asection *section,
a06ea964
NC
7106 bfd_vma offset,
7107 const char **filename_ptr,
7108 const char **functionname_ptr)
7109{
7110 const char *filename = NULL;
7111 asymbol *func = NULL;
7112 bfd_vma low_func = 0;
7113 asymbol **p;
7114
7115 for (p = symbols; *p != NULL; p++)
7116 {
7117 elf_symbol_type *q;
7118
7119 q = (elf_symbol_type *) * p;
7120
7121 switch (ELF_ST_TYPE (q->internal_elf_sym.st_info))
7122 {
7123 default:
7124 break;
7125 case STT_FILE:
7126 filename = bfd_asymbol_name (&q->symbol);
7127 break;
7128 case STT_FUNC:
7129 case STT_NOTYPE:
7130 /* Skip mapping symbols. */
7131 if ((q->symbol.flags & BSF_LOCAL)
7132 && (bfd_is_aarch64_special_symbol_name
7133 (q->symbol.name, BFD_AARCH64_SPECIAL_SYM_TYPE_ANY)))
7134 continue;
7135 /* Fall through. */
7136 if (bfd_get_section (&q->symbol) == section
7137 && q->symbol.value >= low_func && q->symbol.value <= offset)
7138 {
7139 func = (asymbol *) q;
7140 low_func = q->symbol.value;
7141 }
7142 break;
7143 }
7144 }
7145
7146 if (func == NULL)
7147 return FALSE;
7148
7149 if (filename_ptr)
7150 *filename_ptr = filename;
7151 if (functionname_ptr)
7152 *functionname_ptr = bfd_asymbol_name (func);
7153
7154 return TRUE;
7155}
7156
7157
7158/* Find the nearest line to a particular section and offset, for error
7159 reporting. This code is a duplicate of the code in elf.c, except
7160 that it uses aarch64_elf_find_function. */
7161
7162static bfd_boolean
cec5225b 7163elfNN_aarch64_find_nearest_line (bfd *abfd,
a06ea964 7164 asymbol **symbols,
fb167eb2 7165 asection *section,
a06ea964
NC
7166 bfd_vma offset,
7167 const char **filename_ptr,
7168 const char **functionname_ptr,
fb167eb2
AM
7169 unsigned int *line_ptr,
7170 unsigned int *discriminator_ptr)
a06ea964
NC
7171{
7172 bfd_boolean found = FALSE;
7173
fb167eb2 7174 if (_bfd_dwarf2_find_nearest_line (abfd, symbols, NULL, section, offset,
a06ea964 7175 filename_ptr, functionname_ptr,
fb167eb2
AM
7176 line_ptr, discriminator_ptr,
7177 dwarf_debug_sections, 0,
a06ea964
NC
7178 &elf_tdata (abfd)->dwarf2_find_line_info))
7179 {
7180 if (!*functionname_ptr)
fb167eb2 7181 aarch64_elf_find_function (abfd, symbols, section, offset,
a06ea964
NC
7182 *filename_ptr ? NULL : filename_ptr,
7183 functionname_ptr);
7184
7185 return TRUE;
7186 }
7187
fb167eb2
AM
7188 /* Skip _bfd_dwarf1_find_nearest_line since no known AArch64
7189 toolchain uses DWARF1. */
7190
a06ea964
NC
7191 if (!_bfd_stab_section_find_nearest_line (abfd, symbols, section, offset,
7192 &found, filename_ptr,
7193 functionname_ptr, line_ptr,
7194 &elf_tdata (abfd)->line_info))
7195 return FALSE;
7196
7197 if (found && (*functionname_ptr || *line_ptr))
7198 return TRUE;
7199
7200 if (symbols == NULL)
7201 return FALSE;
7202
fb167eb2 7203 if (!aarch64_elf_find_function (abfd, symbols, section, offset,
a06ea964
NC
7204 filename_ptr, functionname_ptr))
7205 return FALSE;
7206
7207 *line_ptr = 0;
7208 return TRUE;
7209}
7210
7211static bfd_boolean
cec5225b 7212elfNN_aarch64_find_inliner_info (bfd *abfd,
a06ea964
NC
7213 const char **filename_ptr,
7214 const char **functionname_ptr,
7215 unsigned int *line_ptr)
7216{
7217 bfd_boolean found;
7218 found = _bfd_dwarf2_find_inliner_info
7219 (abfd, filename_ptr,
7220 functionname_ptr, line_ptr, &elf_tdata (abfd)->dwarf2_find_line_info);
7221 return found;
7222}
7223
7224
7225static void
cec5225b 7226elfNN_aarch64_post_process_headers (bfd *abfd,
1419bbe5 7227 struct bfd_link_info *link_info)
a06ea964
NC
7228{
7229 Elf_Internal_Ehdr *i_ehdrp; /* ELF file header, internal form. */
7230
7231 i_ehdrp = elf_elfheader (abfd);
a06ea964 7232 i_ehdrp->e_ident[EI_ABIVERSION] = AARCH64_ELF_ABI_VERSION;
1419bbe5 7233
78245035 7234 _bfd_elf_post_process_headers (abfd, link_info);
a06ea964
NC
7235}
7236
7237static enum elf_reloc_type_class
cec5225b 7238elfNN_aarch64_reloc_type_class (const struct bfd_link_info *info ATTRIBUTE_UNUSED,
7e612e98
AM
7239 const asection *rel_sec ATTRIBUTE_UNUSED,
7240 const Elf_Internal_Rela *rela)
a06ea964 7241{
cec5225b 7242 switch ((int) ELFNN_R_TYPE (rela->r_info))
a06ea964 7243 {
a6bb11b2 7244 case AARCH64_R (RELATIVE):
a06ea964 7245 return reloc_class_relative;
a6bb11b2 7246 case AARCH64_R (JUMP_SLOT):
a06ea964 7247 return reloc_class_plt;
a6bb11b2 7248 case AARCH64_R (COPY):
a06ea964
NC
7249 return reloc_class_copy;
7250 default:
7251 return reloc_class_normal;
7252 }
7253}
7254
a06ea964
NC
7255/* Handle an AArch64 specific section when reading an object file. This is
7256 called when bfd_section_from_shdr finds a section with an unknown
7257 type. */
7258
7259static bfd_boolean
cec5225b 7260elfNN_aarch64_section_from_shdr (bfd *abfd,
a06ea964
NC
7261 Elf_Internal_Shdr *hdr,
7262 const char *name, int shindex)
7263{
7264 /* There ought to be a place to keep ELF backend specific flags, but
7265 at the moment there isn't one. We just keep track of the
7266 sections by their name, instead. Fortunately, the ABI gives
7267 names for all the AArch64 specific sections, so we will probably get
7268 away with this. */
7269 switch (hdr->sh_type)
7270 {
7271 case SHT_AARCH64_ATTRIBUTES:
7272 break;
7273
7274 default:
7275 return FALSE;
7276 }
7277
7278 if (!_bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex))
7279 return FALSE;
7280
7281 return TRUE;
7282}
7283
7284/* A structure used to record a list of sections, independently
7285 of the next and prev fields in the asection structure. */
7286typedef struct section_list
7287{
7288 asection *sec;
7289 struct section_list *next;
7290 struct section_list *prev;
7291}
7292section_list;
7293
7294/* Unfortunately we need to keep a list of sections for which
7295 an _aarch64_elf_section_data structure has been allocated. This
cec5225b 7296 is because it is possible for functions like elfNN_aarch64_write_section
a06ea964
NC
7297 to be called on a section which has had an elf_data_structure
7298 allocated for it (and so the used_by_bfd field is valid) but
7299 for which the AArch64 extended version of this structure - the
7300 _aarch64_elf_section_data structure - has not been allocated. */
7301static section_list *sections_with_aarch64_elf_section_data = NULL;
7302
7303static void
7304record_section_with_aarch64_elf_section_data (asection *sec)
7305{
7306 struct section_list *entry;
7307
7308 entry = bfd_malloc (sizeof (*entry));
7309 if (entry == NULL)
7310 return;
7311 entry->sec = sec;
7312 entry->next = sections_with_aarch64_elf_section_data;
7313 entry->prev = NULL;
7314 if (entry->next != NULL)
7315 entry->next->prev = entry;
7316 sections_with_aarch64_elf_section_data = entry;
7317}
7318
7319static struct section_list *
7320find_aarch64_elf_section_entry (asection *sec)
7321{
7322 struct section_list *entry;
7323 static struct section_list *last_entry = NULL;
7324
7325 /* This is a short cut for the typical case where the sections are added
7326 to the sections_with_aarch64_elf_section_data list in forward order and
7327 then looked up here in backwards order. This makes a real difference
7328 to the ld-srec/sec64k.exp linker test. */
7329 entry = sections_with_aarch64_elf_section_data;
7330 if (last_entry != NULL)
7331 {
7332 if (last_entry->sec == sec)
7333 entry = last_entry;
7334 else if (last_entry->next != NULL && last_entry->next->sec == sec)
7335 entry = last_entry->next;
7336 }
7337
7338 for (; entry; entry = entry->next)
7339 if (entry->sec == sec)
7340 break;
7341
7342 if (entry)
7343 /* Record the entry prior to this one - it is the entry we are
7344 most likely to want to locate next time. Also this way if we
7345 have been called from
7346 unrecord_section_with_aarch64_elf_section_data () we will not
7347 be caching a pointer that is about to be freed. */
7348 last_entry = entry->prev;
7349
7350 return entry;
7351}
7352
7353static void
7354unrecord_section_with_aarch64_elf_section_data (asection *sec)
7355{
7356 struct section_list *entry;
7357
7358 entry = find_aarch64_elf_section_entry (sec);
7359
7360 if (entry)
7361 {
7362 if (entry->prev != NULL)
7363 entry->prev->next = entry->next;
7364 if (entry->next != NULL)
7365 entry->next->prev = entry->prev;
7366 if (entry == sections_with_aarch64_elf_section_data)
7367 sections_with_aarch64_elf_section_data = entry->next;
7368 free (entry);
7369 }
7370}
7371
7372
7373typedef struct
7374{
7375 void *finfo;
7376 struct bfd_link_info *info;
7377 asection *sec;
7378 int sec_shndx;
7379 int (*func) (void *, const char *, Elf_Internal_Sym *,
7380 asection *, struct elf_link_hash_entry *);
7381} output_arch_syminfo;
7382
7383enum map_symbol_type
7384{
7385 AARCH64_MAP_INSN,
7386 AARCH64_MAP_DATA
7387};
7388
7389
7390/* Output a single mapping symbol. */
7391
7392static bfd_boolean
cec5225b 7393elfNN_aarch64_output_map_sym (output_arch_syminfo *osi,
a06ea964
NC
7394 enum map_symbol_type type, bfd_vma offset)
7395{
7396 static const char *names[2] = { "$x", "$d" };
7397 Elf_Internal_Sym sym;
7398
7399 sym.st_value = (osi->sec->output_section->vma
7400 + osi->sec->output_offset + offset);
7401 sym.st_size = 0;
7402 sym.st_other = 0;
7403 sym.st_info = ELF_ST_INFO (STB_LOCAL, STT_NOTYPE);
7404 sym.st_shndx = osi->sec_shndx;
7405 return osi->func (osi->finfo, names[type], &sym, osi->sec, NULL) == 1;
7406}
7407
a06ea964
NC
7408/* Output a single local symbol for a generated stub. */
7409
7410static bfd_boolean
cec5225b 7411elfNN_aarch64_output_stub_sym (output_arch_syminfo *osi, const char *name,
a06ea964
NC
7412 bfd_vma offset, bfd_vma size)
7413{
7414 Elf_Internal_Sym sym;
7415
7416 sym.st_value = (osi->sec->output_section->vma
7417 + osi->sec->output_offset + offset);
7418 sym.st_size = size;
7419 sym.st_other = 0;
7420 sym.st_info = ELF_ST_INFO (STB_LOCAL, STT_FUNC);
7421 sym.st_shndx = osi->sec_shndx;
7422 return osi->func (osi->finfo, name, &sym, osi->sec, NULL) == 1;
7423}
7424
7425static bfd_boolean
7426aarch64_map_one_stub (struct bfd_hash_entry *gen_entry, void *in_arg)
7427{
cec5225b 7428 struct elf_aarch64_stub_hash_entry *stub_entry;
a06ea964
NC
7429 asection *stub_sec;
7430 bfd_vma addr;
7431 char *stub_name;
7432 output_arch_syminfo *osi;
7433
7434 /* Massage our args to the form they really have. */
cec5225b 7435 stub_entry = (struct elf_aarch64_stub_hash_entry *) gen_entry;
a06ea964
NC
7436 osi = (output_arch_syminfo *) in_arg;
7437
7438 stub_sec = stub_entry->stub_sec;
7439
7440 /* Ensure this stub is attached to the current section being
7441 processed. */
7442 if (stub_sec != osi->sec)
7443 return TRUE;
7444
7445 addr = (bfd_vma) stub_entry->stub_offset;
7446
7447 stub_name = stub_entry->output_name;
7448
7449 switch (stub_entry->stub_type)
7450 {
7451 case aarch64_stub_adrp_branch:
cec5225b 7452 if (!elfNN_aarch64_output_stub_sym (osi, stub_name, addr,
a06ea964
NC
7453 sizeof (aarch64_adrp_branch_stub)))
7454 return FALSE;
cec5225b 7455 if (!elfNN_aarch64_output_map_sym (osi, AARCH64_MAP_INSN, addr))
a06ea964
NC
7456 return FALSE;
7457 break;
7458 case aarch64_stub_long_branch:
cec5225b 7459 if (!elfNN_aarch64_output_stub_sym
a06ea964
NC
7460 (osi, stub_name, addr, sizeof (aarch64_long_branch_stub)))
7461 return FALSE;
cec5225b 7462 if (!elfNN_aarch64_output_map_sym (osi, AARCH64_MAP_INSN, addr))
a06ea964 7463 return FALSE;
cec5225b 7464 if (!elfNN_aarch64_output_map_sym (osi, AARCH64_MAP_DATA, addr + 16))
a06ea964
NC
7465 return FALSE;
7466 break;
68fcca92
JW
7467 case aarch64_stub_erratum_835769_veneer:
7468 if (!elfNN_aarch64_output_stub_sym (osi, stub_name, addr,
7469 sizeof (aarch64_erratum_835769_stub)))
7470 return FALSE;
7471 if (!elfNN_aarch64_output_map_sym (osi, AARCH64_MAP_INSN, addr))
7472 return FALSE;
7473 break;
4106101c
MS
7474 case aarch64_stub_erratum_843419_veneer:
7475 if (!elfNN_aarch64_output_stub_sym (osi, stub_name, addr,
7476 sizeof (aarch64_erratum_843419_stub)))
7477 return FALSE;
7478 if (!elfNN_aarch64_output_map_sym (osi, AARCH64_MAP_INSN, addr))
7479 return FALSE;
7480 break;
7481
a06ea964 7482 default:
8e2fe09f 7483 abort ();
a06ea964
NC
7484 }
7485
7486 return TRUE;
7487}
7488
7489/* Output mapping symbols for linker generated sections. */
7490
7491static bfd_boolean
cec5225b 7492elfNN_aarch64_output_arch_local_syms (bfd *output_bfd,
a06ea964
NC
7493 struct bfd_link_info *info,
7494 void *finfo,
7495 int (*func) (void *, const char *,
7496 Elf_Internal_Sym *,
7497 asection *,
7498 struct elf_link_hash_entry
7499 *))
7500{
7501 output_arch_syminfo osi;
cec5225b 7502 struct elf_aarch64_link_hash_table *htab;
a06ea964 7503
cec5225b 7504 htab = elf_aarch64_hash_table (info);
a06ea964
NC
7505
7506 osi.finfo = finfo;
7507 osi.info = info;
7508 osi.func = func;
7509
7510 /* Long calls stubs. */
7511 if (htab->stub_bfd && htab->stub_bfd->sections)
7512 {
7513 asection *stub_sec;
7514
7515 for (stub_sec = htab->stub_bfd->sections;
7516 stub_sec != NULL; stub_sec = stub_sec->next)
7517 {
7518 /* Ignore non-stub sections. */
7519 if (!strstr (stub_sec->name, STUB_SUFFIX))
7520 continue;
7521
7522 osi.sec = stub_sec;
7523
7524 osi.sec_shndx = _bfd_elf_section_from_bfd_section
7525 (output_bfd, osi.sec->output_section);
7526
61865519
MS
7527 /* The first instruction in a stub is always a branch. */
7528 if (!elfNN_aarch64_output_map_sym (&osi, AARCH64_MAP_INSN, 0))
7529 return FALSE;
7530
a06ea964
NC
7531 bfd_hash_traverse (&htab->stub_hash_table, aarch64_map_one_stub,
7532 &osi);
7533 }
7534 }
7535
7536 /* Finally, output mapping symbols for the PLT. */
7537 if (!htab->root.splt || htab->root.splt->size == 0)
7538 return TRUE;
7539
a06ea964
NC
7540 osi.sec_shndx = _bfd_elf_section_from_bfd_section
7541 (output_bfd, htab->root.splt->output_section);
7542 osi.sec = htab->root.splt;
7543
73524045 7544 elfNN_aarch64_output_map_sym (&osi, AARCH64_MAP_INSN, 0);
a06ea964
NC
7545
7546 return TRUE;
7547
7548}
7549
7550/* Allocate target specific section data. */
7551
7552static bfd_boolean
cec5225b 7553elfNN_aarch64_new_section_hook (bfd *abfd, asection *sec)
a06ea964
NC
7554{
7555 if (!sec->used_by_bfd)
7556 {
7557 _aarch64_elf_section_data *sdata;
7558 bfd_size_type amt = sizeof (*sdata);
7559
7560 sdata = bfd_zalloc (abfd, amt);
7561 if (sdata == NULL)
7562 return FALSE;
7563 sec->used_by_bfd = sdata;
7564 }
7565
7566 record_section_with_aarch64_elf_section_data (sec);
7567
7568 return _bfd_elf_new_section_hook (abfd, sec);
7569}
7570
7571
7572static void
7573unrecord_section_via_map_over_sections (bfd *abfd ATTRIBUTE_UNUSED,
7574 asection *sec,
7575 void *ignore ATTRIBUTE_UNUSED)
7576{
7577 unrecord_section_with_aarch64_elf_section_data (sec);
7578}
7579
7580static bfd_boolean
cec5225b 7581elfNN_aarch64_close_and_cleanup (bfd *abfd)
a06ea964
NC
7582{
7583 if (abfd->sections)
7584 bfd_map_over_sections (abfd,
7585 unrecord_section_via_map_over_sections, NULL);
7586
7587 return _bfd_elf_close_and_cleanup (abfd);
7588}
7589
7590static bfd_boolean
cec5225b 7591elfNN_aarch64_bfd_free_cached_info (bfd *abfd)
a06ea964
NC
7592{
7593 if (abfd->sections)
7594 bfd_map_over_sections (abfd,
7595 unrecord_section_via_map_over_sections, NULL);
7596
7597 return _bfd_free_cached_info (abfd);
7598}
7599
a06ea964
NC
7600/* Create dynamic sections. This is different from the ARM backend in that
7601 the got, plt, gotplt and their relocation sections are all created in the
7602 standard part of the bfd elf backend. */
7603
7604static bfd_boolean
cec5225b 7605elfNN_aarch64_create_dynamic_sections (bfd *dynobj,
a06ea964
NC
7606 struct bfd_link_info *info)
7607{
cec5225b 7608 struct elf_aarch64_link_hash_table *htab;
cc0efaa8
MS
7609
7610 /* We need to create .got section. */
7611 if (!aarch64_elf_create_got_section (dynobj, info))
7612 return FALSE;
a06ea964
NC
7613
7614 if (!_bfd_elf_create_dynamic_sections (dynobj, info))
7615 return FALSE;
7616
cec5225b 7617 htab = elf_aarch64_hash_table (info);
a06ea964 7618 htab->sdynbss = bfd_get_linker_section (dynobj, ".dynbss");
0e1862bb 7619 if (!bfd_link_pic (info))
a06ea964
NC
7620 htab->srelbss = bfd_get_linker_section (dynobj, ".rela.bss");
7621
0e1862bb 7622 if (!htab->sdynbss || (!bfd_link_pic (info) && !htab->srelbss))
a06ea964
NC
7623 abort ();
7624
a06ea964
NC
7625 return TRUE;
7626}
7627
7628
7629/* Allocate space in .plt, .got and associated reloc sections for
7630 dynamic relocs. */
7631
7632static bfd_boolean
cec5225b 7633elfNN_aarch64_allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
a06ea964
NC
7634{
7635 struct bfd_link_info *info;
cec5225b
YZ
7636 struct elf_aarch64_link_hash_table *htab;
7637 struct elf_aarch64_link_hash_entry *eh;
a06ea964
NC
7638 struct elf_dyn_relocs *p;
7639
7640 /* An example of a bfd_link_hash_indirect symbol is versioned
7641 symbol. For example: __gxx_personality_v0(bfd_link_hash_indirect)
7642 -> __gxx_personality_v0(bfd_link_hash_defined)
7643
7644 There is no need to process bfd_link_hash_indirect symbols here
7645 because we will also be presented with the concrete instance of
cec5225b 7646 the symbol and elfNN_aarch64_copy_indirect_symbol () will have been
a06ea964
NC
7647 called to copy all relevant data from the generic to the concrete
7648 symbol instance.
7649 */
7650 if (h->root.type == bfd_link_hash_indirect)
7651 return TRUE;
7652
7653 if (h->root.type == bfd_link_hash_warning)
7654 h = (struct elf_link_hash_entry *) h->root.u.i.link;
7655
7656 info = (struct bfd_link_info *) inf;
cec5225b 7657 htab = elf_aarch64_hash_table (info);
a06ea964 7658
1419bbe5
WN
7659 /* Since STT_GNU_IFUNC symbol must go through PLT, we handle it
7660 here if it is defined and referenced in a non-shared object. */
7661 if (h->type == STT_GNU_IFUNC
7662 && h->def_regular)
7663 return TRUE;
7664 else if (htab->root.dynamic_sections_created && h->plt.refcount > 0)
a06ea964
NC
7665 {
7666 /* Make sure this symbol is output as a dynamic symbol.
7667 Undefined weak syms won't yet be marked as dynamic. */
7668 if (h->dynindx == -1 && !h->forced_local)
7669 {
7670 if (!bfd_elf_link_record_dynamic_symbol (info, h))
7671 return FALSE;
7672 }
7673
0e1862bb 7674 if (bfd_link_pic (info) || WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, 0, h))
a06ea964
NC
7675 {
7676 asection *s = htab->root.splt;
7677
7678 /* If this is the first .plt entry, make room for the special
7679 first entry. */
7680 if (s->size == 0)
7681 s->size += htab->plt_header_size;
7682
7683 h->plt.offset = s->size;
7684
7685 /* If this symbol is not defined in a regular file, and we are
7686 not generating a shared library, then set the symbol to this
7687 location in the .plt. This is required to make function
7688 pointers compare as equal between the normal executable and
7689 the shared library. */
0e1862bb 7690 if (!bfd_link_pic (info) && !h->def_regular)
a06ea964
NC
7691 {
7692 h->root.u.def.section = s;
7693 h->root.u.def.value = h->plt.offset;
7694 }
7695
7696 /* Make room for this entry. For now we only create the
7697 small model PLT entries. We later need to find a way
7698 of relaxing into these from the large model PLT entries. */
7699 s->size += PLT_SMALL_ENTRY_SIZE;
7700
7701 /* We also need to make an entry in the .got.plt section, which
7702 will be placed in the .got section by the linker script. */
7703 htab->root.sgotplt->size += GOT_ENTRY_SIZE;
7704
7705 /* We also need to make an entry in the .rela.plt section. */
7706 htab->root.srelplt->size += RELOC_SIZE (htab);
7707
7708 /* We need to ensure that all GOT entries that serve the PLT
7709 are consecutive with the special GOT slots [0] [1] and
7710 [2]. Any addtional relocations, such as
7711 R_AARCH64_TLSDESC, must be placed after the PLT related
7712 entries. We abuse the reloc_count such that during
7713 sizing we adjust reloc_count to indicate the number of
7714 PLT related reserved entries. In subsequent phases when
7715 filling in the contents of the reloc entries, PLT related
7716 entries are placed by computing their PLT index (0
7717 .. reloc_count). While other none PLT relocs are placed
7718 at the slot indicated by reloc_count and reloc_count is
7719 updated. */
7720
7721 htab->root.srelplt->reloc_count++;
7722 }
7723 else
7724 {
7725 h->plt.offset = (bfd_vma) - 1;
7726 h->needs_plt = 0;
7727 }
7728 }
7729 else
7730 {
7731 h->plt.offset = (bfd_vma) - 1;
7732 h->needs_plt = 0;
7733 }
7734
cec5225b 7735 eh = (struct elf_aarch64_link_hash_entry *) h;
a06ea964
NC
7736 eh->tlsdesc_got_jump_table_offset = (bfd_vma) - 1;
7737
7738 if (h->got.refcount > 0)
7739 {
7740 bfd_boolean dyn;
cec5225b 7741 unsigned got_type = elf_aarch64_hash_entry (h)->got_type;
a06ea964
NC
7742
7743 h->got.offset = (bfd_vma) - 1;
7744
7745 dyn = htab->root.dynamic_sections_created;
7746
7747 /* Make sure this symbol is output as a dynamic symbol.
7748 Undefined weak syms won't yet be marked as dynamic. */
7749 if (dyn && h->dynindx == -1 && !h->forced_local)
7750 {
7751 if (!bfd_elf_link_record_dynamic_symbol (info, h))
7752 return FALSE;
7753 }
7754
7755 if (got_type == GOT_UNKNOWN)
7756 {
7757 }
7758 else if (got_type == GOT_NORMAL)
7759 {
7760 h->got.offset = htab->root.sgot->size;
7761 htab->root.sgot->size += GOT_ENTRY_SIZE;
7762 if ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
7763 || h->root.type != bfd_link_hash_undefweak)
0e1862bb 7764 && (bfd_link_pic (info)
a06ea964
NC
7765 || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h)))
7766 {
7767 htab->root.srelgot->size += RELOC_SIZE (htab);
7768 }
7769 }
7770 else
7771 {
7772 int indx;
7773 if (got_type & GOT_TLSDESC_GD)
7774 {
7775 eh->tlsdesc_got_jump_table_offset =
7776 (htab->root.sgotplt->size
7777 - aarch64_compute_jump_table_size (htab));
7778 htab->root.sgotplt->size += GOT_ENTRY_SIZE * 2;
7779 h->got.offset = (bfd_vma) - 2;
7780 }
7781
7782 if (got_type & GOT_TLS_GD)
7783 {
7784 h->got.offset = htab->root.sgot->size;
7785 htab->root.sgot->size += GOT_ENTRY_SIZE * 2;
7786 }
7787
7788 if (got_type & GOT_TLS_IE)
7789 {
7790 h->got.offset = htab->root.sgot->size;
7791 htab->root.sgot->size += GOT_ENTRY_SIZE;
7792 }
7793
7794 indx = h && h->dynindx != -1 ? h->dynindx : 0;
7795 if ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
7796 || h->root.type != bfd_link_hash_undefweak)
0e1862bb 7797 && (bfd_link_pic (info)
a06ea964
NC
7798 || indx != 0
7799 || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h)))
7800 {
7801 if (got_type & GOT_TLSDESC_GD)
7802 {
7803 htab->root.srelplt->size += RELOC_SIZE (htab);
7804 /* Note reloc_count not incremented here! We have
7805 already adjusted reloc_count for this relocation
7806 type. */
7807
7808 /* TLSDESC PLT is now needed, but not yet determined. */
7809 htab->tlsdesc_plt = (bfd_vma) - 1;
7810 }
7811
7812 if (got_type & GOT_TLS_GD)
7813 htab->root.srelgot->size += RELOC_SIZE (htab) * 2;
7814
7815 if (got_type & GOT_TLS_IE)
7816 htab->root.srelgot->size += RELOC_SIZE (htab);
7817 }
7818 }
7819 }
7820 else
7821 {
7822 h->got.offset = (bfd_vma) - 1;
7823 }
7824
7825 if (eh->dyn_relocs == NULL)
7826 return TRUE;
7827
7828 /* In the shared -Bsymbolic case, discard space allocated for
7829 dynamic pc-relative relocs against symbols which turn out to be
7830 defined in regular objects. For the normal shared case, discard
7831 space for pc-relative relocs that have become local due to symbol
7832 visibility changes. */
7833
0e1862bb 7834 if (bfd_link_pic (info))
a06ea964
NC
7835 {
7836 /* Relocs that use pc_count are those that appear on a call
7837 insn, or certain REL relocs that can generated via assembly.
7838 We want calls to protected symbols to resolve directly to the
7839 function rather than going via the plt. If people want
7840 function pointer comparisons to work as expected then they
7841 should avoid writing weird assembly. */
7842 if (SYMBOL_CALLS_LOCAL (info, h))
7843 {
7844 struct elf_dyn_relocs **pp;
7845
7846 for (pp = &eh->dyn_relocs; (p = *pp) != NULL;)
7847 {
7848 p->count -= p->pc_count;
7849 p->pc_count = 0;
7850 if (p->count == 0)
7851 *pp = p->next;
7852 else
7853 pp = &p->next;
7854 }
7855 }
7856
7857 /* Also discard relocs on undefined weak syms with non-default
7858 visibility. */
7859 if (eh->dyn_relocs != NULL && h->root.type == bfd_link_hash_undefweak)
7860 {
7861 if (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT)
7862 eh->dyn_relocs = NULL;
7863
7864 /* Make sure undefined weak symbols are output as a dynamic
7865 symbol in PIEs. */
7866 else if (h->dynindx == -1
7867 && !h->forced_local
7868 && !bfd_elf_link_record_dynamic_symbol (info, h))
7869 return FALSE;
7870 }
7871
7872 }
7873 else if (ELIMINATE_COPY_RELOCS)
7874 {
7875 /* For the non-shared case, discard space for relocs against
7876 symbols which turn out to need copy relocs or are not
7877 dynamic. */
7878
7879 if (!h->non_got_ref
7880 && ((h->def_dynamic
7881 && !h->def_regular)
7882 || (htab->root.dynamic_sections_created
7883 && (h->root.type == bfd_link_hash_undefweak
7884 || h->root.type == bfd_link_hash_undefined))))
7885 {
7886 /* Make sure this symbol is output as a dynamic symbol.
7887 Undefined weak syms won't yet be marked as dynamic. */
7888 if (h->dynindx == -1
7889 && !h->forced_local
7890 && !bfd_elf_link_record_dynamic_symbol (info, h))
7891 return FALSE;
7892
7893 /* If that succeeded, we know we'll be keeping all the
7894 relocs. */
7895 if (h->dynindx != -1)
7896 goto keep;
7897 }
7898
7899 eh->dyn_relocs = NULL;
7900
7901 keep:;
7902 }
7903
7904 /* Finally, allocate space. */
7905 for (p = eh->dyn_relocs; p != NULL; p = p->next)
7906 {
7907 asection *sreloc;
7908
7909 sreloc = elf_section_data (p->sec)->sreloc;
7910
7911 BFD_ASSERT (sreloc != NULL);
7912
7913 sreloc->size += p->count * RELOC_SIZE (htab);
7914 }
7915
7916 return TRUE;
7917}
7918
1419bbe5
WN
7919/* Allocate space in .plt, .got and associated reloc sections for
7920 ifunc dynamic relocs. */
7921
7922static bfd_boolean
7923elfNN_aarch64_allocate_ifunc_dynrelocs (struct elf_link_hash_entry *h,
7924 void *inf)
7925{
7926 struct bfd_link_info *info;
7927 struct elf_aarch64_link_hash_table *htab;
7928 struct elf_aarch64_link_hash_entry *eh;
7929
7930 /* An example of a bfd_link_hash_indirect symbol is versioned
7931 symbol. For example: __gxx_personality_v0(bfd_link_hash_indirect)
7932 -> __gxx_personality_v0(bfd_link_hash_defined)
7933
7934 There is no need to process bfd_link_hash_indirect symbols here
7935 because we will also be presented with the concrete instance of
7936 the symbol and elfNN_aarch64_copy_indirect_symbol () will have been
7937 called to copy all relevant data from the generic to the concrete
7938 symbol instance.
7939 */
7940 if (h->root.type == bfd_link_hash_indirect)
7941 return TRUE;
7942
7943 if (h->root.type == bfd_link_hash_warning)
7944 h = (struct elf_link_hash_entry *) h->root.u.i.link;
7945
7946 info = (struct bfd_link_info *) inf;
7947 htab = elf_aarch64_hash_table (info);
7948
7949 eh = (struct elf_aarch64_link_hash_entry *) h;
7950
7951 /* Since STT_GNU_IFUNC symbol must go through PLT, we handle it
7952 here if it is defined and referenced in a non-shared object. */
7953 if (h->type == STT_GNU_IFUNC
7954 && h->def_regular)
7955 return _bfd_elf_allocate_ifunc_dyn_relocs (info, h,
7956 &eh->dyn_relocs,
7957 htab->plt_entry_size,
7958 htab->plt_header_size,
7959 GOT_ENTRY_SIZE);
7960 return TRUE;
7961}
7962
7963/* Allocate space in .plt, .got and associated reloc sections for
7964 local dynamic relocs. */
7965
7966static bfd_boolean
7967elfNN_aarch64_allocate_local_dynrelocs (void **slot, void *inf)
7968{
7969 struct elf_link_hash_entry *h
7970 = (struct elf_link_hash_entry *) *slot;
7971
7972 if (h->type != STT_GNU_IFUNC
7973 || !h->def_regular
7974 || !h->ref_regular
7975 || !h->forced_local
7976 || h->root.type != bfd_link_hash_defined)
7977 abort ();
7978
7979 return elfNN_aarch64_allocate_dynrelocs (h, inf);
7980}
7981
7982/* Allocate space in .plt, .got and associated reloc sections for
7983 local ifunc dynamic relocs. */
7984
7985static bfd_boolean
7986elfNN_aarch64_allocate_local_ifunc_dynrelocs (void **slot, void *inf)
7987{
7988 struct elf_link_hash_entry *h
7989 = (struct elf_link_hash_entry *) *slot;
7990
7991 if (h->type != STT_GNU_IFUNC
7992 || !h->def_regular
7993 || !h->ref_regular
7994 || !h->forced_local
7995 || h->root.type != bfd_link_hash_defined)
7996 abort ();
7997
7998 return elfNN_aarch64_allocate_ifunc_dynrelocs (h, inf);
7999}
a06ea964 8000
c2170589
JW
8001/* Find any dynamic relocs that apply to read-only sections. */
8002
8003static bfd_boolean
8004aarch64_readonly_dynrelocs (struct elf_link_hash_entry * h, void * inf)
8005{
8006 struct elf_aarch64_link_hash_entry * eh;
8007 struct elf_dyn_relocs * p;
8008
8009 eh = (struct elf_aarch64_link_hash_entry *) h;
8010 for (p = eh->dyn_relocs; p != NULL; p = p->next)
8011 {
8012 asection *s = p->sec;
8013
8014 if (s != NULL && (s->flags & SEC_READONLY) != 0)
8015 {
8016 struct bfd_link_info *info = (struct bfd_link_info *) inf;
8017
8018 info->flags |= DF_TEXTREL;
8019
8020 /* Not an error, just cut short the traversal. */
8021 return FALSE;
8022 }
8023 }
8024 return TRUE;
8025}
8026
a06ea964
NC
8027/* This is the most important function of all . Innocuosly named
8028 though ! */
8029static bfd_boolean
cec5225b 8030elfNN_aarch64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
a06ea964
NC
8031 struct bfd_link_info *info)
8032{
cec5225b 8033 struct elf_aarch64_link_hash_table *htab;
a06ea964
NC
8034 bfd *dynobj;
8035 asection *s;
8036 bfd_boolean relocs;
8037 bfd *ibfd;
8038
cec5225b 8039 htab = elf_aarch64_hash_table ((info));
a06ea964
NC
8040 dynobj = htab->root.dynobj;
8041
8042 BFD_ASSERT (dynobj != NULL);
8043
8044 if (htab->root.dynamic_sections_created)
8045 {
9b8b325a 8046 if (bfd_link_executable (info) && !info->nointerp)
a06ea964
NC
8047 {
8048 s = bfd_get_linker_section (dynobj, ".interp");
8049 if (s == NULL)
8050 abort ();
8051 s->size = sizeof ELF_DYNAMIC_INTERPRETER;
8052 s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
8053 }
8054 }
8055
8056 /* Set up .got offsets for local syms, and space for local dynamic
8057 relocs. */
c72f2fb2 8058 for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
a06ea964
NC
8059 {
8060 struct elf_aarch64_local_symbol *locals = NULL;
8061 Elf_Internal_Shdr *symtab_hdr;
8062 asection *srel;
8063 unsigned int i;
8064
8065 if (!is_aarch64_elf (ibfd))
8066 continue;
8067
8068 for (s = ibfd->sections; s != NULL; s = s->next)
8069 {
8070 struct elf_dyn_relocs *p;
8071
8072 for (p = (struct elf_dyn_relocs *)
8073 (elf_section_data (s)->local_dynrel); p != NULL; p = p->next)
8074 {
8075 if (!bfd_is_abs_section (p->sec)
8076 && bfd_is_abs_section (p->sec->output_section))
8077 {
8078 /* Input section has been discarded, either because
8079 it is a copy of a linkonce section or due to
8080 linker script /DISCARD/, so we'll be discarding
8081 the relocs too. */
8082 }
8083 else if (p->count != 0)
8084 {
8085 srel = elf_section_data (p->sec)->sreloc;
8086 srel->size += p->count * RELOC_SIZE (htab);
8087 if ((p->sec->output_section->flags & SEC_READONLY) != 0)
8088 info->flags |= DF_TEXTREL;
8089 }
8090 }
8091 }
8092
cec5225b 8093 locals = elf_aarch64_locals (ibfd);
a06ea964
NC
8094 if (!locals)
8095 continue;
8096
8097 symtab_hdr = &elf_symtab_hdr (ibfd);
8098 srel = htab->root.srelgot;
8099 for (i = 0; i < symtab_hdr->sh_info; i++)
8100 {
8101 locals[i].got_offset = (bfd_vma) - 1;
8102 locals[i].tlsdesc_got_jump_table_offset = (bfd_vma) - 1;
8103 if (locals[i].got_refcount > 0)
8104 {
8105 unsigned got_type = locals[i].got_type;
8106 if (got_type & GOT_TLSDESC_GD)
8107 {
8108 locals[i].tlsdesc_got_jump_table_offset =
8109 (htab->root.sgotplt->size
8110 - aarch64_compute_jump_table_size (htab));
8111 htab->root.sgotplt->size += GOT_ENTRY_SIZE * 2;
8112 locals[i].got_offset = (bfd_vma) - 2;
8113 }
8114
8115 if (got_type & GOT_TLS_GD)
8116 {
8117 locals[i].got_offset = htab->root.sgot->size;
8118 htab->root.sgot->size += GOT_ENTRY_SIZE * 2;
8119 }
8120
b53b1bed
JW
8121 if (got_type & GOT_TLS_IE
8122 || got_type & GOT_NORMAL)
a06ea964
NC
8123 {
8124 locals[i].got_offset = htab->root.sgot->size;
8125 htab->root.sgot->size += GOT_ENTRY_SIZE;
8126 }
8127
8128 if (got_type == GOT_UNKNOWN)
8129 {
8130 }
8131
0e1862bb 8132 if (bfd_link_pic (info))
a06ea964
NC
8133 {
8134 if (got_type & GOT_TLSDESC_GD)
8135 {
8136 htab->root.srelplt->size += RELOC_SIZE (htab);
8137 /* Note RELOC_COUNT not incremented here! */
8138 htab->tlsdesc_plt = (bfd_vma) - 1;
8139 }
8140
8141 if (got_type & GOT_TLS_GD)
8142 htab->root.srelgot->size += RELOC_SIZE (htab) * 2;
8143
b53b1bed
JW
8144 if (got_type & GOT_TLS_IE
8145 || got_type & GOT_NORMAL)
a06ea964
NC
8146 htab->root.srelgot->size += RELOC_SIZE (htab);
8147 }
8148 }
8149 else
8150 {
8151 locals[i].got_refcount = (bfd_vma) - 1;
8152 }
8153 }
8154 }
8155
8156
8157 /* Allocate global sym .plt and .got entries, and space for global
8158 sym dynamic relocs. */
cec5225b 8159 elf_link_hash_traverse (&htab->root, elfNN_aarch64_allocate_dynrelocs,
a06ea964
NC
8160 info);
8161
1419bbe5
WN
8162 /* Allocate global ifunc sym .plt and .got entries, and space for global
8163 ifunc sym dynamic relocs. */
8164 elf_link_hash_traverse (&htab->root, elfNN_aarch64_allocate_ifunc_dynrelocs,
8165 info);
8166
8167 /* Allocate .plt and .got entries, and space for local symbols. */
8168 htab_traverse (htab->loc_hash_table,
8169 elfNN_aarch64_allocate_local_dynrelocs,
8170 info);
8171
8172 /* Allocate .plt and .got entries, and space for local ifunc symbols. */
8173 htab_traverse (htab->loc_hash_table,
8174 elfNN_aarch64_allocate_local_ifunc_dynrelocs,
8175 info);
a06ea964
NC
8176
8177 /* For every jump slot reserved in the sgotplt, reloc_count is
8178 incremented. However, when we reserve space for TLS descriptors,
8179 it's not incremented, so in order to compute the space reserved
8180 for them, it suffices to multiply the reloc count by the jump
8181 slot size. */
8182
8183 if (htab->root.srelplt)
8847944f 8184 htab->sgotplt_jump_table_size = aarch64_compute_jump_table_size (htab);
a06ea964
NC
8185
8186 if (htab->tlsdesc_plt)
8187 {
8188 if (htab->root.splt->size == 0)
8189 htab->root.splt->size += PLT_ENTRY_SIZE;
8190
8191 htab->tlsdesc_plt = htab->root.splt->size;
8192 htab->root.splt->size += PLT_TLSDESC_ENTRY_SIZE;
8193
8194 /* If we're not using lazy TLS relocations, don't generate the
8195 GOT entry required. */
8196 if (!(info->flags & DF_BIND_NOW))
8197 {
8198 htab->dt_tlsdesc_got = htab->root.sgot->size;
8199 htab->root.sgot->size += GOT_ENTRY_SIZE;
8200 }
8201 }
8202
68fcca92 8203 /* Init mapping symbols information to use later to distingush between
4106101c
MS
8204 code and data while scanning for errata. */
8205 if (htab->fix_erratum_835769 || htab->fix_erratum_843419)
68fcca92
JW
8206 for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
8207 {
8208 if (!is_aarch64_elf (ibfd))
8209 continue;
8210 bfd_elfNN_aarch64_init_maps (ibfd);
8211 }
8212
a06ea964
NC
8213 /* We now have determined the sizes of the various dynamic sections.
8214 Allocate memory for them. */
8215 relocs = FALSE;
8216 for (s = dynobj->sections; s != NULL; s = s->next)
8217 {
8218 if ((s->flags & SEC_LINKER_CREATED) == 0)
8219 continue;
8220
8221 if (s == htab->root.splt
8222 || s == htab->root.sgot
8223 || s == htab->root.sgotplt
8224 || s == htab->root.iplt
8225 || s == htab->root.igotplt || s == htab->sdynbss)
8226 {
8227 /* Strip this section if we don't need it; see the
8228 comment below. */
8229 }
8230 else if (CONST_STRNEQ (bfd_get_section_name (dynobj, s), ".rela"))
8231 {
8232 if (s->size != 0 && s != htab->root.srelplt)
8233 relocs = TRUE;
8234
8235 /* We use the reloc_count field as a counter if we need
8236 to copy relocs into the output file. */
8237 if (s != htab->root.srelplt)
8238 s->reloc_count = 0;
8239 }
8240 else
8241 {
8242 /* It's not one of our sections, so don't allocate space. */
8243 continue;
8244 }
8245
8246 if (s->size == 0)
8247 {
8248 /* If we don't need this section, strip it from the
8249 output file. This is mostly to handle .rela.bss and
8250 .rela.plt. We must create both sections in
8251 create_dynamic_sections, because they must be created
8252 before the linker maps input sections to output
8253 sections. The linker does that before
8254 adjust_dynamic_symbol is called, and it is that
8255 function which decides whether anything needs to go
8256 into these sections. */
8257
8258 s->flags |= SEC_EXCLUDE;
8259 continue;
8260 }
8261
8262 if ((s->flags & SEC_HAS_CONTENTS) == 0)
8263 continue;
8264
8265 /* Allocate memory for the section contents. We use bfd_zalloc
8266 here in case unused entries are not reclaimed before the
8267 section's contents are written out. This should not happen,
8268 but this way if it does, we get a R_AARCH64_NONE reloc instead
8269 of garbage. */
8270 s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
8271 if (s->contents == NULL)
8272 return FALSE;
8273 }
8274
8275 if (htab->root.dynamic_sections_created)
8276 {
8277 /* Add some entries to the .dynamic section. We fill in the
cec5225b 8278 values later, in elfNN_aarch64_finish_dynamic_sections, but we
a06ea964
NC
8279 must add the entries now so that we get the correct size for
8280 the .dynamic section. The DT_DEBUG entry is filled in by the
8281 dynamic linker and used by the debugger. */
8282#define add_dynamic_entry(TAG, VAL) \
8283 _bfd_elf_add_dynamic_entry (info, TAG, VAL)
8284
0e1862bb 8285 if (bfd_link_executable (info))
a06ea964
NC
8286 {
8287 if (!add_dynamic_entry (DT_DEBUG, 0))
8288 return FALSE;
8289 }
8290
8291 if (htab->root.splt->size != 0)
8292 {
8293 if (!add_dynamic_entry (DT_PLTGOT, 0)
8294 || !add_dynamic_entry (DT_PLTRELSZ, 0)
8295 || !add_dynamic_entry (DT_PLTREL, DT_RELA)
8296 || !add_dynamic_entry (DT_JMPREL, 0))
8297 return FALSE;
8298
8299 if (htab->tlsdesc_plt
8300 && (!add_dynamic_entry (DT_TLSDESC_PLT, 0)
8301 || !add_dynamic_entry (DT_TLSDESC_GOT, 0)))
8302 return FALSE;
8303 }
8304
8305 if (relocs)
8306 {
8307 if (!add_dynamic_entry (DT_RELA, 0)
8308 || !add_dynamic_entry (DT_RELASZ, 0)
8309 || !add_dynamic_entry (DT_RELAENT, RELOC_SIZE (htab)))
8310 return FALSE;
8311
8312 /* If any dynamic relocs apply to a read-only section,
8313 then we need a DT_TEXTREL entry. */
c2170589
JW
8314 if ((info->flags & DF_TEXTREL) == 0)
8315 elf_link_hash_traverse (& htab->root, aarch64_readonly_dynrelocs,
8316 info);
8317
a06ea964
NC
8318 if ((info->flags & DF_TEXTREL) != 0)
8319 {
8320 if (!add_dynamic_entry (DT_TEXTREL, 0))
8321 return FALSE;
8322 }
8323 }
8324 }
8325#undef add_dynamic_entry
8326
8327 return TRUE;
a06ea964
NC
8328}
8329
8330static inline void
caed7120
YZ
8331elf_aarch64_update_plt_entry (bfd *output_bfd,
8332 bfd_reloc_code_real_type r_type,
8333 bfd_byte *plt_entry, bfd_vma value)
a06ea964 8334{
caed7120
YZ
8335 reloc_howto_type *howto = elfNN_aarch64_howto_from_bfd_reloc (r_type);
8336
8337 _bfd_aarch64_elf_put_addend (output_bfd, plt_entry, r_type, howto, value);
a06ea964
NC
8338}
8339
8340static void
cec5225b
YZ
8341elfNN_aarch64_create_small_pltn_entry (struct elf_link_hash_entry *h,
8342 struct elf_aarch64_link_hash_table
1419bbe5
WN
8343 *htab, bfd *output_bfd,
8344 struct bfd_link_info *info)
a06ea964
NC
8345{
8346 bfd_byte *plt_entry;
8347 bfd_vma plt_index;
8348 bfd_vma got_offset;
8349 bfd_vma gotplt_entry_address;
8350 bfd_vma plt_entry_address;
8351 Elf_Internal_Rela rela;
8352 bfd_byte *loc;
1419bbe5
WN
8353 asection *plt, *gotplt, *relplt;
8354
8355 /* When building a static executable, use .iplt, .igot.plt and
8356 .rela.iplt sections for STT_GNU_IFUNC symbols. */
8357 if (htab->root.splt != NULL)
8358 {
8359 plt = htab->root.splt;
8360 gotplt = htab->root.sgotplt;
8361 relplt = htab->root.srelplt;
8362 }
8363 else
8364 {
8365 plt = htab->root.iplt;
8366 gotplt = htab->root.igotplt;
8367 relplt = htab->root.irelplt;
8368 }
8369
8370 /* Get the index in the procedure linkage table which
8371 corresponds to this symbol. This is the index of this symbol
8372 in all the symbols for which we are making plt entries. The
8373 first entry in the procedure linkage table is reserved.
a06ea964 8374
1419bbe5
WN
8375 Get the offset into the .got table of the entry that
8376 corresponds to this function. Each .got entry is GOT_ENTRY_SIZE
8377 bytes. The first three are reserved for the dynamic linker.
692e2b8b 8378
1419bbe5
WN
8379 For static executables, we don't reserve anything. */
8380
8381 if (plt == htab->root.splt)
8382 {
8383 plt_index = (h->plt.offset - htab->plt_header_size) / htab->plt_entry_size;
8384 got_offset = (plt_index + 3) * GOT_ENTRY_SIZE;
8385 }
8386 else
8387 {
8388 plt_index = h->plt.offset / htab->plt_entry_size;
8389 got_offset = plt_index * GOT_ENTRY_SIZE;
8390 }
8391
8392 plt_entry = plt->contents + h->plt.offset;
8393 plt_entry_address = plt->output_section->vma
f44a1f8e 8394 + plt->output_offset + h->plt.offset;
1419bbe5
WN
8395 gotplt_entry_address = gotplt->output_section->vma +
8396 gotplt->output_offset + got_offset;
a06ea964
NC
8397
8398 /* Copy in the boiler-plate for the PLTn entry. */
cec5225b 8399 memcpy (plt_entry, elfNN_aarch64_small_plt_entry, PLT_SMALL_ENTRY_SIZE);
a06ea964
NC
8400
8401 /* Fill in the top 21 bits for this: ADRP x16, PLT_GOT + n * 8.
8402 ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff */
caed7120
YZ
8403 elf_aarch64_update_plt_entry (output_bfd, BFD_RELOC_AARCH64_ADR_HI21_PCREL,
8404 plt_entry,
8405 PG (gotplt_entry_address) -
8406 PG (plt_entry_address));
a06ea964
NC
8407
8408 /* Fill in the lo12 bits for the load from the pltgot. */
caed7120
YZ
8409 elf_aarch64_update_plt_entry (output_bfd, BFD_RELOC_AARCH64_LDSTNN_LO12,
8410 plt_entry + 4,
8411 PG_OFFSET (gotplt_entry_address));
a06ea964 8412
9aff4b7a 8413 /* Fill in the lo12 bits for the add from the pltgot entry. */
caed7120
YZ
8414 elf_aarch64_update_plt_entry (output_bfd, BFD_RELOC_AARCH64_ADD_LO12,
8415 plt_entry + 8,
8416 PG_OFFSET (gotplt_entry_address));
a06ea964
NC
8417
8418 /* All the GOTPLT Entries are essentially initialized to PLT0. */
cec5225b 8419 bfd_put_NN (output_bfd,
1419bbe5
WN
8420 plt->output_section->vma + plt->output_offset,
8421 gotplt->contents + got_offset);
a06ea964 8422
a06ea964 8423 rela.r_offset = gotplt_entry_address;
1419bbe5
WN
8424
8425 if (h->dynindx == -1
0e1862bb 8426 || ((bfd_link_executable (info)
1419bbe5
WN
8427 || ELF_ST_VISIBILITY (h->other) != STV_DEFAULT)
8428 && h->def_regular
8429 && h->type == STT_GNU_IFUNC))
8430 {
8431 /* If an STT_GNU_IFUNC symbol is locally defined, generate
8432 R_AARCH64_IRELATIVE instead of R_AARCH64_JUMP_SLOT. */
8433 rela.r_info = ELFNN_R_INFO (0, AARCH64_R (IRELATIVE));
8434 rela.r_addend = (h->root.u.def.value
8435 + h->root.u.def.section->output_section->vma
8436 + h->root.u.def.section->output_offset);
8437 }
8438 else
8439 {
8440 /* Fill in the entry in the .rela.plt section. */
8441 rela.r_info = ELFNN_R_INFO (h->dynindx, AARCH64_R (JUMP_SLOT));
8442 rela.r_addend = 0;
8443 }
a06ea964
NC
8444
8445 /* Compute the relocation entry to used based on PLT index and do
8446 not adjust reloc_count. The reloc_count has already been adjusted
8447 to account for this entry. */
1419bbe5 8448 loc = relplt->contents + plt_index * RELOC_SIZE (htab);
cec5225b 8449 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
a06ea964
NC
8450}
8451
8452/* Size sections even though they're not dynamic. We use it to setup
8453 _TLS_MODULE_BASE_, if needed. */
8454
8455static bfd_boolean
cec5225b 8456elfNN_aarch64_always_size_sections (bfd *output_bfd,
a06ea964
NC
8457 struct bfd_link_info *info)
8458{
8459 asection *tls_sec;
8460
0e1862bb 8461 if (bfd_link_relocatable (info))
a06ea964
NC
8462 return TRUE;
8463
8464 tls_sec = elf_hash_table (info)->tls_sec;
8465
8466 if (tls_sec)
8467 {
8468 struct elf_link_hash_entry *tlsbase;
8469
8470 tlsbase = elf_link_hash_lookup (elf_hash_table (info),
8471 "_TLS_MODULE_BASE_", TRUE, TRUE, FALSE);
8472
8473 if (tlsbase)
8474 {
8475 struct bfd_link_hash_entry *h = NULL;
8476 const struct elf_backend_data *bed =
8477 get_elf_backend_data (output_bfd);
8478
8479 if (!(_bfd_generic_link_add_one_symbol
8480 (info, output_bfd, "_TLS_MODULE_BASE_", BSF_LOCAL,
8481 tls_sec, 0, NULL, FALSE, bed->collect, &h)))
8482 return FALSE;
8483
8484 tlsbase->type = STT_TLS;
8485 tlsbase = (struct elf_link_hash_entry *) h;
8486 tlsbase->def_regular = 1;
8487 tlsbase->other = STV_HIDDEN;
8488 (*bed->elf_backend_hide_symbol) (info, tlsbase, TRUE);
8489 }
8490 }
8491
8492 return TRUE;
8493}
8494
8495/* Finish up dynamic symbol handling. We set the contents of various
8496 dynamic sections here. */
8497static bfd_boolean
cec5225b 8498elfNN_aarch64_finish_dynamic_symbol (bfd *output_bfd,
a06ea964
NC
8499 struct bfd_link_info *info,
8500 struct elf_link_hash_entry *h,
8501 Elf_Internal_Sym *sym)
8502{
cec5225b
YZ
8503 struct elf_aarch64_link_hash_table *htab;
8504 htab = elf_aarch64_hash_table (info);
a06ea964
NC
8505
8506 if (h->plt.offset != (bfd_vma) - 1)
8507 {
1419bbe5
WN
8508 asection *plt, *gotplt, *relplt;
8509
a06ea964
NC
8510 /* This symbol has an entry in the procedure linkage table. Set
8511 it up. */
8512
1419bbe5
WN
8513 /* When building a static executable, use .iplt, .igot.plt and
8514 .rela.iplt sections for STT_GNU_IFUNC symbols. */
8515 if (htab->root.splt != NULL)
8516 {
8517 plt = htab->root.splt;
8518 gotplt = htab->root.sgotplt;
8519 relplt = htab->root.srelplt;
8520 }
8521 else
8522 {
8523 plt = htab->root.iplt;
8524 gotplt = htab->root.igotplt;
8525 relplt = htab->root.irelplt;
8526 }
8527
8528 /* This symbol has an entry in the procedure linkage table. Set
8529 it up. */
8530 if ((h->dynindx == -1
0e1862bb 8531 && !((h->forced_local || bfd_link_executable (info))
1419bbe5
WN
8532 && h->def_regular
8533 && h->type == STT_GNU_IFUNC))
8534 || plt == NULL
8535 || gotplt == NULL
8536 || relplt == NULL)
a06ea964
NC
8537 abort ();
8538
1419bbe5 8539 elfNN_aarch64_create_small_pltn_entry (h, htab, output_bfd, info);
a06ea964
NC
8540 if (!h->def_regular)
8541 {
8542 /* Mark the symbol as undefined, rather than as defined in
46b87d49 8543 the .plt section. */
a06ea964 8544 sym->st_shndx = SHN_UNDEF;
46b87d49
WN
8545 /* If the symbol is weak we need to clear the value.
8546 Otherwise, the PLT entry would provide a definition for
8547 the symbol even if the symbol wasn't defined anywhere,
8548 and so the symbol would never be NULL. Leave the value if
8549 there were any relocations where pointer equality matters
8550 (this is a clue for the dynamic linker, to make function
8551 pointer comparisons work between an application and shared
8552 library). */
8553 if (!h->ref_regular_nonweak || !h->pointer_equality_needed)
8554 sym->st_value = 0;
a06ea964
NC
8555 }
8556 }
8557
8558 if (h->got.offset != (bfd_vma) - 1
cec5225b 8559 && elf_aarch64_hash_entry (h)->got_type == GOT_NORMAL)
a06ea964
NC
8560 {
8561 Elf_Internal_Rela rela;
8562 bfd_byte *loc;
8563
8564 /* This symbol has an entry in the global offset table. Set it
8565 up. */
8566 if (htab->root.sgot == NULL || htab->root.srelgot == NULL)
8567 abort ();
8568
8569 rela.r_offset = (htab->root.sgot->output_section->vma
8570 + htab->root.sgot->output_offset
8571 + (h->got.offset & ~(bfd_vma) 1));
8572
49206388
WN
8573 if (h->def_regular
8574 && h->type == STT_GNU_IFUNC)
8575 {
0e1862bb 8576 if (bfd_link_pic (info))
49206388
WN
8577 {
8578 /* Generate R_AARCH64_GLOB_DAT. */
8579 goto do_glob_dat;
8580 }
8581 else
8582 {
8583 asection *plt;
8584
8585 if (!h->pointer_equality_needed)
8586 abort ();
8587
8588 /* For non-shared object, we can't use .got.plt, which
8589 contains the real function address if we need pointer
8590 equality. We load the GOT entry with the PLT entry. */
8591 plt = htab->root.splt ? htab->root.splt : htab->root.iplt;
8592 bfd_put_NN (output_bfd, (plt->output_section->vma
8593 + plt->output_offset
8594 + h->plt.offset),
8595 htab->root.sgot->contents
8596 + (h->got.offset & ~(bfd_vma) 1));
8597 return TRUE;
8598 }
8599 }
0e1862bb 8600 else if (bfd_link_pic (info) && SYMBOL_REFERENCES_LOCAL (info, h))
a06ea964
NC
8601 {
8602 if (!h->def_regular)
8603 return FALSE;
8604
8605 BFD_ASSERT ((h->got.offset & 1) != 0);
a6bb11b2 8606 rela.r_info = ELFNN_R_INFO (0, AARCH64_R (RELATIVE));
a06ea964
NC
8607 rela.r_addend = (h->root.u.def.value
8608 + h->root.u.def.section->output_section->vma
8609 + h->root.u.def.section->output_offset);
8610 }
8611 else
8612 {
49206388 8613do_glob_dat:
a06ea964 8614 BFD_ASSERT ((h->got.offset & 1) == 0);
cec5225b 8615 bfd_put_NN (output_bfd, (bfd_vma) 0,
a06ea964 8616 htab->root.sgot->contents + h->got.offset);
a6bb11b2 8617 rela.r_info = ELFNN_R_INFO (h->dynindx, AARCH64_R (GLOB_DAT));
a06ea964
NC
8618 rela.r_addend = 0;
8619 }
8620
8621 loc = htab->root.srelgot->contents;
8622 loc += htab->root.srelgot->reloc_count++ * RELOC_SIZE (htab);
cec5225b 8623 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
a06ea964
NC
8624 }
8625
8626 if (h->needs_copy)
8627 {
8628 Elf_Internal_Rela rela;
8629 bfd_byte *loc;
8630
8631 /* This symbol needs a copy reloc. Set it up. */
8632
8633 if (h->dynindx == -1
8634 || (h->root.type != bfd_link_hash_defined
8635 && h->root.type != bfd_link_hash_defweak)
8636 || htab->srelbss == NULL)
8637 abort ();
8638
8639 rela.r_offset = (h->root.u.def.value
8640 + h->root.u.def.section->output_section->vma
8641 + h->root.u.def.section->output_offset);
a6bb11b2 8642 rela.r_info = ELFNN_R_INFO (h->dynindx, AARCH64_R (COPY));
a06ea964
NC
8643 rela.r_addend = 0;
8644 loc = htab->srelbss->contents;
8645 loc += htab->srelbss->reloc_count++ * RELOC_SIZE (htab);
cec5225b 8646 bfd_elfNN_swap_reloca_out (output_bfd, &rela, loc);
a06ea964
NC
8647 }
8648
8649 /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute. SYM may
8650 be NULL for local symbols. */
8651 if (sym != NULL
9637f6ef 8652 && (h == elf_hash_table (info)->hdynamic
a06ea964
NC
8653 || h == elf_hash_table (info)->hgot))
8654 sym->st_shndx = SHN_ABS;
8655
8656 return TRUE;
8657}
8658
1419bbe5
WN
8659/* Finish up local dynamic symbol handling. We set the contents of
8660 various dynamic sections here. */
8661
8662static bfd_boolean
8663elfNN_aarch64_finish_local_dynamic_symbol (void **slot, void *inf)
8664{
8665 struct elf_link_hash_entry *h
8666 = (struct elf_link_hash_entry *) *slot;
8667 struct bfd_link_info *info
8668 = (struct bfd_link_info *) inf;
8669
8670 return elfNN_aarch64_finish_dynamic_symbol (info->output_bfd,
8671 info, h, NULL);
8672}
8673
a06ea964 8674static void
cec5225b
YZ
8675elfNN_aarch64_init_small_plt0_entry (bfd *output_bfd ATTRIBUTE_UNUSED,
8676 struct elf_aarch64_link_hash_table
a06ea964
NC
8677 *htab)
8678{
8679 /* Fill in PLT0. Fixme:RR Note this doesn't distinguish between
8680 small and large plts and at the minute just generates
8681 the small PLT. */
8682
cec5225b 8683 /* PLT0 of the small PLT looks like this in ELF64 -
a06ea964
NC
8684 stp x16, x30, [sp, #-16]! // Save the reloc and lr on stack.
8685 adrp x16, PLT_GOT + 16 // Get the page base of the GOTPLT
8686 ldr x17, [x16, #:lo12:PLT_GOT+16] // Load the address of the
8687 // symbol resolver
8688 add x16, x16, #:lo12:PLT_GOT+16 // Load the lo12 bits of the
8689 // GOTPLT entry for this.
8690 br x17
cec5225b
YZ
8691 PLT0 will be slightly different in ELF32 due to different got entry
8692 size.
a06ea964 8693 */
caed7120 8694 bfd_vma plt_got_2nd_ent; /* Address of GOT[2]. */
a06ea964
NC
8695 bfd_vma plt_base;
8696
8697
cec5225b 8698 memcpy (htab->root.splt->contents, elfNN_aarch64_small_plt0_entry,
a06ea964
NC
8699 PLT_ENTRY_SIZE);
8700 elf_section_data (htab->root.splt->output_section)->this_hdr.sh_entsize =
8701 PLT_ENTRY_SIZE;
8702
caed7120
YZ
8703 plt_got_2nd_ent = (htab->root.sgotplt->output_section->vma
8704 + htab->root.sgotplt->output_offset
8705 + GOT_ENTRY_SIZE * 2);
a06ea964
NC
8706
8707 plt_base = htab->root.splt->output_section->vma +
f44a1f8e 8708 htab->root.splt->output_offset;
a06ea964
NC
8709
8710 /* Fill in the top 21 bits for this: ADRP x16, PLT_GOT + n * 8.
8711 ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff */
caed7120
YZ
8712 elf_aarch64_update_plt_entry (output_bfd, BFD_RELOC_AARCH64_ADR_HI21_PCREL,
8713 htab->root.splt->contents + 4,
8714 PG (plt_got_2nd_ent) - PG (plt_base + 4));
a06ea964 8715
caed7120
YZ
8716 elf_aarch64_update_plt_entry (output_bfd, BFD_RELOC_AARCH64_LDSTNN_LO12,
8717 htab->root.splt->contents + 8,
8718 PG_OFFSET (plt_got_2nd_ent));
a06ea964 8719
caed7120
YZ
8720 elf_aarch64_update_plt_entry (output_bfd, BFD_RELOC_AARCH64_ADD_LO12,
8721 htab->root.splt->contents + 12,
8722 PG_OFFSET (plt_got_2nd_ent));
a06ea964
NC
8723}
8724
8725static bfd_boolean
cec5225b 8726elfNN_aarch64_finish_dynamic_sections (bfd *output_bfd,
a06ea964
NC
8727 struct bfd_link_info *info)
8728{
cec5225b 8729 struct elf_aarch64_link_hash_table *htab;
a06ea964
NC
8730 bfd *dynobj;
8731 asection *sdyn;
8732
cec5225b 8733 htab = elf_aarch64_hash_table (info);
a06ea964
NC
8734 dynobj = htab->root.dynobj;
8735 sdyn = bfd_get_linker_section (dynobj, ".dynamic");
8736
8737 if (htab->root.dynamic_sections_created)
8738 {
cec5225b 8739 ElfNN_External_Dyn *dyncon, *dynconend;
a06ea964
NC
8740
8741 if (sdyn == NULL || htab->root.sgot == NULL)
8742 abort ();
8743
cec5225b
YZ
8744 dyncon = (ElfNN_External_Dyn *) sdyn->contents;
8745 dynconend = (ElfNN_External_Dyn *) (sdyn->contents + sdyn->size);
a06ea964
NC
8746 for (; dyncon < dynconend; dyncon++)
8747 {
8748 Elf_Internal_Dyn dyn;
8749 asection *s;
8750
cec5225b 8751 bfd_elfNN_swap_dyn_in (dynobj, dyncon, &dyn);
a06ea964
NC
8752
8753 switch (dyn.d_tag)
8754 {
8755 default:
8756 continue;
8757
8758 case DT_PLTGOT:
8759 s = htab->root.sgotplt;
8760 dyn.d_un.d_ptr = s->output_section->vma + s->output_offset;
8761 break;
8762
8763 case DT_JMPREL:
8764 dyn.d_un.d_ptr = htab->root.srelplt->output_section->vma;
8765 break;
8766
8767 case DT_PLTRELSZ:
c955de36 8768 s = htab->root.srelplt;
a06ea964
NC
8769 dyn.d_un.d_val = s->size;
8770 break;
8771
8772 case DT_RELASZ:
8773 /* The procedure linkage table relocs (DT_JMPREL) should
8774 not be included in the overall relocs (DT_RELA).
8775 Therefore, we override the DT_RELASZ entry here to
8776 make it not include the JMPREL relocs. Since the
8777 linker script arranges for .rela.plt to follow all
8778 other relocation sections, we don't have to worry
8779 about changing the DT_RELA entry. */
8780 if (htab->root.srelplt != NULL)
8781 {
c955de36 8782 s = htab->root.srelplt;
a06ea964
NC
8783 dyn.d_un.d_val -= s->size;
8784 }
8785 break;
8786
8787 case DT_TLSDESC_PLT:
8788 s = htab->root.splt;
8789 dyn.d_un.d_ptr = s->output_section->vma + s->output_offset
8790 + htab->tlsdesc_plt;
8791 break;
8792
8793 case DT_TLSDESC_GOT:
8794 s = htab->root.sgot;
8795 dyn.d_un.d_ptr = s->output_section->vma + s->output_offset
8796 + htab->dt_tlsdesc_got;
8797 break;
8798 }
8799
cec5225b 8800 bfd_elfNN_swap_dyn_out (output_bfd, &dyn, dyncon);
a06ea964
NC
8801 }
8802
8803 }
8804
8805 /* Fill in the special first entry in the procedure linkage table. */
8806 if (htab->root.splt && htab->root.splt->size > 0)
8807 {
cec5225b 8808 elfNN_aarch64_init_small_plt0_entry (output_bfd, htab);
a06ea964
NC
8809
8810 elf_section_data (htab->root.splt->output_section)->
8811 this_hdr.sh_entsize = htab->plt_entry_size;
8812
8813
8814 if (htab->tlsdesc_plt)
8815 {
cec5225b 8816 bfd_put_NN (output_bfd, (bfd_vma) 0,
a06ea964
NC
8817 htab->root.sgot->contents + htab->dt_tlsdesc_got);
8818
8819 memcpy (htab->root.splt->contents + htab->tlsdesc_plt,
cec5225b
YZ
8820 elfNN_aarch64_tlsdesc_small_plt_entry,
8821 sizeof (elfNN_aarch64_tlsdesc_small_plt_entry));
a06ea964
NC
8822
8823 {
8824 bfd_vma adrp1_addr =
8825 htab->root.splt->output_section->vma
8826 + htab->root.splt->output_offset + htab->tlsdesc_plt + 4;
8827
caed7120 8828 bfd_vma adrp2_addr = adrp1_addr + 4;
a06ea964
NC
8829
8830 bfd_vma got_addr =
8831 htab->root.sgot->output_section->vma
8832 + htab->root.sgot->output_offset;
8833
8834 bfd_vma pltgot_addr =
8835 htab->root.sgotplt->output_section->vma
8836 + htab->root.sgotplt->output_offset;
8837
8838 bfd_vma dt_tlsdesc_got = got_addr + htab->dt_tlsdesc_got;
caed7120
YZ
8839
8840 bfd_byte *plt_entry =
8841 htab->root.splt->contents + htab->tlsdesc_plt;
a06ea964
NC
8842
8843 /* adrp x2, DT_TLSDESC_GOT */
caed7120
YZ
8844 elf_aarch64_update_plt_entry (output_bfd,
8845 BFD_RELOC_AARCH64_ADR_HI21_PCREL,
8846 plt_entry + 4,
8847 (PG (dt_tlsdesc_got)
8848 - PG (adrp1_addr)));
a06ea964
NC
8849
8850 /* adrp x3, 0 */
caed7120
YZ
8851 elf_aarch64_update_plt_entry (output_bfd,
8852 BFD_RELOC_AARCH64_ADR_HI21_PCREL,
8853 plt_entry + 8,
8854 (PG (pltgot_addr)
8855 - PG (adrp2_addr)));
a06ea964
NC
8856
8857 /* ldr x2, [x2, #0] */
caed7120
YZ
8858 elf_aarch64_update_plt_entry (output_bfd,
8859 BFD_RELOC_AARCH64_LDSTNN_LO12,
8860 plt_entry + 12,
8861 PG_OFFSET (dt_tlsdesc_got));
a06ea964
NC
8862
8863 /* add x3, x3, 0 */
caed7120
YZ
8864 elf_aarch64_update_plt_entry (output_bfd,
8865 BFD_RELOC_AARCH64_ADD_LO12,
8866 plt_entry + 16,
8867 PG_OFFSET (pltgot_addr));
a06ea964
NC
8868 }
8869 }
8870 }
8871
8872 if (htab->root.sgotplt)
8873 {
8874 if (bfd_is_abs_section (htab->root.sgotplt->output_section))
8875 {
8876 (*_bfd_error_handler)
8877 (_("discarded output section: `%A'"), htab->root.sgotplt);
8878 return FALSE;
8879 }
8880
8881 /* Fill in the first three entries in the global offset table. */
8882 if (htab->root.sgotplt->size > 0)
8883 {
8db339a6
MS
8884 bfd_put_NN (output_bfd, (bfd_vma) 0, htab->root.sgotplt->contents);
8885
a06ea964 8886 /* Write GOT[1] and GOT[2], needed for the dynamic linker. */
cec5225b 8887 bfd_put_NN (output_bfd,
a06ea964
NC
8888 (bfd_vma) 0,
8889 htab->root.sgotplt->contents + GOT_ENTRY_SIZE);
cec5225b 8890 bfd_put_NN (output_bfd,
a06ea964
NC
8891 (bfd_vma) 0,
8892 htab->root.sgotplt->contents + GOT_ENTRY_SIZE * 2);
8893 }
8894
8db339a6
MS
8895 if (htab->root.sgot)
8896 {
8897 if (htab->root.sgot->size > 0)
8898 {
8899 bfd_vma addr =
8900 sdyn ? sdyn->output_section->vma + sdyn->output_offset : 0;
8901 bfd_put_NN (output_bfd, addr, htab->root.sgot->contents);
8902 }
8903 }
8904
a06ea964
NC
8905 elf_section_data (htab->root.sgotplt->output_section)->
8906 this_hdr.sh_entsize = GOT_ENTRY_SIZE;
8907 }
8908
8909 if (htab->root.sgot && htab->root.sgot->size > 0)
8910 elf_section_data (htab->root.sgot->output_section)->this_hdr.sh_entsize
8911 = GOT_ENTRY_SIZE;
8912
1419bbe5
WN
8913 /* Fill PLT and GOT entries for local STT_GNU_IFUNC symbols. */
8914 htab_traverse (htab->loc_hash_table,
8915 elfNN_aarch64_finish_local_dynamic_symbol,
8916 info);
8917
a06ea964
NC
8918 return TRUE;
8919}
8920
8921/* Return address for Ith PLT stub in section PLT, for relocation REL
8922 or (bfd_vma) -1 if it should not be included. */
8923
8924static bfd_vma
cec5225b 8925elfNN_aarch64_plt_sym_val (bfd_vma i, const asection *plt,
a06ea964
NC
8926 const arelent *rel ATTRIBUTE_UNUSED)
8927{
8928 return plt->vma + PLT_ENTRY_SIZE + i * PLT_SMALL_ENTRY_SIZE;
8929}
8930
8931
8932/* We use this so we can override certain functions
8933 (though currently we don't). */
8934
cec5225b 8935const struct elf_size_info elfNN_aarch64_size_info =
a06ea964 8936{
cec5225b
YZ
8937 sizeof (ElfNN_External_Ehdr),
8938 sizeof (ElfNN_External_Phdr),
8939 sizeof (ElfNN_External_Shdr),
8940 sizeof (ElfNN_External_Rel),
8941 sizeof (ElfNN_External_Rela),
8942 sizeof (ElfNN_External_Sym),
8943 sizeof (ElfNN_External_Dyn),
a06ea964
NC
8944 sizeof (Elf_External_Note),
8945 4, /* Hash table entry size. */
8946 1, /* Internal relocs per external relocs. */
cec5225b
YZ
8947 ARCH_SIZE, /* Arch size. */
8948 LOG_FILE_ALIGN, /* Log_file_align. */
8949 ELFCLASSNN, EV_CURRENT,
8950 bfd_elfNN_write_out_phdrs,
8951 bfd_elfNN_write_shdrs_and_ehdr,
8952 bfd_elfNN_checksum_contents,
8953 bfd_elfNN_write_relocs,
8954 bfd_elfNN_swap_symbol_in,
8955 bfd_elfNN_swap_symbol_out,
8956 bfd_elfNN_slurp_reloc_table,
8957 bfd_elfNN_slurp_symbol_table,
8958 bfd_elfNN_swap_dyn_in,
8959 bfd_elfNN_swap_dyn_out,
8960 bfd_elfNN_swap_reloc_in,
8961 bfd_elfNN_swap_reloc_out,
8962 bfd_elfNN_swap_reloca_in,
8963 bfd_elfNN_swap_reloca_out
a06ea964
NC
8964};
8965
8966#define ELF_ARCH bfd_arch_aarch64
8967#define ELF_MACHINE_CODE EM_AARCH64
8968#define ELF_MAXPAGESIZE 0x10000
8969#define ELF_MINPAGESIZE 0x1000
8970#define ELF_COMMONPAGESIZE 0x1000
8971
cec5225b
YZ
8972#define bfd_elfNN_close_and_cleanup \
8973 elfNN_aarch64_close_and_cleanup
a06ea964 8974
cec5225b
YZ
8975#define bfd_elfNN_bfd_free_cached_info \
8976 elfNN_aarch64_bfd_free_cached_info
a06ea964 8977
cec5225b
YZ
8978#define bfd_elfNN_bfd_is_target_special_symbol \
8979 elfNN_aarch64_is_target_special_symbol
a06ea964 8980
cec5225b
YZ
8981#define bfd_elfNN_bfd_link_hash_table_create \
8982 elfNN_aarch64_link_hash_table_create
a06ea964 8983
cec5225b
YZ
8984#define bfd_elfNN_bfd_merge_private_bfd_data \
8985 elfNN_aarch64_merge_private_bfd_data
a06ea964 8986
cec5225b
YZ
8987#define bfd_elfNN_bfd_print_private_bfd_data \
8988 elfNN_aarch64_print_private_bfd_data
a06ea964 8989
cec5225b
YZ
8990#define bfd_elfNN_bfd_reloc_type_lookup \
8991 elfNN_aarch64_reloc_type_lookup
a06ea964 8992
cec5225b
YZ
8993#define bfd_elfNN_bfd_reloc_name_lookup \
8994 elfNN_aarch64_reloc_name_lookup
a06ea964 8995
cec5225b
YZ
8996#define bfd_elfNN_bfd_set_private_flags \
8997 elfNN_aarch64_set_private_flags
a06ea964 8998
cec5225b
YZ
8999#define bfd_elfNN_find_inliner_info \
9000 elfNN_aarch64_find_inliner_info
a06ea964 9001
cec5225b
YZ
9002#define bfd_elfNN_find_nearest_line \
9003 elfNN_aarch64_find_nearest_line
a06ea964 9004
cec5225b
YZ
9005#define bfd_elfNN_mkobject \
9006 elfNN_aarch64_mkobject
a06ea964 9007
cec5225b
YZ
9008#define bfd_elfNN_new_section_hook \
9009 elfNN_aarch64_new_section_hook
a06ea964
NC
9010
9011#define elf_backend_adjust_dynamic_symbol \
cec5225b 9012 elfNN_aarch64_adjust_dynamic_symbol
a06ea964
NC
9013
9014#define elf_backend_always_size_sections \
cec5225b 9015 elfNN_aarch64_always_size_sections
a06ea964
NC
9016
9017#define elf_backend_check_relocs \
cec5225b 9018 elfNN_aarch64_check_relocs
a06ea964
NC
9019
9020#define elf_backend_copy_indirect_symbol \
cec5225b 9021 elfNN_aarch64_copy_indirect_symbol
a06ea964
NC
9022
9023/* Create .dynbss, and .rela.bss sections in DYNOBJ, and set up shortcuts
9024 to them in our hash. */
9025#define elf_backend_create_dynamic_sections \
cec5225b 9026 elfNN_aarch64_create_dynamic_sections
a06ea964
NC
9027
9028#define elf_backend_init_index_section \
9029 _bfd_elf_init_2_index_sections
9030
a06ea964 9031#define elf_backend_finish_dynamic_sections \
cec5225b 9032 elfNN_aarch64_finish_dynamic_sections
a06ea964
NC
9033
9034#define elf_backend_finish_dynamic_symbol \
cec5225b 9035 elfNN_aarch64_finish_dynamic_symbol
a06ea964
NC
9036
9037#define elf_backend_gc_sweep_hook \
cec5225b 9038 elfNN_aarch64_gc_sweep_hook
a06ea964
NC
9039
9040#define elf_backend_object_p \
cec5225b 9041 elfNN_aarch64_object_p
a06ea964
NC
9042
9043#define elf_backend_output_arch_local_syms \
cec5225b 9044 elfNN_aarch64_output_arch_local_syms
a06ea964
NC
9045
9046#define elf_backend_plt_sym_val \
cec5225b 9047 elfNN_aarch64_plt_sym_val
a06ea964
NC
9048
9049#define elf_backend_post_process_headers \
cec5225b 9050 elfNN_aarch64_post_process_headers
a06ea964
NC
9051
9052#define elf_backend_relocate_section \
cec5225b 9053 elfNN_aarch64_relocate_section
a06ea964
NC
9054
9055#define elf_backend_reloc_type_class \
cec5225b 9056 elfNN_aarch64_reloc_type_class
a06ea964 9057
a06ea964 9058#define elf_backend_section_from_shdr \
cec5225b 9059 elfNN_aarch64_section_from_shdr
a06ea964
NC
9060
9061#define elf_backend_size_dynamic_sections \
cec5225b 9062 elfNN_aarch64_size_dynamic_sections
a06ea964
NC
9063
9064#define elf_backend_size_info \
cec5225b 9065 elfNN_aarch64_size_info
a06ea964 9066
68fcca92
JW
9067#define elf_backend_write_section \
9068 elfNN_aarch64_write_section
9069
a06ea964 9070#define elf_backend_can_refcount 1
59c108f7 9071#define elf_backend_can_gc_sections 1
a06ea964
NC
9072#define elf_backend_plt_readonly 1
9073#define elf_backend_want_got_plt 1
9074#define elf_backend_want_plt_sym 0
9075#define elf_backend_may_use_rel_p 0
9076#define elf_backend_may_use_rela_p 1
9077#define elf_backend_default_use_rela_p 1
2e0488d3 9078#define elf_backend_rela_normal 1
a06ea964 9079#define elf_backend_got_header_size (GOT_ENTRY_SIZE * 3)
c495064d 9080#define elf_backend_default_execstack 0
32f573bc 9081#define elf_backend_extern_protected_data 1
a06ea964
NC
9082
9083#undef elf_backend_obj_attrs_section
9084#define elf_backend_obj_attrs_section ".ARM.attributes"
9085
cec5225b 9086#include "elfNN-target.h"
This page took 0.674014 seconds and 4 git commands to generate.