1 /* ELF support for AArch64.
2 Copyright 2009-2013 Free Software Foundation, Inc.
3 Contributed by ARM Ltd.
5 This file is part of BFD, the Binary File Descriptor library.
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.
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.
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/>. */
21 /* Notes on implementation:
23 Thread Local Store (TLS)
27 The implementation currently supports both traditional TLS and TLS
28 descriptors, but only general dynamic (GD).
30 For traditional TLS the assembler will present us with code
31 fragments of the form:
34 R_AARCH64_TLSGD_ADR_PAGE21(foo)
35 add x0, :tlsgd_lo12:foo
36 R_AARCH64_TLSGD_ADD_LO12_NC(foo)
40 For TLS descriptors the assembler will present us with code
41 fragments of the form:
43 adrp x0, :tlsdesc:foo R_AARCH64_TLSDESC_ADR_PAGE21(foo)
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)
47 blr x1 R_AARCH64_TLSDESC_CALL(foo)
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.
53 The relocations R_AARCH64_TLSDESC_{ADR_PAGE,LD64_LO12_NC,ADD_LO12_NC}
54 against foo indicate that 'foo' is thread local and should be accessed
55 via a TLS descriptor mechanism.
57 The precise instruction sequence is only relevant from the
58 perspective of linker relaxation which is currently not implemented.
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.
65 In the traditional TLS mechanism, the double GOT entry is used to
66 provide the tls_index structure, containing module and offset
67 entries. The static linker places the relocation R_AARCH64_TLS_DTPMOD64
68 on the module entry. The loader will subsequently fixup this
69 relocation with the module identity.
71 For global traditional TLS symbols the static linker places an
72 R_AARCH64_TLS_DTPREL64 relocation on the offset entry. The loader
73 will subsequently fixup the offset. For local TLS symbols the static
74 linker fixes up offset.
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.
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.
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.
95 aarch64_check_relocs()
97 This function is invoked for each relocation.
99 The TLS relocations R_AARCH64_TLSGD_{ADR_PREL21,ADD_LO12_NC} and
100 R_AARCH64_TLSDESC_{ADR_PAGE,LD64_LO12_NC,ADD_LO12_NC} are
101 spotted. One time creation of local symbol data structures are
102 created when the first local symbol is seen.
104 The reference count for a symbol is incremented. The GOT type for
105 each symbol is marked as general dynamic.
107 elf64_aarch64_allocate_dynrelocs ()
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
115 elf64_aarch64_size_dynamic_sections ()
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.
122 elf64_aarch64_relocate_section ()
124 Calls elf64_aarch64_final_link_relocate ()
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.
134 elf64_aarch64_final_link_relocate ()
136 Fixup the R_AARCH64_TLSGD_{ADR_PREL21, ADD_LO12_NC} relocations. */
140 #include "libiberty.h"
142 #include "bfd_stdint.h"
145 #include "objalloc.h"
146 #include "elf/aarch64.h"
148 static bfd_reloc_status_type
149 bfd_elf_aarch64_put_addend (bfd
*abfd
,
151 reloc_howto_type
*howto
, bfd_signed_vma addend
);
153 #define IS_AARCH64_TLS_RELOC(R_TYPE) \
154 ((R_TYPE) == R_AARCH64_TLSGD_ADR_PAGE21 \
155 || (R_TYPE) == R_AARCH64_TLSGD_ADD_LO12_NC \
156 || (R_TYPE) == R_AARCH64_TLSIE_MOVW_GOTTPREL_G1 \
157 || (R_TYPE) == R_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC \
158 || (R_TYPE) == R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21 \
159 || (R_TYPE) == R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC \
160 || (R_TYPE) == R_AARCH64_TLSIE_LD_GOTTPREL_PREL19 \
161 || (R_TYPE) == R_AARCH64_TLSLE_ADD_TPREL_LO12 \
162 || (R_TYPE) == R_AARCH64_TLSLE_ADD_TPREL_HI12 \
163 || (R_TYPE) == R_AARCH64_TLSLE_ADD_TPREL_LO12_NC \
164 || (R_TYPE) == R_AARCH64_TLSLE_MOVW_TPREL_G2 \
165 || (R_TYPE) == R_AARCH64_TLSLE_MOVW_TPREL_G1 \
166 || (R_TYPE) == R_AARCH64_TLSLE_MOVW_TPREL_G1_NC \
167 || (R_TYPE) == R_AARCH64_TLSLE_MOVW_TPREL_G0 \
168 || (R_TYPE) == R_AARCH64_TLSLE_MOVW_TPREL_G0_NC \
169 || (R_TYPE) == R_AARCH64_TLS_DTPMOD64 \
170 || (R_TYPE) == R_AARCH64_TLS_DTPREL64 \
171 || (R_TYPE) == R_AARCH64_TLS_TPREL64 \
172 || IS_AARCH64_TLSDESC_RELOC ((R_TYPE)))
174 #define IS_AARCH64_TLSDESC_RELOC(R_TYPE) \
175 ((R_TYPE) == R_AARCH64_TLSDESC_LD_PREL19 \
176 || (R_TYPE) == R_AARCH64_TLSDESC_ADR_PREL21 \
177 || (R_TYPE) == R_AARCH64_TLSDESC_ADR_PAGE21 \
178 || (R_TYPE) == R_AARCH64_TLSDESC_ADD_LO12_NC \
179 || (R_TYPE) == R_AARCH64_TLSDESC_LD64_LO12_NC \
180 || (R_TYPE) == R_AARCH64_TLSDESC_OFF_G1 \
181 || (R_TYPE) == R_AARCH64_TLSDESC_OFF_G0_NC \
182 || (R_TYPE) == R_AARCH64_TLSDESC_LDR \
183 || (R_TYPE) == R_AARCH64_TLSDESC_ADD \
184 || (R_TYPE) == R_AARCH64_TLSDESC_CALL \
185 || (R_TYPE) == R_AARCH64_TLSDESC)
187 #define ELIMINATE_COPY_RELOCS 0
189 /* Return the relocation section associated with NAME. HTAB is the
190 bfd's elf64_aarch64_link_hash_entry. */
191 #define RELOC_SECTION(HTAB, NAME) \
192 ((HTAB)->use_rel ? ".rel" NAME : ".rela" NAME)
194 /* Return size of a relocation entry. HTAB is the bfd's
195 elf64_aarch64_link_hash_entry. */
196 #define RELOC_SIZE(HTAB) (sizeof (Elf64_External_Rela))
198 /* Return function to swap relocations in. HTAB is the bfd's
199 elf64_aarch64_link_hash_entry. */
200 #define SWAP_RELOC_IN(HTAB) (bfd_elf64_swap_reloca_in)
202 /* Return function to swap relocations out. HTAB is the bfd's
203 elf64_aarch64_link_hash_entry. */
204 #define SWAP_RELOC_OUT(HTAB) (bfd_elf64_swap_reloca_out)
206 /* GOT Entry size - 8 bytes. */
207 #define GOT_ENTRY_SIZE (8)
208 #define PLT_ENTRY_SIZE (32)
209 #define PLT_SMALL_ENTRY_SIZE (16)
210 #define PLT_TLSDESC_ENTRY_SIZE (32)
212 /* Take the PAGE component of an address or offset. */
213 #define PG(x) ((x) & ~ 0xfff)
214 #define PG_OFFSET(x) ((x) & 0xfff)
216 /* Encoding of the nop instruction */
217 #define INSN_NOP 0xd503201f
219 #define aarch64_compute_jump_table_size(htab) \
220 (((htab)->root.srelplt == NULL) ? 0 \
221 : (htab)->root.srelplt->reloc_count * GOT_ENTRY_SIZE)
223 /* The first entry in a procedure linkage table looks like this
224 if the distance between the PLTGOT and the PLT is < 4GB use
225 these PLT entries. Note that the dynamic linker gets &PLTGOT[2]
226 in x16 and needs to work out PLTGOT[1] by using an address of
228 static const bfd_byte elf64_aarch64_small_plt0_entry
[PLT_ENTRY_SIZE
] =
230 0xf0, 0x7b, 0xbf, 0xa9, /* stp x16, x30, [sp, #-16]! */
231 0x10, 0x00, 0x00, 0x90, /* adrp x16, (GOT+16) */
232 0x11, 0x0A, 0x40, 0xf9, /* ldr x17, [x16, #PLT_GOT+0x10] */
233 0x10, 0x42, 0x00, 0x91, /* add x16, x16,#PLT_GOT+0x10 */
234 0x20, 0x02, 0x1f, 0xd6, /* br x17 */
235 0x1f, 0x20, 0x03, 0xd5, /* nop */
236 0x1f, 0x20, 0x03, 0xd5, /* nop */
237 0x1f, 0x20, 0x03, 0xd5, /* nop */
240 /* Per function entry in a procedure linkage table looks like this
241 if the distance between the PLTGOT and the PLT is < 4GB use
242 these PLT entries. */
243 static const bfd_byte elf64_aarch64_small_plt_entry
[PLT_SMALL_ENTRY_SIZE
] =
245 0x10, 0x00, 0x00, 0x90, /* adrp x16, PLTGOT + n * 8 */
246 0x11, 0x02, 0x40, 0xf9, /* ldr x17, [x16, PLTGOT + n * 8] */
247 0x10, 0x02, 0x00, 0x91, /* add x16, x16, :lo12:PLTGOT + n * 8 */
248 0x20, 0x02, 0x1f, 0xd6, /* br x17. */
251 static const bfd_byte
252 elf64_aarch64_tlsdesc_small_plt_entry
[PLT_TLSDESC_ENTRY_SIZE
] =
254 0xe2, 0x0f, 0xbf, 0xa9, /* stp x2, x3, [sp, #-16]! */
255 0x02, 0x00, 0x00, 0x90, /* adrp x2, 0 */
256 0x03, 0x00, 0x00, 0x90, /* adrp x3, 0 */
257 0x42, 0x08, 0x40, 0xF9, /* ldr x2, [x2, #0] */
258 0x63, 0x00, 0x00, 0x91, /* add x3, x3, 0 */
259 0x40, 0x00, 0x1F, 0xD6, /* br x2 */
260 0x1f, 0x20, 0x03, 0xd5, /* nop */
261 0x1f, 0x20, 0x03, 0xd5, /* nop */
264 #define elf_info_to_howto elf64_aarch64_info_to_howto
265 #define elf_info_to_howto_rel elf64_aarch64_info_to_howto
267 #define AARCH64_ELF_ABI_VERSION 0
268 #define AARCH64_ELF_OS_ABI_VERSION 0
270 /* In case we're on a 32-bit machine, construct a 64-bit "-1" value. */
271 #define ALL_ONES (~ (bfd_vma) 0)
273 static reloc_howto_type elf64_aarch64_howto_none
=
274 HOWTO (R_AARCH64_NONE
, /* type */
276 0, /* size (0 = byte, 1 = short, 2 = long) */
278 FALSE
, /* pc_relative */
280 complain_overflow_dont
,/* complain_on_overflow */
281 bfd_elf_generic_reloc
, /* special_function */
282 "R_AARCH64_NONE", /* name */
283 FALSE
, /* partial_inplace */
286 FALSE
); /* pcrel_offset */
288 static reloc_howto_type elf64_aarch64_howto_dynrelocs
[] =
290 HOWTO (R_AARCH64_COPY
, /* type */
292 2, /* size (0 = byte, 1 = short, 2 = long) */
294 FALSE
, /* pc_relative */
296 complain_overflow_bitfield
, /* complain_on_overflow */
297 bfd_elf_generic_reloc
, /* special_function */
298 "R_AARCH64_COPY", /* name */
299 TRUE
, /* partial_inplace */
300 0xffffffff, /* src_mask */
301 0xffffffff, /* dst_mask */
302 FALSE
), /* pcrel_offset */
304 HOWTO (R_AARCH64_GLOB_DAT
, /* type */
306 2, /* size (0 = byte, 1 = short, 2 = long) */
308 FALSE
, /* pc_relative */
310 complain_overflow_bitfield
, /* complain_on_overflow */
311 bfd_elf_generic_reloc
, /* special_function */
312 "R_AARCH64_GLOB_DAT", /* name */
313 TRUE
, /* partial_inplace */
314 0xffffffff, /* src_mask */
315 0xffffffff, /* dst_mask */
316 FALSE
), /* pcrel_offset */
318 HOWTO (R_AARCH64_JUMP_SLOT
, /* type */
320 2, /* size (0 = byte, 1 = short, 2 = long) */
322 FALSE
, /* pc_relative */
324 complain_overflow_bitfield
, /* complain_on_overflow */
325 bfd_elf_generic_reloc
, /* special_function */
326 "R_AARCH64_JUMP_SLOT", /* name */
327 TRUE
, /* partial_inplace */
328 0xffffffff, /* src_mask */
329 0xffffffff, /* dst_mask */
330 FALSE
), /* pcrel_offset */
332 HOWTO (R_AARCH64_RELATIVE
, /* type */
334 2, /* size (0 = byte, 1 = short, 2 = long) */
336 FALSE
, /* pc_relative */
338 complain_overflow_bitfield
, /* complain_on_overflow */
339 bfd_elf_generic_reloc
, /* special_function */
340 "R_AARCH64_RELATIVE", /* name */
341 TRUE
, /* partial_inplace */
342 ALL_ONES
, /* src_mask */
343 ALL_ONES
, /* dst_mask */
344 FALSE
), /* pcrel_offset */
346 HOWTO (R_AARCH64_TLS_DTPMOD64
, /* type */
348 2, /* size (0 = byte, 1 = short, 2 = long) */
350 FALSE
, /* pc_relative */
352 complain_overflow_dont
, /* complain_on_overflow */
353 bfd_elf_generic_reloc
, /* special_function */
354 "R_AARCH64_TLS_DTPMOD64", /* name */
355 FALSE
, /* partial_inplace */
357 ALL_ONES
, /* dst_mask */
358 FALSE
), /* pc_reloffset */
360 HOWTO (R_AARCH64_TLS_DTPREL64
, /* type */
362 2, /* size (0 = byte, 1 = short, 2 = long) */
364 FALSE
, /* pc_relative */
366 complain_overflow_dont
, /* complain_on_overflow */
367 bfd_elf_generic_reloc
, /* special_function */
368 "R_AARCH64_TLS_DTPREL64", /* name */
369 FALSE
, /* partial_inplace */
371 ALL_ONES
, /* dst_mask */
372 FALSE
), /* pcrel_offset */
374 HOWTO (R_AARCH64_TLS_TPREL64
, /* type */
376 2, /* size (0 = byte, 1 = short, 2 = long) */
378 FALSE
, /* pc_relative */
380 complain_overflow_dont
, /* complain_on_overflow */
381 bfd_elf_generic_reloc
, /* special_function */
382 "R_AARCH64_TLS_TPREL64", /* name */
383 FALSE
, /* partial_inplace */
385 ALL_ONES
, /* dst_mask */
386 FALSE
), /* pcrel_offset */
388 HOWTO (R_AARCH64_TLSDESC
, /* type */
390 2, /* size (0 = byte, 1 = short, 2 = long) */
392 FALSE
, /* pc_relative */
394 complain_overflow_dont
, /* complain_on_overflow */
395 bfd_elf_generic_reloc
, /* special_function */
396 "R_AARCH64_TLSDESC", /* name */
397 FALSE
, /* partial_inplace */
399 ALL_ONES
, /* dst_mask */
400 FALSE
), /* pcrel_offset */
402 HOWTO (R_AARCH64_IRELATIVE
, /* type */
404 2, /* size (0 = byte, 1 = short, 2 = long) */
406 FALSE
, /* pc_relative */
408 complain_overflow_bitfield
, /* complain_on_overflow */
409 bfd_elf_generic_reloc
, /* special_function */
410 "R_AARCH64_IRELATIVE", /* name */
411 FALSE
, /* partial_inplace */
413 ALL_ONES
, /* dst_mask */
414 FALSE
), /* pcrel_offset */
418 /* Note: code such as elf64_aarch64_reloc_type_lookup expect to use e.g.
419 R_AARCH64_PREL64 as an index into this, and find the R_AARCH64_PREL64 HOWTO
422 static reloc_howto_type elf64_aarch64_howto_table
[] =
424 /* Basic data relocations. */
426 HOWTO (R_AARCH64_NULL
, /* type */
428 0, /* size (0 = byte, 1 = short, 2 = long) */
430 FALSE
, /* pc_relative */
432 complain_overflow_dont
, /* complain_on_overflow */
433 bfd_elf_generic_reloc
, /* special_function */
434 "R_AARCH64_NULL", /* name */
435 FALSE
, /* partial_inplace */
438 FALSE
), /* pcrel_offset */
441 HOWTO (R_AARCH64_ABS64
, /* type */
443 4, /* size (4 = long long) */
445 FALSE
, /* pc_relative */
447 complain_overflow_unsigned
, /* complain_on_overflow */
448 bfd_elf_generic_reloc
, /* special_function */
449 "R_AARCH64_ABS64", /* name */
450 FALSE
, /* partial_inplace */
451 ALL_ONES
, /* src_mask */
452 ALL_ONES
, /* dst_mask */
453 FALSE
), /* pcrel_offset */
456 HOWTO (R_AARCH64_ABS32
, /* type */
458 2, /* size (0 = byte, 1 = short, 2 = long) */
460 FALSE
, /* pc_relative */
462 complain_overflow_unsigned
, /* complain_on_overflow */
463 bfd_elf_generic_reloc
, /* special_function */
464 "R_AARCH64_ABS32", /* name */
465 FALSE
, /* partial_inplace */
466 0xffffffff, /* src_mask */
467 0xffffffff, /* dst_mask */
468 FALSE
), /* pcrel_offset */
471 HOWTO (R_AARCH64_ABS16
, /* type */
473 1, /* size (0 = byte, 1 = short, 2 = long) */
475 FALSE
, /* pc_relative */
477 complain_overflow_unsigned
, /* complain_on_overflow */
478 bfd_elf_generic_reloc
, /* special_function */
479 "R_AARCH64_ABS16", /* name */
480 FALSE
, /* partial_inplace */
481 0xffff, /* src_mask */
482 0xffff, /* dst_mask */
483 FALSE
), /* pcrel_offset */
485 /* .xword: (S+A-P) */
486 HOWTO (R_AARCH64_PREL64
, /* type */
488 4, /* size (4 = long long) */
490 TRUE
, /* pc_relative */
492 complain_overflow_signed
, /* complain_on_overflow */
493 bfd_elf_generic_reloc
, /* special_function */
494 "R_AARCH64_PREL64", /* name */
495 FALSE
, /* partial_inplace */
496 ALL_ONES
, /* src_mask */
497 ALL_ONES
, /* dst_mask */
498 TRUE
), /* pcrel_offset */
501 HOWTO (R_AARCH64_PREL32
, /* type */
503 2, /* size (0 = byte, 1 = short, 2 = long) */
505 TRUE
, /* pc_relative */
507 complain_overflow_signed
, /* complain_on_overflow */
508 bfd_elf_generic_reloc
, /* special_function */
509 "R_AARCH64_PREL32", /* name */
510 FALSE
, /* partial_inplace */
511 0xffffffff, /* src_mask */
512 0xffffffff, /* dst_mask */
513 TRUE
), /* pcrel_offset */
516 HOWTO (R_AARCH64_PREL16
, /* type */
518 1, /* size (0 = byte, 1 = short, 2 = long) */
520 TRUE
, /* pc_relative */
522 complain_overflow_signed
, /* complain_on_overflow */
523 bfd_elf_generic_reloc
, /* special_function */
524 "R_AARCH64_PREL16", /* name */
525 FALSE
, /* partial_inplace */
526 0xffff, /* src_mask */
527 0xffff, /* dst_mask */
528 TRUE
), /* pcrel_offset */
530 /* Group relocations to create a 16, 32, 48 or 64 bit
531 unsigned data or abs address inline. */
533 /* MOVZ: ((S+A) >> 0) & 0xffff */
534 HOWTO (R_AARCH64_MOVW_UABS_G0
, /* type */
536 2, /* size (0 = byte, 1 = short, 2 = long) */
538 FALSE
, /* pc_relative */
540 complain_overflow_unsigned
, /* complain_on_overflow */
541 bfd_elf_generic_reloc
, /* special_function */
542 "R_AARCH64_MOVW_UABS_G0", /* name */
543 FALSE
, /* partial_inplace */
544 0xffff, /* src_mask */
545 0xffff, /* dst_mask */
546 FALSE
), /* pcrel_offset */
548 /* MOVK: ((S+A) >> 0) & 0xffff [no overflow check] */
549 HOWTO (R_AARCH64_MOVW_UABS_G0_NC
, /* type */
551 2, /* size (0 = byte, 1 = short, 2 = long) */
553 FALSE
, /* pc_relative */
555 complain_overflow_dont
, /* complain_on_overflow */
556 bfd_elf_generic_reloc
, /* special_function */
557 "R_AARCH64_MOVW_UABS_G0_NC", /* name */
558 FALSE
, /* partial_inplace */
559 0xffff, /* src_mask */
560 0xffff, /* dst_mask */
561 FALSE
), /* pcrel_offset */
563 /* MOVZ: ((S+A) >> 16) & 0xffff */
564 HOWTO (R_AARCH64_MOVW_UABS_G1
, /* type */
566 2, /* size (0 = byte, 1 = short, 2 = long) */
568 FALSE
, /* pc_relative */
570 complain_overflow_unsigned
, /* complain_on_overflow */
571 bfd_elf_generic_reloc
, /* special_function */
572 "R_AARCH64_MOVW_UABS_G1", /* name */
573 FALSE
, /* partial_inplace */
574 0xffff, /* src_mask */
575 0xffff, /* dst_mask */
576 FALSE
), /* pcrel_offset */
578 /* MOVK: ((S+A) >> 16) & 0xffff [no overflow check] */
579 HOWTO (R_AARCH64_MOVW_UABS_G1_NC
, /* type */
581 2, /* size (0 = byte, 1 = short, 2 = long) */
583 FALSE
, /* pc_relative */
585 complain_overflow_dont
, /* complain_on_overflow */
586 bfd_elf_generic_reloc
, /* special_function */
587 "R_AARCH64_MOVW_UABS_G1_NC", /* name */
588 FALSE
, /* partial_inplace */
589 0xffff, /* src_mask */
590 0xffff, /* dst_mask */
591 FALSE
), /* pcrel_offset */
593 /* MOVZ: ((S+A) >> 32) & 0xffff */
594 HOWTO (R_AARCH64_MOVW_UABS_G2
, /* type */
596 2, /* size (0 = byte, 1 = short, 2 = long) */
598 FALSE
, /* pc_relative */
600 complain_overflow_unsigned
, /* complain_on_overflow */
601 bfd_elf_generic_reloc
, /* special_function */
602 "R_AARCH64_MOVW_UABS_G2", /* name */
603 FALSE
, /* partial_inplace */
604 0xffff, /* src_mask */
605 0xffff, /* dst_mask */
606 FALSE
), /* pcrel_offset */
608 /* MOVK: ((S+A) >> 32) & 0xffff [no overflow check] */
609 HOWTO (R_AARCH64_MOVW_UABS_G2_NC
, /* type */
611 2, /* size (0 = byte, 1 = short, 2 = long) */
613 FALSE
, /* pc_relative */
615 complain_overflow_dont
, /* complain_on_overflow */
616 bfd_elf_generic_reloc
, /* special_function */
617 "R_AARCH64_MOVW_UABS_G2_NC", /* name */
618 FALSE
, /* partial_inplace */
619 0xffff, /* src_mask */
620 0xffff, /* dst_mask */
621 FALSE
), /* pcrel_offset */
623 /* MOVZ: ((S+A) >> 48) & 0xffff */
624 HOWTO (R_AARCH64_MOVW_UABS_G3
, /* type */
626 2, /* size (0 = byte, 1 = short, 2 = long) */
628 FALSE
, /* pc_relative */
630 complain_overflow_unsigned
, /* complain_on_overflow */
631 bfd_elf_generic_reloc
, /* special_function */
632 "R_AARCH64_MOVW_UABS_G3", /* name */
633 FALSE
, /* partial_inplace */
634 0xffff, /* src_mask */
635 0xffff, /* dst_mask */
636 FALSE
), /* pcrel_offset */
638 /* Group relocations to create high part of a 16, 32, 48 or 64 bit
639 signed data or abs address inline. Will change instruction
640 to MOVN or MOVZ depending on sign of calculated value. */
642 /* MOV[ZN]: ((S+A) >> 0) & 0xffff */
643 HOWTO (R_AARCH64_MOVW_SABS_G0
, /* type */
645 2, /* size (0 = byte, 1 = short, 2 = long) */
647 FALSE
, /* pc_relative */
649 complain_overflow_signed
, /* complain_on_overflow */
650 bfd_elf_generic_reloc
, /* special_function */
651 "R_AARCH64_MOVW_SABS_G0", /* name */
652 FALSE
, /* partial_inplace */
653 0xffff, /* src_mask */
654 0xffff, /* dst_mask */
655 FALSE
), /* pcrel_offset */
657 /* MOV[ZN]: ((S+A) >> 16) & 0xffff */
658 HOWTO (R_AARCH64_MOVW_SABS_G1
, /* type */
660 2, /* size (0 = byte, 1 = short, 2 = long) */
662 FALSE
, /* pc_relative */
664 complain_overflow_signed
, /* complain_on_overflow */
665 bfd_elf_generic_reloc
, /* special_function */
666 "R_AARCH64_MOVW_SABS_G1", /* name */
667 FALSE
, /* partial_inplace */
668 0xffff, /* src_mask */
669 0xffff, /* dst_mask */
670 FALSE
), /* pcrel_offset */
672 /* MOV[ZN]: ((S+A) >> 32) & 0xffff */
673 HOWTO (R_AARCH64_MOVW_SABS_G2
, /* type */
675 2, /* size (0 = byte, 1 = short, 2 = long) */
677 FALSE
, /* pc_relative */
679 complain_overflow_signed
, /* complain_on_overflow */
680 bfd_elf_generic_reloc
, /* special_function */
681 "R_AARCH64_MOVW_SABS_G2", /* name */
682 FALSE
, /* partial_inplace */
683 0xffff, /* src_mask */
684 0xffff, /* dst_mask */
685 FALSE
), /* pcrel_offset */
687 /* Relocations to generate 19, 21 and 33 bit PC-relative load/store
688 addresses: PG(x) is (x & ~0xfff). */
690 /* LD-lit: ((S+A-P) >> 2) & 0x7ffff */
691 HOWTO (R_AARCH64_LD_PREL_LO19
, /* type */
693 2, /* size (0 = byte, 1 = short, 2 = long) */
695 TRUE
, /* pc_relative */
697 complain_overflow_signed
, /* complain_on_overflow */
698 bfd_elf_generic_reloc
, /* special_function */
699 "R_AARCH64_LD_PREL_LO19", /* name */
700 FALSE
, /* partial_inplace */
701 0x7ffff, /* src_mask */
702 0x7ffff, /* dst_mask */
703 TRUE
), /* pcrel_offset */
705 /* ADR: (S+A-P) & 0x1fffff */
706 HOWTO (R_AARCH64_ADR_PREL_LO21
, /* type */
708 2, /* size (0 = byte, 1 = short, 2 = long) */
710 TRUE
, /* pc_relative */
712 complain_overflow_signed
, /* complain_on_overflow */
713 bfd_elf_generic_reloc
, /* special_function */
714 "R_AARCH64_ADR_PREL_LO21", /* name */
715 FALSE
, /* partial_inplace */
716 0x1fffff, /* src_mask */
717 0x1fffff, /* dst_mask */
718 TRUE
), /* pcrel_offset */
720 /* ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff */
721 HOWTO (R_AARCH64_ADR_PREL_PG_HI21
, /* type */
723 2, /* size (0 = byte, 1 = short, 2 = long) */
725 TRUE
, /* pc_relative */
727 complain_overflow_signed
, /* complain_on_overflow */
728 bfd_elf_generic_reloc
, /* special_function */
729 "R_AARCH64_ADR_PREL_PG_HI21", /* name */
730 FALSE
, /* partial_inplace */
731 0x1fffff, /* src_mask */
732 0x1fffff, /* dst_mask */
733 TRUE
), /* pcrel_offset */
735 /* ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff [no overflow check] */
736 HOWTO (R_AARCH64_ADR_PREL_PG_HI21_NC
, /* type */
738 2, /* size (0 = byte, 1 = short, 2 = long) */
740 TRUE
, /* pc_relative */
742 complain_overflow_dont
, /* complain_on_overflow */
743 bfd_elf_generic_reloc
, /* special_function */
744 "R_AARCH64_ADR_PREL_PG_HI21_NC", /* name */
745 FALSE
, /* partial_inplace */
746 0x1fffff, /* src_mask */
747 0x1fffff, /* dst_mask */
748 TRUE
), /* pcrel_offset */
750 /* ADD: (S+A) & 0xfff [no overflow check] */
751 HOWTO (R_AARCH64_ADD_ABS_LO12_NC
, /* type */
753 2, /* size (0 = byte, 1 = short, 2 = long) */
755 FALSE
, /* pc_relative */
757 complain_overflow_dont
, /* complain_on_overflow */
758 bfd_elf_generic_reloc
, /* special_function */
759 "R_AARCH64_ADD_ABS_LO12_NC", /* name */
760 FALSE
, /* partial_inplace */
761 0x3ffc00, /* src_mask */
762 0x3ffc00, /* dst_mask */
763 FALSE
), /* pcrel_offset */
765 /* LD/ST8: (S+A) & 0xfff */
766 HOWTO (R_AARCH64_LDST8_ABS_LO12_NC
, /* type */
768 2, /* size (0 = byte, 1 = short, 2 = long) */
770 FALSE
, /* pc_relative */
772 complain_overflow_dont
, /* complain_on_overflow */
773 bfd_elf_generic_reloc
, /* special_function */
774 "R_AARCH64_LDST8_ABS_LO12_NC", /* name */
775 FALSE
, /* partial_inplace */
776 0xfff, /* src_mask */
777 0xfff, /* dst_mask */
778 FALSE
), /* pcrel_offset */
780 /* Relocations for control-flow instructions. */
782 /* TBZ/NZ: ((S+A-P) >> 2) & 0x3fff */
783 HOWTO (R_AARCH64_TSTBR14
, /* type */
785 2, /* size (0 = byte, 1 = short, 2 = long) */
787 TRUE
, /* pc_relative */
789 complain_overflow_signed
, /* complain_on_overflow */
790 bfd_elf_generic_reloc
, /* special_function */
791 "R_AARCH64_TSTBR14", /* name */
792 FALSE
, /* partial_inplace */
793 0x3fff, /* src_mask */
794 0x3fff, /* dst_mask */
795 TRUE
), /* pcrel_offset */
797 /* B.cond: ((S+A-P) >> 2) & 0x7ffff */
798 HOWTO (R_AARCH64_CONDBR19
, /* type */
800 2, /* size (0 = byte, 1 = short, 2 = long) */
802 TRUE
, /* pc_relative */
804 complain_overflow_signed
, /* complain_on_overflow */
805 bfd_elf_generic_reloc
, /* special_function */
806 "R_AARCH64_CONDBR19", /* name */
807 FALSE
, /* partial_inplace */
808 0x7ffff, /* src_mask */
809 0x7ffff, /* dst_mask */
810 TRUE
), /* pcrel_offset */
814 /* B: ((S+A-P) >> 2) & 0x3ffffff */
815 HOWTO (R_AARCH64_JUMP26
, /* type */
817 2, /* size (0 = byte, 1 = short, 2 = long) */
819 TRUE
, /* pc_relative */
821 complain_overflow_signed
, /* complain_on_overflow */
822 bfd_elf_generic_reloc
, /* special_function */
823 "R_AARCH64_JUMP26", /* name */
824 FALSE
, /* partial_inplace */
825 0x3ffffff, /* src_mask */
826 0x3ffffff, /* dst_mask */
827 TRUE
), /* pcrel_offset */
829 /* BL: ((S+A-P) >> 2) & 0x3ffffff */
830 HOWTO (R_AARCH64_CALL26
, /* type */
832 2, /* size (0 = byte, 1 = short, 2 = long) */
834 TRUE
, /* pc_relative */
836 complain_overflow_signed
, /* complain_on_overflow */
837 bfd_elf_generic_reloc
, /* special_function */
838 "R_AARCH64_CALL26", /* name */
839 FALSE
, /* partial_inplace */
840 0x3ffffff, /* src_mask */
841 0x3ffffff, /* dst_mask */
842 TRUE
), /* pcrel_offset */
844 /* LD/ST16: (S+A) & 0xffe */
845 HOWTO (R_AARCH64_LDST16_ABS_LO12_NC
, /* type */
847 2, /* size (0 = byte, 1 = short, 2 = long) */
849 FALSE
, /* pc_relative */
851 complain_overflow_dont
, /* complain_on_overflow */
852 bfd_elf_generic_reloc
, /* special_function */
853 "R_AARCH64_LDST16_ABS_LO12_NC", /* name */
854 FALSE
, /* partial_inplace */
855 0xffe, /* src_mask */
856 0xffe, /* dst_mask */
857 FALSE
), /* pcrel_offset */
859 /* LD/ST32: (S+A) & 0xffc */
860 HOWTO (R_AARCH64_LDST32_ABS_LO12_NC
, /* type */
862 2, /* size (0 = byte, 1 = short, 2 = long) */
864 FALSE
, /* pc_relative */
866 complain_overflow_dont
, /* complain_on_overflow */
867 bfd_elf_generic_reloc
, /* special_function */
868 "R_AARCH64_LDST32_ABS_LO12_NC", /* name */
869 FALSE
, /* partial_inplace */
870 0xffc, /* src_mask */
871 0xffc, /* dst_mask */
872 FALSE
), /* pcrel_offset */
874 /* LD/ST64: (S+A) & 0xff8 */
875 HOWTO (R_AARCH64_LDST64_ABS_LO12_NC
, /* type */
877 2, /* size (0 = byte, 1 = short, 2 = long) */
879 FALSE
, /* pc_relative */
881 complain_overflow_dont
, /* complain_on_overflow */
882 bfd_elf_generic_reloc
, /* special_function */
883 "R_AARCH64_LDST64_ABS_LO12_NC", /* name */
884 FALSE
, /* partial_inplace */
885 0xff8, /* src_mask */
886 0xff8, /* dst_mask */
887 FALSE
), /* pcrel_offset */
902 /* LD/ST128: (S+A) & 0xff0 */
903 HOWTO (R_AARCH64_LDST128_ABS_LO12_NC
, /* type */
905 2, /* size (0 = byte, 1 = short, 2 = long) */
907 FALSE
, /* pc_relative */
909 complain_overflow_dont
, /* complain_on_overflow */
910 bfd_elf_generic_reloc
, /* special_function */
911 "R_AARCH64_LDST128_ABS_LO12_NC", /* name */
912 FALSE
, /* partial_inplace */
913 0xff0, /* src_mask */
914 0xff0, /* dst_mask */
915 FALSE
), /* pcrel_offset */
927 /* Set a load-literal immediate field to bits
928 0x1FFFFC of G(S)-P */
929 HOWTO (R_AARCH64_GOT_LD_PREL19
, /* type */
931 2, /* size (0 = byte,1 = short,2 = long) */
933 TRUE
, /* pc_relative */
935 complain_overflow_signed
, /* complain_on_overflow */
936 bfd_elf_generic_reloc
, /* special_function */
937 "R_AARCH64_GOT_LD_PREL19", /* name */
938 FALSE
, /* partial_inplace */
939 0xffffe0, /* src_mask */
940 0xffffe0, /* dst_mask */
941 TRUE
), /* pcrel_offset */
945 /* Get to the page for the GOT entry for the symbol
946 (G(S) - P) using an ADRP instruction. */
947 HOWTO (R_AARCH64_ADR_GOT_PAGE
, /* type */
949 2, /* size (0 = byte, 1 = short, 2 = long) */
951 TRUE
, /* pc_relative */
953 complain_overflow_dont
, /* complain_on_overflow */
954 bfd_elf_generic_reloc
, /* special_function */
955 "R_AARCH64_ADR_GOT_PAGE", /* name */
956 FALSE
, /* partial_inplace */
957 0x1fffff, /* src_mask */
958 0x1fffff, /* dst_mask */
959 TRUE
), /* pcrel_offset */
961 /* LD64: GOT offset G(S) & 0xff8 */
962 HOWTO (R_AARCH64_LD64_GOT_LO12_NC
, /* type */
964 2, /* size (0 = byte, 1 = short, 2 = long) */
966 FALSE
, /* pc_relative */
968 complain_overflow_dont
, /* complain_on_overflow */
969 bfd_elf_generic_reloc
, /* special_function */
970 "R_AARCH64_LD64_GOT_LO12_NC", /* name */
971 FALSE
, /* partial_inplace */
972 0xff8, /* src_mask */
973 0xff8, /* dst_mask */
974 FALSE
) /* pcrel_offset */
977 static reloc_howto_type elf64_aarch64_tls_howto_table
[] =
981 /* Get to the page for the GOT entry for the symbol
982 (G(S) - P) using an ADRP instruction. */
983 HOWTO (R_AARCH64_TLSGD_ADR_PAGE21
, /* type */
985 2, /* size (0 = byte, 1 = short, 2 = long) */
987 TRUE
, /* pc_relative */
989 complain_overflow_dont
, /* complain_on_overflow */
990 bfd_elf_generic_reloc
, /* special_function */
991 "R_AARCH64_TLSGD_ADR_PAGE21", /* name */
992 FALSE
, /* partial_inplace */
993 0x1fffff, /* src_mask */
994 0x1fffff, /* dst_mask */
995 TRUE
), /* pcrel_offset */
997 /* ADD: GOT offset G(S) & 0xff8 [no overflow check] */
998 HOWTO (R_AARCH64_TLSGD_ADD_LO12_NC
, /* type */
1000 2, /* size (0 = byte, 1 = short, 2 = long) */
1002 FALSE
, /* pc_relative */
1004 complain_overflow_dont
, /* complain_on_overflow */
1005 bfd_elf_generic_reloc
, /* special_function */
1006 "R_AARCH64_TLSGD_ADD_LO12_NC", /* name */
1007 FALSE
, /* partial_inplace */
1008 0xfff, /* src_mask */
1009 0xfff, /* dst_mask */
1010 FALSE
), /* pcrel_offset */
1037 HOWTO (R_AARCH64_TLSIE_MOVW_GOTTPREL_G1
, /* type */
1038 16, /* rightshift */
1039 2, /* size (0 = byte, 1 = short, 2 = long) */
1041 FALSE
, /* pc_relative */
1043 complain_overflow_dont
, /* complain_on_overflow */
1044 bfd_elf_generic_reloc
, /* special_function */
1045 "R_AARCH64_TLSIE_MOVW_GOTTPREL_G1", /* name */
1046 FALSE
, /* partial_inplace */
1047 0xffff, /* src_mask */
1048 0xffff, /* dst_mask */
1049 FALSE
), /* pcrel_offset */
1051 HOWTO (R_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC
, /* type */
1053 2, /* size (0 = byte, 1 = short, 2 = long) */
1055 FALSE
, /* pc_relative */
1057 complain_overflow_dont
, /* complain_on_overflow */
1058 bfd_elf_generic_reloc
, /* special_function */
1059 "R_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC", /* name */
1060 FALSE
, /* partial_inplace */
1061 0xffff, /* src_mask */
1062 0xffff, /* dst_mask */
1063 FALSE
), /* pcrel_offset */
1065 HOWTO (R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
, /* type */
1066 12, /* rightshift */
1067 2, /* size (0 = byte, 1 = short, 2 = long) */
1069 FALSE
, /* pc_relative */
1071 complain_overflow_dont
, /* complain_on_overflow */
1072 bfd_elf_generic_reloc
, /* special_function */
1073 "R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21", /* name */
1074 FALSE
, /* partial_inplace */
1075 0x1fffff, /* src_mask */
1076 0x1fffff, /* dst_mask */
1077 FALSE
), /* pcrel_offset */
1079 HOWTO (R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
, /* type */
1081 2, /* size (0 = byte, 1 = short, 2 = long) */
1083 FALSE
, /* pc_relative */
1085 complain_overflow_dont
, /* complain_on_overflow */
1086 bfd_elf_generic_reloc
, /* special_function */
1087 "R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC", /* name */
1088 FALSE
, /* partial_inplace */
1089 0xff8, /* src_mask */
1090 0xff8, /* dst_mask */
1091 FALSE
), /* pcrel_offset */
1093 HOWTO (R_AARCH64_TLSIE_LD_GOTTPREL_PREL19
, /* type */
1095 2, /* size (0 = byte, 1 = short, 2 = long) */
1097 FALSE
, /* pc_relative */
1099 complain_overflow_dont
, /* complain_on_overflow */
1100 bfd_elf_generic_reloc
, /* special_function */
1101 "R_AARCH64_TLSIE_LD_GOTTPREL_PREL19", /* name */
1102 FALSE
, /* partial_inplace */
1103 0x1ffffc, /* src_mask */
1104 0x1ffffc, /* dst_mask */
1105 FALSE
), /* pcrel_offset */
1107 HOWTO (R_AARCH64_TLSLE_MOVW_TPREL_G2
, /* type */
1108 32, /* rightshift */
1109 2, /* size (0 = byte, 1 = short, 2 = long) */
1111 FALSE
, /* pc_relative */
1113 complain_overflow_dont
, /* complain_on_overflow */
1114 bfd_elf_generic_reloc
, /* special_function */
1115 "R_AARCH64_TLSLE_MOVW_TPREL_G2", /* name */
1116 FALSE
, /* partial_inplace */
1117 0xffff, /* src_mask */
1118 0xffff, /* dst_mask */
1119 FALSE
), /* pcrel_offset */
1121 HOWTO (R_AARCH64_TLSLE_MOVW_TPREL_G1
, /* type */
1122 16, /* rightshift */
1123 2, /* size (0 = byte, 1 = short, 2 = long) */
1125 FALSE
, /* pc_relative */
1127 complain_overflow_dont
, /* complain_on_overflow */
1128 bfd_elf_generic_reloc
, /* special_function */
1129 "R_AARCH64_TLSLE_MOVW_TPREL_G1", /* name */
1130 FALSE
, /* partial_inplace */
1131 0xffff, /* src_mask */
1132 0xffff, /* dst_mask */
1133 FALSE
), /* pcrel_offset */
1135 HOWTO (R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
, /* type */
1136 16, /* rightshift */
1137 2, /* size (0 = byte, 1 = short, 2 = long) */
1139 FALSE
, /* pc_relative */
1141 complain_overflow_dont
, /* complain_on_overflow */
1142 bfd_elf_generic_reloc
, /* special_function */
1143 "R_AARCH64_TLSLE_MOVW_TPREL_G1_NC", /* name */
1144 FALSE
, /* partial_inplace */
1145 0xffff, /* src_mask */
1146 0xffff, /* dst_mask */
1147 FALSE
), /* pcrel_offset */
1149 HOWTO (R_AARCH64_TLSLE_MOVW_TPREL_G0
, /* type */
1151 2, /* size (0 = byte, 1 = short, 2 = long) */
1153 FALSE
, /* pc_relative */
1155 complain_overflow_dont
, /* complain_on_overflow */
1156 bfd_elf_generic_reloc
, /* special_function */
1157 "R_AARCH64_TLSLE_MOVW_TPREL_G0", /* name */
1158 FALSE
, /* partial_inplace */
1159 0xffff, /* src_mask */
1160 0xffff, /* dst_mask */
1161 FALSE
), /* pcrel_offset */
1163 HOWTO (R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
, /* type */
1165 2, /* size (0 = byte, 1 = short, 2 = long) */
1167 FALSE
, /* pc_relative */
1169 complain_overflow_dont
, /* complain_on_overflow */
1170 bfd_elf_generic_reloc
, /* special_function */
1171 "R_AARCH64_TLSLE_MOVW_TPREL_G0_NC", /* name */
1172 FALSE
, /* partial_inplace */
1173 0xffff, /* src_mask */
1174 0xffff, /* dst_mask */
1175 FALSE
), /* pcrel_offset */
1177 HOWTO (R_AARCH64_TLSLE_ADD_TPREL_HI12
, /* type */
1178 12, /* rightshift */
1179 2, /* size (0 = byte, 1 = short, 2 = long) */
1181 FALSE
, /* pc_relative */
1183 complain_overflow_dont
, /* complain_on_overflow */
1184 bfd_elf_generic_reloc
, /* special_function */
1185 "R_AARCH64_TLSLE_ADD_TPREL_HI12", /* name */
1186 FALSE
, /* partial_inplace */
1187 0xfff, /* src_mask */
1188 0xfff, /* dst_mask */
1189 FALSE
), /* pcrel_offset */
1191 HOWTO (R_AARCH64_TLSLE_ADD_TPREL_LO12
, /* type */
1193 2, /* size (0 = byte, 1 = short, 2 = long) */
1195 FALSE
, /* pc_relative */
1197 complain_overflow_dont
, /* complain_on_overflow */
1198 bfd_elf_generic_reloc
, /* special_function */
1199 "R_AARCH64_TLSLE_ADD_TPREL_LO12", /* name */
1200 FALSE
, /* partial_inplace */
1201 0xfff, /* src_mask */
1202 0xfff, /* dst_mask */
1203 FALSE
), /* pcrel_offset */
1205 HOWTO (R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
, /* type */
1207 2, /* size (0 = byte, 1 = short, 2 = long) */
1209 FALSE
, /* pc_relative */
1211 complain_overflow_dont
, /* complain_on_overflow */
1212 bfd_elf_generic_reloc
, /* special_function */
1213 "R_AARCH64_TLSLE_ADD_TPREL_LO12_NC", /* name */
1214 FALSE
, /* partial_inplace */
1215 0xfff, /* src_mask */
1216 0xfff, /* dst_mask */
1217 FALSE
), /* pcrel_offset */
1220 static reloc_howto_type elf64_aarch64_tlsdesc_howto_table
[] =
1222 HOWTO (R_AARCH64_TLSDESC_LD_PREL19
, /* type */
1224 2, /* size (0 = byte, 1 = short, 2 = long) */
1226 TRUE
, /* pc_relative */
1228 complain_overflow_dont
, /* complain_on_overflow */
1229 bfd_elf_generic_reloc
, /* special_function */
1230 "R_AARCH64_TLSDESC_LD_PREL19", /* name */
1231 FALSE
, /* partial_inplace */
1232 0x1ffffc, /* src_mask */
1233 0x1ffffc, /* dst_mask */
1234 TRUE
), /* pcrel_offset */
1236 HOWTO (R_AARCH64_TLSDESC_ADR_PREL21
, /* type */
1238 2, /* size (0 = byte, 1 = short, 2 = long) */
1240 TRUE
, /* pc_relative */
1242 complain_overflow_dont
, /* complain_on_overflow */
1243 bfd_elf_generic_reloc
, /* special_function */
1244 "R_AARCH64_TLSDESC_ADR_PREL21", /* name */
1245 FALSE
, /* partial_inplace */
1246 0x1fffff, /* src_mask */
1247 0x1fffff, /* dst_mask */
1248 TRUE
), /* pcrel_offset */
1250 /* Get to the page for the GOT entry for the symbol
1251 (G(S) - P) using an ADRP instruction. */
1252 HOWTO (R_AARCH64_TLSDESC_ADR_PAGE21
, /* type */
1253 12, /* rightshift */
1254 2, /* size (0 = byte, 1 = short, 2 = long) */
1256 TRUE
, /* pc_relative */
1258 complain_overflow_dont
, /* complain_on_overflow */
1259 bfd_elf_generic_reloc
, /* special_function */
1260 "R_AARCH64_TLSDESC_ADR_PAGE21", /* name */
1261 FALSE
, /* partial_inplace */
1262 0x1fffff, /* src_mask */
1263 0x1fffff, /* dst_mask */
1264 TRUE
), /* pcrel_offset */
1266 /* LD64: GOT offset G(S) & 0xfff. */
1267 HOWTO (R_AARCH64_TLSDESC_LD64_LO12_NC
, /* type */
1269 2, /* size (0 = byte, 1 = short, 2 = long) */
1271 FALSE
, /* pc_relative */
1273 complain_overflow_dont
, /* complain_on_overflow */
1274 bfd_elf_generic_reloc
, /* special_function */
1275 "R_AARCH64_TLSDESC_LD64_LO12_NC", /* name */
1276 FALSE
, /* partial_inplace */
1277 0xfff, /* src_mask */
1278 0xfff, /* dst_mask */
1279 FALSE
), /* pcrel_offset */
1281 /* ADD: GOT offset G(S) & 0xfff. */
1282 HOWTO (R_AARCH64_TLSDESC_ADD_LO12_NC
, /* type */
1284 2, /* size (0 = byte, 1 = short, 2 = long) */
1286 FALSE
, /* pc_relative */
1288 complain_overflow_dont
, /* complain_on_overflow */
1289 bfd_elf_generic_reloc
, /* special_function */
1290 "R_AARCH64_TLSDESC_ADD_LO12_NC", /* name */
1291 FALSE
, /* partial_inplace */
1292 0xfff, /* src_mask */
1293 0xfff, /* dst_mask */
1294 FALSE
), /* pcrel_offset */
1296 HOWTO (R_AARCH64_TLSDESC_OFF_G1
, /* type */
1297 16, /* rightshift */
1298 2, /* size (0 = byte, 1 = short, 2 = long) */
1300 FALSE
, /* pc_relative */
1302 complain_overflow_dont
, /* complain_on_overflow */
1303 bfd_elf_generic_reloc
, /* special_function */
1304 "R_AARCH64_TLSDESC_OFF_G1", /* name */
1305 FALSE
, /* partial_inplace */
1306 0xffff, /* src_mask */
1307 0xffff, /* dst_mask */
1308 FALSE
), /* pcrel_offset */
1310 HOWTO (R_AARCH64_TLSDESC_OFF_G0_NC
, /* type */
1312 2, /* size (0 = byte, 1 = short, 2 = long) */
1314 FALSE
, /* pc_relative */
1316 complain_overflow_dont
, /* complain_on_overflow */
1317 bfd_elf_generic_reloc
, /* special_function */
1318 "R_AARCH64_TLSDESC_OFF_G0_NC", /* name */
1319 FALSE
, /* partial_inplace */
1320 0xffff, /* src_mask */
1321 0xffff, /* dst_mask */
1322 FALSE
), /* pcrel_offset */
1324 HOWTO (R_AARCH64_TLSDESC_LDR
, /* type */
1326 2, /* size (0 = byte, 1 = short, 2 = long) */
1328 FALSE
, /* pc_relative */
1330 complain_overflow_dont
, /* complain_on_overflow */
1331 bfd_elf_generic_reloc
, /* special_function */
1332 "R_AARCH64_TLSDESC_LDR", /* name */
1333 FALSE
, /* partial_inplace */
1336 FALSE
), /* pcrel_offset */
1338 HOWTO (R_AARCH64_TLSDESC_ADD
, /* type */
1340 2, /* size (0 = byte, 1 = short, 2 = long) */
1342 FALSE
, /* pc_relative */
1344 complain_overflow_dont
, /* complain_on_overflow */
1345 bfd_elf_generic_reloc
, /* special_function */
1346 "R_AARCH64_TLSDESC_ADD", /* name */
1347 FALSE
, /* partial_inplace */
1350 FALSE
), /* pcrel_offset */
1352 HOWTO (R_AARCH64_TLSDESC_CALL
, /* type */
1354 2, /* size (0 = byte, 1 = short, 2 = long) */
1356 FALSE
, /* pc_relative */
1358 complain_overflow_dont
, /* complain_on_overflow */
1359 bfd_elf_generic_reloc
, /* special_function */
1360 "R_AARCH64_TLSDESC_CALL", /* name */
1361 FALSE
, /* partial_inplace */
1364 FALSE
), /* pcrel_offset */
1367 static reloc_howto_type
*
1368 elf64_aarch64_howto_from_type (unsigned int r_type
)
1370 if (r_type
>= R_AARCH64_static_min
&& r_type
< R_AARCH64_static_max
)
1371 return &elf64_aarch64_howto_table
[r_type
- R_AARCH64_static_min
];
1373 if (r_type
>= R_AARCH64_tls_min
&& r_type
< R_AARCH64_tls_max
)
1374 return &elf64_aarch64_tls_howto_table
[r_type
- R_AARCH64_tls_min
];
1376 if (r_type
>= R_AARCH64_tlsdesc_min
&& r_type
< R_AARCH64_tlsdesc_max
)
1377 return &elf64_aarch64_tlsdesc_howto_table
[r_type
- R_AARCH64_tlsdesc_min
];
1379 if (r_type
>= R_AARCH64_dyn_min
&& r_type
< R_AARCH64_dyn_max
)
1380 return &elf64_aarch64_howto_dynrelocs
[r_type
- R_AARCH64_dyn_min
];
1384 case R_AARCH64_NONE
:
1385 return &elf64_aarch64_howto_none
;
1388 bfd_set_error (bfd_error_bad_value
);
1393 elf64_aarch64_info_to_howto (bfd
*abfd ATTRIBUTE_UNUSED
, arelent
*bfd_reloc
,
1394 Elf_Internal_Rela
*elf_reloc
)
1396 unsigned int r_type
;
1398 r_type
= ELF64_R_TYPE (elf_reloc
->r_info
);
1399 bfd_reloc
->howto
= elf64_aarch64_howto_from_type (r_type
);
1402 struct elf64_aarch64_reloc_map
1404 bfd_reloc_code_real_type bfd_reloc_val
;
1405 unsigned int elf_reloc_val
;
1408 /* All entries in this list must also be present in
1409 elf64_aarch64_howto_table. */
1410 static const struct elf64_aarch64_reloc_map elf64_aarch64_reloc_map
[] =
1412 {BFD_RELOC_NONE
, R_AARCH64_NONE
},
1414 /* Basic data relocations. */
1415 {BFD_RELOC_CTOR
, R_AARCH64_ABS64
},
1416 {BFD_RELOC_64
, R_AARCH64_ABS64
},
1417 {BFD_RELOC_32
, R_AARCH64_ABS32
},
1418 {BFD_RELOC_16
, R_AARCH64_ABS16
},
1419 {BFD_RELOC_64_PCREL
, R_AARCH64_PREL64
},
1420 {BFD_RELOC_32_PCREL
, R_AARCH64_PREL32
},
1421 {BFD_RELOC_16_PCREL
, R_AARCH64_PREL16
},
1423 /* Group relocations to low order bits of a 16, 32, 48 or 64 bit
1425 {BFD_RELOC_AARCH64_MOVW_G0_NC
, R_AARCH64_MOVW_UABS_G0_NC
},
1426 {BFD_RELOC_AARCH64_MOVW_G1_NC
, R_AARCH64_MOVW_UABS_G1_NC
},
1427 {BFD_RELOC_AARCH64_MOVW_G2_NC
, R_AARCH64_MOVW_UABS_G2_NC
},
1429 /* Group relocations to create high bits of a 16, 32, 48 or 64 bit
1430 signed value inline. */
1431 {BFD_RELOC_AARCH64_MOVW_G0_S
, R_AARCH64_MOVW_SABS_G0
},
1432 {BFD_RELOC_AARCH64_MOVW_G1_S
, R_AARCH64_MOVW_SABS_G1
},
1433 {BFD_RELOC_AARCH64_MOVW_G2_S
, R_AARCH64_MOVW_SABS_G2
},
1435 /* Group relocations to create high bits of a 16, 32, 48 or 64 bit
1436 unsigned value inline. */
1437 {BFD_RELOC_AARCH64_MOVW_G0
, R_AARCH64_MOVW_UABS_G0
},
1438 {BFD_RELOC_AARCH64_MOVW_G1
, R_AARCH64_MOVW_UABS_G1
},
1439 {BFD_RELOC_AARCH64_MOVW_G2
, R_AARCH64_MOVW_UABS_G2
},
1440 {BFD_RELOC_AARCH64_MOVW_G3
, R_AARCH64_MOVW_UABS_G3
},
1442 /* Relocations to generate 19, 21 and 33 bit PC-relative load/store. */
1443 {BFD_RELOC_AARCH64_LD_LO19_PCREL
, R_AARCH64_LD_PREL_LO19
},
1444 {BFD_RELOC_AARCH64_ADR_LO21_PCREL
, R_AARCH64_ADR_PREL_LO21
},
1445 {BFD_RELOC_AARCH64_ADR_HI21_PCREL
, R_AARCH64_ADR_PREL_PG_HI21
},
1446 {BFD_RELOC_AARCH64_ADR_HI21_NC_PCREL
, R_AARCH64_ADR_PREL_PG_HI21_NC
},
1447 {BFD_RELOC_AARCH64_ADD_LO12
, R_AARCH64_ADD_ABS_LO12_NC
},
1448 {BFD_RELOC_AARCH64_LDST8_LO12
, R_AARCH64_LDST8_ABS_LO12_NC
},
1449 {BFD_RELOC_AARCH64_LDST16_LO12
, R_AARCH64_LDST16_ABS_LO12_NC
},
1450 {BFD_RELOC_AARCH64_LDST32_LO12
, R_AARCH64_LDST32_ABS_LO12_NC
},
1451 {BFD_RELOC_AARCH64_LDST64_LO12
, R_AARCH64_LDST64_ABS_LO12_NC
},
1452 {BFD_RELOC_AARCH64_LDST128_LO12
, R_AARCH64_LDST128_ABS_LO12_NC
},
1454 /* Relocations for control-flow instructions. */
1455 {BFD_RELOC_AARCH64_TSTBR14
, R_AARCH64_TSTBR14
},
1456 {BFD_RELOC_AARCH64_BRANCH19
, R_AARCH64_CONDBR19
},
1457 {BFD_RELOC_AARCH64_JUMP26
, R_AARCH64_JUMP26
},
1458 {BFD_RELOC_AARCH64_CALL26
, R_AARCH64_CALL26
},
1460 /* Relocations for PIC. */
1461 {BFD_RELOC_AARCH64_GOT_LD_PREL19
, R_AARCH64_GOT_LD_PREL19
},
1462 {BFD_RELOC_AARCH64_ADR_GOT_PAGE
, R_AARCH64_ADR_GOT_PAGE
},
1463 {BFD_RELOC_AARCH64_LD64_GOT_LO12_NC
, R_AARCH64_LD64_GOT_LO12_NC
},
1465 /* Relocations for TLS. */
1466 {BFD_RELOC_AARCH64_TLSGD_ADR_PAGE21
, R_AARCH64_TLSGD_ADR_PAGE21
},
1467 {BFD_RELOC_AARCH64_TLSGD_ADD_LO12_NC
, R_AARCH64_TLSGD_ADD_LO12_NC
},
1468 {BFD_RELOC_AARCH64_TLSIE_MOVW_GOTTPREL_G1
,
1469 R_AARCH64_TLSIE_MOVW_GOTTPREL_G1
},
1470 {BFD_RELOC_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC
,
1471 R_AARCH64_TLSIE_MOVW_GOTTPREL_G0_NC
},
1472 {BFD_RELOC_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
,
1473 R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
},
1474 {BFD_RELOC_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
,
1475 R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
},
1476 {BFD_RELOC_AARCH64_TLSIE_LD_GOTTPREL_PREL19
,
1477 R_AARCH64_TLSIE_LD_GOTTPREL_PREL19
},
1478 {BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G2
, R_AARCH64_TLSLE_MOVW_TPREL_G2
},
1479 {BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1
, R_AARCH64_TLSLE_MOVW_TPREL_G1
},
1480 {BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G1_NC
,
1481 R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
},
1482 {BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0
, R_AARCH64_TLSLE_MOVW_TPREL_G0
},
1483 {BFD_RELOC_AARCH64_TLSLE_MOVW_TPREL_G0_NC
,
1484 R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
},
1485 {BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12
, R_AARCH64_TLSLE_ADD_TPREL_LO12
},
1486 {BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_HI12
, R_AARCH64_TLSLE_ADD_TPREL_HI12
},
1487 {BFD_RELOC_AARCH64_TLSLE_ADD_TPREL_LO12_NC
,
1488 R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
},
1489 {BFD_RELOC_AARCH64_TLSDESC_LD_PREL19
, R_AARCH64_TLSDESC_LD_PREL19
},
1490 {BFD_RELOC_AARCH64_TLSDESC_ADR_PREL21
, R_AARCH64_TLSDESC_ADR_PREL21
},
1491 {BFD_RELOC_AARCH64_TLSDESC_ADR_PAGE21
, R_AARCH64_TLSDESC_ADR_PAGE21
},
1492 {BFD_RELOC_AARCH64_TLSDESC_ADD_LO12_NC
, R_AARCH64_TLSDESC_ADD_LO12_NC
},
1493 {BFD_RELOC_AARCH64_TLSDESC_LD64_LO12_NC
, R_AARCH64_TLSDESC_LD64_LO12_NC
},
1494 {BFD_RELOC_AARCH64_TLSDESC_OFF_G1
, R_AARCH64_TLSDESC_OFF_G1
},
1495 {BFD_RELOC_AARCH64_TLSDESC_OFF_G0_NC
, R_AARCH64_TLSDESC_OFF_G0_NC
},
1496 {BFD_RELOC_AARCH64_TLSDESC_LDR
, R_AARCH64_TLSDESC_LDR
},
1497 {BFD_RELOC_AARCH64_TLSDESC_ADD
, R_AARCH64_TLSDESC_ADD
},
1498 {BFD_RELOC_AARCH64_TLSDESC_CALL
, R_AARCH64_TLSDESC_CALL
},
1499 {BFD_RELOC_AARCH64_TLS_DTPMOD64
, R_AARCH64_TLS_DTPMOD64
},
1500 {BFD_RELOC_AARCH64_TLS_DTPREL64
, R_AARCH64_TLS_DTPREL64
},
1501 {BFD_RELOC_AARCH64_TLS_TPREL64
, R_AARCH64_TLS_TPREL64
},
1502 {BFD_RELOC_AARCH64_TLSDESC
, R_AARCH64_TLSDESC
},
1505 static reloc_howto_type
*
1506 elf64_aarch64_reloc_type_lookup (bfd
*abfd ATTRIBUTE_UNUSED
,
1507 bfd_reloc_code_real_type code
)
1511 for (i
= 0; i
< ARRAY_SIZE (elf64_aarch64_reloc_map
); i
++)
1512 if (elf64_aarch64_reloc_map
[i
].bfd_reloc_val
== code
)
1513 return elf64_aarch64_howto_from_type
1514 (elf64_aarch64_reloc_map
[i
].elf_reloc_val
);
1516 bfd_set_error (bfd_error_bad_value
);
1520 static reloc_howto_type
*
1521 elf64_aarch64_reloc_name_lookup (bfd
*abfd ATTRIBUTE_UNUSED
,
1526 for (i
= 0; i
< ARRAY_SIZE (elf64_aarch64_howto_table
); i
++)
1527 if (elf64_aarch64_howto_table
[i
].name
!= NULL
1528 && strcasecmp (elf64_aarch64_howto_table
[i
].name
, r_name
) == 0)
1529 return &elf64_aarch64_howto_table
[i
];
1534 /* Support for core dump NOTE sections. */
1537 elf64_aarch64_grok_prstatus (bfd
*abfd
, Elf_Internal_Note
*note
)
1542 switch (note
->descsz
)
1547 case 408: /* sizeof(struct elf_prstatus) on Linux/arm64. */
1549 elf_tdata (abfd
)->core
->signal
1550 = bfd_get_16 (abfd
, note
->descdata
+ 12);
1553 elf_tdata (abfd
)->core
->lwpid
1554 = bfd_get_32 (abfd
, note
->descdata
+ 32);
1563 /* Make a ".reg/999" section. */
1564 return _bfd_elfcore_make_pseudosection (abfd
, ".reg",
1565 size
, note
->descpos
+ offset
);
1568 #define TARGET_LITTLE_SYM bfd_elf64_littleaarch64_vec
1569 #define TARGET_LITTLE_NAME "elf64-littleaarch64"
1570 #define TARGET_BIG_SYM bfd_elf64_bigaarch64_vec
1571 #define TARGET_BIG_NAME "elf64-bigaarch64"
1573 #define elf_backend_grok_prstatus elf64_aarch64_grok_prstatus
1575 typedef unsigned long int insn32
;
1577 /* The linker script knows the section names for placement.
1578 The entry_names are used to do simple name mangling on the stubs.
1579 Given a function name, and its type, the stub can be found. The
1580 name can be changed. The only requirement is the %s be present. */
1581 #define STUB_ENTRY_NAME "__%s_veneer"
1583 /* The name of the dynamic interpreter. This is put in the .interp
1585 #define ELF_DYNAMIC_INTERPRETER "/lib/ld.so.1"
1587 #define AARCH64_MAX_FWD_BRANCH_OFFSET \
1588 (((1 << 25) - 1) << 2)
1589 #define AARCH64_MAX_BWD_BRANCH_OFFSET \
1592 #define AARCH64_MAX_ADRP_IMM ((1 << 20) - 1)
1593 #define AARCH64_MIN_ADRP_IMM (-(1 << 20))
1596 aarch64_valid_for_adrp_p (bfd_vma value
, bfd_vma place
)
1598 bfd_signed_vma offset
= (bfd_signed_vma
) (PG (value
) - PG (place
)) >> 12;
1599 return offset
<= AARCH64_MAX_ADRP_IMM
&& offset
>= AARCH64_MIN_ADRP_IMM
;
1603 aarch64_valid_branch_p (bfd_vma value
, bfd_vma place
)
1605 bfd_signed_vma offset
= (bfd_signed_vma
) (value
- place
);
1606 return (offset
<= AARCH64_MAX_FWD_BRANCH_OFFSET
1607 && offset
>= AARCH64_MAX_BWD_BRANCH_OFFSET
);
1610 static const uint32_t aarch64_adrp_branch_stub
[] =
1612 0x90000010, /* adrp ip0, X */
1613 /* R_AARCH64_ADR_HI21_PCREL(X) */
1614 0x91000210, /* add ip0, ip0, :lo12:X */
1615 /* R_AARCH64_ADD_ABS_LO12_NC(X) */
1616 0xd61f0200, /* br ip0 */
1619 static const uint32_t aarch64_long_branch_stub
[] =
1621 0x58000090, /* ldr ip0, 1f */
1622 0x10000011, /* adr ip1, #0 */
1623 0x8b110210, /* add ip0, ip0, ip1 */
1624 0xd61f0200, /* br ip0 */
1625 0x00000000, /* 1: .xword
1626 R_AARCH64_PREL64(X) + 12
1631 /* Section name for stubs is the associated section name plus this
1633 #define STUB_SUFFIX ".stub"
1635 enum elf64_aarch64_stub_type
1638 aarch64_stub_adrp_branch
,
1639 aarch64_stub_long_branch
,
1642 struct elf64_aarch64_stub_hash_entry
1644 /* Base hash table entry structure. */
1645 struct bfd_hash_entry root
;
1647 /* The stub section. */
1650 /* Offset within stub_sec of the beginning of this stub. */
1651 bfd_vma stub_offset
;
1653 /* Given the symbol's value and its section we can determine its final
1654 value when building the stubs (so the stub knows where to jump). */
1655 bfd_vma target_value
;
1656 asection
*target_section
;
1658 enum elf64_aarch64_stub_type stub_type
;
1660 /* The symbol table entry, if any, that this was derived from. */
1661 struct elf64_aarch64_link_hash_entry
*h
;
1663 /* Destination symbol type */
1664 unsigned char st_type
;
1666 /* Where this stub is being called from, or, in the case of combined
1667 stub sections, the first input section in the group. */
1670 /* The name for the local symbol at the start of this stub. The
1671 stub name in the hash table has to be unique; this does not, so
1672 it can be friendlier. */
1676 /* Used to build a map of a section. This is required for mixed-endian
1679 typedef struct elf64_elf_section_map
1684 elf64_aarch64_section_map
;
1687 typedef struct _aarch64_elf_section_data
1689 struct bfd_elf_section_data elf
;
1690 unsigned int mapcount
;
1691 unsigned int mapsize
;
1692 elf64_aarch64_section_map
*map
;
1694 _aarch64_elf_section_data
;
1696 #define elf64_aarch64_section_data(sec) \
1697 ((_aarch64_elf_section_data *) elf_section_data (sec))
1699 /* The size of the thread control block. */
1702 struct elf_aarch64_local_symbol
1704 unsigned int got_type
;
1705 bfd_signed_vma got_refcount
;
1708 /* Offset of the GOTPLT entry reserved for the TLS descriptor. The
1709 offset is from the end of the jump table and reserved entries
1712 The magic value (bfd_vma) -1 indicates that an offset has not be
1714 bfd_vma tlsdesc_got_jump_table_offset
;
1717 struct elf_aarch64_obj_tdata
1719 struct elf_obj_tdata root
;
1721 /* local symbol descriptors */
1722 struct elf_aarch64_local_symbol
*locals
;
1724 /* Zero to warn when linking objects with incompatible enum sizes. */
1725 int no_enum_size_warning
;
1727 /* Zero to warn when linking objects with incompatible wchar_t sizes. */
1728 int no_wchar_size_warning
;
1731 #define elf_aarch64_tdata(bfd) \
1732 ((struct elf_aarch64_obj_tdata *) (bfd)->tdata.any)
1734 #define elf64_aarch64_locals(bfd) (elf_aarch64_tdata (bfd)->locals)
1736 #define is_aarch64_elf(bfd) \
1737 (bfd_get_flavour (bfd) == bfd_target_elf_flavour \
1738 && elf_tdata (bfd) != NULL \
1739 && elf_object_id (bfd) == AARCH64_ELF_DATA)
1742 elf64_aarch64_mkobject (bfd
*abfd
)
1744 return bfd_elf_allocate_object (abfd
, sizeof (struct elf_aarch64_obj_tdata
),
1748 #define elf64_aarch64_hash_entry(ent) \
1749 ((struct elf64_aarch64_link_hash_entry *)(ent))
1751 #define GOT_UNKNOWN 0
1752 #define GOT_NORMAL 1
1753 #define GOT_TLS_GD 2
1754 #define GOT_TLS_IE 4
1755 #define GOT_TLSDESC_GD 8
1757 #define GOT_TLS_GD_ANY_P(type) ((type & GOT_TLS_GD) || (type & GOT_TLSDESC_GD))
1759 /* AArch64 ELF linker hash entry. */
1760 struct elf64_aarch64_link_hash_entry
1762 struct elf_link_hash_entry root
;
1764 /* Track dynamic relocs copied for this symbol. */
1765 struct elf_dyn_relocs
*dyn_relocs
;
1767 /* Since PLT entries have variable size, we need to record the
1768 index into .got.plt instead of recomputing it from the PLT
1770 bfd_signed_vma plt_got_offset
;
1772 /* Bit mask representing the type of GOT entry(s) if any required by
1774 unsigned int got_type
;
1776 /* A pointer to the most recently used stub hash entry against this
1778 struct elf64_aarch64_stub_hash_entry
*stub_cache
;
1780 /* Offset of the GOTPLT entry reserved for the TLS descriptor. The offset
1781 is from the end of the jump table and reserved entries within the PLTGOT.
1783 The magic value (bfd_vma) -1 indicates that an offset has not
1785 bfd_vma tlsdesc_got_jump_table_offset
;
1789 elf64_aarch64_symbol_got_type (struct elf_link_hash_entry
*h
,
1791 unsigned long r_symndx
)
1794 return elf64_aarch64_hash_entry (h
)->got_type
;
1796 if (! elf64_aarch64_locals (abfd
))
1799 return elf64_aarch64_locals (abfd
)[r_symndx
].got_type
;
1802 /* Traverse an AArch64 ELF linker hash table. */
1803 #define elf64_aarch64_link_hash_traverse(table, func, info) \
1804 (elf_link_hash_traverse \
1806 (bfd_boolean (*) (struct elf_link_hash_entry *, void *)) (func), \
1809 /* Get the AArch64 elf linker hash table from a link_info structure. */
1810 #define elf64_aarch64_hash_table(info) \
1811 ((struct elf64_aarch64_link_hash_table *) ((info)->hash))
1813 #define aarch64_stub_hash_lookup(table, string, create, copy) \
1814 ((struct elf64_aarch64_stub_hash_entry *) \
1815 bfd_hash_lookup ((table), (string), (create), (copy)))
1817 /* AArch64 ELF linker hash table. */
1818 struct elf64_aarch64_link_hash_table
1820 /* The main hash table. */
1821 struct elf_link_hash_table root
;
1823 /* Nonzero to force PIC branch veneers. */
1826 /* The number of bytes in the initial entry in the PLT. */
1827 bfd_size_type plt_header_size
;
1829 /* The number of bytes in the subsequent PLT etries. */
1830 bfd_size_type plt_entry_size
;
1832 /* Short-cuts to get to dynamic linker sections. */
1836 /* Small local sym cache. */
1837 struct sym_cache sym_cache
;
1839 /* For convenience in allocate_dynrelocs. */
1842 /* The amount of space used by the reserved portion of the sgotplt
1843 section, plus whatever space is used by the jump slots. */
1844 bfd_vma sgotplt_jump_table_size
;
1846 /* The stub hash table. */
1847 struct bfd_hash_table stub_hash_table
;
1849 /* Linker stub bfd. */
1852 /* Linker call-backs. */
1853 asection
*(*add_stub_section
) (const char *, asection
*);
1854 void (*layout_sections_again
) (void);
1856 /* Array to keep track of which stub sections have been created, and
1857 information on stub grouping. */
1860 /* This is the section to which stubs in the group will be
1863 /* The stub section. */
1867 /* Assorted information used by elf64_aarch64_size_stubs. */
1868 unsigned int bfd_count
;
1870 asection
**input_list
;
1872 /* The offset into splt of the PLT entry for the TLS descriptor
1873 resolver. Special values are 0, if not necessary (or not found
1874 to be necessary yet), and -1 if needed but not determined
1876 bfd_vma tlsdesc_plt
;
1878 /* The GOT offset for the lazy trampoline. Communicated to the
1879 loader via DT_TLSDESC_GOT. The magic value (bfd_vma) -1
1880 indicates an offset is not allocated. */
1881 bfd_vma dt_tlsdesc_got
;
1883 /* Used by local STT_GNU_IFUNC symbols. */
1884 htab_t loc_hash_table
;
1885 void * loc_hash_memory
;
1887 /* The index of the next R_AARCH64_JUMP_SLOT entry in .rela.plt. */
1888 bfd_vma next_jump_slot_index
;
1889 /* The index of the next R_AARCH64_IRELATIVE entry in .rela.plt. */
1890 bfd_vma next_irelative_index
;
1894 /* Return non-zero if the indicated VALUE has overflowed the maximum
1895 range expressible by a unsigned number with the indicated number of
1898 static bfd_reloc_status_type
1899 aarch64_unsigned_overflow (bfd_vma value
, unsigned int bits
)
1902 if (bits
>= sizeof (bfd_vma
) * 8)
1903 return bfd_reloc_ok
;
1904 lim
= (bfd_vma
) 1 << bits
;
1906 return bfd_reloc_overflow
;
1907 return bfd_reloc_ok
;
1911 /* Return non-zero if the indicated VALUE has overflowed the maximum
1912 range expressible by an signed number with the indicated number of
1915 static bfd_reloc_status_type
1916 aarch64_signed_overflow (bfd_vma value
, unsigned int bits
)
1918 bfd_signed_vma svalue
= (bfd_signed_vma
) value
;
1921 if (bits
>= sizeof (bfd_vma
) * 8)
1922 return bfd_reloc_ok
;
1923 lim
= (bfd_signed_vma
) 1 << (bits
- 1);
1924 if (svalue
< -lim
|| svalue
>= lim
)
1925 return bfd_reloc_overflow
;
1926 return bfd_reloc_ok
;
1929 /* Create an entry in an AArch64 ELF linker hash table. */
1931 static struct bfd_hash_entry
*
1932 elf64_aarch64_link_hash_newfunc (struct bfd_hash_entry
*entry
,
1933 struct bfd_hash_table
*table
,
1936 struct elf64_aarch64_link_hash_entry
*ret
=
1937 (struct elf64_aarch64_link_hash_entry
*) entry
;
1939 /* Allocate the structure if it has not already been allocated by a
1942 ret
= bfd_hash_allocate (table
,
1943 sizeof (struct elf64_aarch64_link_hash_entry
));
1945 return (struct bfd_hash_entry
*) ret
;
1947 /* Call the allocation method of the superclass. */
1948 ret
= ((struct elf64_aarch64_link_hash_entry
*)
1949 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry
*) ret
,
1953 ret
->dyn_relocs
= NULL
;
1954 ret
->got_type
= GOT_UNKNOWN
;
1955 ret
->plt_got_offset
= (bfd_vma
) - 1;
1956 ret
->stub_cache
= NULL
;
1957 ret
->tlsdesc_got_jump_table_offset
= (bfd_vma
) - 1;
1960 return (struct bfd_hash_entry
*) ret
;
1963 /* Initialize an entry in the stub hash table. */
1965 static struct bfd_hash_entry
*
1966 stub_hash_newfunc (struct bfd_hash_entry
*entry
,
1967 struct bfd_hash_table
*table
, const char *string
)
1969 /* Allocate the structure if it has not already been allocated by a
1973 entry
= bfd_hash_allocate (table
,
1975 elf64_aarch64_stub_hash_entry
));
1980 /* Call the allocation method of the superclass. */
1981 entry
= bfd_hash_newfunc (entry
, table
, string
);
1984 struct elf64_aarch64_stub_hash_entry
*eh
;
1986 /* Initialize the local fields. */
1987 eh
= (struct elf64_aarch64_stub_hash_entry
*) entry
;
1988 eh
->stub_sec
= NULL
;
1989 eh
->stub_offset
= 0;
1990 eh
->target_value
= 0;
1991 eh
->target_section
= NULL
;
1992 eh
->stub_type
= aarch64_stub_none
;
2000 /* Compute a hash of a local hash entry. We use elf_link_hash_entry
2001 for local symbol so that we can handle local STT_GNU_IFUNC symbols
2002 as global symbol. We reuse indx and dynstr_index for local symbol
2003 hash since they aren't used by global symbols in this backend. */
2006 elf_aarch64_local_htab_hash (const void *ptr
)
2008 struct elf_link_hash_entry
*h
2009 = (struct elf_link_hash_entry
*) ptr
;
2010 return ELF_LOCAL_SYMBOL_HASH (h
->indx
, h
->dynstr_index
);
2013 /* Compare local hash entries. */
2016 elf_aarch64_local_htab_eq (const void *ptr1
, const void *ptr2
)
2018 struct elf_link_hash_entry
*h1
2019 = (struct elf_link_hash_entry
*) ptr1
;
2020 struct elf_link_hash_entry
*h2
2021 = (struct elf_link_hash_entry
*) ptr2
;
2023 return h1
->indx
== h2
->indx
&& h1
->dynstr_index
== h2
->dynstr_index
;
2026 /* Find and/or create a hash entry for local symbol. */
2028 static struct elf_link_hash_entry
*
2029 elf_aarch64_get_local_sym_hash (struct elf64_aarch64_link_hash_table
*htab
,
2030 bfd
*abfd
, const Elf_Internal_Rela
*rel
,
2033 struct elf64_aarch64_link_hash_entry e
, *ret
;
2034 asection
*sec
= abfd
->sections
;
2035 hashval_t h
= ELF_LOCAL_SYMBOL_HASH (sec
->id
,
2036 ELF64_R_SYM (rel
->r_info
));
2039 e
.root
.indx
= sec
->id
;
2040 e
.root
.dynstr_index
= ELF64_R_SYM (rel
->r_info
);
2041 slot
= htab_find_slot_with_hash (htab
->loc_hash_table
, &e
, h
,
2042 create
? INSERT
: NO_INSERT
);
2049 ret
= (struct elf64_aarch64_link_hash_entry
*) *slot
;
2053 ret
= (struct elf64_aarch64_link_hash_entry
*)
2054 objalloc_alloc ((struct objalloc
*) htab
->loc_hash_memory
,
2055 sizeof (struct elf64_aarch64_link_hash_entry
));
2058 memset (ret
, 0, sizeof (*ret
));
2059 ret
->root
.indx
= sec
->id
;
2060 ret
->root
.dynstr_index
= ELF64_R_SYM (rel
->r_info
);
2061 ret
->root
.dynindx
= -1;
2067 /* Copy the extra info we tack onto an elf_link_hash_entry. */
2070 elf64_aarch64_copy_indirect_symbol (struct bfd_link_info
*info
,
2071 struct elf_link_hash_entry
*dir
,
2072 struct elf_link_hash_entry
*ind
)
2074 struct elf64_aarch64_link_hash_entry
*edir
, *eind
;
2076 edir
= (struct elf64_aarch64_link_hash_entry
*) dir
;
2077 eind
= (struct elf64_aarch64_link_hash_entry
*) ind
;
2079 if (eind
->dyn_relocs
!= NULL
)
2081 if (edir
->dyn_relocs
!= NULL
)
2083 struct elf_dyn_relocs
**pp
;
2084 struct elf_dyn_relocs
*p
;
2086 /* Add reloc counts against the indirect sym to the direct sym
2087 list. Merge any entries against the same section. */
2088 for (pp
= &eind
->dyn_relocs
; (p
= *pp
) != NULL
;)
2090 struct elf_dyn_relocs
*q
;
2092 for (q
= edir
->dyn_relocs
; q
!= NULL
; q
= q
->next
)
2093 if (q
->sec
== p
->sec
)
2095 q
->pc_count
+= p
->pc_count
;
2096 q
->count
+= p
->count
;
2103 *pp
= edir
->dyn_relocs
;
2106 edir
->dyn_relocs
= eind
->dyn_relocs
;
2107 eind
->dyn_relocs
= NULL
;
2110 if (ind
->root
.type
== bfd_link_hash_indirect
)
2112 /* Copy over PLT info. */
2113 if (dir
->got
.refcount
<= 0)
2115 edir
->got_type
= eind
->got_type
;
2116 eind
->got_type
= GOT_UNKNOWN
;
2120 _bfd_elf_link_hash_copy_indirect (info
, dir
, ind
);
2123 /* Create an AArch64 elf linker hash table. */
2125 static struct bfd_link_hash_table
*
2126 elf64_aarch64_link_hash_table_create (bfd
*abfd
)
2128 struct elf64_aarch64_link_hash_table
*ret
;
2129 bfd_size_type amt
= sizeof (struct elf64_aarch64_link_hash_table
);
2131 ret
= bfd_zmalloc (amt
);
2135 if (!_bfd_elf_link_hash_table_init
2136 (&ret
->root
, abfd
, elf64_aarch64_link_hash_newfunc
,
2137 sizeof (struct elf64_aarch64_link_hash_entry
), AARCH64_ELF_DATA
))
2143 ret
->plt_header_size
= PLT_ENTRY_SIZE
;
2144 ret
->plt_entry_size
= PLT_SMALL_ENTRY_SIZE
;
2146 ret
->dt_tlsdesc_got
= (bfd_vma
) - 1;
2148 if (!bfd_hash_table_init (&ret
->stub_hash_table
, stub_hash_newfunc
,
2149 sizeof (struct elf64_aarch64_stub_hash_entry
)))
2155 ret
->loc_hash_table
= htab_try_create (1024,
2156 elf_aarch64_local_htab_hash
,
2157 elf_aarch64_local_htab_eq
,
2159 ret
->loc_hash_memory
= objalloc_create ();
2160 if (!ret
->loc_hash_table
|| !ret
->loc_hash_memory
)
2166 return &ret
->root
.root
;
2169 /* Free the derived linker hash table. */
2172 elf64_aarch64_hash_table_free (struct bfd_link_hash_table
*hash
)
2174 struct elf64_aarch64_link_hash_table
*ret
2175 = (struct elf64_aarch64_link_hash_table
*) hash
;
2177 if (ret
->loc_hash_table
)
2178 htab_delete (ret
->loc_hash_table
);
2179 if (ret
->loc_hash_memory
)
2180 objalloc_free ((struct objalloc
*) ret
->loc_hash_memory
);
2182 bfd_hash_table_free (&ret
->stub_hash_table
);
2183 _bfd_elf_link_hash_table_free (hash
);
2187 aarch64_resolve_relocation (unsigned int r_type
, bfd_vma place
, bfd_vma value
,
2188 bfd_vma addend
, bfd_boolean weak_undef_p
)
2192 case R_AARCH64_TLSDESC_CALL
:
2193 case R_AARCH64_NONE
:
2194 case R_AARCH64_NULL
:
2197 case R_AARCH64_ADR_PREL_LO21
:
2198 case R_AARCH64_CONDBR19
:
2199 case R_AARCH64_LD_PREL_LO19
:
2200 case R_AARCH64_PREL16
:
2201 case R_AARCH64_PREL32
:
2202 case R_AARCH64_PREL64
:
2203 case R_AARCH64_TSTBR14
:
2206 value
= value
+ addend
- place
;
2209 case R_AARCH64_CALL26
:
2210 case R_AARCH64_JUMP26
:
2211 value
= value
+ addend
- place
;
2214 case R_AARCH64_ABS16
:
2215 case R_AARCH64_ABS32
:
2216 case R_AARCH64_MOVW_SABS_G0
:
2217 case R_AARCH64_MOVW_SABS_G1
:
2218 case R_AARCH64_MOVW_SABS_G2
:
2219 case R_AARCH64_MOVW_UABS_G0
:
2220 case R_AARCH64_MOVW_UABS_G0_NC
:
2221 case R_AARCH64_MOVW_UABS_G1
:
2222 case R_AARCH64_MOVW_UABS_G1_NC
:
2223 case R_AARCH64_MOVW_UABS_G2
:
2224 case R_AARCH64_MOVW_UABS_G2_NC
:
2225 case R_AARCH64_MOVW_UABS_G3
:
2226 value
= value
+ addend
;
2229 case R_AARCH64_ADR_PREL_PG_HI21
:
2230 case R_AARCH64_ADR_PREL_PG_HI21_NC
:
2233 value
= PG (value
+ addend
) - PG (place
);
2236 case R_AARCH64_GOT_LD_PREL19
:
2237 value
= value
+ addend
- place
;
2240 case R_AARCH64_ADR_GOT_PAGE
:
2241 case R_AARCH64_TLSDESC_ADR_PAGE21
:
2242 case R_AARCH64_TLSGD_ADR_PAGE21
:
2243 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
2244 value
= PG (value
+ addend
) - PG (place
);
2247 case R_AARCH64_ADD_ABS_LO12_NC
:
2248 case R_AARCH64_LD64_GOT_LO12_NC
:
2249 case R_AARCH64_LDST8_ABS_LO12_NC
:
2250 case R_AARCH64_LDST16_ABS_LO12_NC
:
2251 case R_AARCH64_LDST32_ABS_LO12_NC
:
2252 case R_AARCH64_LDST64_ABS_LO12_NC
:
2253 case R_AARCH64_LDST128_ABS_LO12_NC
:
2254 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
2255 case R_AARCH64_TLSDESC_ADD
:
2256 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
2257 case R_AARCH64_TLSDESC_LDR
:
2258 case R_AARCH64_TLSGD_ADD_LO12_NC
:
2259 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
2260 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
2261 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
2262 value
= PG_OFFSET (value
+ addend
);
2265 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
2266 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
2267 value
= (value
+ addend
) & (bfd_vma
) 0xffff0000;
2269 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
2270 value
= (value
+ addend
) & (bfd_vma
) 0xfff000;
2273 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
2274 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
2275 value
= (value
+ addend
) & (bfd_vma
) 0xffff;
2278 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
2279 value
= (value
+ addend
) & ~(bfd_vma
) 0xffffffff;
2280 value
-= place
& ~(bfd_vma
) 0xffffffff;
2287 aarch64_relocate (unsigned int r_type
, bfd
*input_bfd
, asection
*input_section
,
2288 bfd_vma offset
, bfd_vma value
)
2290 reloc_howto_type
*howto
;
2293 howto
= elf64_aarch64_howto_from_type (r_type
);
2294 place
= (input_section
->output_section
->vma
+ input_section
->output_offset
2296 value
= aarch64_resolve_relocation (r_type
, place
, value
, 0, FALSE
);
2297 return bfd_elf_aarch64_put_addend (input_bfd
,
2298 input_section
->contents
+ offset
,
2302 static enum elf64_aarch64_stub_type
2303 aarch64_select_branch_stub (bfd_vma value
, bfd_vma place
)
2305 if (aarch64_valid_for_adrp_p (value
, place
))
2306 return aarch64_stub_adrp_branch
;
2307 return aarch64_stub_long_branch
;
2310 /* Determine the type of stub needed, if any, for a call. */
2312 static enum elf64_aarch64_stub_type
2313 aarch64_type_of_stub (struct bfd_link_info
*info
,
2314 asection
*input_sec
,
2315 const Elf_Internal_Rela
*rel
,
2316 unsigned char st_type
,
2317 struct elf64_aarch64_link_hash_entry
*hash
,
2318 bfd_vma destination
)
2321 bfd_signed_vma branch_offset
;
2322 unsigned int r_type
;
2323 struct elf64_aarch64_link_hash_table
*globals
;
2324 enum elf64_aarch64_stub_type stub_type
= aarch64_stub_none
;
2325 bfd_boolean via_plt_p
;
2327 if (st_type
!= STT_FUNC
)
2330 globals
= elf64_aarch64_hash_table (info
);
2331 via_plt_p
= (globals
->root
.splt
!= NULL
&& hash
!= NULL
2332 && hash
->root
.plt
.offset
!= (bfd_vma
) - 1);
2337 /* Determine where the call point is. */
2338 location
= (input_sec
->output_offset
2339 + input_sec
->output_section
->vma
+ rel
->r_offset
);
2341 branch_offset
= (bfd_signed_vma
) (destination
- location
);
2343 r_type
= ELF64_R_TYPE (rel
->r_info
);
2345 /* We don't want to redirect any old unconditional jump in this way,
2346 only one which is being used for a sibcall, where it is
2347 acceptable for the IP0 and IP1 registers to be clobbered. */
2348 if ((r_type
== R_AARCH64_CALL26
|| r_type
== R_AARCH64_JUMP26
)
2349 && (branch_offset
> AARCH64_MAX_FWD_BRANCH_OFFSET
2350 || branch_offset
< AARCH64_MAX_BWD_BRANCH_OFFSET
))
2352 stub_type
= aarch64_stub_long_branch
;
2358 /* Build a name for an entry in the stub hash table. */
2361 elf64_aarch64_stub_name (const asection
*input_section
,
2362 const asection
*sym_sec
,
2363 const struct elf64_aarch64_link_hash_entry
*hash
,
2364 const Elf_Internal_Rela
*rel
)
2371 len
= 8 + 1 + strlen (hash
->root
.root
.root
.string
) + 1 + 16 + 1;
2372 stub_name
= bfd_malloc (len
);
2373 if (stub_name
!= NULL
)
2374 snprintf (stub_name
, len
, "%08x_%s+%" BFD_VMA_FMT
"x",
2375 (unsigned int) input_section
->id
,
2376 hash
->root
.root
.root
.string
,
2381 len
= 8 + 1 + 8 + 1 + 8 + 1 + 16 + 1;
2382 stub_name
= bfd_malloc (len
);
2383 if (stub_name
!= NULL
)
2384 snprintf (stub_name
, len
, "%08x_%x:%x+%" BFD_VMA_FMT
"x",
2385 (unsigned int) input_section
->id
,
2386 (unsigned int) sym_sec
->id
,
2387 (unsigned int) ELF64_R_SYM (rel
->r_info
),
2394 /* Look up an entry in the stub hash. Stub entries are cached because
2395 creating the stub name takes a bit of time. */
2397 static struct elf64_aarch64_stub_hash_entry
*
2398 elf64_aarch64_get_stub_entry (const asection
*input_section
,
2399 const asection
*sym_sec
,
2400 struct elf_link_hash_entry
*hash
,
2401 const Elf_Internal_Rela
*rel
,
2402 struct elf64_aarch64_link_hash_table
*htab
)
2404 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
2405 struct elf64_aarch64_link_hash_entry
*h
=
2406 (struct elf64_aarch64_link_hash_entry
*) hash
;
2407 const asection
*id_sec
;
2409 if ((input_section
->flags
& SEC_CODE
) == 0)
2412 /* If this input section is part of a group of sections sharing one
2413 stub section, then use the id of the first section in the group.
2414 Stub names need to include a section id, as there may well be
2415 more than one stub used to reach say, printf, and we need to
2416 distinguish between them. */
2417 id_sec
= htab
->stub_group
[input_section
->id
].link_sec
;
2419 if (h
!= NULL
&& h
->stub_cache
!= NULL
2420 && h
->stub_cache
->h
== h
&& h
->stub_cache
->id_sec
== id_sec
)
2422 stub_entry
= h
->stub_cache
;
2428 stub_name
= elf64_aarch64_stub_name (id_sec
, sym_sec
, h
, rel
);
2429 if (stub_name
== NULL
)
2432 stub_entry
= aarch64_stub_hash_lookup (&htab
->stub_hash_table
,
2433 stub_name
, FALSE
, FALSE
);
2435 h
->stub_cache
= stub_entry
;
2443 /* Add a new stub entry to the stub hash. Not all fields of the new
2444 stub entry are initialised. */
2446 static struct elf64_aarch64_stub_hash_entry
*
2447 elf64_aarch64_add_stub (const char *stub_name
,
2449 struct elf64_aarch64_link_hash_table
*htab
)
2453 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
2455 link_sec
= htab
->stub_group
[section
->id
].link_sec
;
2456 stub_sec
= htab
->stub_group
[section
->id
].stub_sec
;
2457 if (stub_sec
== NULL
)
2459 stub_sec
= htab
->stub_group
[link_sec
->id
].stub_sec
;
2460 if (stub_sec
== NULL
)
2466 namelen
= strlen (link_sec
->name
);
2467 len
= namelen
+ sizeof (STUB_SUFFIX
);
2468 s_name
= bfd_alloc (htab
->stub_bfd
, len
);
2472 memcpy (s_name
, link_sec
->name
, namelen
);
2473 memcpy (s_name
+ namelen
, STUB_SUFFIX
, sizeof (STUB_SUFFIX
));
2474 stub_sec
= (*htab
->add_stub_section
) (s_name
, link_sec
);
2475 if (stub_sec
== NULL
)
2477 htab
->stub_group
[link_sec
->id
].stub_sec
= stub_sec
;
2479 htab
->stub_group
[section
->id
].stub_sec
= stub_sec
;
2482 /* Enter this entry into the linker stub hash table. */
2483 stub_entry
= aarch64_stub_hash_lookup (&htab
->stub_hash_table
, stub_name
,
2485 if (stub_entry
== NULL
)
2487 (*_bfd_error_handler
) (_("%s: cannot create stub entry %s"),
2488 section
->owner
, stub_name
);
2492 stub_entry
->stub_sec
= stub_sec
;
2493 stub_entry
->stub_offset
= 0;
2494 stub_entry
->id_sec
= link_sec
;
2500 aarch64_build_one_stub (struct bfd_hash_entry
*gen_entry
,
2501 void *in_arg ATTRIBUTE_UNUSED
)
2503 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
2508 unsigned int template_size
;
2509 const uint32_t *template;
2512 /* Massage our args to the form they really have. */
2513 stub_entry
= (struct elf64_aarch64_stub_hash_entry
*) gen_entry
;
2515 stub_sec
= stub_entry
->stub_sec
;
2517 /* Make a note of the offset within the stubs for this entry. */
2518 stub_entry
->stub_offset
= stub_sec
->size
;
2519 loc
= stub_sec
->contents
+ stub_entry
->stub_offset
;
2521 stub_bfd
= stub_sec
->owner
;
2523 /* This is the address of the stub destination. */
2524 sym_value
= (stub_entry
->target_value
2525 + stub_entry
->target_section
->output_offset
2526 + stub_entry
->target_section
->output_section
->vma
);
2528 if (stub_entry
->stub_type
== aarch64_stub_long_branch
)
2530 bfd_vma place
= (stub_entry
->stub_offset
+ stub_sec
->output_section
->vma
2531 + stub_sec
->output_offset
);
2533 /* See if we can relax the stub. */
2534 if (aarch64_valid_for_adrp_p (sym_value
, place
))
2535 stub_entry
->stub_type
= aarch64_select_branch_stub (sym_value
, place
);
2538 switch (stub_entry
->stub_type
)
2540 case aarch64_stub_adrp_branch
:
2541 template = aarch64_adrp_branch_stub
;
2542 template_size
= sizeof (aarch64_adrp_branch_stub
);
2544 case aarch64_stub_long_branch
:
2545 template = aarch64_long_branch_stub
;
2546 template_size
= sizeof (aarch64_long_branch_stub
);
2553 for (i
= 0; i
< (template_size
/ sizeof template[0]); i
++)
2555 bfd_putl32 (template[i
], loc
);
2559 template_size
= (template_size
+ 7) & ~7;
2560 stub_sec
->size
+= template_size
;
2562 switch (stub_entry
->stub_type
)
2564 case aarch64_stub_adrp_branch
:
2565 if (aarch64_relocate (R_AARCH64_ADR_PREL_PG_HI21
, stub_bfd
, stub_sec
,
2566 stub_entry
->stub_offset
, sym_value
))
2567 /* The stub would not have been relaxed if the offset was out
2571 _bfd_final_link_relocate
2572 (elf64_aarch64_howto_from_type (R_AARCH64_ADD_ABS_LO12_NC
),
2576 stub_entry
->stub_offset
+ 4,
2581 case aarch64_stub_long_branch
:
2582 /* We want the value relative to the address 12 bytes back from the
2584 _bfd_final_link_relocate (elf64_aarch64_howto_from_type
2585 (R_AARCH64_PREL64
), stub_bfd
, stub_sec
,
2587 stub_entry
->stub_offset
+ 16,
2597 /* As above, but don't actually build the stub. Just bump offset so
2598 we know stub section sizes. */
2601 aarch64_size_one_stub (struct bfd_hash_entry
*gen_entry
,
2602 void *in_arg ATTRIBUTE_UNUSED
)
2604 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
2607 /* Massage our args to the form they really have. */
2608 stub_entry
= (struct elf64_aarch64_stub_hash_entry
*) gen_entry
;
2610 switch (stub_entry
->stub_type
)
2612 case aarch64_stub_adrp_branch
:
2613 size
= sizeof (aarch64_adrp_branch_stub
);
2615 case aarch64_stub_long_branch
:
2616 size
= sizeof (aarch64_long_branch_stub
);
2624 size
= (size
+ 7) & ~7;
2625 stub_entry
->stub_sec
->size
+= size
;
2629 /* External entry points for sizing and building linker stubs. */
2631 /* Set up various things so that we can make a list of input sections
2632 for each output section included in the link. Returns -1 on error,
2633 0 when no stubs will be needed, and 1 on success. */
2636 elf64_aarch64_setup_section_lists (bfd
*output_bfd
,
2637 struct bfd_link_info
*info
)
2640 unsigned int bfd_count
;
2641 int top_id
, top_index
;
2643 asection
**input_list
, **list
;
2645 struct elf64_aarch64_link_hash_table
*htab
=
2646 elf64_aarch64_hash_table (info
);
2648 if (!is_elf_hash_table (htab
))
2651 /* Count the number of input BFDs and find the top input section id. */
2652 for (input_bfd
= info
->input_bfds
, bfd_count
= 0, top_id
= 0;
2653 input_bfd
!= NULL
; input_bfd
= input_bfd
->link_next
)
2656 for (section
= input_bfd
->sections
;
2657 section
!= NULL
; section
= section
->next
)
2659 if (top_id
< section
->id
)
2660 top_id
= section
->id
;
2663 htab
->bfd_count
= bfd_count
;
2665 amt
= sizeof (struct map_stub
) * (top_id
+ 1);
2666 htab
->stub_group
= bfd_zmalloc (amt
);
2667 if (htab
->stub_group
== NULL
)
2670 /* We can't use output_bfd->section_count here to find the top output
2671 section index as some sections may have been removed, and
2672 _bfd_strip_section_from_output doesn't renumber the indices. */
2673 for (section
= output_bfd
->sections
, top_index
= 0;
2674 section
!= NULL
; section
= section
->next
)
2676 if (top_index
< section
->index
)
2677 top_index
= section
->index
;
2680 htab
->top_index
= top_index
;
2681 amt
= sizeof (asection
*) * (top_index
+ 1);
2682 input_list
= bfd_malloc (amt
);
2683 htab
->input_list
= input_list
;
2684 if (input_list
== NULL
)
2687 /* For sections we aren't interested in, mark their entries with a
2688 value we can check later. */
2689 list
= input_list
+ top_index
;
2691 *list
= bfd_abs_section_ptr
;
2692 while (list
-- != input_list
);
2694 for (section
= output_bfd
->sections
;
2695 section
!= NULL
; section
= section
->next
)
2697 if ((section
->flags
& SEC_CODE
) != 0)
2698 input_list
[section
->index
] = NULL
;
2704 /* Used by elf64_aarch64_next_input_section and group_sections. */
2705 #define PREV_SEC(sec) (htab->stub_group[(sec)->id].link_sec)
2707 /* The linker repeatedly calls this function for each input section,
2708 in the order that input sections are linked into output sections.
2709 Build lists of input sections to determine groupings between which
2710 we may insert linker stubs. */
2713 elf64_aarch64_next_input_section (struct bfd_link_info
*info
, asection
*isec
)
2715 struct elf64_aarch64_link_hash_table
*htab
=
2716 elf64_aarch64_hash_table (info
);
2718 if (isec
->output_section
->index
<= htab
->top_index
)
2720 asection
**list
= htab
->input_list
+ isec
->output_section
->index
;
2722 if (*list
!= bfd_abs_section_ptr
)
2724 /* Steal the link_sec pointer for our list. */
2725 /* This happens to make the list in reverse order,
2726 which is what we want. */
2727 PREV_SEC (isec
) = *list
;
2733 /* See whether we can group stub sections together. Grouping stub
2734 sections may result in fewer stubs. More importantly, we need to
2735 put all .init* and .fini* stubs at the beginning of the .init or
2736 .fini output sections respectively, because glibc splits the
2737 _init and _fini functions into multiple parts. Putting a stub in
2738 the middle of a function is not a good idea. */
2741 group_sections (struct elf64_aarch64_link_hash_table
*htab
,
2742 bfd_size_type stub_group_size
,
2743 bfd_boolean stubs_always_before_branch
)
2745 asection
**list
= htab
->input_list
+ htab
->top_index
;
2749 asection
*tail
= *list
;
2751 if (tail
== bfd_abs_section_ptr
)
2754 while (tail
!= NULL
)
2758 bfd_size_type total
;
2762 while ((prev
= PREV_SEC (curr
)) != NULL
2763 && ((total
+= curr
->output_offset
- prev
->output_offset
)
2767 /* OK, the size from the start of CURR to the end is less
2768 than stub_group_size and thus can be handled by one stub
2769 section. (Or the tail section is itself larger than
2770 stub_group_size, in which case we may be toast.)
2771 We should really be keeping track of the total size of
2772 stubs added here, as stubs contribute to the final output
2776 prev
= PREV_SEC (tail
);
2777 /* Set up this stub group. */
2778 htab
->stub_group
[tail
->id
].link_sec
= curr
;
2780 while (tail
!= curr
&& (tail
= prev
) != NULL
);
2782 /* But wait, there's more! Input sections up to stub_group_size
2783 bytes before the stub section can be handled by it too. */
2784 if (!stubs_always_before_branch
)
2788 && ((total
+= tail
->output_offset
- prev
->output_offset
)
2792 prev
= PREV_SEC (tail
);
2793 htab
->stub_group
[tail
->id
].link_sec
= curr
;
2799 while (list
-- != htab
->input_list
);
2801 free (htab
->input_list
);
2806 /* Determine and set the size of the stub section for a final link.
2808 The basic idea here is to examine all the relocations looking for
2809 PC-relative calls to a target that is unreachable with a "bl"
2813 elf64_aarch64_size_stubs (bfd
*output_bfd
,
2815 struct bfd_link_info
*info
,
2816 bfd_signed_vma group_size
,
2817 asection
* (*add_stub_section
) (const char *,
2819 void (*layout_sections_again
) (void))
2821 bfd_size_type stub_group_size
;
2822 bfd_boolean stubs_always_before_branch
;
2823 bfd_boolean stub_changed
= 0;
2824 struct elf64_aarch64_link_hash_table
*htab
= elf64_aarch64_hash_table (info
);
2826 /* Propagate mach to stub bfd, because it may not have been
2827 finalized when we created stub_bfd. */
2828 bfd_set_arch_mach (stub_bfd
, bfd_get_arch (output_bfd
),
2829 bfd_get_mach (output_bfd
));
2831 /* Stash our params away. */
2832 htab
->stub_bfd
= stub_bfd
;
2833 htab
->add_stub_section
= add_stub_section
;
2834 htab
->layout_sections_again
= layout_sections_again
;
2835 stubs_always_before_branch
= group_size
< 0;
2837 stub_group_size
= -group_size
;
2839 stub_group_size
= group_size
;
2841 if (stub_group_size
== 1)
2843 /* Default values. */
2844 /* Aarch64 branch range is +-128MB. The value used is 1MB less. */
2845 stub_group_size
= 127 * 1024 * 1024;
2848 group_sections (htab
, stub_group_size
, stubs_always_before_branch
);
2853 unsigned int bfd_indx
;
2856 for (input_bfd
= info
->input_bfds
, bfd_indx
= 0;
2857 input_bfd
!= NULL
; input_bfd
= input_bfd
->link_next
, bfd_indx
++)
2859 Elf_Internal_Shdr
*symtab_hdr
;
2861 Elf_Internal_Sym
*local_syms
= NULL
;
2863 /* We'll need the symbol table in a second. */
2864 symtab_hdr
= &elf_tdata (input_bfd
)->symtab_hdr
;
2865 if (symtab_hdr
->sh_info
== 0)
2868 /* Walk over each section attached to the input bfd. */
2869 for (section
= input_bfd
->sections
;
2870 section
!= NULL
; section
= section
->next
)
2872 Elf_Internal_Rela
*internal_relocs
, *irelaend
, *irela
;
2874 /* If there aren't any relocs, then there's nothing more
2876 if ((section
->flags
& SEC_RELOC
) == 0
2877 || section
->reloc_count
== 0
2878 || (section
->flags
& SEC_CODE
) == 0)
2881 /* If this section is a link-once section that will be
2882 discarded, then don't create any stubs. */
2883 if (section
->output_section
== NULL
2884 || section
->output_section
->owner
!= output_bfd
)
2887 /* Get the relocs. */
2889 = _bfd_elf_link_read_relocs (input_bfd
, section
, NULL
,
2890 NULL
, info
->keep_memory
);
2891 if (internal_relocs
== NULL
)
2892 goto error_ret_free_local
;
2894 /* Now examine each relocation. */
2895 irela
= internal_relocs
;
2896 irelaend
= irela
+ section
->reloc_count
;
2897 for (; irela
< irelaend
; irela
++)
2899 unsigned int r_type
, r_indx
;
2900 enum elf64_aarch64_stub_type stub_type
;
2901 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
2904 bfd_vma destination
;
2905 struct elf64_aarch64_link_hash_entry
*hash
;
2906 const char *sym_name
;
2908 const asection
*id_sec
;
2909 unsigned char st_type
;
2912 r_type
= ELF64_R_TYPE (irela
->r_info
);
2913 r_indx
= ELF64_R_SYM (irela
->r_info
);
2915 if (r_type
>= (unsigned int) R_AARCH64_end
)
2917 bfd_set_error (bfd_error_bad_value
);
2918 error_ret_free_internal
:
2919 if (elf_section_data (section
)->relocs
== NULL
)
2920 free (internal_relocs
);
2921 goto error_ret_free_local
;
2924 /* Only look for stubs on unconditional branch and
2925 branch and link instructions. */
2926 if (r_type
!= (unsigned int) R_AARCH64_CALL26
2927 && r_type
!= (unsigned int) R_AARCH64_JUMP26
)
2930 /* Now determine the call target, its name, value,
2937 if (r_indx
< symtab_hdr
->sh_info
)
2939 /* It's a local symbol. */
2940 Elf_Internal_Sym
*sym
;
2941 Elf_Internal_Shdr
*hdr
;
2943 if (local_syms
== NULL
)
2946 = (Elf_Internal_Sym
*) symtab_hdr
->contents
;
2947 if (local_syms
== NULL
)
2949 = bfd_elf_get_elf_syms (input_bfd
, symtab_hdr
,
2950 symtab_hdr
->sh_info
, 0,
2952 if (local_syms
== NULL
)
2953 goto error_ret_free_internal
;
2956 sym
= local_syms
+ r_indx
;
2957 hdr
= elf_elfsections (input_bfd
)[sym
->st_shndx
];
2958 sym_sec
= hdr
->bfd_section
;
2960 /* This is an undefined symbol. It can never
2964 if (ELF_ST_TYPE (sym
->st_info
) != STT_SECTION
)
2965 sym_value
= sym
->st_value
;
2966 destination
= (sym_value
+ irela
->r_addend
2967 + sym_sec
->output_offset
2968 + sym_sec
->output_section
->vma
);
2969 st_type
= ELF_ST_TYPE (sym
->st_info
);
2971 = bfd_elf_string_from_elf_section (input_bfd
,
2972 symtab_hdr
->sh_link
,
2979 e_indx
= r_indx
- symtab_hdr
->sh_info
;
2980 hash
= ((struct elf64_aarch64_link_hash_entry
*)
2981 elf_sym_hashes (input_bfd
)[e_indx
]);
2983 while (hash
->root
.root
.type
== bfd_link_hash_indirect
2984 || hash
->root
.root
.type
== bfd_link_hash_warning
)
2985 hash
= ((struct elf64_aarch64_link_hash_entry
*)
2986 hash
->root
.root
.u
.i
.link
);
2988 if (hash
->root
.root
.type
== bfd_link_hash_defined
2989 || hash
->root
.root
.type
== bfd_link_hash_defweak
)
2991 struct elf64_aarch64_link_hash_table
*globals
=
2992 elf64_aarch64_hash_table (info
);
2993 sym_sec
= hash
->root
.root
.u
.def
.section
;
2994 sym_value
= hash
->root
.root
.u
.def
.value
;
2995 /* For a destination in a shared library,
2996 use the PLT stub as target address to
2997 decide whether a branch stub is
2999 if (globals
->root
.splt
!= NULL
&& hash
!= NULL
3000 && hash
->root
.plt
.offset
!= (bfd_vma
) - 1)
3002 sym_sec
= globals
->root
.splt
;
3003 sym_value
= hash
->root
.plt
.offset
;
3004 if (sym_sec
->output_section
!= NULL
)
3005 destination
= (sym_value
3006 + sym_sec
->output_offset
3008 sym_sec
->output_section
->vma
);
3010 else if (sym_sec
->output_section
!= NULL
)
3011 destination
= (sym_value
+ irela
->r_addend
3012 + sym_sec
->output_offset
3013 + sym_sec
->output_section
->vma
);
3015 else if (hash
->root
.root
.type
== bfd_link_hash_undefined
3016 || (hash
->root
.root
.type
3017 == bfd_link_hash_undefweak
))
3019 /* For a shared library, use the PLT stub as
3020 target address to decide whether a long
3021 branch stub is needed.
3022 For absolute code, they cannot be handled. */
3023 struct elf64_aarch64_link_hash_table
*globals
=
3024 elf64_aarch64_hash_table (info
);
3026 if (globals
->root
.splt
!= NULL
&& hash
!= NULL
3027 && hash
->root
.plt
.offset
!= (bfd_vma
) - 1)
3029 sym_sec
= globals
->root
.splt
;
3030 sym_value
= hash
->root
.plt
.offset
;
3031 if (sym_sec
->output_section
!= NULL
)
3032 destination
= (sym_value
3033 + sym_sec
->output_offset
3035 sym_sec
->output_section
->vma
);
3042 bfd_set_error (bfd_error_bad_value
);
3043 goto error_ret_free_internal
;
3045 st_type
= ELF_ST_TYPE (hash
->root
.type
);
3046 sym_name
= hash
->root
.root
.root
.string
;
3049 /* Determine what (if any) linker stub is needed. */
3050 stub_type
= aarch64_type_of_stub
3051 (info
, section
, irela
, st_type
, hash
, destination
);
3052 if (stub_type
== aarch64_stub_none
)
3055 /* Support for grouping stub sections. */
3056 id_sec
= htab
->stub_group
[section
->id
].link_sec
;
3058 /* Get the name of this stub. */
3059 stub_name
= elf64_aarch64_stub_name (id_sec
, sym_sec
, hash
,
3062 goto error_ret_free_internal
;
3065 aarch64_stub_hash_lookup (&htab
->stub_hash_table
,
3066 stub_name
, FALSE
, FALSE
);
3067 if (stub_entry
!= NULL
)
3069 /* The proper stub has already been created. */
3074 stub_entry
= elf64_aarch64_add_stub (stub_name
, section
,
3076 if (stub_entry
== NULL
)
3079 goto error_ret_free_internal
;
3082 stub_entry
->target_value
= sym_value
;
3083 stub_entry
->target_section
= sym_sec
;
3084 stub_entry
->stub_type
= stub_type
;
3085 stub_entry
->h
= hash
;
3086 stub_entry
->st_type
= st_type
;
3088 if (sym_name
== NULL
)
3089 sym_name
= "unnamed";
3090 len
= sizeof (STUB_ENTRY_NAME
) + strlen (sym_name
);
3091 stub_entry
->output_name
= bfd_alloc (htab
->stub_bfd
, len
);
3092 if (stub_entry
->output_name
== NULL
)
3095 goto error_ret_free_internal
;
3098 snprintf (stub_entry
->output_name
, len
, STUB_ENTRY_NAME
,
3101 stub_changed
= TRUE
;
3104 /* We're done with the internal relocs, free them. */
3105 if (elf_section_data (section
)->relocs
== NULL
)
3106 free (internal_relocs
);
3113 /* OK, we've added some stubs. Find out the new size of the
3115 for (stub_sec
= htab
->stub_bfd
->sections
;
3116 stub_sec
!= NULL
; stub_sec
= stub_sec
->next
)
3119 bfd_hash_traverse (&htab
->stub_hash_table
, aarch64_size_one_stub
, htab
);
3121 /* Ask the linker to do its stuff. */
3122 (*htab
->layout_sections_again
) ();
3123 stub_changed
= FALSE
;
3128 error_ret_free_local
:
3132 /* Build all the stubs associated with the current output file. The
3133 stubs are kept in a hash table attached to the main linker hash
3134 table. We also set up the .plt entries for statically linked PIC
3135 functions here. This function is called via aarch64_elf_finish in the
3139 elf64_aarch64_build_stubs (struct bfd_link_info
*info
)
3142 struct bfd_hash_table
*table
;
3143 struct elf64_aarch64_link_hash_table
*htab
;
3145 htab
= elf64_aarch64_hash_table (info
);
3147 for (stub_sec
= htab
->stub_bfd
->sections
;
3148 stub_sec
!= NULL
; stub_sec
= stub_sec
->next
)
3152 /* Ignore non-stub sections. */
3153 if (!strstr (stub_sec
->name
, STUB_SUFFIX
))
3156 /* Allocate memory to hold the linker stubs. */
3157 size
= stub_sec
->size
;
3158 stub_sec
->contents
= bfd_zalloc (htab
->stub_bfd
, size
);
3159 if (stub_sec
->contents
== NULL
&& size
!= 0)
3164 /* Build the stubs as directed by the stub hash table. */
3165 table
= &htab
->stub_hash_table
;
3166 bfd_hash_traverse (table
, aarch64_build_one_stub
, info
);
3172 /* Add an entry to the code/data map for section SEC. */
3175 elf64_aarch64_section_map_add (asection
*sec
, char type
, bfd_vma vma
)
3177 struct _aarch64_elf_section_data
*sec_data
=
3178 elf64_aarch64_section_data (sec
);
3179 unsigned int newidx
;
3181 if (sec_data
->map
== NULL
)
3183 sec_data
->map
= bfd_malloc (sizeof (elf64_aarch64_section_map
));
3184 sec_data
->mapcount
= 0;
3185 sec_data
->mapsize
= 1;
3188 newidx
= sec_data
->mapcount
++;
3190 if (sec_data
->mapcount
> sec_data
->mapsize
)
3192 sec_data
->mapsize
*= 2;
3193 sec_data
->map
= bfd_realloc_or_free
3194 (sec_data
->map
, sec_data
->mapsize
* sizeof (elf64_aarch64_section_map
));
3199 sec_data
->map
[newidx
].vma
= vma
;
3200 sec_data
->map
[newidx
].type
= type
;
3205 /* Initialise maps of insn/data for input BFDs. */
3207 bfd_elf64_aarch64_init_maps (bfd
*abfd
)
3209 Elf_Internal_Sym
*isymbuf
;
3210 Elf_Internal_Shdr
*hdr
;
3211 unsigned int i
, localsyms
;
3213 /* Make sure that we are dealing with an AArch64 elf binary. */
3214 if (!is_aarch64_elf (abfd
))
3217 if ((abfd
->flags
& DYNAMIC
) != 0)
3220 hdr
= &elf_symtab_hdr (abfd
);
3221 localsyms
= hdr
->sh_info
;
3223 /* Obtain a buffer full of symbols for this BFD. The hdr->sh_info field
3224 should contain the number of local symbols, which should come before any
3225 global symbols. Mapping symbols are always local. */
3226 isymbuf
= bfd_elf_get_elf_syms (abfd
, hdr
, localsyms
, 0, NULL
, NULL
, NULL
);
3228 /* No internal symbols read? Skip this BFD. */
3229 if (isymbuf
== NULL
)
3232 for (i
= 0; i
< localsyms
; i
++)
3234 Elf_Internal_Sym
*isym
= &isymbuf
[i
];
3235 asection
*sec
= bfd_section_from_elf_index (abfd
, isym
->st_shndx
);
3238 if (sec
!= NULL
&& ELF_ST_BIND (isym
->st_info
) == STB_LOCAL
)
3240 name
= bfd_elf_string_from_elf_section (abfd
,
3244 if (bfd_is_aarch64_special_symbol_name
3245 (name
, BFD_AARCH64_SPECIAL_SYM_TYPE_MAP
))
3246 elf64_aarch64_section_map_add (sec
, name
[1], isym
->st_value
);
3251 /* Set option values needed during linking. */
3253 bfd_elf64_aarch64_set_options (struct bfd
*output_bfd
,
3254 struct bfd_link_info
*link_info
,
3256 int no_wchar_warn
, int pic_veneer
)
3258 struct elf64_aarch64_link_hash_table
*globals
;
3260 globals
= elf64_aarch64_hash_table (link_info
);
3261 globals
->pic_veneer
= pic_veneer
;
3263 BFD_ASSERT (is_aarch64_elf (output_bfd
));
3264 elf_aarch64_tdata (output_bfd
)->no_enum_size_warning
= no_enum_warn
;
3265 elf_aarch64_tdata (output_bfd
)->no_wchar_size_warning
= no_wchar_warn
;
3268 #define MASK(n) ((1u << (n)) - 1)
3270 /* Decode the 26-bit offset of unconditional branch. */
3271 static inline uint32_t
3272 decode_branch_ofs_26 (uint32_t insn
)
3274 return insn
& MASK (26);
3277 /* Decode the 19-bit offset of conditional branch and compare & branch. */
3278 static inline uint32_t
3279 decode_cond_branch_ofs_19 (uint32_t insn
)
3281 return (insn
>> 5) & MASK (19);
3284 /* Decode the 19-bit offset of load literal. */
3285 static inline uint32_t
3286 decode_ld_lit_ofs_19 (uint32_t insn
)
3288 return (insn
>> 5) & MASK (19);
3291 /* Decode the 14-bit offset of test & branch. */
3292 static inline uint32_t
3293 decode_tst_branch_ofs_14 (uint32_t insn
)
3295 return (insn
>> 5) & MASK (14);
3298 /* Decode the 16-bit imm of move wide. */
3299 static inline uint32_t
3300 decode_movw_imm (uint32_t insn
)
3302 return (insn
>> 5) & MASK (16);
3305 /* Decode the 21-bit imm of adr. */
3306 static inline uint32_t
3307 decode_adr_imm (uint32_t insn
)
3309 return ((insn
>> 29) & MASK (2)) | ((insn
>> 3) & (MASK (19) << 2));
3312 /* Decode the 12-bit imm of add immediate. */
3313 static inline uint32_t
3314 decode_add_imm (uint32_t insn
)
3316 return (insn
>> 10) & MASK (12);
3320 /* Encode the 26-bit offset of unconditional branch. */
3321 static inline uint32_t
3322 reencode_branch_ofs_26 (uint32_t insn
, uint32_t ofs
)
3324 return (insn
& ~MASK (26)) | (ofs
& MASK (26));
3327 /* Encode the 19-bit offset of conditional branch and compare & branch. */
3328 static inline uint32_t
3329 reencode_cond_branch_ofs_19 (uint32_t insn
, uint32_t ofs
)
3331 return (insn
& ~(MASK (19) << 5)) | ((ofs
& MASK (19)) << 5);
3334 /* Decode the 19-bit offset of load literal. */
3335 static inline uint32_t
3336 reencode_ld_lit_ofs_19 (uint32_t insn
, uint32_t ofs
)
3338 return (insn
& ~(MASK (19) << 5)) | ((ofs
& MASK (19)) << 5);
3341 /* Encode the 14-bit offset of test & branch. */
3342 static inline uint32_t
3343 reencode_tst_branch_ofs_14 (uint32_t insn
, uint32_t ofs
)
3345 return (insn
& ~(MASK (14) << 5)) | ((ofs
& MASK (14)) << 5);
3348 /* Reencode the imm field of move wide. */
3349 static inline uint32_t
3350 reencode_movw_imm (uint32_t insn
, uint32_t imm
)
3352 return (insn
& ~(MASK (16) << 5)) | ((imm
& MASK (16)) << 5);
3355 /* Reencode the imm field of adr. */
3356 static inline uint32_t
3357 reencode_adr_imm (uint32_t insn
, uint32_t imm
)
3359 return (insn
& ~((MASK (2) << 29) | (MASK (19) << 5)))
3360 | ((imm
& MASK (2)) << 29) | ((imm
& (MASK (19) << 2)) << 3);
3363 /* Reencode the imm field of ld/st pos immediate. */
3364 static inline uint32_t
3365 reencode_ldst_pos_imm (uint32_t insn
, uint32_t imm
)
3367 return (insn
& ~(MASK (12) << 10)) | ((imm
& MASK (12)) << 10);
3370 /* Reencode the imm field of add immediate. */
3371 static inline uint32_t
3372 reencode_add_imm (uint32_t insn
, uint32_t imm
)
3374 return (insn
& ~(MASK (12) << 10)) | ((imm
& MASK (12)) << 10);
3377 /* Reencode mov[zn] to movz. */
3378 static inline uint32_t
3379 reencode_movzn_to_movz (uint32_t opcode
)
3381 return opcode
| (1 << 30);
3384 /* Reencode mov[zn] to movn. */
3385 static inline uint32_t
3386 reencode_movzn_to_movn (uint32_t opcode
)
3388 return opcode
& ~(1 << 30);
3391 /* Insert the addend/value into the instruction or data object being
3393 static bfd_reloc_status_type
3394 bfd_elf_aarch64_put_addend (bfd
*abfd
,
3396 reloc_howto_type
*howto
, bfd_signed_vma addend
)
3398 bfd_reloc_status_type status
= bfd_reloc_ok
;
3399 bfd_signed_vma old_addend
= addend
;
3403 size
= bfd_get_reloc_size (howto
);
3407 contents
= bfd_get_16 (abfd
, address
);
3410 if (howto
->src_mask
!= 0xffffffff)
3411 /* Must be 32-bit instruction, always little-endian. */
3412 contents
= bfd_getl32 (address
);
3414 /* Must be 32-bit data (endianness dependent). */
3415 contents
= bfd_get_32 (abfd
, address
);
3418 contents
= bfd_get_64 (abfd
, address
);
3424 switch (howto
->complain_on_overflow
)
3426 case complain_overflow_dont
:
3428 case complain_overflow_signed
:
3429 status
= aarch64_signed_overflow (addend
,
3430 howto
->bitsize
+ howto
->rightshift
);
3432 case complain_overflow_unsigned
:
3433 status
= aarch64_unsigned_overflow (addend
,
3434 howto
->bitsize
+ howto
->rightshift
);
3436 case complain_overflow_bitfield
:
3441 addend
>>= howto
->rightshift
;
3443 switch (howto
->type
)
3445 case R_AARCH64_JUMP26
:
3446 case R_AARCH64_CALL26
:
3447 contents
= reencode_branch_ofs_26 (contents
, addend
);
3450 case R_AARCH64_CONDBR19
:
3451 contents
= reencode_cond_branch_ofs_19 (contents
, addend
);
3454 case R_AARCH64_TSTBR14
:
3455 contents
= reencode_tst_branch_ofs_14 (contents
, addend
);
3458 case R_AARCH64_LD_PREL_LO19
:
3459 case R_AARCH64_GOT_LD_PREL19
:
3460 if (old_addend
& ((1 << howto
->rightshift
) - 1))
3461 return bfd_reloc_overflow
;
3462 contents
= reencode_ld_lit_ofs_19 (contents
, addend
);
3465 case R_AARCH64_TLSDESC_CALL
:
3468 case R_AARCH64_TLSGD_ADR_PAGE21
:
3469 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
3470 case R_AARCH64_TLSDESC_ADR_PAGE21
:
3471 case R_AARCH64_ADR_GOT_PAGE
:
3472 case R_AARCH64_ADR_PREL_LO21
:
3473 case R_AARCH64_ADR_PREL_PG_HI21
:
3474 case R_AARCH64_ADR_PREL_PG_HI21_NC
:
3475 contents
= reencode_adr_imm (contents
, addend
);
3478 case R_AARCH64_TLSGD_ADD_LO12_NC
:
3479 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
3480 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
3481 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
3482 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
3483 case R_AARCH64_ADD_ABS_LO12_NC
:
3484 /* Corresponds to: add rd, rn, #uimm12 to provide the low order
3485 12 bits of the page offset following
3486 R_AARCH64_ADR_PREL_PG_HI21 which computes the
3487 (pc-relative) page base. */
3488 contents
= reencode_add_imm (contents
, addend
);
3491 case R_AARCH64_LDST8_ABS_LO12_NC
:
3492 case R_AARCH64_LDST16_ABS_LO12_NC
:
3493 case R_AARCH64_LDST32_ABS_LO12_NC
:
3494 case R_AARCH64_LDST64_ABS_LO12_NC
:
3495 case R_AARCH64_LDST128_ABS_LO12_NC
:
3496 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
3497 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
3498 case R_AARCH64_LD64_GOT_LO12_NC
:
3499 if (old_addend
& ((1 << howto
->rightshift
) - 1))
3500 return bfd_reloc_overflow
;
3501 /* Used for ldr*|str* rt, [rn, #uimm12] to provide the low order
3502 12 bits of the page offset following R_AARCH64_ADR_PREL_PG_HI21
3503 which computes the (pc-relative) page base. */
3504 contents
= reencode_ldst_pos_imm (contents
, addend
);
3507 /* Group relocations to create high bits of a 16, 32, 48 or 64
3508 bit signed data or abs address inline. Will change
3509 instruction to MOVN or MOVZ depending on sign of calculated
3512 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
3513 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
3514 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
3515 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
3516 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
3517 case R_AARCH64_MOVW_SABS_G0
:
3518 case R_AARCH64_MOVW_SABS_G1
:
3519 case R_AARCH64_MOVW_SABS_G2
:
3520 /* NOTE: We can only come here with movz or movn. */
3523 /* Force use of MOVN. */
3525 contents
= reencode_movzn_to_movn (contents
);
3529 /* Force use of MOVZ. */
3530 contents
= reencode_movzn_to_movz (contents
);
3534 /* Group relocations to create a 16, 32, 48 or 64 bit unsigned
3535 data or abs address inline. */
3537 case R_AARCH64_MOVW_UABS_G0
:
3538 case R_AARCH64_MOVW_UABS_G0_NC
:
3539 case R_AARCH64_MOVW_UABS_G1
:
3540 case R_AARCH64_MOVW_UABS_G1_NC
:
3541 case R_AARCH64_MOVW_UABS_G2
:
3542 case R_AARCH64_MOVW_UABS_G2_NC
:
3543 case R_AARCH64_MOVW_UABS_G3
:
3544 contents
= reencode_movw_imm (contents
, addend
);
3548 /* Repack simple data */
3549 if (howto
->dst_mask
& (howto
->dst_mask
+ 1))
3550 return bfd_reloc_notsupported
;
3552 contents
= ((contents
& ~howto
->dst_mask
) | (addend
& howto
->dst_mask
));
3559 bfd_put_16 (abfd
, contents
, address
);
3562 if (howto
->dst_mask
!= 0xffffffff)
3563 /* must be 32-bit instruction, always little-endian */
3564 bfd_putl32 (contents
, address
);
3566 /* must be 32-bit data (endianness dependent) */
3567 bfd_put_32 (abfd
, contents
, address
);
3570 bfd_put_64 (abfd
, contents
, address
);
3580 aarch64_calculate_got_entry_vma (struct elf_link_hash_entry
*h
,
3581 struct elf64_aarch64_link_hash_table
3582 *globals
, struct bfd_link_info
*info
,
3583 bfd_vma value
, bfd
*output_bfd
,
3584 bfd_boolean
*unresolved_reloc_p
)
3586 bfd_vma off
= (bfd_vma
) - 1;
3587 asection
*basegot
= globals
->root
.sgot
;
3588 bfd_boolean dyn
= globals
->root
.dynamic_sections_created
;
3592 off
= h
->got
.offset
;
3593 BFD_ASSERT (off
!= (bfd_vma
) - 1);
3594 if (!WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn
, info
->shared
, h
)
3596 && SYMBOL_REFERENCES_LOCAL (info
, h
))
3597 || (ELF_ST_VISIBILITY (h
->other
)
3598 && h
->root
.type
== bfd_link_hash_undefweak
))
3600 /* This is actually a static link, or it is a -Bsymbolic link
3601 and the symbol is defined locally. We must initialize this
3602 entry in the global offset table. Since the offset must
3603 always be a multiple of 8, we use the least significant bit
3604 to record whether we have initialized it already.
3605 When doing a dynamic link, we create a .rel(a).got relocation
3606 entry to initialize the value. This is done in the
3607 finish_dynamic_symbol routine. */
3612 bfd_put_64 (output_bfd
, value
, basegot
->contents
+ off
);
3617 *unresolved_reloc_p
= FALSE
;
3619 off
= off
+ basegot
->output_section
->vma
+ basegot
->output_offset
;
3625 /* Change R_TYPE to a more efficient access model where possible,
3626 return the new reloc type. */
3629 aarch64_tls_transition_without_check (unsigned int r_type
,
3630 struct elf_link_hash_entry
*h
)
3632 bfd_boolean is_local
= h
== NULL
;
3635 case R_AARCH64_TLSGD_ADR_PAGE21
:
3636 case R_AARCH64_TLSDESC_ADR_PAGE21
:
3638 ? R_AARCH64_TLSLE_MOVW_TPREL_G1
: R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
;
3640 case R_AARCH64_TLSGD_ADD_LO12_NC
:
3641 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
3643 ? R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
3644 : R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
;
3646 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
3647 return is_local
? R_AARCH64_TLSLE_MOVW_TPREL_G1
: r_type
;
3649 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
3650 return is_local
? R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
: r_type
;
3652 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
3653 case R_AARCH64_TLSDESC_CALL
:
3654 /* Instructions with these relocations will become NOPs. */
3655 return R_AARCH64_NONE
;
3662 aarch64_reloc_got_type (unsigned int r_type
)
3666 case R_AARCH64_LD64_GOT_LO12_NC
:
3667 case R_AARCH64_ADR_GOT_PAGE
:
3668 case R_AARCH64_GOT_LD_PREL19
:
3671 case R_AARCH64_TLSGD_ADR_PAGE21
:
3672 case R_AARCH64_TLSGD_ADD_LO12_NC
:
3675 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
3676 case R_AARCH64_TLSDESC_ADR_PAGE21
:
3677 case R_AARCH64_TLSDESC_CALL
:
3678 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
3679 return GOT_TLSDESC_GD
;
3681 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
3682 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
3685 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
3686 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
3687 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
3688 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
3689 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
3690 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
3691 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
3692 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
3699 aarch64_can_relax_tls (bfd
*input_bfd
,
3700 struct bfd_link_info
*info
,
3701 unsigned int r_type
,
3702 struct elf_link_hash_entry
*h
,
3703 unsigned long r_symndx
)
3705 unsigned int symbol_got_type
;
3706 unsigned int reloc_got_type
;
3708 if (! IS_AARCH64_TLS_RELOC (r_type
))
3711 symbol_got_type
= elf64_aarch64_symbol_got_type (h
, input_bfd
, r_symndx
);
3712 reloc_got_type
= aarch64_reloc_got_type (r_type
);
3714 if (symbol_got_type
== GOT_TLS_IE
&& GOT_TLS_GD_ANY_P (reloc_got_type
))
3720 if (h
&& h
->root
.type
== bfd_link_hash_undefweak
)
3727 aarch64_tls_transition (bfd
*input_bfd
,
3728 struct bfd_link_info
*info
,
3729 unsigned int r_type
,
3730 struct elf_link_hash_entry
*h
,
3731 unsigned long r_symndx
)
3733 if (! aarch64_can_relax_tls (input_bfd
, info
, r_type
, h
, r_symndx
))
3736 return aarch64_tls_transition_without_check (r_type
, h
);
3739 /* Return the base VMA address which should be subtracted from real addresses
3740 when resolving R_AARCH64_TLS_DTPREL64 relocation. */
3743 dtpoff_base (struct bfd_link_info
*info
)
3745 /* If tls_sec is NULL, we should have signalled an error already. */
3746 BFD_ASSERT (elf_hash_table (info
)->tls_sec
!= NULL
);
3747 return elf_hash_table (info
)->tls_sec
->vma
;
3751 /* Return the base VMA address which should be subtracted from real addresses
3752 when resolving R_AARCH64_TLS_GOTTPREL64 relocations. */
3755 tpoff_base (struct bfd_link_info
*info
)
3757 struct elf_link_hash_table
*htab
= elf_hash_table (info
);
3759 /* If tls_sec is NULL, we should have signalled an error already. */
3760 if (htab
->tls_sec
== NULL
)
3763 bfd_vma base
= align_power ((bfd_vma
) TCB_SIZE
,
3764 htab
->tls_sec
->alignment_power
);
3765 return htab
->tls_sec
->vma
- base
;
3769 symbol_got_offset_ref (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3770 unsigned long r_symndx
)
3772 /* Calculate the address of the GOT entry for symbol
3773 referred to in h. */
3775 return &h
->got
.offset
;
3779 struct elf_aarch64_local_symbol
*l
;
3781 l
= elf64_aarch64_locals (input_bfd
);
3782 return &l
[r_symndx
].got_offset
;
3787 symbol_got_offset_mark (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3788 unsigned long r_symndx
)
3791 p
= symbol_got_offset_ref (input_bfd
, h
, r_symndx
);
3796 symbol_got_offset_mark_p (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3797 unsigned long r_symndx
)
3800 value
= * symbol_got_offset_ref (input_bfd
, h
, r_symndx
);
3805 symbol_got_offset (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3806 unsigned long r_symndx
)
3809 value
= * symbol_got_offset_ref (input_bfd
, h
, r_symndx
);
3815 symbol_tlsdesc_got_offset_ref (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3816 unsigned long r_symndx
)
3818 /* Calculate the address of the GOT entry for symbol
3819 referred to in h. */
3822 struct elf64_aarch64_link_hash_entry
*eh
;
3823 eh
= (struct elf64_aarch64_link_hash_entry
*) h
;
3824 return &eh
->tlsdesc_got_jump_table_offset
;
3829 struct elf_aarch64_local_symbol
*l
;
3831 l
= elf64_aarch64_locals (input_bfd
);
3832 return &l
[r_symndx
].tlsdesc_got_jump_table_offset
;
3837 symbol_tlsdesc_got_offset_mark (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3838 unsigned long r_symndx
)
3841 p
= symbol_tlsdesc_got_offset_ref (input_bfd
, h
, r_symndx
);
3846 symbol_tlsdesc_got_offset_mark_p (bfd
*input_bfd
,
3847 struct elf_link_hash_entry
*h
,
3848 unsigned long r_symndx
)
3851 value
= * symbol_tlsdesc_got_offset_ref (input_bfd
, h
, r_symndx
);
3856 symbol_tlsdesc_got_offset (bfd
*input_bfd
, struct elf_link_hash_entry
*h
,
3857 unsigned long r_symndx
)
3860 value
= * symbol_tlsdesc_got_offset_ref (input_bfd
, h
, r_symndx
);
3865 /* Perform a relocation as part of a final link. */
3866 static bfd_reloc_status_type
3867 elf64_aarch64_final_link_relocate (reloc_howto_type
*howto
,
3870 asection
*input_section
,
3872 Elf_Internal_Rela
*rel
,
3874 struct bfd_link_info
*info
,
3876 struct elf_link_hash_entry
*h
,
3877 bfd_boolean
*unresolved_reloc_p
,
3878 bfd_boolean save_addend
,
3879 bfd_vma
*saved_addend
,
3880 Elf_Internal_Sym
*sym
)
3882 Elf_Internal_Shdr
*symtab_hdr
;
3883 unsigned int r_type
= howto
->type
;
3884 unsigned long r_symndx
;
3885 bfd_byte
*hit_data
= contents
+ rel
->r_offset
;
3887 bfd_signed_vma signed_addend
;
3888 struct elf64_aarch64_link_hash_table
*globals
;
3889 bfd_boolean weak_undef_p
;
3891 globals
= elf64_aarch64_hash_table (info
);
3893 symtab_hdr
= &elf_symtab_hdr (input_bfd
);
3895 BFD_ASSERT (is_aarch64_elf (input_bfd
));
3897 r_symndx
= ELF64_R_SYM (rel
->r_info
);
3899 /* It is possible to have linker relaxations on some TLS access
3900 models. Update our information here. */
3901 r_type
= aarch64_tls_transition (input_bfd
, info
, r_type
, h
, r_symndx
);
3903 if (r_type
!= howto
->type
)
3904 howto
= elf64_aarch64_howto_from_type (r_type
);
3906 place
= input_section
->output_section
->vma
3907 + input_section
->output_offset
+ rel
->r_offset
;
3909 /* Get addend, accumulating the addend for consecutive relocs
3910 which refer to the same offset. */
3911 signed_addend
= saved_addend
? *saved_addend
: 0;
3912 signed_addend
+= rel
->r_addend
;
3914 weak_undef_p
= (h
? h
->root
.type
== bfd_link_hash_undefweak
3915 : bfd_is_und_section (sym_sec
));
3917 /* Since STT_GNU_IFUNC symbol must go through PLT, we handle
3918 it here if it is defined in a non-shared object. */
3920 && h
->type
== STT_GNU_IFUNC
3928 if ((input_section
->flags
& SEC_ALLOC
) == 0
3929 || h
->plt
.offset
== (bfd_vma
) -1)
3932 /* STT_GNU_IFUNC symbol must go through PLT. */
3933 plt
= globals
->root
.splt
? globals
->root
.splt
: globals
->root
.iplt
;
3934 value
= (plt
->output_section
->vma
+ plt
->output_offset
+ h
->plt
.offset
);
3939 if (h
->root
.root
.string
)
3940 name
= h
->root
.root
.string
;
3942 name
= bfd_elf_sym_name (input_bfd
, symtab_hdr
, sym
,
3944 (*_bfd_error_handler
)
3945 (_("%B: relocation %s against STT_GNU_IFUNC "
3946 "symbol `%s' isn't handled by %s"), input_bfd
,
3947 howto
->name
, name
, __FUNCTION__
);
3948 bfd_set_error (bfd_error_bad_value
);
3951 case R_AARCH64_ABS64
:
3952 if (rel
->r_addend
!= 0)
3954 if (h
->root
.root
.string
)
3955 name
= h
->root
.root
.string
;
3957 name
= bfd_elf_sym_name (input_bfd
, symtab_hdr
,
3959 (*_bfd_error_handler
)
3960 (_("%B: relocation %s against STT_GNU_IFUNC "
3961 "symbol `%s' has non-zero addend: %d"),
3962 input_bfd
, howto
->name
, name
, rel
->r_addend
);
3963 bfd_set_error (bfd_error_bad_value
);
3967 /* Generate dynamic relocation only when there is a
3968 non-GOT reference in a shared object. */
3969 if (info
->shared
&& h
->non_got_ref
)
3971 Elf_Internal_Rela outrel
;
3974 /* Need a dynamic relocation to get the real function
3976 outrel
.r_offset
= _bfd_elf_section_offset (output_bfd
,
3980 if (outrel
.r_offset
== (bfd_vma
) -1
3981 || outrel
.r_offset
== (bfd_vma
) -2)
3984 outrel
.r_offset
+= (input_section
->output_section
->vma
3985 + input_section
->output_offset
);
3987 if (h
->dynindx
== -1
3989 || info
->executable
)
3991 /* This symbol is resolved locally. */
3992 outrel
.r_info
= ELF64_R_INFO (0, R_AARCH64_IRELATIVE
);
3993 outrel
.r_addend
= (h
->root
.u
.def
.value
3994 + h
->root
.u
.def
.section
->output_section
->vma
3995 + h
->root
.u
.def
.section
->output_offset
);
3999 outrel
.r_info
= ELF64_R_INFO (h
->dynindx
, r_type
);
4000 outrel
.r_addend
= 0;
4003 sreloc
= globals
->root
.irelifunc
;
4004 elf_append_rela (output_bfd
, sreloc
, &outrel
);
4006 /* If this reloc is against an external symbol, we
4007 do not want to fiddle with the addend. Otherwise,
4008 we need to include the symbol value so that it
4009 becomes an addend for the dynamic reloc. For an
4010 internal symbol, we have updated addend. */
4011 return bfd_reloc_ok
;
4014 case R_AARCH64_JUMP26
:
4015 case R_AARCH64_CALL26
:
4016 return _bfd_final_link_relocate (howto
, input_bfd
, input_section
,
4017 contents
, rel
->r_offset
, value
,
4019 case R_AARCH64_LD64_GOT_LO12_NC
:
4020 case R_AARCH64_ADR_GOT_PAGE
:
4021 case R_AARCH64_GOT_LD_PREL19
:
4022 base_got
= globals
->root
.sgot
;
4023 off
= h
->got
.offset
;
4025 if (base_got
== NULL
)
4028 if (off
== (bfd_vma
) -1)
4032 /* We can't use h->got.offset here to save state, or
4033 even just remember the offset, as finish_dynamic_symbol
4034 would use that as offset into .got. */
4036 if (globals
->root
.splt
!= NULL
)
4038 plt_index
= h
->plt
.offset
/ globals
->plt_entry_size
- 1;
4039 off
= (plt_index
+ 3) * GOT_ENTRY_SIZE
;
4040 base_got
= globals
->root
.sgotplt
;
4044 plt_index
= h
->plt
.offset
/ globals
->plt_entry_size
;
4045 off
= plt_index
* GOT_ENTRY_SIZE
;
4046 base_got
= globals
->root
.igotplt
;
4049 if (h
->dynindx
== -1
4053 /* This references the local defitionion. We must
4054 initialize this entry in the global offset table.
4055 Since the offset must always be a multiple of 8,
4056 we use the least significant bit to record
4057 whether we have initialized it already.
4059 When doing a dynamic link, we create a .rela.got
4060 relocation entry to initialize the value. This
4061 is done in the finish_dynamic_symbol routine. */
4066 bfd_put_64 (output_bfd
, value
,
4067 base_got
->contents
+ off
);
4068 /* Note that this is harmless for the GOTPLT64
4069 case, as -1 | 1 still is -1. */
4073 value
= (base_got
->output_section
->vma
4074 + base_got
->output_offset
+ off
);
4077 value
= aarch64_calculate_got_entry_vma (h
, globals
, info
,
4079 unresolved_reloc_p
);
4080 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4082 return _bfd_final_link_relocate (howto
, input_bfd
, input_section
,
4083 contents
, rel
->r_offset
, value
,
4085 case R_AARCH64_ADR_PREL_PG_HI21
:
4086 case R_AARCH64_ADD_ABS_LO12_NC
:
4093 case R_AARCH64_NONE
:
4094 case R_AARCH64_NULL
:
4095 case R_AARCH64_TLSDESC_CALL
:
4096 *unresolved_reloc_p
= FALSE
;
4097 return bfd_reloc_ok
;
4099 case R_AARCH64_ABS64
:
4101 /* When generating a shared object or relocatable executable, these
4102 relocations are copied into the output file to be resolved at
4104 if (((info
->shared
== TRUE
) || globals
->root
.is_relocatable_executable
)
4105 && (input_section
->flags
& SEC_ALLOC
)
4107 || ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
4108 || h
->root
.type
!= bfd_link_hash_undefweak
))
4110 Elf_Internal_Rela outrel
;
4112 bfd_boolean skip
, relocate
;
4115 *unresolved_reloc_p
= FALSE
;
4120 outrel
.r_addend
= signed_addend
;
4122 _bfd_elf_section_offset (output_bfd
, info
, input_section
,
4124 if (outrel
.r_offset
== (bfd_vma
) - 1)
4126 else if (outrel
.r_offset
== (bfd_vma
) - 2)
4132 outrel
.r_offset
+= (input_section
->output_section
->vma
4133 + input_section
->output_offset
);
4136 memset (&outrel
, 0, sizeof outrel
);
4139 && (!info
->shared
|| !info
->symbolic
|| !h
->def_regular
))
4140 outrel
.r_info
= ELF64_R_INFO (h
->dynindx
, r_type
);
4145 /* On SVR4-ish systems, the dynamic loader cannot
4146 relocate the text and data segments independently,
4147 so the symbol does not matter. */
4149 outrel
.r_info
= ELF64_R_INFO (symbol
, R_AARCH64_RELATIVE
);
4150 outrel
.r_addend
+= value
;
4153 sreloc
= elf_section_data (input_section
)->sreloc
;
4154 if (sreloc
== NULL
|| sreloc
->contents
== NULL
)
4155 return bfd_reloc_notsupported
;
4157 loc
= sreloc
->contents
+ sreloc
->reloc_count
++ * RELOC_SIZE (globals
);
4158 bfd_elf64_swap_reloca_out (output_bfd
, &outrel
, loc
);
4160 if (sreloc
->reloc_count
* RELOC_SIZE (globals
) > sreloc
->size
)
4162 /* Sanity to check that we have previously allocated
4163 sufficient space in the relocation section for the
4164 number of relocations we actually want to emit. */
4168 /* If this reloc is against an external symbol, we do not want to
4169 fiddle with the addend. Otherwise, we need to include the symbol
4170 value so that it becomes an addend for the dynamic reloc. */
4172 return bfd_reloc_ok
;
4174 return _bfd_final_link_relocate (howto
, input_bfd
, input_section
,
4175 contents
, rel
->r_offset
, value
,
4179 value
+= signed_addend
;
4182 case R_AARCH64_JUMP26
:
4183 case R_AARCH64_CALL26
:
4185 asection
*splt
= globals
->root
.splt
;
4186 bfd_boolean via_plt_p
=
4187 splt
!= NULL
&& h
!= NULL
&& h
->plt
.offset
!= (bfd_vma
) - 1;
4189 /* A call to an undefined weak symbol is converted to a jump to
4190 the next instruction unless a PLT entry will be created.
4191 The jump to the next instruction is optimized as a NOP.
4192 Do the same for local undefined symbols. */
4193 if (weak_undef_p
&& ! via_plt_p
)
4195 bfd_putl32 (INSN_NOP
, hit_data
);
4196 return bfd_reloc_ok
;
4199 /* If the call goes through a PLT entry, make sure to
4200 check distance to the right destination address. */
4203 value
= (splt
->output_section
->vma
4204 + splt
->output_offset
+ h
->plt
.offset
);
4205 *unresolved_reloc_p
= FALSE
;
4208 /* If the target symbol is global and marked as a function the
4209 relocation applies a function call or a tail call. In this
4210 situation we can veneer out of range branches. The veneers
4211 use IP0 and IP1 hence cannot be used arbitrary out of range
4212 branches that occur within the body of a function. */
4213 if (h
&& h
->type
== STT_FUNC
)
4215 /* Check if a stub has to be inserted because the destination
4217 if (! aarch64_valid_branch_p (value
, place
))
4219 /* The target is out of reach, so redirect the branch to
4220 the local stub for this function. */
4221 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
4222 stub_entry
= elf64_aarch64_get_stub_entry (input_section
,
4225 if (stub_entry
!= NULL
)
4226 value
= (stub_entry
->stub_offset
4227 + stub_entry
->stub_sec
->output_offset
4228 + stub_entry
->stub_sec
->output_section
->vma
);
4232 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4233 signed_addend
, weak_undef_p
);
4236 case R_AARCH64_ABS16
:
4237 case R_AARCH64_ABS32
:
4238 case R_AARCH64_ADD_ABS_LO12_NC
:
4239 case R_AARCH64_ADR_PREL_LO21
:
4240 case R_AARCH64_ADR_PREL_PG_HI21
:
4241 case R_AARCH64_ADR_PREL_PG_HI21_NC
:
4242 case R_AARCH64_CONDBR19
:
4243 case R_AARCH64_LD_PREL_LO19
:
4244 case R_AARCH64_LDST8_ABS_LO12_NC
:
4245 case R_AARCH64_LDST16_ABS_LO12_NC
:
4246 case R_AARCH64_LDST32_ABS_LO12_NC
:
4247 case R_AARCH64_LDST64_ABS_LO12_NC
:
4248 case R_AARCH64_LDST128_ABS_LO12_NC
:
4249 case R_AARCH64_MOVW_SABS_G0
:
4250 case R_AARCH64_MOVW_SABS_G1
:
4251 case R_AARCH64_MOVW_SABS_G2
:
4252 case R_AARCH64_MOVW_UABS_G0
:
4253 case R_AARCH64_MOVW_UABS_G0_NC
:
4254 case R_AARCH64_MOVW_UABS_G1
:
4255 case R_AARCH64_MOVW_UABS_G1_NC
:
4256 case R_AARCH64_MOVW_UABS_G2
:
4257 case R_AARCH64_MOVW_UABS_G2_NC
:
4258 case R_AARCH64_MOVW_UABS_G3
:
4259 case R_AARCH64_PREL16
:
4260 case R_AARCH64_PREL32
:
4261 case R_AARCH64_PREL64
:
4262 case R_AARCH64_TSTBR14
:
4263 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4264 signed_addend
, weak_undef_p
);
4267 case R_AARCH64_LD64_GOT_LO12_NC
:
4268 case R_AARCH64_ADR_GOT_PAGE
:
4269 case R_AARCH64_GOT_LD_PREL19
:
4270 if (globals
->root
.sgot
== NULL
)
4271 BFD_ASSERT (h
!= NULL
);
4275 value
= aarch64_calculate_got_entry_vma (h
, globals
, info
, value
,
4277 unresolved_reloc_p
);
4278 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4283 case R_AARCH64_TLSGD_ADR_PAGE21
:
4284 case R_AARCH64_TLSGD_ADD_LO12_NC
:
4285 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
4286 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
4287 if (globals
->root
.sgot
== NULL
)
4288 return bfd_reloc_notsupported
;
4290 value
= (symbol_got_offset (input_bfd
, h
, r_symndx
)
4291 + globals
->root
.sgot
->output_section
->vma
4292 + globals
->root
.sgot
->output_section
->output_offset
);
4294 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4296 *unresolved_reloc_p
= FALSE
;
4299 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
4300 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
4301 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
4302 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
4303 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
4304 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
4305 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
4306 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
4307 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4308 signed_addend
- tpoff_base (info
), weak_undef_p
);
4309 *unresolved_reloc_p
= FALSE
;
4312 case R_AARCH64_TLSDESC_ADR_PAGE21
:
4313 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
4314 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
4315 case R_AARCH64_TLSDESC_ADD
:
4316 case R_AARCH64_TLSDESC_LDR
:
4317 if (globals
->root
.sgot
== NULL
)
4318 return bfd_reloc_notsupported
;
4320 value
= (symbol_tlsdesc_got_offset (input_bfd
, h
, r_symndx
)
4321 + globals
->root
.sgotplt
->output_section
->vma
4322 + globals
->root
.sgotplt
->output_section
->output_offset
4323 + globals
->sgotplt_jump_table_size
);
4325 value
= aarch64_resolve_relocation (r_type
, place
, value
,
4327 *unresolved_reloc_p
= FALSE
;
4331 return bfd_reloc_notsupported
;
4335 *saved_addend
= value
;
4337 /* Only apply the final relocation in a sequence. */
4339 return bfd_reloc_continue
;
4341 return bfd_elf_aarch64_put_addend (input_bfd
, hit_data
, howto
, value
);
4344 /* Handle TLS relaxations. Relaxing is possible for symbols that use
4345 R_AARCH64_TLSDESC_ADR_{PAGE, LD64_LO12_NC, ADD_LO12_NC} during a static
4348 Return bfd_reloc_ok if we're done, bfd_reloc_continue if the caller
4349 is to then call final_link_relocate. Return other values in the
4352 static bfd_reloc_status_type
4353 elf64_aarch64_tls_relax (struct elf64_aarch64_link_hash_table
*globals
,
4354 bfd
*input_bfd
, bfd_byte
*contents
,
4355 Elf_Internal_Rela
*rel
, struct elf_link_hash_entry
*h
)
4357 bfd_boolean is_local
= h
== NULL
;
4358 unsigned int r_type
= ELF64_R_TYPE (rel
->r_info
);
4361 BFD_ASSERT (globals
&& input_bfd
&& contents
&& rel
);
4365 case R_AARCH64_TLSGD_ADR_PAGE21
:
4366 case R_AARCH64_TLSDESC_ADR_PAGE21
:
4369 /* GD->LE relaxation:
4370 adrp x0, :tlsgd:var => movz x0, :tprel_g1:var
4372 adrp x0, :tlsdesc:var => movz x0, :tprel_g1:var
4374 bfd_putl32 (0xd2a00000, contents
+ rel
->r_offset
);
4375 return bfd_reloc_continue
;
4379 /* GD->IE relaxation:
4380 adrp x0, :tlsgd:var => adrp x0, :gottprel:var
4382 adrp x0, :tlsdesc:var => adrp x0, :gottprel:var
4384 insn
= bfd_getl32 (contents
+ rel
->r_offset
);
4385 return bfd_reloc_continue
;
4388 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
4391 /* GD->LE relaxation:
4392 ldr xd, [x0, #:tlsdesc_lo12:var] => movk x0, :tprel_g0_nc:var
4394 bfd_putl32 (0xf2800000, contents
+ rel
->r_offset
);
4395 return bfd_reloc_continue
;
4399 /* GD->IE relaxation:
4400 ldr xd, [x0, #:tlsdesc_lo12:var] => ldr x0, [x0, #:gottprel_lo12:var]
4402 insn
= bfd_getl32 (contents
+ rel
->r_offset
);
4404 bfd_putl32 (insn
, contents
+ rel
->r_offset
);
4405 return bfd_reloc_continue
;
4408 case R_AARCH64_TLSGD_ADD_LO12_NC
:
4411 /* GD->LE relaxation
4412 add x0, #:tlsgd_lo12:var => movk x0, :tprel_g0_nc:var
4413 bl __tls_get_addr => mrs x1, tpidr_el0
4414 nop => add x0, x1, x0
4417 /* First kill the tls_get_addr reloc on the bl instruction. */
4418 BFD_ASSERT (rel
->r_offset
+ 4 == rel
[1].r_offset
);
4419 rel
[1].r_info
= ELF64_R_INFO (STN_UNDEF
, R_AARCH64_NONE
);
4421 bfd_putl32 (0xf2800000, contents
+ rel
->r_offset
);
4422 bfd_putl32 (0xd53bd041, contents
+ rel
->r_offset
+ 4);
4423 bfd_putl32 (0x8b000020, contents
+ rel
->r_offset
+ 8);
4424 return bfd_reloc_continue
;
4428 /* GD->IE relaxation
4429 ADD x0, #:tlsgd_lo12:var => ldr x0, [x0, #:gottprel_lo12:var]
4430 BL __tls_get_addr => mrs x1, tpidr_el0
4432 NOP => add x0, x1, x0
4435 BFD_ASSERT (ELF64_R_TYPE (rel
[1].r_info
) == R_AARCH64_CALL26
);
4437 /* Remove the relocation on the BL instruction. */
4438 rel
[1].r_info
= ELF64_R_INFO (STN_UNDEF
, R_AARCH64_NONE
);
4440 bfd_putl32 (0xf9400000, contents
+ rel
->r_offset
);
4442 /* We choose to fixup the BL and NOP instructions using the
4443 offset from the second relocation to allow flexibility in
4444 scheduling instructions between the ADD and BL. */
4445 bfd_putl32 (0xd53bd041, contents
+ rel
[1].r_offset
);
4446 bfd_putl32 (0x8b000020, contents
+ rel
[1].r_offset
+ 4);
4447 return bfd_reloc_continue
;
4450 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
4451 case R_AARCH64_TLSDESC_CALL
:
4452 /* GD->IE/LE relaxation:
4453 add x0, x0, #:tlsdesc_lo12:var => nop
4456 bfd_putl32 (INSN_NOP
, contents
+ rel
->r_offset
);
4457 return bfd_reloc_ok
;
4459 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
4460 /* IE->LE relaxation:
4461 adrp xd, :gottprel:var => movz xd, :tprel_g1:var
4465 insn
= bfd_getl32 (contents
+ rel
->r_offset
);
4466 bfd_putl32 (0xd2a00000 | (insn
& 0x1f), contents
+ rel
->r_offset
);
4468 return bfd_reloc_continue
;
4470 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
4471 /* IE->LE relaxation:
4472 ldr xd, [xm, #:gottprel_lo12:var] => movk xd, :tprel_g0_nc:var
4476 insn
= bfd_getl32 (contents
+ rel
->r_offset
);
4477 bfd_putl32 (0xf2800000 | (insn
& 0x1f), contents
+ rel
->r_offset
);
4479 return bfd_reloc_continue
;
4482 return bfd_reloc_continue
;
4485 return bfd_reloc_ok
;
4488 /* Relocate an AArch64 ELF section. */
4491 elf64_aarch64_relocate_section (bfd
*output_bfd
,
4492 struct bfd_link_info
*info
,
4494 asection
*input_section
,
4496 Elf_Internal_Rela
*relocs
,
4497 Elf_Internal_Sym
*local_syms
,
4498 asection
**local_sections
)
4500 Elf_Internal_Shdr
*symtab_hdr
;
4501 struct elf_link_hash_entry
**sym_hashes
;
4502 Elf_Internal_Rela
*rel
;
4503 Elf_Internal_Rela
*relend
;
4505 struct elf64_aarch64_link_hash_table
*globals
;
4506 bfd_boolean save_addend
= FALSE
;
4509 globals
= elf64_aarch64_hash_table (info
);
4511 symtab_hdr
= &elf_symtab_hdr (input_bfd
);
4512 sym_hashes
= elf_sym_hashes (input_bfd
);
4515 relend
= relocs
+ input_section
->reloc_count
;
4516 for (; rel
< relend
; rel
++)
4518 unsigned int r_type
;
4519 unsigned int relaxed_r_type
;
4520 reloc_howto_type
*howto
;
4521 unsigned long r_symndx
;
4522 Elf_Internal_Sym
*sym
;
4524 struct elf_link_hash_entry
*h
;
4526 bfd_reloc_status_type r
;
4529 bfd_boolean unresolved_reloc
= FALSE
;
4530 char *error_message
= NULL
;
4532 r_symndx
= ELF64_R_SYM (rel
->r_info
);
4533 r_type
= ELF64_R_TYPE (rel
->r_info
);
4535 bfd_reloc
.howto
= elf64_aarch64_howto_from_type (r_type
);
4536 howto
= bfd_reloc
.howto
;
4540 (*_bfd_error_handler
)
4541 (_("%B: unrecognized relocation (0x%x) in section `%A'"),
4542 input_bfd
, input_section
, r_type
);
4550 if (r_symndx
< symtab_hdr
->sh_info
)
4552 sym
= local_syms
+ r_symndx
;
4553 sym_type
= ELF64_ST_TYPE (sym
->st_info
);
4554 sec
= local_sections
[r_symndx
];
4556 /* An object file might have a reference to a local
4557 undefined symbol. This is a daft object file, but we
4558 should at least do something about it. */
4559 if (r_type
!= R_AARCH64_NONE
&& r_type
!= R_AARCH64_NULL
4560 && bfd_is_und_section (sec
)
4561 && ELF_ST_BIND (sym
->st_info
) != STB_WEAK
)
4563 if (!info
->callbacks
->undefined_symbol
4564 (info
, bfd_elf_string_from_elf_section
4565 (input_bfd
, symtab_hdr
->sh_link
, sym
->st_name
),
4566 input_bfd
, input_section
, rel
->r_offset
, TRUE
))
4570 relocation
= _bfd_elf_rela_local_sym (output_bfd
, sym
, &sec
, rel
);
4572 /* Relocate against local STT_GNU_IFUNC symbol. */
4573 if (!info
->relocatable
4574 && ELF_ST_TYPE (sym
->st_info
) == STT_GNU_IFUNC
)
4576 h
= elf_aarch64_get_local_sym_hash (globals
, input_bfd
,
4581 /* Set STT_GNU_IFUNC symbol value. */
4582 h
->root
.u
.def
.value
= sym
->st_value
;
4583 h
->root
.u
.def
.section
= sec
;
4590 RELOC_FOR_GLOBAL_SYMBOL (info
, input_bfd
, input_section
, rel
,
4591 r_symndx
, symtab_hdr
, sym_hashes
,
4593 unresolved_reloc
, warned
);
4598 if (sec
!= NULL
&& discarded_section (sec
))
4599 RELOC_AGAINST_DISCARDED_SECTION (info
, input_bfd
, input_section
,
4600 rel
, 1, relend
, howto
, 0, contents
);
4602 if (info
->relocatable
)
4604 /* This is a relocatable link. We don't have to change
4605 anything, unless the reloc is against a section symbol,
4606 in which case we have to adjust according to where the
4607 section symbol winds up in the output section. */
4608 if (sym
!= NULL
&& ELF_ST_TYPE (sym
->st_info
) == STT_SECTION
)
4609 rel
->r_addend
+= sec
->output_offset
;
4614 name
= h
->root
.root
.string
;
4617 name
= (bfd_elf_string_from_elf_section
4618 (input_bfd
, symtab_hdr
->sh_link
, sym
->st_name
));
4619 if (name
== NULL
|| *name
== '\0')
4620 name
= bfd_section_name (input_bfd
, sec
);
4624 && r_type
!= R_AARCH64_NONE
4625 && r_type
!= R_AARCH64_NULL
4627 || h
->root
.type
== bfd_link_hash_defined
4628 || h
->root
.type
== bfd_link_hash_defweak
)
4629 && IS_AARCH64_TLS_RELOC (r_type
) != (sym_type
== STT_TLS
))
4631 (*_bfd_error_handler
)
4632 ((sym_type
== STT_TLS
4633 ? _("%B(%A+0x%lx): %s used with TLS symbol %s")
4634 : _("%B(%A+0x%lx): %s used with non-TLS symbol %s")),
4636 input_section
, (long) rel
->r_offset
, howto
->name
, name
);
4640 /* We relax only if we can see that there can be a valid transition
4641 from a reloc type to another.
4642 We call elf64_aarch64_final_link_relocate unless we're completely
4643 done, i.e., the relaxation produced the final output we want. */
4645 relaxed_r_type
= aarch64_tls_transition (input_bfd
, info
, r_type
,
4647 if (relaxed_r_type
!= r_type
)
4649 r_type
= relaxed_r_type
;
4650 howto
= elf64_aarch64_howto_from_type (r_type
);
4652 r
= elf64_aarch64_tls_relax (globals
, input_bfd
, contents
, rel
, h
);
4653 unresolved_reloc
= 0;
4656 r
= bfd_reloc_continue
;
4658 /* There may be multiple consecutive relocations for the
4659 same offset. In that case we are supposed to treat the
4660 output of each relocation as the addend for the next. */
4661 if (rel
+ 1 < relend
4662 && rel
->r_offset
== rel
[1].r_offset
4663 && ELF64_R_TYPE (rel
[1].r_info
) != R_AARCH64_NONE
4664 && ELF64_R_TYPE (rel
[1].r_info
) != R_AARCH64_NULL
)
4667 save_addend
= FALSE
;
4669 if (r
== bfd_reloc_continue
)
4670 r
= elf64_aarch64_final_link_relocate (howto
, input_bfd
, output_bfd
,
4671 input_section
, contents
, rel
,
4672 relocation
, info
, sec
,
4673 h
, &unresolved_reloc
,
4674 save_addend
, &addend
, sym
);
4678 case R_AARCH64_TLSGD_ADR_PAGE21
:
4679 case R_AARCH64_TLSGD_ADD_LO12_NC
:
4680 if (! symbol_got_offset_mark_p (input_bfd
, h
, r_symndx
))
4682 bfd_boolean need_relocs
= FALSE
;
4687 off
= symbol_got_offset (input_bfd
, h
, r_symndx
);
4688 indx
= h
&& h
->dynindx
!= -1 ? h
->dynindx
: 0;
4691 (info
->shared
|| indx
!= 0) &&
4693 || ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
4694 || h
->root
.type
!= bfd_link_hash_undefweak
);
4696 BFD_ASSERT (globals
->root
.srelgot
!= NULL
);
4700 Elf_Internal_Rela rela
;
4701 rela
.r_info
= ELF64_R_INFO (indx
, R_AARCH64_TLS_DTPMOD64
);
4703 rela
.r_offset
= globals
->root
.sgot
->output_section
->vma
+
4704 globals
->root
.sgot
->output_offset
+ off
;
4707 loc
= globals
->root
.srelgot
->contents
;
4708 loc
+= globals
->root
.srelgot
->reloc_count
++
4709 * RELOC_SIZE (htab
);
4710 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
4714 bfd_put_64 (output_bfd
,
4715 relocation
- dtpoff_base (info
),
4716 globals
->root
.sgot
->contents
+ off
4721 /* This TLS symbol is global. We emit a
4722 relocation to fixup the tls offset at load
4725 ELF64_R_INFO (indx
, R_AARCH64_TLS_DTPREL64
);
4728 (globals
->root
.sgot
->output_section
->vma
4729 + globals
->root
.sgot
->output_offset
+ off
4732 loc
= globals
->root
.srelgot
->contents
;
4733 loc
+= globals
->root
.srelgot
->reloc_count
++
4734 * RELOC_SIZE (globals
);
4735 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
4736 bfd_put_64 (output_bfd
, (bfd_vma
) 0,
4737 globals
->root
.sgot
->contents
+ off
4743 bfd_put_64 (output_bfd
, (bfd_vma
) 1,
4744 globals
->root
.sgot
->contents
+ off
);
4745 bfd_put_64 (output_bfd
,
4746 relocation
- dtpoff_base (info
),
4747 globals
->root
.sgot
->contents
+ off
4751 symbol_got_offset_mark (input_bfd
, h
, r_symndx
);
4755 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
4756 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
4757 if (! symbol_got_offset_mark_p (input_bfd
, h
, r_symndx
))
4759 bfd_boolean need_relocs
= FALSE
;
4764 off
= symbol_got_offset (input_bfd
, h
, r_symndx
);
4766 indx
= h
&& h
->dynindx
!= -1 ? h
->dynindx
: 0;
4769 (info
->shared
|| indx
!= 0) &&
4771 || ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
4772 || h
->root
.type
!= bfd_link_hash_undefweak
);
4774 BFD_ASSERT (globals
->root
.srelgot
!= NULL
);
4778 Elf_Internal_Rela rela
;
4781 rela
.r_addend
= relocation
- dtpoff_base (info
);
4785 rela
.r_info
= ELF64_R_INFO (indx
, R_AARCH64_TLS_TPREL64
);
4786 rela
.r_offset
= globals
->root
.sgot
->output_section
->vma
+
4787 globals
->root
.sgot
->output_offset
+ off
;
4789 loc
= globals
->root
.srelgot
->contents
;
4790 loc
+= globals
->root
.srelgot
->reloc_count
++
4791 * RELOC_SIZE (htab
);
4793 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
4795 bfd_put_64 (output_bfd
, rela
.r_addend
,
4796 globals
->root
.sgot
->contents
+ off
);
4799 bfd_put_64 (output_bfd
, relocation
- tpoff_base (info
),
4800 globals
->root
.sgot
->contents
+ off
);
4802 symbol_got_offset_mark (input_bfd
, h
, r_symndx
);
4806 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
4807 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
4808 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
4809 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
4810 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
4811 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
4812 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
4813 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
4816 case R_AARCH64_TLSDESC_ADR_PAGE21
:
4817 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
4818 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
4819 if (! symbol_tlsdesc_got_offset_mark_p (input_bfd
, h
, r_symndx
))
4821 bfd_boolean need_relocs
= FALSE
;
4822 int indx
= h
&& h
->dynindx
!= -1 ? h
->dynindx
: 0;
4823 bfd_vma off
= symbol_tlsdesc_got_offset (input_bfd
, h
, r_symndx
);
4825 need_relocs
= (h
== NULL
4826 || ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
4827 || h
->root
.type
!= bfd_link_hash_undefweak
);
4829 BFD_ASSERT (globals
->root
.srelgot
!= NULL
);
4830 BFD_ASSERT (globals
->root
.sgot
!= NULL
);
4835 Elf_Internal_Rela rela
;
4836 rela
.r_info
= ELF64_R_INFO (indx
, R_AARCH64_TLSDESC
);
4838 rela
.r_offset
= (globals
->root
.sgotplt
->output_section
->vma
4839 + globals
->root
.sgotplt
->output_offset
4840 + off
+ globals
->sgotplt_jump_table_size
);
4843 rela
.r_addend
= relocation
- dtpoff_base (info
);
4845 /* Allocate the next available slot in the PLT reloc
4846 section to hold our R_AARCH64_TLSDESC, the next
4847 available slot is determined from reloc_count,
4848 which we step. But note, reloc_count was
4849 artifically moved down while allocating slots for
4850 real PLT relocs such that all of the PLT relocs
4851 will fit above the initial reloc_count and the
4852 extra stuff will fit below. */
4853 loc
= globals
->root
.srelplt
->contents
;
4854 loc
+= globals
->root
.srelplt
->reloc_count
++
4855 * RELOC_SIZE (globals
);
4857 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
4859 bfd_put_64 (output_bfd
, (bfd_vma
) 0,
4860 globals
->root
.sgotplt
->contents
+ off
+
4861 globals
->sgotplt_jump_table_size
);
4862 bfd_put_64 (output_bfd
, (bfd_vma
) 0,
4863 globals
->root
.sgotplt
->contents
+ off
+
4864 globals
->sgotplt_jump_table_size
+
4868 symbol_tlsdesc_got_offset_mark (input_bfd
, h
, r_symndx
);
4877 /* Dynamic relocs are not propagated for SEC_DEBUGGING sections
4878 because such sections are not SEC_ALLOC and thus ld.so will
4879 not process them. */
4880 if (unresolved_reloc
4881 && !((input_section
->flags
& SEC_DEBUGGING
) != 0
4883 && _bfd_elf_section_offset (output_bfd
, info
, input_section
,
4884 +rel
->r_offset
) != (bfd_vma
) - 1)
4886 (*_bfd_error_handler
)
4888 ("%B(%A+0x%lx): unresolvable %s relocation against symbol `%s'"),
4889 input_bfd
, input_section
, (long) rel
->r_offset
, howto
->name
,
4890 h
->root
.root
.string
);
4894 if (r
!= bfd_reloc_ok
&& r
!= bfd_reloc_continue
)
4898 case bfd_reloc_overflow
:
4899 /* If the overflowing reloc was to an undefined symbol,
4900 we have already printed one error message and there
4901 is no point complaining again. */
4903 h
->root
.type
!= bfd_link_hash_undefined
)
4904 && (!((*info
->callbacks
->reloc_overflow
)
4905 (info
, (h
? &h
->root
: NULL
), name
, howto
->name
,
4906 (bfd_vma
) 0, input_bfd
, input_section
,
4911 case bfd_reloc_undefined
:
4912 if (!((*info
->callbacks
->undefined_symbol
)
4913 (info
, name
, input_bfd
, input_section
,
4914 rel
->r_offset
, TRUE
)))
4918 case bfd_reloc_outofrange
:
4919 error_message
= _("out of range");
4922 case bfd_reloc_notsupported
:
4923 error_message
= _("unsupported relocation");
4926 case bfd_reloc_dangerous
:
4927 /* error_message should already be set. */
4931 error_message
= _("unknown error");
4935 BFD_ASSERT (error_message
!= NULL
);
4936 if (!((*info
->callbacks
->reloc_dangerous
)
4937 (info
, error_message
, input_bfd
, input_section
,
4948 /* Set the right machine number. */
4951 elf64_aarch64_object_p (bfd
*abfd
)
4953 bfd_default_set_arch_mach (abfd
, bfd_arch_aarch64
, bfd_mach_aarch64
);
4957 /* Function to keep AArch64 specific flags in the ELF header. */
4960 elf64_aarch64_set_private_flags (bfd
*abfd
, flagword flags
)
4962 if (elf_flags_init (abfd
) && elf_elfheader (abfd
)->e_flags
!= flags
)
4967 elf_elfheader (abfd
)->e_flags
= flags
;
4968 elf_flags_init (abfd
) = TRUE
;
4974 /* Copy backend specific data from one object module to another. */
4977 elf64_aarch64_copy_private_bfd_data (bfd
*ibfd
, bfd
*obfd
)
4981 if (!is_aarch64_elf (ibfd
) || !is_aarch64_elf (obfd
))
4984 in_flags
= elf_elfheader (ibfd
)->e_flags
;
4986 elf_elfheader (obfd
)->e_flags
= in_flags
;
4987 elf_flags_init (obfd
) = TRUE
;
4989 /* Also copy the EI_OSABI field. */
4990 elf_elfheader (obfd
)->e_ident
[EI_OSABI
] =
4991 elf_elfheader (ibfd
)->e_ident
[EI_OSABI
];
4993 /* Copy object attributes. */
4994 _bfd_elf_copy_obj_attributes (ibfd
, obfd
);
4999 /* Merge backend specific data from an object file to the output
5000 object file when linking. */
5003 elf64_aarch64_merge_private_bfd_data (bfd
*ibfd
, bfd
*obfd
)
5007 bfd_boolean flags_compatible
= TRUE
;
5010 /* Check if we have the same endianess. */
5011 if (!_bfd_generic_verify_endian_match (ibfd
, obfd
))
5014 if (!is_aarch64_elf (ibfd
) || !is_aarch64_elf (obfd
))
5017 /* The input BFD must have had its flags initialised. */
5018 /* The following seems bogus to me -- The flags are initialized in
5019 the assembler but I don't think an elf_flags_init field is
5020 written into the object. */
5021 /* BFD_ASSERT (elf_flags_init (ibfd)); */
5023 in_flags
= elf_elfheader (ibfd
)->e_flags
;
5024 out_flags
= elf_elfheader (obfd
)->e_flags
;
5026 if (!elf_flags_init (obfd
))
5028 /* If the input is the default architecture and had the default
5029 flags then do not bother setting the flags for the output
5030 architecture, instead allow future merges to do this. If no
5031 future merges ever set these flags then they will retain their
5032 uninitialised values, which surprise surprise, correspond
5033 to the default values. */
5034 if (bfd_get_arch_info (ibfd
)->the_default
5035 && elf_elfheader (ibfd
)->e_flags
== 0)
5038 elf_flags_init (obfd
) = TRUE
;
5039 elf_elfheader (obfd
)->e_flags
= in_flags
;
5041 if (bfd_get_arch (obfd
) == bfd_get_arch (ibfd
)
5042 && bfd_get_arch_info (obfd
)->the_default
)
5043 return bfd_set_arch_mach (obfd
, bfd_get_arch (ibfd
),
5044 bfd_get_mach (ibfd
));
5049 /* Identical flags must be compatible. */
5050 if (in_flags
== out_flags
)
5053 /* Check to see if the input BFD actually contains any sections. If
5054 not, its flags may not have been initialised either, but it
5055 cannot actually cause any incompatiblity. Do not short-circuit
5056 dynamic objects; their section list may be emptied by
5057 elf_link_add_object_symbols.
5059 Also check to see if there are no code sections in the input.
5060 In this case there is no need to check for code specific flags.
5061 XXX - do we need to worry about floating-point format compatability
5062 in data sections ? */
5063 if (!(ibfd
->flags
& DYNAMIC
))
5065 bfd_boolean null_input_bfd
= TRUE
;
5066 bfd_boolean only_data_sections
= TRUE
;
5068 for (sec
= ibfd
->sections
; sec
!= NULL
; sec
= sec
->next
)
5070 if ((bfd_get_section_flags (ibfd
, sec
)
5071 & (SEC_LOAD
| SEC_CODE
| SEC_HAS_CONTENTS
))
5072 == (SEC_LOAD
| SEC_CODE
| SEC_HAS_CONTENTS
))
5073 only_data_sections
= FALSE
;
5075 null_input_bfd
= FALSE
;
5079 if (null_input_bfd
|| only_data_sections
)
5083 return flags_compatible
;
5086 /* Display the flags field. */
5089 elf64_aarch64_print_private_bfd_data (bfd
*abfd
, void *ptr
)
5091 FILE *file
= (FILE *) ptr
;
5092 unsigned long flags
;
5094 BFD_ASSERT (abfd
!= NULL
&& ptr
!= NULL
);
5096 /* Print normal ELF private data. */
5097 _bfd_elf_print_private_bfd_data (abfd
, ptr
);
5099 flags
= elf_elfheader (abfd
)->e_flags
;
5100 /* Ignore init flag - it may not be set, despite the flags field
5101 containing valid data. */
5103 /* xgettext:c-format */
5104 fprintf (file
, _("private flags = %lx:"), elf_elfheader (abfd
)->e_flags
);
5107 fprintf (file
, _("<Unrecognised flag bits set>"));
5114 /* Update the got entry reference counts for the section being removed. */
5117 elf64_aarch64_gc_sweep_hook (bfd
*abfd
,
5118 struct bfd_link_info
*info
,
5120 const Elf_Internal_Rela
* relocs
)
5122 struct elf64_aarch64_link_hash_table
*htab
;
5123 Elf_Internal_Shdr
*symtab_hdr
;
5124 struct elf_link_hash_entry
**sym_hashes
;
5125 struct elf_aarch64_local_symbol
*locals
;
5126 const Elf_Internal_Rela
*rel
, *relend
;
5128 if (info
->relocatable
)
5131 htab
= elf64_aarch64_hash_table (info
);
5136 elf_section_data (sec
)->local_dynrel
= NULL
;
5138 symtab_hdr
= &elf_symtab_hdr (abfd
);
5139 sym_hashes
= elf_sym_hashes (abfd
);
5141 locals
= elf64_aarch64_locals (abfd
);
5143 relend
= relocs
+ sec
->reloc_count
;
5144 for (rel
= relocs
; rel
< relend
; rel
++)
5146 unsigned long r_symndx
;
5147 unsigned int r_type
;
5148 struct elf_link_hash_entry
*h
= NULL
;
5150 r_symndx
= ELF64_R_SYM (rel
->r_info
);
5151 if (r_symndx
>= symtab_hdr
->sh_info
)
5153 h
= sym_hashes
[r_symndx
- symtab_hdr
->sh_info
];
5154 while (h
->root
.type
== bfd_link_hash_indirect
5155 || h
->root
.type
== bfd_link_hash_warning
)
5156 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
5160 /* A local symbol. */
5161 Elf_Internal_Sym
*isym
;
5163 isym
= bfd_sym_from_r_symndx (&htab
->sym_cache
,
5166 /* Check relocation against local STT_GNU_IFUNC symbol. */
5168 && ELF_ST_TYPE (isym
->st_info
) == STT_GNU_IFUNC
)
5170 h
= elf_aarch64_get_local_sym_hash (htab
, abfd
, rel
, FALSE
);
5178 struct elf64_aarch64_link_hash_entry
*eh
;
5179 struct elf_dyn_relocs
**pp
;
5180 struct elf_dyn_relocs
*p
;
5182 eh
= (struct elf64_aarch64_link_hash_entry
*) h
;
5184 for (pp
= &eh
->dyn_relocs
; (p
= *pp
) != NULL
; pp
= &p
->next
)
5187 /* Everything must go for SEC. */
5193 r_type
= ELF64_R_TYPE (rel
->r_info
);
5194 r_type
= aarch64_tls_transition (abfd
,info
, r_type
, h
,r_symndx
);
5197 case R_AARCH64_LD64_GOT_LO12_NC
:
5198 case R_AARCH64_GOT_LD_PREL19
:
5199 case R_AARCH64_ADR_GOT_PAGE
:
5200 case R_AARCH64_TLSGD_ADR_PAGE21
:
5201 case R_AARCH64_TLSGD_ADD_LO12_NC
:
5202 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
5203 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
5204 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
5205 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
5206 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
5207 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
5208 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
5209 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
5210 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
5211 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
5212 case R_AARCH64_TLSDESC_ADR_PAGE21
:
5213 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
5214 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
5217 if (h
->got
.refcount
> 0)
5218 h
->got
.refcount
-= 1;
5220 if (h
->type
== STT_GNU_IFUNC
)
5222 if (h
->plt
.refcount
> 0)
5223 h
->plt
.refcount
-= 1;
5226 else if (locals
!= NULL
)
5228 if (locals
[r_symndx
].got_refcount
> 0)
5229 locals
[r_symndx
].got_refcount
-= 1;
5233 case R_AARCH64_ADR_PREL_PG_HI21_NC
:
5234 case R_AARCH64_ADR_PREL_PG_HI21
:
5235 case R_AARCH64_ADR_PREL_LO21
:
5236 if (h
!= NULL
&& info
->executable
)
5238 if (h
->plt
.refcount
> 0)
5239 h
->plt
.refcount
-= 1;
5243 case R_AARCH64_CALL26
:
5244 case R_AARCH64_JUMP26
:
5245 /* If this is a local symbol then we resolve it
5246 directly without creating a PLT entry. */
5250 if (h
->plt
.refcount
> 0)
5251 h
->plt
.refcount
-= 1;
5254 case R_AARCH64_ABS64
:
5257 if (h
->plt
.refcount
> 0)
5258 h
->plt
.refcount
-= 1;
5270 /* Adjust a symbol defined by a dynamic object and referenced by a
5271 regular object. The current definition is in some section of the
5272 dynamic object, but we're not including those sections. We have to
5273 change the definition to something the rest of the link can
5277 elf64_aarch64_adjust_dynamic_symbol (struct bfd_link_info
*info
,
5278 struct elf_link_hash_entry
*h
)
5280 struct elf64_aarch64_link_hash_table
*htab
;
5283 /* If this is a function, put it in the procedure linkage table. We
5284 will fill in the contents of the procedure linkage table later,
5285 when we know the address of the .got section. */
5286 if (h
->type
== STT_FUNC
|| h
->type
== STT_GNU_IFUNC
|| h
->needs_plt
)
5288 if (h
->plt
.refcount
<= 0
5289 || (h
->type
!= STT_GNU_IFUNC
5290 && (SYMBOL_CALLS_LOCAL (info
, h
)
5291 || (ELF_ST_VISIBILITY (h
->other
) != STV_DEFAULT
5292 && h
->root
.type
== bfd_link_hash_undefweak
))))
5294 /* This case can occur if we saw a CALL26 reloc in
5295 an input file, but the symbol wasn't referred to
5296 by a dynamic object or all references were
5297 garbage collected. In which case we can end up
5299 h
->plt
.offset
= (bfd_vma
) - 1;
5306 /* It's possible that we incorrectly decided a .plt reloc was
5307 needed for an R_X86_64_PC32 reloc to a non-function sym in
5308 check_relocs. We can't decide accurately between function and
5309 non-function syms in check-relocs; Objects loaded later in
5310 the link may change h->type. So fix it now. */
5311 h
->plt
.offset
= (bfd_vma
) - 1;
5314 /* If this is a weak symbol, and there is a real definition, the
5315 processor independent code will have arranged for us to see the
5316 real definition first, and we can just use the same value. */
5317 if (h
->u
.weakdef
!= NULL
)
5319 BFD_ASSERT (h
->u
.weakdef
->root
.type
== bfd_link_hash_defined
5320 || h
->u
.weakdef
->root
.type
== bfd_link_hash_defweak
);
5321 h
->root
.u
.def
.section
= h
->u
.weakdef
->root
.u
.def
.section
;
5322 h
->root
.u
.def
.value
= h
->u
.weakdef
->root
.u
.def
.value
;
5323 if (ELIMINATE_COPY_RELOCS
|| info
->nocopyreloc
)
5324 h
->non_got_ref
= h
->u
.weakdef
->non_got_ref
;
5328 /* If we are creating a shared library, we must presume that the
5329 only references to the symbol are via the global offset table.
5330 For such cases we need not do anything here; the relocations will
5331 be handled correctly by relocate_section. */
5335 /* If there are no references to this symbol that do not use the
5336 GOT, we don't need to generate a copy reloc. */
5337 if (!h
->non_got_ref
)
5340 /* If -z nocopyreloc was given, we won't generate them either. */
5341 if (info
->nocopyreloc
)
5347 /* We must allocate the symbol in our .dynbss section, which will
5348 become part of the .bss section of the executable. There will be
5349 an entry for this symbol in the .dynsym section. The dynamic
5350 object will contain position independent code, so all references
5351 from the dynamic object to this symbol will go through the global
5352 offset table. The dynamic linker will use the .dynsym entry to
5353 determine the address it must put in the global offset table, so
5354 both the dynamic object and the regular object will refer to the
5355 same memory location for the variable. */
5357 htab
= elf64_aarch64_hash_table (info
);
5359 /* We must generate a R_AARCH64_COPY reloc to tell the dynamic linker
5360 to copy the initial value out of the dynamic object and into the
5361 runtime process image. */
5362 if ((h
->root
.u
.def
.section
->flags
& SEC_ALLOC
) != 0 && h
->size
!= 0)
5364 htab
->srelbss
->size
+= RELOC_SIZE (htab
);
5370 return _bfd_elf_adjust_dynamic_copy (h
, s
);
5375 elf64_aarch64_allocate_local_symbols (bfd
*abfd
, unsigned number
)
5377 struct elf_aarch64_local_symbol
*locals
;
5378 locals
= elf64_aarch64_locals (abfd
);
5381 locals
= (struct elf_aarch64_local_symbol
*)
5382 bfd_zalloc (abfd
, number
* sizeof (struct elf_aarch64_local_symbol
));
5385 elf64_aarch64_locals (abfd
) = locals
;
5390 /* Look through the relocs for a section during the first phase. */
5393 elf64_aarch64_check_relocs (bfd
*abfd
, struct bfd_link_info
*info
,
5394 asection
*sec
, const Elf_Internal_Rela
*relocs
)
5396 Elf_Internal_Shdr
*symtab_hdr
;
5397 struct elf_link_hash_entry
**sym_hashes
;
5398 const Elf_Internal_Rela
*rel
;
5399 const Elf_Internal_Rela
*rel_end
;
5402 struct elf64_aarch64_link_hash_table
*htab
;
5404 if (info
->relocatable
)
5407 BFD_ASSERT (is_aarch64_elf (abfd
));
5409 htab
= elf64_aarch64_hash_table (info
);
5412 symtab_hdr
= &elf_symtab_hdr (abfd
);
5413 sym_hashes
= elf_sym_hashes (abfd
);
5415 rel_end
= relocs
+ sec
->reloc_count
;
5416 for (rel
= relocs
; rel
< rel_end
; rel
++)
5418 struct elf_link_hash_entry
*h
;
5419 unsigned long r_symndx
;
5420 unsigned int r_type
;
5421 Elf_Internal_Sym
*isym
;
5423 r_symndx
= ELF64_R_SYM (rel
->r_info
);
5424 r_type
= ELF64_R_TYPE (rel
->r_info
);
5426 if (r_symndx
>= NUM_SHDR_ENTRIES (symtab_hdr
))
5428 (*_bfd_error_handler
) (_("%B: bad symbol index: %d"), abfd
,
5433 if (r_symndx
< symtab_hdr
->sh_info
)
5435 /* A local symbol. */
5436 isym
= bfd_sym_from_r_symndx (&htab
->sym_cache
,
5441 /* Check relocation against local STT_GNU_IFUNC symbol. */
5442 if (ELF_ST_TYPE (isym
->st_info
) == STT_GNU_IFUNC
)
5444 h
= elf_aarch64_get_local_sym_hash (htab
, abfd
, rel
,
5449 /* Fake a STT_GNU_IFUNC symbol. */
5450 h
->type
= STT_GNU_IFUNC
;
5453 h
->forced_local
= 1;
5454 h
->root
.type
= bfd_link_hash_defined
;
5461 h
= sym_hashes
[r_symndx
- symtab_hdr
->sh_info
];
5462 while (h
->root
.type
== bfd_link_hash_indirect
5463 || h
->root
.type
== bfd_link_hash_warning
)
5464 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
5466 /* PR15323, ref flags aren't set for references in the same
5468 h
->root
.non_ir_ref
= 1;
5473 /* Create the ifunc sections for static executables. If we
5474 never see an indirect function symbol nor we are building
5475 a static executable, those sections will be empty and
5476 won't appear in output. */
5482 case R_AARCH64_ABS64
:
5483 case R_AARCH64_CALL26
:
5484 case R_AARCH64_JUMP26
:
5485 case R_AARCH64_LD64_GOT_LO12_NC
:
5486 case R_AARCH64_ADR_GOT_PAGE
:
5487 case R_AARCH64_GOT_LD_PREL19
:
5488 case R_AARCH64_ADR_PREL_PG_HI21
:
5489 case R_AARCH64_ADD_ABS_LO12_NC
:
5490 if (htab
->root
.dynobj
== NULL
)
5491 htab
->root
.dynobj
= abfd
;
5492 if (!_bfd_elf_create_ifunc_sections (htab
->root
.dynobj
, info
))
5497 /* It is referenced by a non-shared object. */
5499 h
->root
.non_ir_ref
= 1;
5502 /* Could be done earlier, if h were already available. */
5503 r_type
= aarch64_tls_transition (abfd
, info
, r_type
, h
, r_symndx
);
5507 case R_AARCH64_ABS64
:
5509 /* We don't need to handle relocs into sections not going into
5510 the "real" output. */
5511 if ((sec
->flags
& SEC_ALLOC
) == 0)
5519 h
->plt
.refcount
+= 1;
5520 h
->pointer_equality_needed
= 1;
5523 /* No need to do anything if we're not creating a shared
5529 struct elf_dyn_relocs
*p
;
5530 struct elf_dyn_relocs
**head
;
5532 /* We must copy these reloc types into the output file.
5533 Create a reloc section in dynobj and make room for
5537 if (htab
->root
.dynobj
== NULL
)
5538 htab
->root
.dynobj
= abfd
;
5540 sreloc
= _bfd_elf_make_dynamic_reloc_section
5541 (sec
, htab
->root
.dynobj
, 3, abfd
, /*rela? */ TRUE
);
5547 /* If this is a global symbol, we count the number of
5548 relocations we need for this symbol. */
5551 struct elf64_aarch64_link_hash_entry
*eh
;
5552 eh
= (struct elf64_aarch64_link_hash_entry
*) h
;
5553 head
= &eh
->dyn_relocs
;
5557 /* Track dynamic relocs needed for local syms too.
5558 We really need local syms available to do this
5564 isym
= bfd_sym_from_r_symndx (&htab
->sym_cache
,
5569 s
= bfd_section_from_elf_index (abfd
, isym
->st_shndx
);
5573 /* Beware of type punned pointers vs strict aliasing
5575 vpp
= &(elf_section_data (s
)->local_dynrel
);
5576 head
= (struct elf_dyn_relocs
**) vpp
;
5580 if (p
== NULL
|| p
->sec
!= sec
)
5582 bfd_size_type amt
= sizeof *p
;
5583 p
= ((struct elf_dyn_relocs
*)
5584 bfd_zalloc (htab
->root
.dynobj
, amt
));
5597 /* RR: We probably want to keep a consistency check that
5598 there are no dangling GOT_PAGE relocs. */
5599 case R_AARCH64_LD64_GOT_LO12_NC
:
5600 case R_AARCH64_GOT_LD_PREL19
:
5601 case R_AARCH64_ADR_GOT_PAGE
:
5602 case R_AARCH64_TLSGD_ADR_PAGE21
:
5603 case R_AARCH64_TLSGD_ADD_LO12_NC
:
5604 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21
:
5605 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC
:
5606 case R_AARCH64_TLSLE_ADD_TPREL_LO12
:
5607 case R_AARCH64_TLSLE_ADD_TPREL_HI12
:
5608 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC
:
5609 case R_AARCH64_TLSLE_MOVW_TPREL_G2
:
5610 case R_AARCH64_TLSLE_MOVW_TPREL_G1
:
5611 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC
:
5612 case R_AARCH64_TLSLE_MOVW_TPREL_G0
:
5613 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC
:
5614 case R_AARCH64_TLSDESC_ADR_PAGE21
:
5615 case R_AARCH64_TLSDESC_ADD_LO12_NC
:
5616 case R_AARCH64_TLSDESC_LD64_LO12_NC
:
5619 unsigned old_got_type
;
5621 got_type
= aarch64_reloc_got_type (r_type
);
5625 h
->got
.refcount
+= 1;
5626 old_got_type
= elf64_aarch64_hash_entry (h
)->got_type
;
5630 struct elf_aarch64_local_symbol
*locals
;
5632 if (!elf64_aarch64_allocate_local_symbols
5633 (abfd
, symtab_hdr
->sh_info
))
5636 locals
= elf64_aarch64_locals (abfd
);
5637 BFD_ASSERT (r_symndx
< symtab_hdr
->sh_info
);
5638 locals
[r_symndx
].got_refcount
+= 1;
5639 old_got_type
= locals
[r_symndx
].got_type
;
5642 /* If a variable is accessed with both general dynamic TLS
5643 methods, two slots may be created. */
5644 if (GOT_TLS_GD_ANY_P (old_got_type
) && GOT_TLS_GD_ANY_P (got_type
))
5645 got_type
|= old_got_type
;
5647 /* We will already have issued an error message if there
5648 is a TLS/non-TLS mismatch, based on the symbol type.
5649 So just combine any TLS types needed. */
5650 if (old_got_type
!= GOT_UNKNOWN
&& old_got_type
!= GOT_NORMAL
5651 && got_type
!= GOT_NORMAL
)
5652 got_type
|= old_got_type
;
5654 /* If the symbol is accessed by both IE and GD methods, we
5655 are able to relax. Turn off the GD flag, without
5656 messing up with any other kind of TLS types that may be
5658 if ((got_type
& GOT_TLS_IE
) && GOT_TLS_GD_ANY_P (got_type
))
5659 got_type
&= ~ (GOT_TLSDESC_GD
| GOT_TLS_GD
);
5661 if (old_got_type
!= got_type
)
5664 elf64_aarch64_hash_entry (h
)->got_type
= got_type
;
5667 struct elf_aarch64_local_symbol
*locals
;
5668 locals
= elf64_aarch64_locals (abfd
);
5669 BFD_ASSERT (r_symndx
< symtab_hdr
->sh_info
);
5670 locals
[r_symndx
].got_type
= got_type
;
5674 if (htab
->root
.sgot
== NULL
)
5676 if (htab
->root
.dynobj
== NULL
)
5677 htab
->root
.dynobj
= abfd
;
5678 if (!_bfd_elf_create_got_section (htab
->root
.dynobj
, info
))
5684 case R_AARCH64_ADR_PREL_PG_HI21_NC
:
5685 case R_AARCH64_ADR_PREL_PG_HI21
:
5686 case R_AARCH64_ADR_PREL_LO21
:
5687 if (h
!= NULL
&& info
->executable
)
5689 /* If this reloc is in a read-only section, we might
5690 need a copy reloc. We can't check reliably at this
5691 stage whether the section is read-only, as input
5692 sections have not yet been mapped to output sections.
5693 Tentatively set the flag for now, and correct in
5694 adjust_dynamic_symbol. */
5696 h
->plt
.refcount
+= 1;
5697 h
->pointer_equality_needed
= 1;
5699 /* FIXME:: RR need to handle these in shared libraries
5700 and essentially bomb out as these being non-PIC
5701 relocations in shared libraries. */
5704 case R_AARCH64_CALL26
:
5705 case R_AARCH64_JUMP26
:
5706 /* If this is a local symbol then we resolve it
5707 directly without creating a PLT entry. */
5712 if (h
->plt
.refcount
<= 0)
5713 h
->plt
.refcount
= 1;
5715 h
->plt
.refcount
+= 1;
5722 /* Treat mapping symbols as special target symbols. */
5725 elf64_aarch64_is_target_special_symbol (bfd
*abfd ATTRIBUTE_UNUSED
,
5728 return bfd_is_aarch64_special_symbol_name (sym
->name
,
5729 BFD_AARCH64_SPECIAL_SYM_TYPE_ANY
);
5732 /* This is a copy of elf_find_function () from elf.c except that
5733 AArch64 mapping symbols are ignored when looking for function names. */
5736 aarch64_elf_find_function (bfd
*abfd ATTRIBUTE_UNUSED
,
5740 const char **filename_ptr
,
5741 const char **functionname_ptr
)
5743 const char *filename
= NULL
;
5744 asymbol
*func
= NULL
;
5745 bfd_vma low_func
= 0;
5748 for (p
= symbols
; *p
!= NULL
; p
++)
5752 q
= (elf_symbol_type
*) * p
;
5754 switch (ELF_ST_TYPE (q
->internal_elf_sym
.st_info
))
5759 filename
= bfd_asymbol_name (&q
->symbol
);
5763 /* Skip mapping symbols. */
5764 if ((q
->symbol
.flags
& BSF_LOCAL
)
5765 && (bfd_is_aarch64_special_symbol_name
5766 (q
->symbol
.name
, BFD_AARCH64_SPECIAL_SYM_TYPE_ANY
)))
5769 if (bfd_get_section (&q
->symbol
) == section
5770 && q
->symbol
.value
>= low_func
&& q
->symbol
.value
<= offset
)
5772 func
= (asymbol
*) q
;
5773 low_func
= q
->symbol
.value
;
5783 *filename_ptr
= filename
;
5784 if (functionname_ptr
)
5785 *functionname_ptr
= bfd_asymbol_name (func
);
5791 /* Find the nearest line to a particular section and offset, for error
5792 reporting. This code is a duplicate of the code in elf.c, except
5793 that it uses aarch64_elf_find_function. */
5796 elf64_aarch64_find_nearest_line (bfd
*abfd
,
5800 const char **filename_ptr
,
5801 const char **functionname_ptr
,
5802 unsigned int *line_ptr
)
5804 bfd_boolean found
= FALSE
;
5806 /* We skip _bfd_dwarf1_find_nearest_line since no known AArch64
5807 toolchain uses it. */
5809 if (_bfd_dwarf2_find_nearest_line (abfd
, dwarf_debug_sections
,
5810 section
, symbols
, offset
,
5811 filename_ptr
, functionname_ptr
,
5813 &elf_tdata (abfd
)->dwarf2_find_line_info
))
5815 if (!*functionname_ptr
)
5816 aarch64_elf_find_function (abfd
, section
, symbols
, offset
,
5817 *filename_ptr
? NULL
: filename_ptr
,
5823 if (!_bfd_stab_section_find_nearest_line (abfd
, symbols
, section
, offset
,
5824 &found
, filename_ptr
,
5825 functionname_ptr
, line_ptr
,
5826 &elf_tdata (abfd
)->line_info
))
5829 if (found
&& (*functionname_ptr
|| *line_ptr
))
5832 if (symbols
== NULL
)
5835 if (!aarch64_elf_find_function (abfd
, section
, symbols
, offset
,
5836 filename_ptr
, functionname_ptr
))
5844 elf64_aarch64_find_inliner_info (bfd
*abfd
,
5845 const char **filename_ptr
,
5846 const char **functionname_ptr
,
5847 unsigned int *line_ptr
)
5850 found
= _bfd_dwarf2_find_inliner_info
5851 (abfd
, filename_ptr
,
5852 functionname_ptr
, line_ptr
, &elf_tdata (abfd
)->dwarf2_find_line_info
);
5858 elf64_aarch64_post_process_headers (bfd
*abfd
,
5859 struct bfd_link_info
*link_info
)
5861 Elf_Internal_Ehdr
*i_ehdrp
; /* ELF file header, internal form. */
5863 i_ehdrp
= elf_elfheader (abfd
);
5864 i_ehdrp
->e_ident
[EI_ABIVERSION
] = AARCH64_ELF_ABI_VERSION
;
5866 _bfd_elf_set_osabi (abfd
, link_info
);
5869 static enum elf_reloc_type_class
5870 elf64_aarch64_reloc_type_class (const struct bfd_link_info
*info ATTRIBUTE_UNUSED
,
5871 const asection
*rel_sec ATTRIBUTE_UNUSED
,
5872 const Elf_Internal_Rela
*rela
)
5874 switch ((int) ELF64_R_TYPE (rela
->r_info
))
5876 case R_AARCH64_RELATIVE
:
5877 return reloc_class_relative
;
5878 case R_AARCH64_JUMP_SLOT
:
5879 return reloc_class_plt
;
5880 case R_AARCH64_COPY
:
5881 return reloc_class_copy
;
5883 return reloc_class_normal
;
5887 /* Set the right machine number for an AArch64 ELF file. */
5890 elf64_aarch64_section_flags (flagword
*flags
, const Elf_Internal_Shdr
*hdr
)
5892 if (hdr
->sh_type
== SHT_NOTE
)
5893 *flags
|= SEC_LINK_ONCE
| SEC_LINK_DUPLICATES_SAME_CONTENTS
;
5898 /* Handle an AArch64 specific section when reading an object file. This is
5899 called when bfd_section_from_shdr finds a section with an unknown
5903 elf64_aarch64_section_from_shdr (bfd
*abfd
,
5904 Elf_Internal_Shdr
*hdr
,
5905 const char *name
, int shindex
)
5907 /* There ought to be a place to keep ELF backend specific flags, but
5908 at the moment there isn't one. We just keep track of the
5909 sections by their name, instead. Fortunately, the ABI gives
5910 names for all the AArch64 specific sections, so we will probably get
5912 switch (hdr
->sh_type
)
5914 case SHT_AARCH64_ATTRIBUTES
:
5921 if (!_bfd_elf_make_section_from_shdr (abfd
, hdr
, name
, shindex
))
5927 /* A structure used to record a list of sections, independently
5928 of the next and prev fields in the asection structure. */
5929 typedef struct section_list
5932 struct section_list
*next
;
5933 struct section_list
*prev
;
5937 /* Unfortunately we need to keep a list of sections for which
5938 an _aarch64_elf_section_data structure has been allocated. This
5939 is because it is possible for functions like elf64_aarch64_write_section
5940 to be called on a section which has had an elf_data_structure
5941 allocated for it (and so the used_by_bfd field is valid) but
5942 for which the AArch64 extended version of this structure - the
5943 _aarch64_elf_section_data structure - has not been allocated. */
5944 static section_list
*sections_with_aarch64_elf_section_data
= NULL
;
5947 record_section_with_aarch64_elf_section_data (asection
*sec
)
5949 struct section_list
*entry
;
5951 entry
= bfd_malloc (sizeof (*entry
));
5955 entry
->next
= sections_with_aarch64_elf_section_data
;
5957 if (entry
->next
!= NULL
)
5958 entry
->next
->prev
= entry
;
5959 sections_with_aarch64_elf_section_data
= entry
;
5962 static struct section_list
*
5963 find_aarch64_elf_section_entry (asection
*sec
)
5965 struct section_list
*entry
;
5966 static struct section_list
*last_entry
= NULL
;
5968 /* This is a short cut for the typical case where the sections are added
5969 to the sections_with_aarch64_elf_section_data list in forward order and
5970 then looked up here in backwards order. This makes a real difference
5971 to the ld-srec/sec64k.exp linker test. */
5972 entry
= sections_with_aarch64_elf_section_data
;
5973 if (last_entry
!= NULL
)
5975 if (last_entry
->sec
== sec
)
5977 else if (last_entry
->next
!= NULL
&& last_entry
->next
->sec
== sec
)
5978 entry
= last_entry
->next
;
5981 for (; entry
; entry
= entry
->next
)
5982 if (entry
->sec
== sec
)
5986 /* Record the entry prior to this one - it is the entry we are
5987 most likely to want to locate next time. Also this way if we
5988 have been called from
5989 unrecord_section_with_aarch64_elf_section_data () we will not
5990 be caching a pointer that is about to be freed. */
5991 last_entry
= entry
->prev
;
5997 unrecord_section_with_aarch64_elf_section_data (asection
*sec
)
5999 struct section_list
*entry
;
6001 entry
= find_aarch64_elf_section_entry (sec
);
6005 if (entry
->prev
!= NULL
)
6006 entry
->prev
->next
= entry
->next
;
6007 if (entry
->next
!= NULL
)
6008 entry
->next
->prev
= entry
->prev
;
6009 if (entry
== sections_with_aarch64_elf_section_data
)
6010 sections_with_aarch64_elf_section_data
= entry
->next
;
6019 struct bfd_link_info
*info
;
6022 int (*func
) (void *, const char *, Elf_Internal_Sym
*,
6023 asection
*, struct elf_link_hash_entry
*);
6024 } output_arch_syminfo
;
6026 enum map_symbol_type
6033 /* Output a single mapping symbol. */
6036 elf64_aarch64_output_map_sym (output_arch_syminfo
*osi
,
6037 enum map_symbol_type type
, bfd_vma offset
)
6039 static const char *names
[2] = { "$x", "$d" };
6040 Elf_Internal_Sym sym
;
6042 sym
.st_value
= (osi
->sec
->output_section
->vma
6043 + osi
->sec
->output_offset
+ offset
);
6046 sym
.st_info
= ELF_ST_INFO (STB_LOCAL
, STT_NOTYPE
);
6047 sym
.st_shndx
= osi
->sec_shndx
;
6048 return osi
->func (osi
->finfo
, names
[type
], &sym
, osi
->sec
, NULL
) == 1;
6053 /* Output mapping symbols for PLT entries associated with H. */
6056 elf64_aarch64_output_plt_map (struct elf_link_hash_entry
*h
, void *inf
)
6058 output_arch_syminfo
*osi
= (output_arch_syminfo
*) inf
;
6061 if (h
->root
.type
== bfd_link_hash_indirect
)
6064 if (h
->root
.type
== bfd_link_hash_warning
)
6065 /* When warning symbols are created, they **replace** the "real"
6066 entry in the hash table, thus we never get to see the real
6067 symbol in a hash traversal. So look at it now. */
6068 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
6070 if (h
->plt
.offset
== (bfd_vma
) - 1)
6073 addr
= h
->plt
.offset
;
6076 if (!elf64_aarch64_output_map_sym (osi
, AARCH64_MAP_INSN
, addr
))
6083 /* Output a single local symbol for a generated stub. */
6086 elf64_aarch64_output_stub_sym (output_arch_syminfo
*osi
, const char *name
,
6087 bfd_vma offset
, bfd_vma size
)
6089 Elf_Internal_Sym sym
;
6091 sym
.st_value
= (osi
->sec
->output_section
->vma
6092 + osi
->sec
->output_offset
+ offset
);
6095 sym
.st_info
= ELF_ST_INFO (STB_LOCAL
, STT_FUNC
);
6096 sym
.st_shndx
= osi
->sec_shndx
;
6097 return osi
->func (osi
->finfo
, name
, &sym
, osi
->sec
, NULL
) == 1;
6101 aarch64_map_one_stub (struct bfd_hash_entry
*gen_entry
, void *in_arg
)
6103 struct elf64_aarch64_stub_hash_entry
*stub_entry
;
6107 output_arch_syminfo
*osi
;
6109 /* Massage our args to the form they really have. */
6110 stub_entry
= (struct elf64_aarch64_stub_hash_entry
*) gen_entry
;
6111 osi
= (output_arch_syminfo
*) in_arg
;
6113 stub_sec
= stub_entry
->stub_sec
;
6115 /* Ensure this stub is attached to the current section being
6117 if (stub_sec
!= osi
->sec
)
6120 addr
= (bfd_vma
) stub_entry
->stub_offset
;
6122 stub_name
= stub_entry
->output_name
;
6124 switch (stub_entry
->stub_type
)
6126 case aarch64_stub_adrp_branch
:
6127 if (!elf64_aarch64_output_stub_sym (osi
, stub_name
, addr
,
6128 sizeof (aarch64_adrp_branch_stub
)))
6130 if (!elf64_aarch64_output_map_sym (osi
, AARCH64_MAP_INSN
, addr
))
6133 case aarch64_stub_long_branch
:
6134 if (!elf64_aarch64_output_stub_sym
6135 (osi
, stub_name
, addr
, sizeof (aarch64_long_branch_stub
)))
6137 if (!elf64_aarch64_output_map_sym (osi
, AARCH64_MAP_INSN
, addr
))
6139 if (!elf64_aarch64_output_map_sym (osi
, AARCH64_MAP_DATA
, addr
+ 16))
6149 /* Output mapping symbols for linker generated sections. */
6152 elf64_aarch64_output_arch_local_syms (bfd
*output_bfd
,
6153 struct bfd_link_info
*info
,
6155 int (*func
) (void *, const char *,
6158 struct elf_link_hash_entry
6161 output_arch_syminfo osi
;
6162 struct elf64_aarch64_link_hash_table
*htab
;
6164 htab
= elf64_aarch64_hash_table (info
);
6170 /* Long calls stubs. */
6171 if (htab
->stub_bfd
&& htab
->stub_bfd
->sections
)
6175 for (stub_sec
= htab
->stub_bfd
->sections
;
6176 stub_sec
!= NULL
; stub_sec
= stub_sec
->next
)
6178 /* Ignore non-stub sections. */
6179 if (!strstr (stub_sec
->name
, STUB_SUFFIX
))
6184 osi
.sec_shndx
= _bfd_elf_section_from_bfd_section
6185 (output_bfd
, osi
.sec
->output_section
);
6187 bfd_hash_traverse (&htab
->stub_hash_table
, aarch64_map_one_stub
,
6192 /* Finally, output mapping symbols for the PLT. */
6193 if (!htab
->root
.splt
|| htab
->root
.splt
->size
== 0)
6196 /* For now live without mapping symbols for the plt. */
6197 osi
.sec_shndx
= _bfd_elf_section_from_bfd_section
6198 (output_bfd
, htab
->root
.splt
->output_section
);
6199 osi
.sec
= htab
->root
.splt
;
6201 elf_link_hash_traverse (&htab
->root
, elf64_aarch64_output_plt_map
,
6208 /* Allocate target specific section data. */
6211 elf64_aarch64_new_section_hook (bfd
*abfd
, asection
*sec
)
6213 if (!sec
->used_by_bfd
)
6215 _aarch64_elf_section_data
*sdata
;
6216 bfd_size_type amt
= sizeof (*sdata
);
6218 sdata
= bfd_zalloc (abfd
, amt
);
6221 sec
->used_by_bfd
= sdata
;
6224 record_section_with_aarch64_elf_section_data (sec
);
6226 return _bfd_elf_new_section_hook (abfd
, sec
);
6231 unrecord_section_via_map_over_sections (bfd
*abfd ATTRIBUTE_UNUSED
,
6233 void *ignore ATTRIBUTE_UNUSED
)
6235 unrecord_section_with_aarch64_elf_section_data (sec
);
6239 elf64_aarch64_close_and_cleanup (bfd
*abfd
)
6242 bfd_map_over_sections (abfd
,
6243 unrecord_section_via_map_over_sections
, NULL
);
6245 return _bfd_elf_close_and_cleanup (abfd
);
6249 elf64_aarch64_bfd_free_cached_info (bfd
*abfd
)
6252 bfd_map_over_sections (abfd
,
6253 unrecord_section_via_map_over_sections
, NULL
);
6255 return _bfd_free_cached_info (abfd
);
6258 /* Create dynamic sections. This is different from the ARM backend in that
6259 the got, plt, gotplt and their relocation sections are all created in the
6260 standard part of the bfd elf backend. */
6263 elf64_aarch64_create_dynamic_sections (bfd
*dynobj
,
6264 struct bfd_link_info
*info
)
6266 struct elf64_aarch64_link_hash_table
*htab
;
6267 struct elf_link_hash_entry
*h
;
6269 if (!_bfd_elf_create_dynamic_sections (dynobj
, info
))
6272 htab
= elf64_aarch64_hash_table (info
);
6273 htab
->sdynbss
= bfd_get_linker_section (dynobj
, ".dynbss");
6275 htab
->srelbss
= bfd_get_linker_section (dynobj
, ".rela.bss");
6277 if (!htab
->sdynbss
|| (!info
->shared
&& !htab
->srelbss
))
6280 /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the
6281 dynobj's .got section. We don't do this in the linker script
6282 because we don't want to define the symbol if we are not creating
6283 a global offset table. */
6284 h
= _bfd_elf_define_linkage_sym (dynobj
, info
,
6285 htab
->root
.sgot
, "_GLOBAL_OFFSET_TABLE_");
6286 elf_hash_table (info
)->hgot
= h
;
6294 /* Allocate space in .plt, .got and associated reloc sections for
6298 elf64_aarch64_allocate_dynrelocs (struct elf_link_hash_entry
*h
, void *inf
)
6300 struct bfd_link_info
*info
;
6301 struct elf64_aarch64_link_hash_table
*htab
;
6302 struct elf64_aarch64_link_hash_entry
*eh
;
6303 struct elf_dyn_relocs
*p
;
6305 /* An example of a bfd_link_hash_indirect symbol is versioned
6306 symbol. For example: __gxx_personality_v0(bfd_link_hash_indirect)
6307 -> __gxx_personality_v0(bfd_link_hash_defined)
6309 There is no need to process bfd_link_hash_indirect symbols here
6310 because we will also be presented with the concrete instance of
6311 the symbol and elf64_aarch64_copy_indirect_symbol () will have been
6312 called to copy all relevant data from the generic to the concrete
6315 if (h
->root
.type
== bfd_link_hash_indirect
)
6318 if (h
->root
.type
== bfd_link_hash_warning
)
6319 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
6321 info
= (struct bfd_link_info
*) inf
;
6322 htab
= elf64_aarch64_hash_table (info
);
6324 eh
= (struct elf64_aarch64_link_hash_entry
*) h
;
6326 /* Since STT_GNU_IFUNC symbol must go through PLT, we handle it
6327 here if it is defined and referenced in a non-shared object. */
6328 if (h
->type
== STT_GNU_IFUNC
6330 return _bfd_elf_allocate_ifunc_dyn_relocs (info
, h
,
6332 htab
->plt_entry_size
,
6333 htab
->plt_header_size
,
6335 else if (htab
->root
.dynamic_sections_created
&& h
->plt
.refcount
> 0)
6337 /* Make sure this symbol is output as a dynamic symbol.
6338 Undefined weak syms won't yet be marked as dynamic. */
6339 if (h
->dynindx
== -1 && !h
->forced_local
)
6341 if (!bfd_elf_link_record_dynamic_symbol (info
, h
))
6345 if (info
->shared
|| WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, 0, h
))
6347 asection
*s
= htab
->root
.splt
;
6349 /* If this is the first .plt entry, make room for the special
6352 s
->size
+= htab
->plt_header_size
;
6354 h
->plt
.offset
= s
->size
;
6356 /* If this symbol is not defined in a regular file, and we are
6357 not generating a shared library, then set the symbol to this
6358 location in the .plt. This is required to make function
6359 pointers compare as equal between the normal executable and
6360 the shared library. */
6361 if (!info
->shared
&& !h
->def_regular
)
6363 h
->root
.u
.def
.section
= s
;
6364 h
->root
.u
.def
.value
= h
->plt
.offset
;
6367 /* Make room for this entry. For now we only create the
6368 small model PLT entries. We later need to find a way
6369 of relaxing into these from the large model PLT entries. */
6370 s
->size
+= PLT_SMALL_ENTRY_SIZE
;
6372 /* We also need to make an entry in the .got.plt section, which
6373 will be placed in the .got section by the linker script. */
6374 htab
->root
.sgotplt
->size
+= GOT_ENTRY_SIZE
;
6376 /* We also need to make an entry in the .rela.plt section. */
6377 htab
->root
.srelplt
->size
+= RELOC_SIZE (htab
);
6379 /* We need to ensure that all GOT entries that serve the PLT
6380 are consecutive with the special GOT slots [0] [1] and
6381 [2]. Any addtional relocations, such as
6382 R_AARCH64_TLSDESC, must be placed after the PLT related
6383 entries. We abuse the reloc_count such that during
6384 sizing we adjust reloc_count to indicate the number of
6385 PLT related reserved entries. In subsequent phases when
6386 filling in the contents of the reloc entries, PLT related
6387 entries are placed by computing their PLT index (0
6388 .. reloc_count). While other none PLT relocs are placed
6389 at the slot indicated by reloc_count and reloc_count is
6392 htab
->root
.srelplt
->reloc_count
++;
6396 h
->plt
.offset
= (bfd_vma
) - 1;
6402 h
->plt
.offset
= (bfd_vma
) - 1;
6406 eh
->tlsdesc_got_jump_table_offset
= (bfd_vma
) - 1;
6408 if (h
->got
.refcount
> 0)
6411 unsigned got_type
= elf64_aarch64_hash_entry (h
)->got_type
;
6413 h
->got
.offset
= (bfd_vma
) - 1;
6415 dyn
= htab
->root
.dynamic_sections_created
;
6417 /* Make sure this symbol is output as a dynamic symbol.
6418 Undefined weak syms won't yet be marked as dynamic. */
6419 if (dyn
&& h
->dynindx
== -1 && !h
->forced_local
)
6421 if (!bfd_elf_link_record_dynamic_symbol (info
, h
))
6425 if (got_type
== GOT_UNKNOWN
)
6428 else if (got_type
== GOT_NORMAL
)
6430 h
->got
.offset
= htab
->root
.sgot
->size
;
6431 htab
->root
.sgot
->size
+= GOT_ENTRY_SIZE
;
6432 if ((ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
6433 || h
->root
.type
!= bfd_link_hash_undefweak
)
6435 || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn
, 0, h
)))
6437 htab
->root
.srelgot
->size
+= RELOC_SIZE (htab
);
6443 if (got_type
& GOT_TLSDESC_GD
)
6445 eh
->tlsdesc_got_jump_table_offset
=
6446 (htab
->root
.sgotplt
->size
6447 - aarch64_compute_jump_table_size (htab
));
6448 htab
->root
.sgotplt
->size
+= GOT_ENTRY_SIZE
* 2;
6449 h
->got
.offset
= (bfd_vma
) - 2;
6452 if (got_type
& GOT_TLS_GD
)
6454 h
->got
.offset
= htab
->root
.sgot
->size
;
6455 htab
->root
.sgot
->size
+= GOT_ENTRY_SIZE
* 2;
6458 if (got_type
& GOT_TLS_IE
)
6460 h
->got
.offset
= htab
->root
.sgot
->size
;
6461 htab
->root
.sgot
->size
+= GOT_ENTRY_SIZE
;
6464 indx
= h
&& h
->dynindx
!= -1 ? h
->dynindx
: 0;
6465 if ((ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
6466 || h
->root
.type
!= bfd_link_hash_undefweak
)
6469 || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn
, 0, h
)))
6471 if (got_type
& GOT_TLSDESC_GD
)
6473 htab
->root
.srelplt
->size
+= RELOC_SIZE (htab
);
6474 /* Note reloc_count not incremented here! We have
6475 already adjusted reloc_count for this relocation
6478 /* TLSDESC PLT is now needed, but not yet determined. */
6479 htab
->tlsdesc_plt
= (bfd_vma
) - 1;
6482 if (got_type
& GOT_TLS_GD
)
6483 htab
->root
.srelgot
->size
+= RELOC_SIZE (htab
) * 2;
6485 if (got_type
& GOT_TLS_IE
)
6486 htab
->root
.srelgot
->size
+= RELOC_SIZE (htab
);
6492 h
->got
.offset
= (bfd_vma
) - 1;
6495 if (eh
->dyn_relocs
== NULL
)
6498 /* In the shared -Bsymbolic case, discard space allocated for
6499 dynamic pc-relative relocs against symbols which turn out to be
6500 defined in regular objects. For the normal shared case, discard
6501 space for pc-relative relocs that have become local due to symbol
6502 visibility changes. */
6506 /* Relocs that use pc_count are those that appear on a call
6507 insn, or certain REL relocs that can generated via assembly.
6508 We want calls to protected symbols to resolve directly to the
6509 function rather than going via the plt. If people want
6510 function pointer comparisons to work as expected then they
6511 should avoid writing weird assembly. */
6512 if (SYMBOL_CALLS_LOCAL (info
, h
))
6514 struct elf_dyn_relocs
**pp
;
6516 for (pp
= &eh
->dyn_relocs
; (p
= *pp
) != NULL
;)
6518 p
->count
-= p
->pc_count
;
6527 /* Also discard relocs on undefined weak syms with non-default
6529 if (eh
->dyn_relocs
!= NULL
&& h
->root
.type
== bfd_link_hash_undefweak
)
6531 if (ELF_ST_VISIBILITY (h
->other
) != STV_DEFAULT
)
6532 eh
->dyn_relocs
= NULL
;
6534 /* Make sure undefined weak symbols are output as a dynamic
6536 else if (h
->dynindx
== -1
6538 && !bfd_elf_link_record_dynamic_symbol (info
, h
))
6543 else if (ELIMINATE_COPY_RELOCS
)
6545 /* For the non-shared case, discard space for relocs against
6546 symbols which turn out to need copy relocs or are not
6552 || (htab
->root
.dynamic_sections_created
6553 && (h
->root
.type
== bfd_link_hash_undefweak
6554 || h
->root
.type
== bfd_link_hash_undefined
))))
6556 /* Make sure this symbol is output as a dynamic symbol.
6557 Undefined weak syms won't yet be marked as dynamic. */
6558 if (h
->dynindx
== -1
6560 && !bfd_elf_link_record_dynamic_symbol (info
, h
))
6563 /* If that succeeded, we know we'll be keeping all the
6565 if (h
->dynindx
!= -1)
6569 eh
->dyn_relocs
= NULL
;
6574 /* Finally, allocate space. */
6575 for (p
= eh
->dyn_relocs
; p
!= NULL
; p
= p
->next
)
6579 sreloc
= elf_section_data (p
->sec
)->sreloc
;
6581 BFD_ASSERT (sreloc
!= NULL
);
6583 sreloc
->size
+= p
->count
* RELOC_SIZE (htab
);
6590 /* Allocate space in .plt, .got and associated reloc sections for
6591 local dynamic relocs. */
6594 elf_aarch64_allocate_local_dynrelocs (void **slot
, void *inf
)
6596 struct elf_link_hash_entry
*h
6597 = (struct elf_link_hash_entry
*) *slot
;
6599 if (h
->type
!= STT_GNU_IFUNC
6603 || h
->root
.type
!= bfd_link_hash_defined
)
6606 return elf64_aarch64_allocate_dynrelocs (h
, inf
);
6610 /* This is the most important function of all . Innocuosly named
6613 elf64_aarch64_size_dynamic_sections (bfd
*output_bfd ATTRIBUTE_UNUSED
,
6614 struct bfd_link_info
*info
)
6616 struct elf64_aarch64_link_hash_table
*htab
;
6622 htab
= elf64_aarch64_hash_table ((info
));
6623 dynobj
= htab
->root
.dynobj
;
6625 BFD_ASSERT (dynobj
!= NULL
);
6627 if (htab
->root
.dynamic_sections_created
)
6629 if (info
->executable
)
6631 s
= bfd_get_linker_section (dynobj
, ".interp");
6634 s
->size
= sizeof ELF_DYNAMIC_INTERPRETER
;
6635 s
->contents
= (unsigned char *) ELF_DYNAMIC_INTERPRETER
;
6639 /* Set up .got offsets for local syms, and space for local dynamic
6641 for (ibfd
= info
->input_bfds
; ibfd
!= NULL
; ibfd
= ibfd
->link_next
)
6643 struct elf_aarch64_local_symbol
*locals
= NULL
;
6644 Elf_Internal_Shdr
*symtab_hdr
;
6648 if (!is_aarch64_elf (ibfd
))
6651 for (s
= ibfd
->sections
; s
!= NULL
; s
= s
->next
)
6653 struct elf_dyn_relocs
*p
;
6655 for (p
= (struct elf_dyn_relocs
*)
6656 (elf_section_data (s
)->local_dynrel
); p
!= NULL
; p
= p
->next
)
6658 if (!bfd_is_abs_section (p
->sec
)
6659 && bfd_is_abs_section (p
->sec
->output_section
))
6661 /* Input section has been discarded, either because
6662 it is a copy of a linkonce section or due to
6663 linker script /DISCARD/, so we'll be discarding
6666 else if (p
->count
!= 0)
6668 srel
= elf_section_data (p
->sec
)->sreloc
;
6669 srel
->size
+= p
->count
* RELOC_SIZE (htab
);
6670 if ((p
->sec
->output_section
->flags
& SEC_READONLY
) != 0)
6671 info
->flags
|= DF_TEXTREL
;
6676 locals
= elf64_aarch64_locals (ibfd
);
6680 symtab_hdr
= &elf_symtab_hdr (ibfd
);
6681 srel
= htab
->root
.srelgot
;
6682 for (i
= 0; i
< symtab_hdr
->sh_info
; i
++)
6684 locals
[i
].got_offset
= (bfd_vma
) - 1;
6685 locals
[i
].tlsdesc_got_jump_table_offset
= (bfd_vma
) - 1;
6686 if (locals
[i
].got_refcount
> 0)
6688 unsigned got_type
= locals
[i
].got_type
;
6689 if (got_type
& GOT_TLSDESC_GD
)
6691 locals
[i
].tlsdesc_got_jump_table_offset
=
6692 (htab
->root
.sgotplt
->size
6693 - aarch64_compute_jump_table_size (htab
));
6694 htab
->root
.sgotplt
->size
+= GOT_ENTRY_SIZE
* 2;
6695 locals
[i
].got_offset
= (bfd_vma
) - 2;
6698 if (got_type
& GOT_TLS_GD
)
6700 locals
[i
].got_offset
= htab
->root
.sgot
->size
;
6701 htab
->root
.sgot
->size
+= GOT_ENTRY_SIZE
* 2;
6704 if (got_type
& GOT_TLS_IE
)
6706 locals
[i
].got_offset
= htab
->root
.sgot
->size
;
6707 htab
->root
.sgot
->size
+= GOT_ENTRY_SIZE
;
6710 if (got_type
== GOT_UNKNOWN
)
6714 if (got_type
== GOT_NORMAL
)
6720 if (got_type
& GOT_TLSDESC_GD
)
6722 htab
->root
.srelplt
->size
+= RELOC_SIZE (htab
);
6723 /* Note RELOC_COUNT not incremented here! */
6724 htab
->tlsdesc_plt
= (bfd_vma
) - 1;
6727 if (got_type
& GOT_TLS_GD
)
6728 htab
->root
.srelgot
->size
+= RELOC_SIZE (htab
) * 2;
6730 if (got_type
& GOT_TLS_IE
)
6731 htab
->root
.srelgot
->size
+= RELOC_SIZE (htab
);
6736 locals
[i
].got_refcount
= (bfd_vma
) - 1;
6742 /* Allocate global sym .plt and .got entries, and space for global
6743 sym dynamic relocs. */
6744 elf_link_hash_traverse (&htab
->root
, elf64_aarch64_allocate_dynrelocs
,
6747 /* Allocate .plt and .got entries, and space for local symbols. */
6748 htab_traverse (htab
->loc_hash_table
,
6749 elf_aarch64_allocate_local_dynrelocs
,
6752 /* For every jump slot reserved in the sgotplt, reloc_count is
6753 incremented. However, when we reserve space for TLS descriptors,
6754 it's not incremented, so in order to compute the space reserved
6755 for them, it suffices to multiply the reloc count by the jump
6758 if (htab
->root
.srelplt
)
6760 htab
->sgotplt_jump_table_size
= aarch64_compute_jump_table_size (htab
);
6761 htab
->next_irelative_index
= htab
->root
.srelplt
->reloc_count
- 1;
6763 else if (htab
->root
.irelplt
)
6764 htab
->next_irelative_index
= htab
->root
.irelplt
->reloc_count
- 1;
6766 if (htab
->tlsdesc_plt
)
6768 if (htab
->root
.splt
->size
== 0)
6769 htab
->root
.splt
->size
+= PLT_ENTRY_SIZE
;
6771 htab
->tlsdesc_plt
= htab
->root
.splt
->size
;
6772 htab
->root
.splt
->size
+= PLT_TLSDESC_ENTRY_SIZE
;
6774 /* If we're not using lazy TLS relocations, don't generate the
6775 GOT entry required. */
6776 if (!(info
->flags
& DF_BIND_NOW
))
6778 htab
->dt_tlsdesc_got
= htab
->root
.sgot
->size
;
6779 htab
->root
.sgot
->size
+= GOT_ENTRY_SIZE
;
6783 /* We now have determined the sizes of the various dynamic sections.
6784 Allocate memory for them. */
6786 for (s
= dynobj
->sections
; s
!= NULL
; s
= s
->next
)
6788 if ((s
->flags
& SEC_LINKER_CREATED
) == 0)
6791 if (s
== htab
->root
.splt
6792 || s
== htab
->root
.sgot
6793 || s
== htab
->root
.sgotplt
6794 || s
== htab
->root
.iplt
6795 || s
== htab
->root
.igotplt
|| s
== htab
->sdynbss
)
6797 /* Strip this section if we don't need it; see the
6800 else if (CONST_STRNEQ (bfd_get_section_name (dynobj
, s
), ".rela"))
6802 if (s
->size
!= 0 && s
!= htab
->root
.srelplt
)
6805 /* We use the reloc_count field as a counter if we need
6806 to copy relocs into the output file. */
6807 if (s
!= htab
->root
.srelplt
)
6812 /* It's not one of our sections, so don't allocate space. */
6818 /* If we don't need this section, strip it from the
6819 output file. This is mostly to handle .rela.bss and
6820 .rela.plt. We must create both sections in
6821 create_dynamic_sections, because they must be created
6822 before the linker maps input sections to output
6823 sections. The linker does that before
6824 adjust_dynamic_symbol is called, and it is that
6825 function which decides whether anything needs to go
6826 into these sections. */
6828 s
->flags
|= SEC_EXCLUDE
;
6832 if ((s
->flags
& SEC_HAS_CONTENTS
) == 0)
6835 /* Allocate memory for the section contents. We use bfd_zalloc
6836 here in case unused entries are not reclaimed before the
6837 section's contents are written out. This should not happen,
6838 but this way if it does, we get a R_AARCH64_NONE reloc instead
6840 s
->contents
= (bfd_byte
*) bfd_zalloc (dynobj
, s
->size
);
6841 if (s
->contents
== NULL
)
6845 if (htab
->root
.dynamic_sections_created
)
6847 /* Add some entries to the .dynamic section. We fill in the
6848 values later, in elf64_aarch64_finish_dynamic_sections, but we
6849 must add the entries now so that we get the correct size for
6850 the .dynamic section. The DT_DEBUG entry is filled in by the
6851 dynamic linker and used by the debugger. */
6852 #define add_dynamic_entry(TAG, VAL) \
6853 _bfd_elf_add_dynamic_entry (info, TAG, VAL)
6855 if (info
->executable
)
6857 if (!add_dynamic_entry (DT_DEBUG
, 0))
6861 if (htab
->root
.splt
->size
!= 0)
6863 if (!add_dynamic_entry (DT_PLTGOT
, 0)
6864 || !add_dynamic_entry (DT_PLTRELSZ
, 0)
6865 || !add_dynamic_entry (DT_PLTREL
, DT_RELA
)
6866 || !add_dynamic_entry (DT_JMPREL
, 0))
6869 if (htab
->tlsdesc_plt
6870 && (!add_dynamic_entry (DT_TLSDESC_PLT
, 0)
6871 || !add_dynamic_entry (DT_TLSDESC_GOT
, 0)))
6877 if (!add_dynamic_entry (DT_RELA
, 0)
6878 || !add_dynamic_entry (DT_RELASZ
, 0)
6879 || !add_dynamic_entry (DT_RELAENT
, RELOC_SIZE (htab
)))
6882 /* If any dynamic relocs apply to a read-only section,
6883 then we need a DT_TEXTREL entry. */
6884 if ((info
->flags
& DF_TEXTREL
) != 0)
6886 if (!add_dynamic_entry (DT_TEXTREL
, 0))
6891 #undef add_dynamic_entry
6899 elf64_aarch64_update_plt_entry (bfd
*output_bfd
,
6900 unsigned int r_type
,
6901 bfd_byte
*plt_entry
, bfd_vma value
)
6903 reloc_howto_type
*howto
;
6904 howto
= elf64_aarch64_howto_from_type (r_type
);
6905 bfd_elf_aarch64_put_addend (output_bfd
, plt_entry
, howto
, value
);
6909 elf64_aarch64_create_small_pltn_entry (struct elf_link_hash_entry
*h
,
6910 struct elf64_aarch64_link_hash_table
6911 *htab
, bfd
*output_bfd
,
6912 struct bfd_link_info
*info
)
6914 bfd_byte
*plt_entry
;
6917 bfd_vma gotplt_entry_address
;
6918 bfd_vma plt_entry_address
;
6919 Elf_Internal_Rela rela
;
6921 asection
*plt
, *gotplt
, *relplt
;
6923 /* When building a static executable, use .iplt, .igot.plt and
6924 .rela.iplt sections for STT_GNU_IFUNC symbols. */
6925 if (htab
->root
.splt
!= NULL
)
6927 plt
= htab
->root
.splt
;
6928 gotplt
= htab
->root
.sgotplt
;
6929 relplt
= htab
->root
.srelplt
;
6933 plt
= htab
->root
.iplt
;
6934 gotplt
= htab
->root
.igotplt
;
6935 relplt
= htab
->root
.irelplt
;
6938 /* Get the index in the procedure linkage table which
6939 corresponds to this symbol. This is the index of this symbol
6940 in all the symbols for which we are making plt entries. The
6941 first entry in the procedure linkage table is reserved.
6943 Get the offset into the .got table of the entry that
6944 corresponds to this function. Each .got entry is GOT_ENTRY_SIZE
6945 bytes. The first three are reserved for the dynamic linker.
6947 For static executables, we don't reserve anything. */
6949 if (plt
== htab
->root
.splt
)
6951 got_offset
= (h
->plt
.offset
- htab
->plt_header_size
) / htab
->plt_entry_size
;
6952 got_offset
= (got_offset
+ 3) * GOT_ENTRY_SIZE
;
6956 got_offset
= h
->plt
.offset
/ htab
->plt_entry_size
;
6957 got_offset
= got_offset
* GOT_ENTRY_SIZE
;
6960 plt_entry
= plt
->contents
+ h
->plt
.offset
;
6961 plt_entry_address
= plt
->output_section
->vma
6962 + plt
->output_section
->output_offset
+ h
->plt
.offset
;
6963 gotplt_entry_address
= gotplt
->output_section
->vma
+
6964 gotplt
->output_offset
+ got_offset
;
6966 /* Copy in the boiler-plate for the PLTn entry. */
6967 memcpy (plt_entry
, elf64_aarch64_small_plt_entry
, PLT_SMALL_ENTRY_SIZE
);
6969 /* Fill in the top 21 bits for this: ADRP x16, PLT_GOT + n * 8.
6970 ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff */
6971 elf64_aarch64_update_plt_entry (output_bfd
, R_AARCH64_ADR_PREL_PG_HI21
,
6973 PG (gotplt_entry_address
) -
6974 PG (plt_entry_address
));
6976 /* Fill in the lo12 bits for the load from the pltgot. */
6977 elf64_aarch64_update_plt_entry (output_bfd
, R_AARCH64_LDST64_ABS_LO12_NC
,
6979 PG_OFFSET (gotplt_entry_address
));
6981 /* Fill in the the lo12 bits for the add from the pltgot entry. */
6982 elf64_aarch64_update_plt_entry (output_bfd
, R_AARCH64_ADD_ABS_LO12_NC
,
6984 PG_OFFSET (gotplt_entry_address
));
6986 /* All the GOTPLT Entries are essentially initialized to PLT0. */
6987 bfd_put_64 (output_bfd
,
6988 plt
->output_section
->vma
+ plt
->output_offset
,
6989 gotplt
->contents
+ got_offset
);
6991 rela
.r_offset
= gotplt_entry_address
;
6993 if (h
->dynindx
== -1
6994 || ((info
->executable
6995 || ELF_ST_VISIBILITY (h
->other
) != STV_DEFAULT
)
6997 && h
->type
== STT_GNU_IFUNC
))
6999 /* If an STT_GNU_IFUNC symbol is locally defined, generate
7000 R_AARCH64_IRELATIVE instead of R_AARCH64_JUMP_SLOT. */
7001 rela
.r_info
= ELF64_R_INFO (0, R_AARCH64_IRELATIVE
);
7002 rela
.r_addend
= (h
->root
.u
.def
.value
7003 + h
->root
.u
.def
.section
->output_section
->vma
7004 + h
->root
.u
.def
.section
->output_offset
);
7005 /* R_AARCH64_IRELATIVE comes last. */
7006 plt_index
= htab
->next_irelative_index
--;
7010 /* Fill in the entry in the .rela.plt section. */
7011 rela
.r_info
= ELF64_R_INFO (h
->dynindx
, R_AARCH64_JUMP_SLOT
);
7013 plt_index
= htab
->next_jump_slot_index
++;
7016 /* Compute the relocation entry to used based on PLT index and do
7017 not adjust reloc_count. The reloc_count has already been adjusted
7018 to account for this entry. */
7019 loc
= relplt
->contents
+ plt_index
* RELOC_SIZE (htab
);
7020 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
7023 /* Size sections even though they're not dynamic. We use it to setup
7024 _TLS_MODULE_BASE_, if needed. */
7027 elf64_aarch64_always_size_sections (bfd
*output_bfd
,
7028 struct bfd_link_info
*info
)
7032 if (info
->relocatable
)
7035 tls_sec
= elf_hash_table (info
)->tls_sec
;
7039 struct elf_link_hash_entry
*tlsbase
;
7041 tlsbase
= elf_link_hash_lookup (elf_hash_table (info
),
7042 "_TLS_MODULE_BASE_", TRUE
, TRUE
, FALSE
);
7046 struct bfd_link_hash_entry
*h
= NULL
;
7047 const struct elf_backend_data
*bed
=
7048 get_elf_backend_data (output_bfd
);
7050 if (!(_bfd_generic_link_add_one_symbol
7051 (info
, output_bfd
, "_TLS_MODULE_BASE_", BSF_LOCAL
,
7052 tls_sec
, 0, NULL
, FALSE
, bed
->collect
, &h
)))
7055 tlsbase
->type
= STT_TLS
;
7056 tlsbase
= (struct elf_link_hash_entry
*) h
;
7057 tlsbase
->def_regular
= 1;
7058 tlsbase
->other
= STV_HIDDEN
;
7059 (*bed
->elf_backend_hide_symbol
) (info
, tlsbase
, TRUE
);
7066 /* Finish up dynamic symbol handling. We set the contents of various
7067 dynamic sections here. */
7069 elf64_aarch64_finish_dynamic_symbol (bfd
*output_bfd
,
7070 struct bfd_link_info
*info
,
7071 struct elf_link_hash_entry
*h
,
7072 Elf_Internal_Sym
*sym
)
7074 struct elf64_aarch64_link_hash_table
*htab
;
7075 htab
= elf64_aarch64_hash_table (info
);
7077 if (h
->plt
.offset
!= (bfd_vma
) - 1)
7079 asection
*plt
, *gotplt
, *relplt
;
7081 /* This symbol has an entry in the procedure linkage table. Set
7084 /* When building a static executable, use .iplt, .igot.plt and
7085 .rela.iplt sections for STT_GNU_IFUNC symbols. */
7086 if (htab
->root
.splt
!= NULL
)
7088 plt
= htab
->root
.splt
;
7089 gotplt
= htab
->root
.sgotplt
;
7090 relplt
= htab
->root
.srelplt
;
7094 plt
= htab
->root
.iplt
;
7095 gotplt
= htab
->root
.igotplt
;
7096 relplt
= htab
->root
.irelplt
;
7099 /* This symbol has an entry in the procedure linkage table. Set
7101 if ((h
->dynindx
== -1
7102 && !((h
->forced_local
|| info
->executable
)
7104 && h
->type
== STT_GNU_IFUNC
))
7110 elf64_aarch64_create_small_pltn_entry (h
, htab
, output_bfd
, info
);
7111 if (!h
->def_regular
)
7113 /* Mark the symbol as undefined, rather than as defined in
7114 the .plt section. Leave the value alone. This is a clue
7115 for the dynamic linker, to make function pointer
7116 comparisons work between an application and shared
7118 sym
->st_shndx
= SHN_UNDEF
;
7122 if (h
->got
.offset
!= (bfd_vma
) - 1
7123 && elf64_aarch64_hash_entry (h
)->got_type
== GOT_NORMAL
)
7125 Elf_Internal_Rela rela
;
7128 /* This symbol has an entry in the global offset table. Set it
7130 if (htab
->root
.sgot
== NULL
|| htab
->root
.srelgot
== NULL
)
7133 rela
.r_offset
= (htab
->root
.sgot
->output_section
->vma
7134 + htab
->root
.sgot
->output_offset
7135 + (h
->got
.offset
& ~(bfd_vma
) 1));
7137 if (info
->shared
&& SYMBOL_REFERENCES_LOCAL (info
, h
))
7139 if (!h
->def_regular
)
7142 BFD_ASSERT ((h
->got
.offset
& 1) != 0);
7143 rela
.r_info
= ELF64_R_INFO (0, R_AARCH64_RELATIVE
);
7144 rela
.r_addend
= (h
->root
.u
.def
.value
7145 + h
->root
.u
.def
.section
->output_section
->vma
7146 + h
->root
.u
.def
.section
->output_offset
);
7150 BFD_ASSERT ((h
->got
.offset
& 1) == 0);
7151 bfd_put_64 (output_bfd
, (bfd_vma
) 0,
7152 htab
->root
.sgot
->contents
+ h
->got
.offset
);
7153 rela
.r_info
= ELF64_R_INFO (h
->dynindx
, R_AARCH64_GLOB_DAT
);
7157 loc
= htab
->root
.srelgot
->contents
;
7158 loc
+= htab
->root
.srelgot
->reloc_count
++ * RELOC_SIZE (htab
);
7159 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
7164 Elf_Internal_Rela rela
;
7167 /* This symbol needs a copy reloc. Set it up. */
7169 if (h
->dynindx
== -1
7170 || (h
->root
.type
!= bfd_link_hash_defined
7171 && h
->root
.type
!= bfd_link_hash_defweak
)
7172 || htab
->srelbss
== NULL
)
7175 rela
.r_offset
= (h
->root
.u
.def
.value
7176 + h
->root
.u
.def
.section
->output_section
->vma
7177 + h
->root
.u
.def
.section
->output_offset
);
7178 rela
.r_info
= ELF64_R_INFO (h
->dynindx
, R_AARCH64_COPY
);
7180 loc
= htab
->srelbss
->contents
;
7181 loc
+= htab
->srelbss
->reloc_count
++ * RELOC_SIZE (htab
);
7182 bfd_elf64_swap_reloca_out (output_bfd
, &rela
, loc
);
7185 /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute. SYM may
7186 be NULL for local symbols. */
7188 && (h
== elf_hash_table (info
)->hdynamic
7189 || h
== elf_hash_table (info
)->hgot
))
7190 sym
->st_shndx
= SHN_ABS
;
7195 /* Finish up local dynamic symbol handling. We set the contents of
7196 various dynamic sections here. */
7199 elf_aarch64_finish_local_dynamic_symbol (void **slot
, void *inf
)
7201 struct elf_link_hash_entry
*h
7202 = (struct elf_link_hash_entry
*) *slot
;
7203 struct bfd_link_info
*info
7204 = (struct bfd_link_info
*) inf
;
7206 return elf64_aarch64_finish_dynamic_symbol (info
->output_bfd
,
7211 elf64_aarch64_init_small_plt0_entry (bfd
*output_bfd ATTRIBUTE_UNUSED
,
7212 struct elf64_aarch64_link_hash_table
7215 /* Fill in PLT0. Fixme:RR Note this doesn't distinguish between
7216 small and large plts and at the minute just generates
7219 /* PLT0 of the small PLT looks like this -
7220 stp x16, x30, [sp, #-16]! // Save the reloc and lr on stack.
7221 adrp x16, PLT_GOT + 16 // Get the page base of the GOTPLT
7222 ldr x17, [x16, #:lo12:PLT_GOT+16] // Load the address of the
7224 add x16, x16, #:lo12:PLT_GOT+16 // Load the lo12 bits of the
7225 // GOTPLT entry for this.
7228 bfd_vma plt_got_base
;
7232 memcpy (htab
->root
.splt
->contents
, elf64_aarch64_small_plt0_entry
,
7234 elf_section_data (htab
->root
.splt
->output_section
)->this_hdr
.sh_entsize
=
7237 plt_got_base
= (htab
->root
.sgotplt
->output_section
->vma
7238 + htab
->root
.sgotplt
->output_offset
);
7240 plt_base
= htab
->root
.splt
->output_section
->vma
+
7241 htab
->root
.splt
->output_section
->output_offset
;
7243 /* Fill in the top 21 bits for this: ADRP x16, PLT_GOT + n * 8.
7244 ADRP: ((PG(S+A)-PG(P)) >> 12) & 0x1fffff */
7245 elf64_aarch64_update_plt_entry (output_bfd
, R_AARCH64_ADR_PREL_PG_HI21
,
7246 htab
->root
.splt
->contents
+ 4,
7247 PG (plt_got_base
+ 16) - PG (plt_base
+ 4));
7249 elf64_aarch64_update_plt_entry (output_bfd
, R_AARCH64_LDST64_ABS_LO12_NC
,
7250 htab
->root
.splt
->contents
+ 8,
7251 PG_OFFSET (plt_got_base
+ 16));
7253 elf64_aarch64_update_plt_entry (output_bfd
, R_AARCH64_ADD_ABS_LO12_NC
,
7254 htab
->root
.splt
->contents
+ 12,
7255 PG_OFFSET (plt_got_base
+ 16));
7259 elf64_aarch64_finish_dynamic_sections (bfd
*output_bfd
,
7260 struct bfd_link_info
*info
)
7262 struct elf64_aarch64_link_hash_table
*htab
;
7266 htab
= elf64_aarch64_hash_table (info
);
7267 dynobj
= htab
->root
.dynobj
;
7268 sdyn
= bfd_get_linker_section (dynobj
, ".dynamic");
7270 if (htab
->root
.dynamic_sections_created
)
7272 Elf64_External_Dyn
*dyncon
, *dynconend
;
7274 if (sdyn
== NULL
|| htab
->root
.sgot
== NULL
)
7277 dyncon
= (Elf64_External_Dyn
*) sdyn
->contents
;
7278 dynconend
= (Elf64_External_Dyn
*) (sdyn
->contents
+ sdyn
->size
);
7279 for (; dyncon
< dynconend
; dyncon
++)
7281 Elf_Internal_Dyn dyn
;
7284 bfd_elf64_swap_dyn_in (dynobj
, dyncon
, &dyn
);
7292 s
= htab
->root
.sgotplt
;
7293 dyn
.d_un
.d_ptr
= s
->output_section
->vma
+ s
->output_offset
;
7297 dyn
.d_un
.d_ptr
= htab
->root
.srelplt
->output_section
->vma
;
7301 s
= htab
->root
.srelplt
->output_section
;
7302 dyn
.d_un
.d_val
= s
->size
;
7306 /* The procedure linkage table relocs (DT_JMPREL) should
7307 not be included in the overall relocs (DT_RELA).
7308 Therefore, we override the DT_RELASZ entry here to
7309 make it not include the JMPREL relocs. Since the
7310 linker script arranges for .rela.plt to follow all
7311 other relocation sections, we don't have to worry
7312 about changing the DT_RELA entry. */
7313 if (htab
->root
.srelplt
!= NULL
)
7315 s
= htab
->root
.srelplt
->output_section
;
7316 dyn
.d_un
.d_val
-= s
->size
;
7320 case DT_TLSDESC_PLT
:
7321 s
= htab
->root
.splt
;
7322 dyn
.d_un
.d_ptr
= s
->output_section
->vma
+ s
->output_offset
7323 + htab
->tlsdesc_plt
;
7326 case DT_TLSDESC_GOT
:
7327 s
= htab
->root
.sgot
;
7328 dyn
.d_un
.d_ptr
= s
->output_section
->vma
+ s
->output_offset
7329 + htab
->dt_tlsdesc_got
;
7333 bfd_elf64_swap_dyn_out (output_bfd
, &dyn
, dyncon
);
7338 /* Fill in the special first entry in the procedure linkage table. */
7339 if (htab
->root
.splt
&& htab
->root
.splt
->size
> 0)
7341 elf64_aarch64_init_small_plt0_entry (output_bfd
, htab
);
7343 elf_section_data (htab
->root
.splt
->output_section
)->
7344 this_hdr
.sh_entsize
= htab
->plt_entry_size
;
7347 if (htab
->tlsdesc_plt
)
7349 bfd_put_64 (output_bfd
, (bfd_vma
) 0,
7350 htab
->root
.sgot
->contents
+ htab
->dt_tlsdesc_got
);
7352 memcpy (htab
->root
.splt
->contents
+ htab
->tlsdesc_plt
,
7353 elf64_aarch64_tlsdesc_small_plt_entry
,
7354 sizeof (elf64_aarch64_tlsdesc_small_plt_entry
));
7357 bfd_vma adrp1_addr
=
7358 htab
->root
.splt
->output_section
->vma
7359 + htab
->root
.splt
->output_offset
+ htab
->tlsdesc_plt
+ 4;
7361 bfd_vma adrp2_addr
=
7362 htab
->root
.splt
->output_section
->vma
7363 + htab
->root
.splt
->output_offset
+ htab
->tlsdesc_plt
+ 8;
7366 htab
->root
.sgot
->output_section
->vma
7367 + htab
->root
.sgot
->output_offset
;
7369 bfd_vma pltgot_addr
=
7370 htab
->root
.sgotplt
->output_section
->vma
7371 + htab
->root
.sgotplt
->output_offset
;
7373 bfd_vma dt_tlsdesc_got
= got_addr
+ htab
->dt_tlsdesc_got
;
7376 /* adrp x2, DT_TLSDESC_GOT */
7377 opcode
= bfd_get_32 (output_bfd
,
7378 htab
->root
.splt
->contents
7379 + htab
->tlsdesc_plt
+ 4);
7380 opcode
= reencode_adr_imm
7381 (opcode
, (PG (dt_tlsdesc_got
) - PG (adrp1_addr
)) >> 12);
7382 bfd_put_32 (output_bfd
, opcode
,
7383 htab
->root
.splt
->contents
+ htab
->tlsdesc_plt
+ 4);
7386 opcode
= bfd_get_32 (output_bfd
,
7387 htab
->root
.splt
->contents
7388 + htab
->tlsdesc_plt
+ 8);
7389 opcode
= reencode_adr_imm
7390 (opcode
, (PG (pltgot_addr
) - PG (adrp2_addr
)) >> 12);
7391 bfd_put_32 (output_bfd
, opcode
,
7392 htab
->root
.splt
->contents
+ htab
->tlsdesc_plt
+ 8);
7394 /* ldr x2, [x2, #0] */
7395 opcode
= bfd_get_32 (output_bfd
,
7396 htab
->root
.splt
->contents
7397 + htab
->tlsdesc_plt
+ 12);
7398 opcode
= reencode_ldst_pos_imm (opcode
,
7399 PG_OFFSET (dt_tlsdesc_got
) >> 3);
7400 bfd_put_32 (output_bfd
, opcode
,
7401 htab
->root
.splt
->contents
+ htab
->tlsdesc_plt
+ 12);
7404 opcode
= bfd_get_32 (output_bfd
,
7405 htab
->root
.splt
->contents
7406 + htab
->tlsdesc_plt
+ 16);
7407 opcode
= reencode_add_imm (opcode
, PG_OFFSET (pltgot_addr
));
7408 bfd_put_32 (output_bfd
, opcode
,
7409 htab
->root
.splt
->contents
+ htab
->tlsdesc_plt
+ 16);
7414 if (htab
->root
.sgotplt
)
7416 if (bfd_is_abs_section (htab
->root
.sgotplt
->output_section
))
7418 (*_bfd_error_handler
)
7419 (_("discarded output section: `%A'"), htab
->root
.sgotplt
);
7423 /* Fill in the first three entries in the global offset table. */
7424 if (htab
->root
.sgotplt
->size
> 0)
7426 /* Set the first entry in the global offset table to the address of
7427 the dynamic section. */
7429 bfd_put_64 (output_bfd
, (bfd_vma
) 0,
7430 htab
->root
.sgotplt
->contents
);
7432 bfd_put_64 (output_bfd
,
7433 sdyn
->output_section
->vma
+ sdyn
->output_offset
,
7434 htab
->root
.sgotplt
->contents
);
7435 /* Write GOT[1] and GOT[2], needed for the dynamic linker. */
7436 bfd_put_64 (output_bfd
,
7438 htab
->root
.sgotplt
->contents
+ GOT_ENTRY_SIZE
);
7439 bfd_put_64 (output_bfd
,
7441 htab
->root
.sgotplt
->contents
+ GOT_ENTRY_SIZE
* 2);
7444 elf_section_data (htab
->root
.sgotplt
->output_section
)->
7445 this_hdr
.sh_entsize
= GOT_ENTRY_SIZE
;
7448 if (htab
->root
.sgot
&& htab
->root
.sgot
->size
> 0)
7449 elf_section_data (htab
->root
.sgot
->output_section
)->this_hdr
.sh_entsize
7452 /* Fill PLT and GOT entries for local STT_GNU_IFUNC symbols. */
7453 htab_traverse (htab
->loc_hash_table
,
7454 elf_aarch64_finish_local_dynamic_symbol
,
7460 /* Return address for Ith PLT stub in section PLT, for relocation REL
7461 or (bfd_vma) -1 if it should not be included. */
7464 elf64_aarch64_plt_sym_val (bfd_vma i
, const asection
*plt
,
7465 const arelent
*rel ATTRIBUTE_UNUSED
)
7467 return plt
->vma
+ PLT_ENTRY_SIZE
+ i
* PLT_SMALL_ENTRY_SIZE
;
7470 /* Hook called by the linker routine which adds symbols from an object
7474 elf64_aarch64_add_symbol_hook (bfd
*abfd
, struct bfd_link_info
*info
,
7475 Elf_Internal_Sym
*sym
,
7476 const char **namep ATTRIBUTE_UNUSED
,
7477 flagword
*flagsp ATTRIBUTE_UNUSED
,
7478 asection
**secp ATTRIBUTE_UNUSED
,
7479 bfd_vma
*valp ATTRIBUTE_UNUSED
)
7481 if ((abfd
->flags
& DYNAMIC
) == 0
7482 && (ELF_ST_TYPE (sym
->st_info
) == STT_GNU_IFUNC
7483 || ELF_ST_BIND (sym
->st_info
) == STB_GNU_UNIQUE
))
7484 elf_tdata (info
->output_bfd
)->has_gnu_symbols
= TRUE
;
7489 /* We use this so we can override certain functions
7490 (though currently we don't). */
7492 const struct elf_size_info elf64_aarch64_size_info
=
7494 sizeof (Elf64_External_Ehdr
),
7495 sizeof (Elf64_External_Phdr
),
7496 sizeof (Elf64_External_Shdr
),
7497 sizeof (Elf64_External_Rel
),
7498 sizeof (Elf64_External_Rela
),
7499 sizeof (Elf64_External_Sym
),
7500 sizeof (Elf64_External_Dyn
),
7501 sizeof (Elf_External_Note
),
7502 4, /* Hash table entry size. */
7503 1, /* Internal relocs per external relocs. */
7504 64, /* Arch size. */
7505 3, /* Log_file_align. */
7506 ELFCLASS64
, EV_CURRENT
,
7507 bfd_elf64_write_out_phdrs
,
7508 bfd_elf64_write_shdrs_and_ehdr
,
7509 bfd_elf64_checksum_contents
,
7510 bfd_elf64_write_relocs
,
7511 bfd_elf64_swap_symbol_in
,
7512 bfd_elf64_swap_symbol_out
,
7513 bfd_elf64_slurp_reloc_table
,
7514 bfd_elf64_slurp_symbol_table
,
7515 bfd_elf64_swap_dyn_in
,
7516 bfd_elf64_swap_dyn_out
,
7517 bfd_elf64_swap_reloc_in
,
7518 bfd_elf64_swap_reloc_out
,
7519 bfd_elf64_swap_reloca_in
,
7520 bfd_elf64_swap_reloca_out
7523 #define ELF_ARCH bfd_arch_aarch64
7524 #define ELF_MACHINE_CODE EM_AARCH64
7525 #define ELF_MAXPAGESIZE 0x10000
7526 #define ELF_MINPAGESIZE 0x1000
7527 #define ELF_COMMONPAGESIZE 0x1000
7529 #define bfd_elf64_close_and_cleanup \
7530 elf64_aarch64_close_and_cleanup
7532 #define bfd_elf64_bfd_copy_private_bfd_data \
7533 elf64_aarch64_copy_private_bfd_data
7535 #define bfd_elf64_bfd_free_cached_info \
7536 elf64_aarch64_bfd_free_cached_info
7538 #define bfd_elf64_bfd_is_target_special_symbol \
7539 elf64_aarch64_is_target_special_symbol
7541 #define bfd_elf64_bfd_link_hash_table_create \
7542 elf64_aarch64_link_hash_table_create
7544 #define bfd_elf64_bfd_link_hash_table_free \
7545 elf64_aarch64_hash_table_free
7547 #define bfd_elf64_bfd_merge_private_bfd_data \
7548 elf64_aarch64_merge_private_bfd_data
7550 #define bfd_elf64_bfd_print_private_bfd_data \
7551 elf64_aarch64_print_private_bfd_data
7553 #define bfd_elf64_bfd_reloc_type_lookup \
7554 elf64_aarch64_reloc_type_lookup
7556 #define bfd_elf64_bfd_reloc_name_lookup \
7557 elf64_aarch64_reloc_name_lookup
7559 #define bfd_elf64_bfd_set_private_flags \
7560 elf64_aarch64_set_private_flags
7562 #define bfd_elf64_find_inliner_info \
7563 elf64_aarch64_find_inliner_info
7565 #define bfd_elf64_find_nearest_line \
7566 elf64_aarch64_find_nearest_line
7568 #define bfd_elf64_mkobject \
7569 elf64_aarch64_mkobject
7571 #define bfd_elf64_new_section_hook \
7572 elf64_aarch64_new_section_hook
7574 #define elf_backend_adjust_dynamic_symbol \
7575 elf64_aarch64_adjust_dynamic_symbol
7577 #define elf_backend_always_size_sections \
7578 elf64_aarch64_always_size_sections
7580 #define elf_backend_check_relocs \
7581 elf64_aarch64_check_relocs
7583 #define elf_backend_copy_indirect_symbol \
7584 elf64_aarch64_copy_indirect_symbol
7586 /* Create .dynbss, and .rela.bss sections in DYNOBJ, and set up shortcuts
7587 to them in our hash. */
7588 #define elf_backend_create_dynamic_sections \
7589 elf64_aarch64_create_dynamic_sections
7591 #define elf_backend_init_index_section \
7592 _bfd_elf_init_2_index_sections
7594 #define elf_backend_finish_dynamic_sections \
7595 elf64_aarch64_finish_dynamic_sections
7597 #define elf_backend_finish_dynamic_symbol \
7598 elf64_aarch64_finish_dynamic_symbol
7600 #define elf_backend_gc_sweep_hook \
7601 elf64_aarch64_gc_sweep_hook
7603 #define elf_backend_object_p \
7604 elf64_aarch64_object_p
7606 #define elf_backend_output_arch_local_syms \
7607 elf64_aarch64_output_arch_local_syms
7609 #define elf_backend_plt_sym_val \
7610 elf64_aarch64_plt_sym_val
7612 #define elf_backend_post_process_headers \
7613 elf64_aarch64_post_process_headers
7615 #define elf_backend_relocate_section \
7616 elf64_aarch64_relocate_section
7618 #define elf_backend_reloc_type_class \
7619 elf64_aarch64_reloc_type_class
7621 #define elf_backend_section_flags \
7622 elf64_aarch64_section_flags
7624 #define elf_backend_section_from_shdr \
7625 elf64_aarch64_section_from_shdr
7627 #define elf_backend_size_dynamic_sections \
7628 elf64_aarch64_size_dynamic_sections
7630 #define elf_backend_size_info \
7631 elf64_aarch64_size_info
7633 #define elf_backend_add_symbol_hook \
7634 elf64_aarch64_add_symbol_hook
7636 #define elf_backend_can_refcount 1
7637 #define elf_backend_can_gc_sections 1
7638 #define elf_backend_plt_readonly 1
7639 #define elf_backend_want_got_plt 1
7640 #define elf_backend_want_plt_sym 0
7641 #define elf_backend_may_use_rel_p 0
7642 #define elf_backend_may_use_rela_p 1
7643 #define elf_backend_default_use_rela_p 1
7644 #define elf_backend_got_header_size (GOT_ENTRY_SIZE * 3)
7645 #define elf_backend_default_execstack 0
7647 #undef elf_backend_obj_attrs_section
7648 #define elf_backend_obj_attrs_section ".ARM.attributes"
7650 #include "elf64-target.h"