1//===- AArch64.cpp --------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "InputFiles.h"
10#include "OutputSections.h"
11#include "RelocScan.h"
12#include "Symbols.h"
13#include "SyntheticSections.h"
14#include "Target.h"
15#include "TargetImpl.h"
16#include "llvm/BinaryFormat/ELF.h"
17#include "llvm/Support/Endian.h"
18
19using namespace llvm;
20using namespace llvm::support::endian;
21using namespace llvm::ELF;
22using namespace lld;
23using namespace lld::elf;
24
25// Page(Expr) is the page address of the expression Expr, defined
26// as (Expr & ~0xFFF). (This applies even if the machine page size
27// supported by the platform has a different value.)
28uint64_t elf::getAArch64Page(uint64_t expr) {
29 return expr & ~static_cast<uint64_t>(0xFFF);
30}
31
32// A BTI landing pad is a valid target for an indirect branch when the Branch
33// Target Identification has been enabled. As linker generated branches are
34// via x16 the BTI landing pads are defined as: BTI C, BTI J, BTI JC, PACIASP,
35// PACIBSP.
36bool elf::isAArch64BTILandingPad(Ctx &ctx, Symbol &s, int64_t a) {
37 // PLT entries accessed indirectly have a BTI c.
38 if (s.isInPlt(ctx))
39 return true;
40 Defined *d = dyn_cast<Defined>(Val: &s);
41 if (!isa_and_nonnull<InputSection>(Val: d->section))
42 // All places that we cannot disassemble are responsible for making
43 // the target a BTI landing pad.
44 return true;
45 InputSection *isec = cast<InputSection>(Val: d->section);
46 uint64_t off = d->value + a;
47 // Likely user error, but protect ourselves against out of bounds
48 // access.
49 if (off >= isec->getSize())
50 return true;
51 const uint8_t *buf = isec->content().begin();
52 // Synthetic sections may have a size but empty data - Assume that they won't
53 // contain a landing pad
54 if (buf == nullptr && isa<SyntheticSection>(Val: isec))
55 return false;
56
57 const uint32_t instr = read32le(P: buf + off);
58 // All BTI instructions are HINT instructions which all have same encoding
59 // apart from bits [11:5]
60 if ((instr & 0xd503201f) == 0xd503201f &&
61 is_contained(Set: {/*PACIASP*/ 0xd503233f, /*PACIBSP*/ 0xd503237f,
62 /*BTI C*/ 0xd503245f, /*BTI J*/ 0xd503249f,
63 /*BTI JC*/ 0xd50324df},
64 Element: instr))
65 return true;
66 return false;
67}
68
69namespace {
70class AArch64 : public TargetInfo {
71public:
72 AArch64(Ctx &);
73 RelExpr getRelExpr(RelType type, const Symbol &s,
74 const uint8_t *loc) const override;
75 RelType getDynRel(RelType type) const override;
76 int64_t getImplicitAddend(const uint8_t *buf, RelType type) const override;
77 void writeGotPlt(uint8_t *buf, const Symbol &s) const override;
78 void writeIgotPlt(uint8_t *buf, const Symbol &s) const override;
79 void writePltHeader(uint8_t *buf) const override;
80 void writePlt(uint8_t *buf, const Symbol &sym,
81 uint64_t pltEntryAddr) const override;
82 template <class ELFT, class RelTy>
83 void scanSectionImpl(InputSectionBase &sec, Relocs<RelTy> rels,
84 unsigned shard);
85 void scanSection(InputSectionBase &sec, unsigned shard) override {
86 if (ctx.arg.ekind == ELF64BEKind)
87 elf::scanSection1<AArch64, ELF64BE>(target&: *this, sec, shard);
88 else
89 elf::scanSection1<AArch64, ELF64LE>(target&: *this, sec, shard);
90 }
91 bool needsThunk(RelExpr expr, RelType type, const InputFile *file,
92 uint64_t branchAddr, const Symbol &s,
93 int64_t a) const override;
94 uint32_t getThunkSectionSpacing() const override;
95 bool inBranchRange(RelType type, uint64_t src, uint64_t dst) const override;
96 bool usesOnlyLowPageBits(RelType type) const override;
97 void relocate(uint8_t *loc, const Relocation &rel,
98 uint64_t val) const override;
99 void relocateAlloc(InputSection &sec, uint8_t *buf) const override;
100 void applyBranchToBranchOpt() const override;
101
102private:
103 void relaxTlsGdToLe(uint8_t *loc, const Relocation &rel, uint64_t val) const;
104 void relaxTlsGdToIe(uint8_t *loc, const Relocation &rel, uint64_t val) const;
105 void relaxTlsIeToLe(uint8_t *loc, const Relocation &rel, uint64_t val) const;
106};
107
108struct AArch64Relaxer {
109 Ctx &ctx;
110 SmallPtrSet<Symbol *, 32> unsafeToRelaxAdrpLdr;
111
112 AArch64Relaxer(Ctx &ctx, ArrayRef<Relocation> relocs, uint64_t secAddr,
113 uint8_t *buf);
114 bool tryRelaxAdrpAdd(const Relocation &adrpRel, const Relocation &addRel,
115 uint64_t secAddr, uint8_t *buf) const;
116 bool tryRelaxAdrpLdr(const Relocation &adrpRel, const Relocation &ldrRel,
117 uint64_t secAddr, uint8_t *buf) const;
118 bool isLegalAdrpLdrRelaxationCandidate(const Relocation &adrpRel,
119 const Relocation &ldrRel,
120 uint64_t secAddr, uint8_t *buf) const;
121};
122} // namespace
123
124// Return the bits [Start, End] from Val shifted Start bits.
125// For instance, getBits(0xF0, 4, 8) returns 0xF.
126static uint64_t getBits(uint64_t val, int start, int end) {
127 uint64_t mask = ((uint64_t)1 << (end + 1 - start)) - 1;
128 return (val >> start) & mask;
129}
130
131AArch64::AArch64(Ctx &ctx) : TargetInfo(ctx) {
132 copyRel = R_AARCH64_COPY;
133 relativeRel = R_AARCH64_RELATIVE;
134 iRelativeRel = R_AARCH64_IRELATIVE;
135 iRelSymbolicRel = R_AARCH64_FUNCINIT64;
136 gotRel = R_AARCH64_GLOB_DAT;
137 pltRel = R_AARCH64_JUMP_SLOT;
138 symbolicRel = R_AARCH64_ABS64;
139 tlsDescRel = R_AARCH64_TLSDESC;
140 tlsGotRel = R_AARCH64_TLS_TPREL64;
141 pltHeaderSize = 32;
142 pltEntrySize = 16;
143 ipltEntrySize = 16;
144 defaultMaxPageSize = 65536;
145
146 // Align to the 2 MiB page size (known as a superpage or huge page).
147 // FreeBSD automatically promotes 2 MiB-aligned allocations.
148 defaultImageBase = 0x200000;
149
150 needsThunks = true;
151}
152
153// Only needed to support relocations used by relocateNonAlloc and
154// preprocessRelocs.
155RelExpr AArch64::getRelExpr(RelType type, const Symbol &s,
156 const uint8_t *loc) const {
157 switch (type) {
158 case R_AARCH64_ABS32:
159 case R_AARCH64_ABS64:
160 return R_ABS;
161 case R_AARCH64_PREL32:
162 case R_AARCH64_PREL64:
163 return R_PC;
164 case R_AARCH64_TLS_DTPREL64:
165 return R_DTPREL;
166 case R_AARCH64_NONE:
167 return R_NONE;
168 default:
169 Err(ctx) << getErrorLoc(ctx, loc) << "unknown relocation (" << type.v
170 << ") against symbol " << &s;
171 return R_NONE;
172 }
173}
174
175bool AArch64::usesOnlyLowPageBits(RelType type) const {
176 switch (type) {
177 default:
178 return false;
179 case R_AARCH64_ADD_ABS_LO12_NC:
180 case R_AARCH64_LD64_GOT_LO12_NC:
181 case R_AARCH64_AUTH_LD64_GOT_LO12_NC:
182 case R_AARCH64_AUTH_GOT_ADD_LO12_NC:
183 case R_AARCH64_LDST128_ABS_LO12_NC:
184 case R_AARCH64_LDST16_ABS_LO12_NC:
185 case R_AARCH64_LDST32_ABS_LO12_NC:
186 case R_AARCH64_LDST64_ABS_LO12_NC:
187 case R_AARCH64_LDST8_ABS_LO12_NC:
188 case R_AARCH64_TLSDESC_ADD_LO12:
189 case R_AARCH64_TLSDESC_LD64_LO12:
190 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
191 return true;
192 }
193}
194
195template <class ELFT, class RelTy>
196void AArch64::scanSectionImpl(InputSectionBase &sec, Relocs<RelTy> rels,
197 unsigned shard) {
198 RelocScan rs(ctx, &sec, shard);
199 sec.relocations.reserve(N: rels.size());
200
201 for (auto it = rels.begin(); it != rels.end(); ++it) {
202 const RelTy &rel = *it;
203 uint32_t symIdx = rel.getSymbol(false);
204 Symbol &sym = sec.getFile<ELFT>()->getSymbol(symIdx);
205 uint64_t offset = rel.r_offset;
206 RelType type = rel.getType(false);
207 if (sym.isUndefined() && symIdx != 0 &&
208 rs.maybeReportUndefined(sym&: cast<Undefined>(Val&: sym), offset))
209 continue;
210 int64_t addend = rs.getAddend<ELFT>(rel, type);
211 RelExpr expr;
212 // Relocation types that only need a RelExpr set `expr` and break out of
213 // the switch to reach rs.process(). Types that need special handling
214 // (fast-path helpers, TLS) call a handler and use `continue`.
215 switch (type) {
216 case R_AARCH64_NONE:
217 continue;
218
219 // Absolute relocations:
220 case R_AARCH64_ABS16:
221 case R_AARCH64_ABS32:
222 case R_AARCH64_ABS64:
223 case R_AARCH64_FUNCINIT64:
224 case R_AARCH64_ADD_ABS_LO12_NC:
225 case R_AARCH64_LDST128_ABS_LO12_NC:
226 case R_AARCH64_LDST16_ABS_LO12_NC:
227 case R_AARCH64_LDST32_ABS_LO12_NC:
228 case R_AARCH64_LDST64_ABS_LO12_NC:
229 case R_AARCH64_LDST8_ABS_LO12_NC:
230 case R_AARCH64_MOVW_SABS_G0:
231 case R_AARCH64_MOVW_SABS_G1:
232 case R_AARCH64_MOVW_SABS_G2:
233 case R_AARCH64_MOVW_UABS_G0:
234 case R_AARCH64_MOVW_UABS_G0_NC:
235 case R_AARCH64_MOVW_UABS_G1:
236 case R_AARCH64_MOVW_UABS_G1_NC:
237 case R_AARCH64_MOVW_UABS_G2:
238 case R_AARCH64_MOVW_UABS_G2_NC:
239 case R_AARCH64_MOVW_UABS_G3:
240 expr = R_ABS;
241 break;
242
243 case R_AARCH64_AUTH_ABS64:
244 expr = RE_AARCH64_AUTH;
245 break;
246
247 case R_AARCH64_PATCHINST:
248 if (!isAbsolute(sym))
249 Err(ctx) << getErrorLoc(ctx, loc: sec.content().data() + offset)
250 << "R_AARCH64_PATCHINST relocation against non-absolute "
251 "symbol "
252 << &sym;
253 expr = R_ABS;
254 break;
255
256 // PC-relative relocations:
257 case R_AARCH64_PREL16:
258 case R_AARCH64_PREL32:
259 case R_AARCH64_PREL64:
260 case R_AARCH64_ADR_PREL_LO21:
261 case R_AARCH64_LD_PREL_LO19:
262 case R_AARCH64_MOVW_PREL_G0:
263 case R_AARCH64_MOVW_PREL_G0_NC:
264 case R_AARCH64_MOVW_PREL_G1:
265 case R_AARCH64_MOVW_PREL_G1_NC:
266 case R_AARCH64_MOVW_PREL_G2:
267 case R_AARCH64_MOVW_PREL_G2_NC:
268 case R_AARCH64_MOVW_PREL_G3:
269 rs.processR_PC(type, offset, addend, sym);
270 continue;
271
272 // Page-PC relocations:
273 case R_AARCH64_ADR_PREL_PG_HI21:
274 case R_AARCH64_ADR_PREL_PG_HI21_NC:
275 expr = RE_AARCH64_PAGE_PC;
276 break;
277
278 // PLT-generating relocations:
279 case R_AARCH64_PLT32:
280 sym.thunkAccessed = true;
281 [[fallthrough]];
282 case R_AARCH64_CALL26:
283 case R_AARCH64_CONDBR19:
284 case R_AARCH64_JUMP26:
285 case R_AARCH64_TSTBR14:
286 rs.processR_PLT_PC(type, offset, addend, sym);
287 continue;
288
289 // GOT relocations:
290 case R_AARCH64_ADR_GOT_PAGE:
291 expr = RE_AARCH64_GOT_PAGE_PC;
292 break;
293 case R_AARCH64_LD64_GOT_LO12_NC:
294 expr = R_GOT;
295 break;
296 case R_AARCH64_LD64_GOTPAGE_LO15:
297 expr = RE_AARCH64_GOT_PAGE;
298 break;
299 case R_AARCH64_GOTPCREL32:
300 case R_AARCH64_GOT_LD_PREL19:
301 expr = R_GOT_PC;
302 break;
303
304 // AUTH GOT relocations. Set NEEDS_GOT_AUTH to detect incompatibility with
305 // NEEDS_GOT_NONAUTH. rs.process does not set the flag.
306 case R_AARCH64_AUTH_LD64_GOT_LO12_NC:
307 case R_AARCH64_AUTH_GOT_ADD_LO12_NC:
308 sym.setFlags(NEEDS_GOT | NEEDS_GOT_AUTH);
309 rs.processAux(expr: R_GOT, type, offset, sym, addend);
310 continue;
311 case R_AARCH64_AUTH_GOT_LD_PREL19:
312 case R_AARCH64_AUTH_GOT_ADR_PREL_LO21:
313 sym.setFlags(NEEDS_GOT | NEEDS_GOT_AUTH);
314 rs.processAux(expr: R_GOT_PC, type, offset, sym, addend);
315 continue;
316 case R_AARCH64_AUTH_ADR_GOT_PAGE:
317 sym.setFlags(NEEDS_GOT | NEEDS_GOT_AUTH);
318 rs.processAux(expr: RE_AARCH64_GOT_PAGE_PC, type, offset, sym, addend);
319 continue;
320
321 // TLS LE relocations:
322 case R_AARCH64_TLSLE_ADD_TPREL_HI12:
323 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC:
324 case R_AARCH64_TLSLE_LDST8_TPREL_LO12_NC:
325 case R_AARCH64_TLSLE_LDST16_TPREL_LO12_NC:
326 case R_AARCH64_TLSLE_LDST32_TPREL_LO12_NC:
327 case R_AARCH64_TLSLE_LDST64_TPREL_LO12_NC:
328 case R_AARCH64_TLSLE_LDST128_TPREL_LO12_NC:
329 case R_AARCH64_TLSLE_MOVW_TPREL_G0:
330 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC:
331 case R_AARCH64_TLSLE_MOVW_TPREL_G1:
332 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC:
333 case R_AARCH64_TLSLE_MOVW_TPREL_G2:
334 if (rs.checkTlsLe(offset, sym, type))
335 continue;
336 expr = R_TPREL;
337 break;
338
339 // TLS IE relocations:
340 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
341 rs.handleTlsIe(ieExpr: RE_AARCH64_GOT_PAGE_PC, type, offset, addend, sym);
342 continue;
343 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
344 rs.handleTlsIe(ieExpr: R_GOT, type, offset, addend, sym);
345 continue;
346
347 // TLSDESC relocations:
348 case R_AARCH64_TLSDESC_ADR_PAGE21:
349 rs.handleTlsDesc(sharedExpr: RE_AARCH64_TLSDESC_PAGE, ieExpr: RE_AARCH64_GOT_PAGE_PC, type,
350 offset, addend, sym);
351 continue;
352 case R_AARCH64_TLSDESC_LD64_LO12:
353 case R_AARCH64_TLSDESC_ADD_LO12:
354 rs.handleTlsDesc(sharedExpr: R_TLSDESC, ieExpr: R_GOT, type, offset, addend, sym);
355 continue;
356 case R_AARCH64_TLSDESC_CALL:
357 sym.setFlags(NEEDS_TLSDESC_NONAUTH);
358 if (!ctx.arg.shared)
359 sec.addReloc(r: {.expr: R_TPREL, .type: type, .offset: offset, .addend: addend, .sym: &sym});
360 continue;
361
362 // AUTH TLSDESC relocations. Do not optimize to LE/IE because PAUTHELF64
363 // only supports the descriptor based TLS (TLSDESC).
364 // https://github.com/ARM-software/abi-aa/blob/main/pauthabielf64/pauthabielf64.rst#general-restrictions
365 case R_AARCH64_AUTH_TLSDESC_ADR_PAGE21:
366 sym.setFlags(NEEDS_TLSDESC | NEEDS_TLSDESC_AUTH);
367 sec.addReloc(r: {.expr: RE_AARCH64_TLSDESC_PAGE, .type: type, .offset: offset, .addend: addend, .sym: &sym});
368 continue;
369 case R_AARCH64_AUTH_TLSDESC_LD64_LO12:
370 case R_AARCH64_AUTH_TLSDESC_ADD_LO12:
371 sym.setFlags(NEEDS_TLSDESC | NEEDS_TLSDESC_AUTH);
372 sec.addReloc(r: {.expr: R_TLSDESC, .type: type, .offset: offset, .addend: addend, .sym: &sym});
373 continue;
374
375 default:
376 Err(ctx) << getErrorLoc(ctx, loc: sec.content().data() + offset)
377 << "unknown relocation (" << type.v << ") against symbol "
378 << &sym;
379 continue;
380 }
381 rs.process(expr, type, offset, sym, addend);
382 }
383
384 if (ctx.arg.branchToBranch)
385 llvm::stable_sort(sec.relocs(),
386 [](auto &l, auto &r) { return l.offset < r.offset; });
387}
388
389RelType AArch64::getDynRel(RelType type) const {
390 if (type == R_AARCH64_ABS64 || type == R_AARCH64_AUTH_ABS64 ||
391 type == R_AARCH64_FUNCINIT64)
392 return type;
393 return R_AARCH64_NONE;
394}
395
396int64_t AArch64::getImplicitAddend(const uint8_t *buf, RelType type) const {
397 switch (type) {
398 case R_AARCH64_TLSDESC:
399 return read64(ctx, p: buf + 8);
400 case R_AARCH64_NONE:
401 case R_AARCH64_GLOB_DAT:
402 case R_AARCH64_AUTH_GLOB_DAT:
403 case R_AARCH64_JUMP_SLOT:
404 return 0;
405 case R_AARCH64_ABS16:
406 case R_AARCH64_PREL16:
407 return SignExtend64<16>(x: read16(ctx, p: buf));
408 case R_AARCH64_ABS32:
409 case R_AARCH64_PREL32:
410 return SignExtend64<32>(x: read32(ctx, p: buf));
411 case R_AARCH64_ABS64:
412 case R_AARCH64_PREL64:
413 case R_AARCH64_RELATIVE:
414 case R_AARCH64_IRELATIVE:
415 case R_AARCH64_TLS_TPREL64:
416 return read64(ctx, p: buf);
417
418 // The following relocation types all point at instructions, and
419 // relocate an immediate field in the instruction.
420 //
421 // The general rule, from AAELF64 §5.7.2 "Addends and PC-bias",
422 // says: "If the relocation relocates an instruction the immediate
423 // field of the instruction is extracted, scaled as required by
424 // the instruction field encoding, and sign-extended to 64 bits".
425
426 // The R_AARCH64_MOVW family operates on wide MOV/MOVK/MOVZ
427 // instructions, which have a 16-bit immediate field with its low
428 // bit in bit 5 of the instruction encoding. When the immediate
429 // field is used as an implicit addend for REL-type relocations,
430 // it is treated as added to the low bits of the output value, not
431 // shifted depending on the relocation type.
432 //
433 // This allows REL relocations to express the requirement 'please
434 // add 12345 to this symbol value and give me the four 16-bit
435 // chunks of the result', by putting the same addend 12345 in all
436 // four instructions. Carries between the 16-bit chunks are
437 // handled correctly, because the whole 64-bit addition is done
438 // once per relocation.
439 case R_AARCH64_MOVW_UABS_G0:
440 case R_AARCH64_MOVW_UABS_G0_NC:
441 case R_AARCH64_MOVW_UABS_G1:
442 case R_AARCH64_MOVW_UABS_G1_NC:
443 case R_AARCH64_MOVW_UABS_G2:
444 case R_AARCH64_MOVW_UABS_G2_NC:
445 case R_AARCH64_MOVW_UABS_G3:
446 return SignExtend64<16>(x: getBits(val: read32le(P: buf), start: 5, end: 20));
447
448 // R_AARCH64_TSTBR14 points at a TBZ or TBNZ instruction, which
449 // has a 14-bit offset measured in instructions, i.e. shifted left
450 // by 2.
451 case R_AARCH64_TSTBR14:
452 return SignExtend64<16>(x: getBits(val: read32le(P: buf), start: 5, end: 18) << 2);
453
454 // R_AARCH64_CONDBR19 operates on the ordinary B.cond instruction,
455 // which has a 19-bit offset measured in instructions.
456 //
457 // R_AARCH64_LD_PREL_LO19 operates on the LDR (literal)
458 // instruction, which also has a 19-bit offset, measured in 4-byte
459 // chunks. So the calculation is the same as for
460 // R_AARCH64_CONDBR19.
461 case R_AARCH64_CONDBR19:
462 case R_AARCH64_LD_PREL_LO19:
463 return SignExtend64<21>(x: getBits(val: read32le(P: buf), start: 5, end: 23) << 2);
464
465 // R_AARCH64_ADD_ABS_LO12_NC operates on ADD (immediate). The
466 // immediate can optionally be shifted left by 12 bits, but this
467 // relocation is intended for the case where it is not.
468 case R_AARCH64_ADD_ABS_LO12_NC:
469 return SignExtend64<12>(x: getBits(val: read32le(P: buf), start: 10, end: 21));
470
471 // R_AARCH64_ADR_PREL_LO21 operates on an ADR instruction, whose
472 // 21-bit immediate is split between two bits high up in the word
473 // (in fact the two _lowest_ order bits of the value) and 19 bits
474 // lower down.
475 //
476 // R_AARCH64_ADR_PREL_PG_HI21[_NC] operate on an ADRP instruction,
477 // which encodes the immediate in the same way, but will shift it
478 // left by 12 bits when the instruction executes. For the same
479 // reason as the MOVW family, we don't apply that left shift here.
480 case R_AARCH64_ADR_PREL_LO21:
481 case R_AARCH64_ADR_PREL_PG_HI21:
482 case R_AARCH64_ADR_PREL_PG_HI21_NC:
483 return SignExtend64<21>(x: (getBits(val: read32le(P: buf), start: 5, end: 23) << 2) |
484 getBits(val: read32le(P: buf), start: 29, end: 30));
485
486 // R_AARCH64_{JUMP,CALL}26 operate on B and BL, which have a
487 // 26-bit offset measured in instructions.
488 case R_AARCH64_JUMP26:
489 case R_AARCH64_CALL26:
490 return SignExtend64<28>(x: getBits(val: read32le(P: buf), start: 0, end: 25) << 2);
491
492 default:
493 InternalErr(ctx, buf) << "cannot read addend for relocation " << type;
494 return 0;
495 }
496}
497
498void AArch64::writeGotPlt(uint8_t *buf, const Symbol &) const {
499 write64(ctx, p: buf, v: ctx.in.plt->getVA());
500}
501
502void AArch64::writeIgotPlt(uint8_t *buf, const Symbol &s) const {
503 if (ctx.arg.writeAddends)
504 write64(ctx, p: buf, v: s.getVA(ctx));
505}
506
507void AArch64::writePltHeader(uint8_t *buf) const {
508 const uint8_t pltData[] = {
509 0xf0, 0x7b, 0xbf, 0xa9, // stp x16, x30, [sp,#-16]!
510 0x10, 0x00, 0x00, 0x90, // adrp x16, Page(&(.got.plt[2]))
511 0x11, 0x02, 0x40, 0xf9, // ldr x17, [x16, Offset(&(.got.plt[2]))]
512 0x10, 0x02, 0x00, 0x91, // add x16, x16, Offset(&(.got.plt[2]))
513 0x20, 0x02, 0x1f, 0xd6, // br x17
514 0x1f, 0x20, 0x03, 0xd5, // nop
515 0x1f, 0x20, 0x03, 0xd5, // nop
516 0x1f, 0x20, 0x03, 0xd5 // nop
517 };
518 memcpy(dest: buf, src: pltData, n: sizeof(pltData));
519
520 uint64_t got = ctx.in.gotPlt->getVA();
521 uint64_t plt = ctx.in.plt->getVA();
522 relocateNoSym(loc: buf + 4, type: R_AARCH64_ADR_PREL_PG_HI21,
523 val: getAArch64Page(expr: got + 16) - getAArch64Page(expr: plt + 4));
524 relocateNoSym(loc: buf + 8, type: R_AARCH64_LDST64_ABS_LO12_NC, val: got + 16);
525 relocateNoSym(loc: buf + 12, type: R_AARCH64_ADD_ABS_LO12_NC, val: got + 16);
526}
527
528void AArch64::writePlt(uint8_t *buf, const Symbol &sym,
529 uint64_t pltEntryAddr) const {
530 const uint8_t inst[] = {
531 0x10, 0x00, 0x00, 0x90, // adrp x16, Page(&(.got.plt[n]))
532 0x11, 0x02, 0x40, 0xf9, // ldr x17, [x16, Offset(&(.got.plt[n]))]
533 0x10, 0x02, 0x00, 0x91, // add x16, x16, Offset(&(.got.plt[n]))
534 0x20, 0x02, 0x1f, 0xd6 // br x17
535 };
536 memcpy(dest: buf, src: inst, n: sizeof(inst));
537
538 uint64_t gotPltEntryAddr = sym.getGotPltVA(ctx);
539 relocateNoSym(loc: buf, type: R_AARCH64_ADR_PREL_PG_HI21,
540 val: getAArch64Page(expr: gotPltEntryAddr) - getAArch64Page(expr: pltEntryAddr));
541 relocateNoSym(loc: buf + 4, type: R_AARCH64_LDST64_ABS_LO12_NC, val: gotPltEntryAddr);
542 relocateNoSym(loc: buf + 8, type: R_AARCH64_ADD_ABS_LO12_NC, val: gotPltEntryAddr);
543}
544
545bool AArch64::needsThunk(RelExpr expr, RelType type, const InputFile *file,
546 uint64_t branchAddr, const Symbol &s,
547 int64_t a) const {
548 // If s is an undefined weak symbol and does not have a PLT entry then it will
549 // be resolved as a branch to the next instruction. If it is hidden, its
550 // binding has been converted to local, so we just check isUndefined() here. A
551 // undefined non-weak symbol will have been errored.
552 if (s.isUndefined() && !s.isInPlt(ctx))
553 return false;
554 // ELF for the ARM 64-bit architecture, section Call and Jump relocations
555 // only permits range extension thunks for R_AARCH64_CALL26 and
556 // R_AARCH64_JUMP26 relocation types.
557 if (type != R_AARCH64_CALL26 && type != R_AARCH64_JUMP26 &&
558 type != R_AARCH64_PLT32)
559 return false;
560 uint64_t dst = expr == R_PLT_PC ? s.getPltVA(ctx) : s.getVA(ctx, addend: a);
561 return !inBranchRange(type, src: branchAddr, dst);
562}
563
564uint32_t AArch64::getThunkSectionSpacing() const {
565 // See comment in Arch/ARM.cpp for a more detailed explanation of
566 // getThunkSectionSpacing(). For AArch64 the only branches we are permitted to
567 // Thunk have a range of +/- 128 MiB
568 return (128 * 1024 * 1024) - 0x30000;
569}
570
571bool AArch64::inBranchRange(RelType type, uint64_t src, uint64_t dst) const {
572 if (type != R_AARCH64_CALL26 && type != R_AARCH64_JUMP26 &&
573 type != R_AARCH64_PLT32)
574 return true;
575 // The AArch64 call and unconditional branch instructions have a range of
576 // +/- 128 MiB. The PLT32 relocation supports a range up to +/- 2 GiB.
577 uint64_t range =
578 type == R_AARCH64_PLT32 ? (UINT64_C(1) << 31) : (128 * 1024 * 1024);
579 if (dst > src) {
580 // Immediate of branch is signed.
581 range -= 4;
582 return dst - src <= range;
583 }
584 return src - dst <= range;
585}
586
587static void write32AArch64Addr(uint8_t *l, uint64_t imm) {
588 uint32_t immLo = (imm & 0x3) << 29;
589 uint32_t immHi = (imm & 0x1FFFFC) << 3;
590 uint64_t mask = (0x3 << 29) | (0x1FFFFC << 3);
591 write32le(P: l, V: (read32le(P: l) & ~mask) | immLo | immHi);
592}
593
594static void writeMaskedBits32le(uint8_t *p, int32_t v, uint32_t mask) {
595 write32le(P: p, V: (read32le(P: p) & ~mask) | v);
596}
597
598// Update the immediate field in a AARCH64 ldr, str, and add instruction.
599static void write32Imm12(uint8_t *l, uint64_t imm) {
600 writeMaskedBits32le(p: l, v: (imm & 0xFFF) << 10, mask: 0xFFF << 10);
601}
602
603// Update the immediate field in an AArch64 movk, movn or movz instruction
604// for a signed relocation, and update the opcode of a movn or movz instruction
605// to match the sign of the operand.
606static void writeSMovWImm(uint8_t *loc, uint32_t imm) {
607 uint32_t inst = read32le(P: loc);
608 // Opcode field is bits 30, 29, with 10 = movz, 00 = movn and 11 = movk.
609 if (!(inst & (1 << 29))) {
610 // movn or movz.
611 if (imm & 0x10000) {
612 // Change opcode to movn, which takes an inverted operand.
613 imm ^= 0xFFFF;
614 inst &= ~(1 << 30);
615 } else {
616 // Change opcode to movz.
617 inst |= 1 << 30;
618 }
619 }
620 write32le(P: loc, V: inst | ((imm & 0xFFFF) << 5));
621}
622
623void AArch64::relocate(uint8_t *loc, const Relocation &rel,
624 uint64_t val) const {
625 switch (rel.type) {
626 case R_AARCH64_ABS16:
627 checkIntUInt(ctx, loc, v: val, n: 16, rel);
628 write16(ctx, p: loc, v: val);
629 break;
630 case R_AARCH64_PREL16:
631 checkInt(ctx, loc, v: val, n: 16, rel);
632 write16(ctx, p: loc, v: val);
633 break;
634 case R_AARCH64_ABS32:
635 checkIntUInt(ctx, loc, v: val, n: 32, rel);
636 write32(ctx, p: loc, v: val);
637 break;
638 case R_AARCH64_PATCHINST:
639 if (!rel.sym->isUndefined()) {
640 checkUInt(ctx, loc, v: val, n: 32, rel);
641 write32le(P: loc, V: val);
642 }
643 break;
644 case R_AARCH64_PREL32:
645 case R_AARCH64_PLT32:
646 case R_AARCH64_GOTPCREL32:
647 checkInt(ctx, loc, v: val, n: 32, rel);
648 write32(ctx, p: loc, v: val);
649 break;
650 case R_AARCH64_ABS64:
651 write64(ctx, p: loc, v: val);
652 break;
653 case R_AARCH64_PREL64:
654 write64(ctx, p: loc, v: val);
655 break;
656 case R_AARCH64_AUTH_ABS64:
657 // This is used for the addend of a .relr.auth.dyn entry,
658 // which is a 32-bit value; the upper 32 bits are used to
659 // encode the schema.
660 checkInt(ctx, loc, v: val, n: 32, rel);
661 write32(ctx, p: loc, v: val);
662 break;
663 case R_AARCH64_TLS_DTPREL64:
664 write64(ctx, p: loc, v: val);
665 break;
666 case R_AARCH64_ADD_ABS_LO12_NC:
667 case R_AARCH64_AUTH_GOT_ADD_LO12_NC:
668 write32Imm12(l: loc, imm: val);
669 break;
670 case R_AARCH64_ADR_GOT_PAGE:
671 case R_AARCH64_AUTH_ADR_GOT_PAGE:
672 case R_AARCH64_ADR_PREL_PG_HI21:
673 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
674 case R_AARCH64_TLSDESC_ADR_PAGE21:
675 case R_AARCH64_AUTH_TLSDESC_ADR_PAGE21:
676 checkInt(ctx, loc, v: val, n: 33, rel);
677 [[fallthrough]];
678 case R_AARCH64_ADR_PREL_PG_HI21_NC:
679 write32AArch64Addr(l: loc, imm: val >> 12);
680 break;
681 case R_AARCH64_ADR_PREL_LO21:
682 case R_AARCH64_AUTH_GOT_ADR_PREL_LO21:
683 checkInt(ctx, loc, v: val, n: 21, rel);
684 write32AArch64Addr(l: loc, imm: val);
685 break;
686 case R_AARCH64_JUMP26:
687 // Normally we would just write the bits of the immediate field, however
688 // when patching instructions for the cpu errata fix -fix-cortex-a53-843419
689 // we want to replace a non-branch instruction with a branch immediate
690 // instruction. By writing all the bits of the instruction including the
691 // opcode and the immediate (0 001 | 01 imm26) we can do this
692 // transformation by placing a R_AARCH64_JUMP26 relocation at the offset of
693 // the instruction we want to patch.
694 write32le(P: loc, V: 0x14000000);
695 [[fallthrough]];
696 case R_AARCH64_CALL26:
697 checkInt(ctx, loc, v: val, n: 28, rel);
698 writeMaskedBits32le(p: loc, v: (val & 0x0FFFFFFC) >> 2, mask: 0x0FFFFFFC >> 2);
699 break;
700 case R_AARCH64_CONDBR19:
701 case R_AARCH64_LD_PREL_LO19:
702 case R_AARCH64_GOT_LD_PREL19:
703 case R_AARCH64_AUTH_GOT_LD_PREL19:
704 checkAlignment(ctx, loc, v: val, n: 4, rel);
705 checkInt(ctx, loc, v: val, n: 21, rel);
706 writeMaskedBits32le(p: loc, v: (val & 0x1FFFFC) << 3, mask: 0x1FFFFC << 3);
707 break;
708 case R_AARCH64_LDST8_ABS_LO12_NC:
709 case R_AARCH64_TLSLE_LDST8_TPREL_LO12_NC:
710 write32Imm12(l: loc, imm: getBits(val, start: 0, end: 11));
711 break;
712 case R_AARCH64_LDST16_ABS_LO12_NC:
713 case R_AARCH64_TLSLE_LDST16_TPREL_LO12_NC:
714 checkAlignment(ctx, loc, v: val, n: 2, rel);
715 write32Imm12(l: loc, imm: getBits(val, start: 1, end: 11));
716 break;
717 case R_AARCH64_LDST32_ABS_LO12_NC:
718 case R_AARCH64_TLSLE_LDST32_TPREL_LO12_NC:
719 checkAlignment(ctx, loc, v: val, n: 4, rel);
720 write32Imm12(l: loc, imm: getBits(val, start: 2, end: 11));
721 break;
722 case R_AARCH64_LDST64_ABS_LO12_NC:
723 case R_AARCH64_LD64_GOT_LO12_NC:
724 case R_AARCH64_AUTH_LD64_GOT_LO12_NC:
725 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
726 case R_AARCH64_TLSLE_LDST64_TPREL_LO12_NC:
727 case R_AARCH64_TLSDESC_LD64_LO12:
728 case R_AARCH64_AUTH_TLSDESC_LD64_LO12:
729 checkAlignment(ctx, loc, v: val, n: 8, rel);
730 write32Imm12(l: loc, imm: getBits(val, start: 3, end: 11));
731 break;
732 case R_AARCH64_LDST128_ABS_LO12_NC:
733 case R_AARCH64_TLSLE_LDST128_TPREL_LO12_NC:
734 checkAlignment(ctx, loc, v: val, n: 16, rel);
735 write32Imm12(l: loc, imm: getBits(val, start: 4, end: 11));
736 break;
737 case R_AARCH64_LD64_GOTPAGE_LO15:
738 checkAlignment(ctx, loc, v: val, n: 8, rel);
739 write32Imm12(l: loc, imm: getBits(val, start: 3, end: 14));
740 break;
741 case R_AARCH64_MOVW_UABS_G0:
742 checkUInt(ctx, loc, v: val, n: 16, rel);
743 [[fallthrough]];
744 case R_AARCH64_MOVW_UABS_G0_NC:
745 writeMaskedBits32le(p: loc, v: (val & 0xFFFF) << 5, mask: 0xFFFF << 5);
746 break;
747 case R_AARCH64_MOVW_UABS_G1:
748 checkUInt(ctx, loc, v: val, n: 32, rel);
749 [[fallthrough]];
750 case R_AARCH64_MOVW_UABS_G1_NC:
751 writeMaskedBits32le(p: loc, v: (val & 0xFFFF0000) >> 11, mask: 0xFFFF0000 >> 11);
752 break;
753 case R_AARCH64_MOVW_UABS_G2:
754 checkUInt(ctx, loc, v: val, n: 48, rel);
755 [[fallthrough]];
756 case R_AARCH64_MOVW_UABS_G2_NC:
757 writeMaskedBits32le(p: loc, v: (val & 0xFFFF00000000) >> 27,
758 mask: 0xFFFF00000000 >> 27);
759 break;
760 case R_AARCH64_MOVW_UABS_G3:
761 writeMaskedBits32le(p: loc, v: (val & 0xFFFF000000000000) >> 43,
762 mask: 0xFFFF000000000000 >> 43);
763 break;
764 case R_AARCH64_MOVW_PREL_G0:
765 case R_AARCH64_MOVW_SABS_G0:
766 case R_AARCH64_TLSLE_MOVW_TPREL_G0:
767 checkInt(ctx, loc, v: val, n: 17, rel);
768 [[fallthrough]];
769 case R_AARCH64_MOVW_PREL_G0_NC:
770 case R_AARCH64_TLSLE_MOVW_TPREL_G0_NC:
771 writeSMovWImm(loc, imm: val);
772 break;
773 case R_AARCH64_MOVW_PREL_G1:
774 case R_AARCH64_MOVW_SABS_G1:
775 case R_AARCH64_TLSLE_MOVW_TPREL_G1:
776 checkInt(ctx, loc, v: val, n: 33, rel);
777 [[fallthrough]];
778 case R_AARCH64_MOVW_PREL_G1_NC:
779 case R_AARCH64_TLSLE_MOVW_TPREL_G1_NC:
780 writeSMovWImm(loc, imm: val >> 16);
781 break;
782 case R_AARCH64_MOVW_PREL_G2:
783 case R_AARCH64_MOVW_SABS_G2:
784 case R_AARCH64_TLSLE_MOVW_TPREL_G2:
785 checkInt(ctx, loc, v: val, n: 49, rel);
786 [[fallthrough]];
787 case R_AARCH64_MOVW_PREL_G2_NC:
788 writeSMovWImm(loc, imm: val >> 32);
789 break;
790 case R_AARCH64_MOVW_PREL_G3:
791 writeSMovWImm(loc, imm: val >> 48);
792 break;
793 case R_AARCH64_TSTBR14:
794 checkInt(ctx, loc, v: val, n: 16, rel);
795 writeMaskedBits32le(p: loc, v: (val & 0xFFFC) << 3, mask: 0xFFFC << 3);
796 break;
797 case R_AARCH64_TLSLE_ADD_TPREL_HI12:
798 checkUInt(ctx, loc, v: val, n: 24, rel);
799 if (ctx.arg.relax && (val >> 12) == 0) {
800 uint32_t inst = read32le(P: loc);
801 // The W-form zero-extends Xd, so only the X-form is a nop.
802 if ((inst & (1u << 31)) && (inst & 0x1f) == ((inst >> 5) & 0x1f)) {
803 write32le(P: loc, V: 0xd503201f); // nop
804 break;
805 }
806 }
807 write32Imm12(l: loc, imm: val >> 12);
808 break;
809 case R_AARCH64_TLSLE_ADD_TPREL_LO12_NC:
810 case R_AARCH64_TLSDESC_ADD_LO12:
811 case R_AARCH64_AUTH_TLSDESC_ADD_LO12:
812 write32Imm12(l: loc, imm: val);
813 break;
814 case R_AARCH64_TLSDESC:
815 // For R_AARCH64_TLSDESC the addend is stored in the second 64-bit word.
816 write64(ctx, p: loc + 8, v: val);
817 break;
818 default:
819 llvm_unreachable("unknown relocation");
820 }
821}
822
823void AArch64::relaxTlsGdToLe(uint8_t *loc, const Relocation &rel,
824 uint64_t val) const {
825 // TLSDESC Global-Dynamic relocation are in the form:
826 // adrp x0, :tlsdesc:v [R_AARCH64_TLSDESC_ADR_PAGE21]
827 // ldr x1, [x0, #:tlsdesc_lo12:v [R_AARCH64_TLSDESC_LD64_LO12]
828 // add x0, x0, :tlsdesc_los:v [R_AARCH64_TLSDESC_ADD_LO12]
829 // .tlsdesccall [R_AARCH64_TLSDESC_CALL]
830 // blr x1
831 // And it can optimized to:
832 // movz x0, #0x0, lsl #16
833 // movk x0, #0x10
834 // nop
835 // nop
836 checkUInt(ctx, loc, v: val, n: 32, rel);
837
838 switch (rel.type) {
839 case R_AARCH64_TLSDESC_ADD_LO12:
840 case R_AARCH64_TLSDESC_CALL:
841 write32le(P: loc, V: 0xd503201f); // nop
842 return;
843 case R_AARCH64_TLSDESC_ADR_PAGE21:
844 write32le(P: loc, V: 0xd2a00000 | (((val >> 16) & 0xffff) << 5)); // movz
845 return;
846 case R_AARCH64_TLSDESC_LD64_LO12:
847 write32le(P: loc, V: 0xf2800000 | ((val & 0xffff) << 5)); // movk
848 return;
849 default:
850 llvm_unreachable("unsupported relocation for TLS GD to LE relaxation");
851 }
852}
853
854void AArch64::relaxTlsGdToIe(uint8_t *loc, const Relocation &rel,
855 uint64_t val) const {
856 // TLSDESC Global-Dynamic relocation are in the form:
857 // adrp x0, :tlsdesc:v [R_AARCH64_TLSDESC_ADR_PAGE21]
858 // ldr x1, [x0, #:tlsdesc_lo12:v [R_AARCH64_TLSDESC_LD64_LO12]
859 // add x0, x0, :tlsdesc_los:v [R_AARCH64_TLSDESC_ADD_LO12]
860 // .tlsdesccall [R_AARCH64_TLSDESC_CALL]
861 // blr x1
862 // And it can optimized to:
863 // adrp x0, :gottprel:v
864 // ldr x0, [x0, :gottprel_lo12:v]
865 // nop
866 // nop
867
868 switch (rel.type) {
869 case R_AARCH64_TLSDESC_ADD_LO12:
870 case R_AARCH64_TLSDESC_CALL:
871 write32le(P: loc, V: 0xd503201f); // nop
872 break;
873 case R_AARCH64_TLSDESC_ADR_PAGE21:
874 write32le(P: loc, V: 0x90000000); // adrp
875 relocateNoSym(loc, type: R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21, val);
876 break;
877 case R_AARCH64_TLSDESC_LD64_LO12:
878 write32le(P: loc, V: 0xf9400000); // ldr
879 relocateNoSym(loc, type: R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC, val);
880 break;
881 default:
882 llvm_unreachable("unsupported relocation for TLS GD to IE relaxation");
883 }
884}
885
886void AArch64::relaxTlsIeToLe(uint8_t *loc, const Relocation &rel,
887 uint64_t val) const {
888 checkUInt(ctx, loc, v: val, n: 32, rel);
889
890 if (rel.type == R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21) {
891 // Generate MOVZ.
892 uint32_t regNo = read32le(P: loc) & 0x1f;
893 write32le(P: loc, V: (0xd2a00000 | regNo) | (((val >> 16) & 0xffff) << 5));
894 return;
895 }
896 if (rel.type == R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC) {
897 // Generate MOVK.
898 uint32_t regNo = read32le(P: loc) & 0x1f;
899 write32le(P: loc, V: (0xf2800000 | regNo) | ((val & 0xffff) << 5));
900 return;
901 }
902 llvm_unreachable("invalid relocation for TLS IE to LE relaxation");
903}
904
905AArch64Relaxer::AArch64Relaxer(Ctx &ctx, ArrayRef<Relocation> relocs,
906 uint64_t secAddr, uint8_t *buf)
907 : ctx(ctx) {
908 if (!ctx.arg.relax)
909 return;
910 // For a given symbol R_AARCH64_ADR_GOT_PAGE and R_AARCH64_LD64_GOT_LO12_NC
911 // relaxation is all-or-nothing. We can't relax only some of them, as there
912 // may be a jump destination between the two relocations.
913 size_t i = 0;
914 const size_t size = relocs.size();
915 for (; i != size; ++i) {
916 if (relocs[i].type == R_AARCH64_ADR_GOT_PAGE) {
917 if (i + 1 < size && relocs[i + 1].type == R_AARCH64_LD64_GOT_LO12_NC &&
918 !unsafeToRelaxAdrpLdr.contains(Ptr: relocs[i].sym) &&
919 isLegalAdrpLdrRelaxationCandidate(adrpRel: relocs[i], ldrRel: relocs[i + 1], secAddr,
920 buf)) {
921 ++i;
922 continue;
923 }
924 unsafeToRelaxAdrpLdr.insert(Ptr: relocs[i].sym);
925 } else if (relocs[i].type == R_AARCH64_LD64_GOT_LO12_NC) {
926 unsafeToRelaxAdrpLdr.insert(Ptr: relocs[i].sym);
927 }
928 }
929}
930
931bool AArch64Relaxer::tryRelaxAdrpAdd(const Relocation &adrpRel,
932 const Relocation &addRel, uint64_t secAddr,
933 uint8_t *buf) const {
934 // When the address of sym is within the range of ADR then
935 // we may relax
936 // ADRP xn, sym
937 // ADD xn, xn, :lo12: sym
938 // to
939 // NOP
940 // ADR xn, sym
941 if (!ctx.arg.relax || addRel.type != R_AARCH64_ADD_ABS_LO12_NC)
942 return false;
943 // Check if the relocations apply to consecutive instructions.
944 if (adrpRel.offset + 4 != addRel.offset)
945 return false;
946 if (adrpRel.sym != addRel.sym)
947 return false;
948 if (adrpRel.addend != 0 || addRel.addend != 0)
949 return false;
950
951 uint32_t adrpInstr = read32le(P: buf + adrpRel.offset);
952 uint32_t addInstr = read32le(P: buf + addRel.offset);
953 // Check if the first instruction is ADRP and the second instruction is ADD.
954 if ((adrpInstr & 0x9f000000) != 0x90000000 ||
955 (addInstr & 0xffc00000) != 0x91000000)
956 return false;
957 uint32_t adrpDestReg = adrpInstr & 0x1f;
958 uint32_t addDestReg = addInstr & 0x1f;
959 uint32_t addSrcReg = (addInstr >> 5) & 0x1f;
960 if (adrpDestReg != addDestReg || adrpDestReg != addSrcReg)
961 return false;
962
963 Symbol &sym = *adrpRel.sym;
964 // Check if the address difference is within 1MiB range.
965 int64_t val = sym.getVA(ctx) - (secAddr + addRel.offset);
966 if (val < -1024 * 1024 || val >= 1024 * 1024)
967 return false;
968
969 Relocation adrRel = {.expr: R_ABS, .type: R_AARCH64_ADR_PREL_LO21, .offset: addRel.offset,
970 /*addend=*/0, .sym: &sym};
971 // nop
972 write32le(P: buf + adrpRel.offset, V: 0xd503201f);
973 // adr x_<dest_reg>
974 write32le(P: buf + adrRel.offset, V: 0x10000000 | adrpDestReg);
975 ctx.target->relocate(loc: buf + adrRel.offset, rel: adrRel, val);
976 return true;
977}
978
979bool AArch64Relaxer::isLegalAdrpLdrRelaxationCandidate(
980 const Relocation &adrpRel, const Relocation &ldrRel, uint64_t secAddr,
981 uint8_t *buf) const {
982 // Check if the relocations apply to consecutive instructions.
983 if (adrpRel.offset + 4 != ldrRel.offset)
984 return false;
985 // Check if the relocations reference the same symbol and
986 // skip undefined, preemptible and STT_GNU_IFUNC symbols.
987 if (!adrpRel.sym || adrpRel.sym != ldrRel.sym || !adrpRel.sym->isDefined() ||
988 adrpRel.sym->isPreemptible || adrpRel.sym->isGnuIFunc())
989 return false;
990 // Check if the addends of the both relocations are zero.
991 if (adrpRel.addend != 0 || ldrRel.addend != 0)
992 return false;
993 uint32_t adrpInstr = read32le(P: buf + adrpRel.offset);
994 uint32_t ldrInstr = read32le(P: buf + ldrRel.offset);
995 // Check if the first instruction is ADRP and the second instruction is LDR.
996 if ((adrpInstr & 0x9f000000) != 0x90000000 ||
997 (ldrInstr & 0x3b000000) != 0x39000000)
998 return false;
999 // Check the value of the sf bit.
1000 if (!(ldrInstr >> 31))
1001 return false;
1002 uint32_t adrpDestReg = adrpInstr & 0x1f;
1003 uint32_t ldrDestReg = ldrInstr & 0x1f;
1004 uint32_t ldrSrcReg = (ldrInstr >> 5) & 0x1f;
1005 // Check if ADPR and LDR use the same register.
1006 if (adrpDestReg != ldrDestReg || adrpDestReg != ldrSrcReg)
1007 return false;
1008
1009 Symbol &sym = *adrpRel.sym;
1010 // GOT references to absolute symbols can't be relaxed to use ADRP/ADD in
1011 // position-independent code because these instructions produce a relative
1012 // address.
1013 if (ctx.arg.isPic && !cast<Defined>(Val&: sym).section)
1014 return false;
1015 // Check if the address difference is within 4GB range.
1016 int64_t val =
1017 getAArch64Page(expr: sym.getVA(ctx)) - getAArch64Page(expr: secAddr + adrpRel.offset);
1018 if (val != llvm::SignExtend64(X: val, B: 33))
1019 return false;
1020
1021 return true;
1022}
1023
1024bool AArch64Relaxer::tryRelaxAdrpLdr(const Relocation &adrpRel,
1025 const Relocation &ldrRel, uint64_t secAddr,
1026 uint8_t *buf) const {
1027 // When the definition of sym is not preemptible then we may
1028 // be able to relax
1029 // ADRP xn, :got: sym
1030 // LDR xn, [ xn :got_lo12: sym]
1031 // to
1032 // ADRP xn, sym
1033 // ADD xn, xn, :lo_12: sym
1034
1035 if (!ctx.arg.relax || adrpRel.type != R_AARCH64_ADR_GOT_PAGE ||
1036 ldrRel.type != R_AARCH64_LD64_GOT_LO12_NC)
1037 return false;
1038
1039 Symbol *sym = adrpRel.sym;
1040 if (unsafeToRelaxAdrpLdr.contains(Ptr: sym))
1041 return false;
1042
1043 assert(isLegalAdrpLdrRelaxationCandidate(adrpRel, ldrRel, secAddr, buf) &&
1044 "Should have been marked as unsafe");
1045
1046 uint32_t adrpInstr = read32le(P: buf + adrpRel.offset);
1047 uint32_t adrpDestReg = adrpInstr & 0x1f;
1048 Relocation adrpSymRel = {.expr: RE_AARCH64_PAGE_PC, .type: R_AARCH64_ADR_PREL_PG_HI21,
1049 .offset: adrpRel.offset, /*addend=*/0, .sym: sym};
1050 Relocation addRel = {.expr: R_ABS, .type: R_AARCH64_ADD_ABS_LO12_NC, .offset: ldrRel.offset,
1051 /*addend=*/0, .sym: sym};
1052
1053 // adrp x_<dest_reg>
1054 write32le(P: buf + adrpSymRel.offset, V: 0x90000000 | adrpDestReg);
1055 // add x_<dest reg>, x_<dest reg>
1056 write32le(P: buf + addRel.offset, V: 0x91000000 | adrpDestReg | (adrpDestReg << 5));
1057
1058 ctx.target->relocate(
1059 loc: buf + adrpSymRel.offset, rel: adrpSymRel,
1060 val: SignExtend64(X: getAArch64Page(expr: sym->getVA(ctx)) -
1061 getAArch64Page(expr: secAddr + adrpSymRel.offset),
1062 B: 64));
1063 ctx.target->relocate(loc: buf + addRel.offset, rel: addRel,
1064 val: SignExtend64(X: sym->getVA(ctx), B: 64));
1065 tryRelaxAdrpAdd(adrpRel: adrpSymRel, addRel, secAddr, buf);
1066 return true;
1067}
1068
1069// Tagged symbols have upper address bits that are added by the dynamic loader,
1070// and thus need the full 64-bit GOT entry. Do not relax such symbols.
1071static bool needsGotForMemtag(const Relocation &rel) {
1072 return rel.sym->isTagged() && needsGot(expr: rel.expr);
1073}
1074
1075void AArch64::relocateAlloc(InputSection &sec, uint8_t *buf) const {
1076 uint64_t secAddr = sec.getOutputSection()->addr + sec.outSecOff;
1077 const ArrayRef<Relocation> relocs = sec.relocs();
1078 AArch64Relaxer relaxer(ctx, relocs, secAddr, buf);
1079 for (size_t i = 0, size = relocs.size(); i != size; ++i) {
1080 const Relocation &rel = relocs[i];
1081 if (rel.expr == R_NONE) // See finalizeAddressDependentContent()
1082 continue;
1083 uint8_t *loc = buf + rel.offset;
1084 const uint64_t val = sec.getRelocTargetVA(ctx, r: rel, p: secAddr + rel.offset);
1085
1086 if (needsGotForMemtag(rel)) {
1087 relocate(loc, rel, val);
1088 continue;
1089 }
1090
1091 switch (rel.type) {
1092 case R_AARCH64_ADR_GOT_PAGE:
1093 if (i + 1 < size &&
1094 relaxer.tryRelaxAdrpLdr(adrpRel: rel, ldrRel: relocs[i + 1], secAddr, buf)) {
1095 ++i;
1096 continue;
1097 }
1098 break;
1099 case R_AARCH64_ADR_PREL_PG_HI21:
1100 if (i + 1 < size &&
1101 relaxer.tryRelaxAdrpAdd(adrpRel: rel, addRel: relocs[i + 1], secAddr, buf)) {
1102 ++i;
1103 continue;
1104 }
1105 break;
1106
1107 case R_AARCH64_TLSDESC_ADR_PAGE21:
1108 case R_AARCH64_TLSDESC_LD64_LO12:
1109 case R_AARCH64_TLSDESC_ADD_LO12:
1110 case R_AARCH64_TLSDESC_CALL:
1111 if (rel.expr == R_TPREL)
1112 relaxTlsGdToLe(loc, rel, val);
1113 else if (rel.expr == RE_AARCH64_GOT_PAGE_PC || rel.expr == R_GOT)
1114 relaxTlsGdToIe(loc, rel, val);
1115 else
1116 relocate(loc, rel, val);
1117 continue;
1118 case R_AARCH64_TLSIE_ADR_GOTTPREL_PAGE21:
1119 case R_AARCH64_TLSIE_LD64_GOTTPREL_LO12_NC:
1120 if (rel.expr == R_TPREL)
1121 relaxTlsIeToLe(loc, rel, val);
1122 else
1123 relocate(loc, rel, val);
1124 continue;
1125 default:
1126 break;
1127 }
1128
1129 relocate(loc, rel, val);
1130 }
1131}
1132
1133static std::optional<uint64_t> getControlTransferAddend(InputSection &is,
1134 Relocation &r) {
1135 // Identify a control transfer relocation for the branch-to-branch
1136 // optimization. A "control transfer relocation" means a B or BL
1137 // target but it also includes relative vtable relocations for example.
1138 //
1139 // We require the relocation type to be JUMP26, CALL26 or PLT32. With a
1140 // relocation type of PLT32 the value may be assumed to be used for branching
1141 // directly to the symbol and the addend is only used to produce the relocated
1142 // value (hence the effective addend is always 0). This is because if a PLT is
1143 // needed the addend will be added to the address of the PLT, and it doesn't
1144 // make sense to branch into the middle of a PLT. For example, relative vtable
1145 // relocations use PLT32 and 0 or a positive value as the addend but still are
1146 // used to branch to the symbol.
1147 //
1148 // With JUMP26 or CALL26 the only reasonable interpretation of a non-zero
1149 // addend is that we are branching to symbol+addend so that becomes the
1150 // effective addend.
1151 if (r.type == R_AARCH64_PLT32)
1152 return 0;
1153 if (r.type == R_AARCH64_JUMP26 || r.type == R_AARCH64_CALL26)
1154 return r.addend;
1155 return std::nullopt;
1156}
1157
1158static std::pair<Relocation *, uint64_t>
1159getBranchInfoAtTarget(InputSection &is, uint64_t offset) {
1160 auto *i = llvm::partition_point(
1161 Range&: is.relocations, P: [&](Relocation &r) { return r.offset < offset; });
1162 if (i != is.relocations.end() && i->offset == offset &&
1163 i->type == R_AARCH64_JUMP26) {
1164 return {i, i->addend};
1165 }
1166 return {nullptr, 0};
1167}
1168
1169static void redirectControlTransferRelocations(Relocation &r1,
1170 const Relocation &r2) {
1171 r1.expr = r2.expr;
1172 r1.sym = r2.sym;
1173 // With PLT32 we must respect the original addend as that affects the value's
1174 // interpretation. With the other relocation types the original addend is
1175 // irrelevant because it referred to an offset within the original target
1176 // section so we overwrite it.
1177 if (r1.type == R_AARCH64_PLT32)
1178 r1.addend += r2.addend;
1179 else
1180 r1.addend = r2.addend;
1181}
1182
1183void AArch64::applyBranchToBranchOpt() const {
1184 applyBranchToBranchOptImpl(ctx, getControlTransferAddend,
1185 getBranchInfoAtTarget,
1186 redirectControlTransferRelocations);
1187}
1188
1189// AArch64 may use security features in variant PLT sequences. These are:
1190// Pointer Authentication (PAC), introduced in armv8.3-a and Branch Target
1191// Indicator (BTI) introduced in armv8.5-a. The additional instructions used
1192// in the variant Plt sequences are encoded in the Hint space so they can be
1193// deployed on older architectures, which treat the instructions as a nop.
1194// PAC and BTI can be combined leading to the following combinations:
1195// writePltHeader
1196// writePltHeaderBti (no PAC Header needed)
1197// writePlt
1198// writePltBti (BTI only)
1199// writePltPac (PAC only)
1200// writePltBtiPac (BTI and PAC)
1201//
1202// When PAC is enabled the dynamic loader encrypts the address that it places
1203// in the .got.plt using the pacia1716 instruction which encrypts the value in
1204// x17 using the modifier in x16. The static linker places autia1716 before the
1205// indirect branch to x17 to authenticate the address in x17 with the modifier
1206// in x16. This makes it more difficult for an attacker to modify the value in
1207// the .got.plt.
1208//
1209// When BTI is enabled all indirect branches must land on a bti instruction.
1210// The static linker must place a bti instruction at the start of any PLT entry
1211// that may be the target of an indirect branch. As the PLT entries call the
1212// lazy resolver indirectly this must have a bti instruction at start. In
1213// general a bti instruction is not needed for a PLT entry as indirect calls
1214// are resolved to the function address and not the PLT entry for the function.
1215// There are a small number of cases where the PLT address can escape, such as
1216// taking the address of a function or ifunc via a non got-generating
1217// relocation, and a shared library refers to that symbol.
1218//
1219// We use the bti c variant of the instruction which permits indirect branches
1220// (br) via x16/x17 and indirect function calls (blr) via any register. The ABI
1221// guarantees that all indirect branches from code requiring BTI protection
1222// will go via x16/x17
1223
1224namespace {
1225class AArch64BtiPac final : public AArch64 {
1226public:
1227 AArch64BtiPac(Ctx &);
1228 void writePltHeader(uint8_t *buf) const override;
1229 void writePlt(uint8_t *buf, const Symbol &sym,
1230 uint64_t pltEntryAddr) const override;
1231
1232private:
1233 bool btiHeader; // bti instruction needed in PLT Header and Entry
1234 enum {
1235 PEK_NoAuth,
1236 PEK_AuthHint, // use autia1716 instr for authenticated branch in PLT entry
1237 PEK_Auth, // use braa instr for authenticated branch in PLT entry
1238 } pacEntryKind;
1239};
1240} // namespace
1241
1242AArch64BtiPac::AArch64BtiPac(Ctx &ctx) : AArch64(ctx) {
1243 btiHeader = (ctx.arg.andFeatures & GNU_PROPERTY_AARCH64_FEATURE_1_BTI);
1244 // A BTI (Branch Target Indicator) Plt Entry is only required if the
1245 // address of the PLT entry can be taken by the program, which permits an
1246 // indirect jump to the PLT entry. This can happen when the address
1247 // of the PLT entry for a function is canonicalised due to the address of
1248 // the function in an executable being taken by a shared library, or
1249 // non-preemptible ifunc referenced by non-GOT-generating, non-PLT-generating
1250 // relocations.
1251 // The PAC PLT entries require dynamic loader support and this isn't known
1252 // from properties in the objects, so we use the command line flag.
1253 // By default we only use hint-space instructions, but if we detect the
1254 // PAuthABI, which requires v8.3-A, we can use the non-hint space
1255 // instructions.
1256
1257 if (ctx.arg.zPacPlt) {
1258 if (ctx.aarch64PauthAbiCoreInfo && ctx.aarch64PauthAbiCoreInfo->isValid())
1259 pacEntryKind = PEK_Auth;
1260 else
1261 pacEntryKind = PEK_AuthHint;
1262 } else {
1263 pacEntryKind = PEK_NoAuth;
1264 }
1265
1266 if (btiHeader || (pacEntryKind != PEK_NoAuth)) {
1267 pltEntrySize = 24;
1268 ipltEntrySize = 24;
1269 }
1270}
1271
1272void AArch64BtiPac::writePltHeader(uint8_t *buf) const {
1273 const uint8_t btiData[] = { 0x5f, 0x24, 0x03, 0xd5 }; // bti c
1274 const uint8_t pltData[] = {
1275 0xf0, 0x7b, 0xbf, 0xa9, // stp x16, x30, [sp,#-16]!
1276 0x10, 0x00, 0x00, 0x90, // adrp x16, Page(&(.got.plt[2]))
1277 0x11, 0x02, 0x40, 0xf9, // ldr x17, [x16, Offset(&(.got.plt[2]))]
1278 0x10, 0x02, 0x00, 0x91, // add x16, x16, Offset(&(.got.plt[2]))
1279 0x20, 0x02, 0x1f, 0xd6, // br x17
1280 0x1f, 0x20, 0x03, 0xd5, // nop
1281 0x1f, 0x20, 0x03, 0xd5 // nop
1282 };
1283 const uint8_t nopData[] = { 0x1f, 0x20, 0x03, 0xd5 }; // nop
1284
1285 uint64_t got = ctx.in.gotPlt->getVA();
1286 uint64_t plt = ctx.in.plt->getVA();
1287
1288 if (btiHeader) {
1289 // PltHeader is called indirectly by plt[N]. Prefix pltData with a BTI C
1290 // instruction.
1291 memcpy(dest: buf, src: btiData, n: sizeof(btiData));
1292 buf += sizeof(btiData);
1293 plt += sizeof(btiData);
1294 }
1295 memcpy(dest: buf, src: pltData, n: sizeof(pltData));
1296
1297 relocateNoSym(loc: buf + 4, type: R_AARCH64_ADR_PREL_PG_HI21,
1298 val: getAArch64Page(expr: got + 16) - getAArch64Page(expr: plt + 4));
1299 relocateNoSym(loc: buf + 8, type: R_AARCH64_LDST64_ABS_LO12_NC, val: got + 16);
1300 relocateNoSym(loc: buf + 12, type: R_AARCH64_ADD_ABS_LO12_NC, val: got + 16);
1301 if (!btiHeader)
1302 // We didn't add the BTI c instruction so round out size with NOP.
1303 memcpy(dest: buf + sizeof(pltData), src: nopData, n: sizeof(nopData));
1304}
1305
1306void AArch64BtiPac::writePlt(uint8_t *buf, const Symbol &sym,
1307 uint64_t pltEntryAddr) const {
1308 // The PLT entry is of the form:
1309 // [btiData] addrInst (pacBr | stdBr) [nopData]
1310 const uint8_t btiData[] = { 0x5f, 0x24, 0x03, 0xd5 }; // bti c
1311 const uint8_t addrInst[] = {
1312 0x10, 0x00, 0x00, 0x90, // adrp x16, Page(&(.got.plt[n]))
1313 0x11, 0x02, 0x40, 0xf9, // ldr x17, [x16, Offset(&(.got.plt[n]))]
1314 0x10, 0x02, 0x00, 0x91 // add x16, x16, Offset(&(.got.plt[n]))
1315 };
1316 const uint8_t pacHintBr[] = {
1317 0x9f, 0x21, 0x03, 0xd5, // autia1716
1318 0x20, 0x02, 0x1f, 0xd6 // br x17
1319 };
1320 const uint8_t pacBr[] = {
1321 0x30, 0x0a, 0x1f, 0xd7, // braa x17, x16
1322 0x1f, 0x20, 0x03, 0xd5 // nop
1323 };
1324 const uint8_t stdBr[] = {
1325 0x20, 0x02, 0x1f, 0xd6, // br x17
1326 0x1f, 0x20, 0x03, 0xd5 // nop
1327 };
1328 const uint8_t nopData[] = { 0x1f, 0x20, 0x03, 0xd5 }; // nop
1329
1330 // NEEDS_COPY indicates a non-ifunc canonical PLT entry whose address may
1331 // escape to shared objects. isInIplt indicates a non-preemptible ifunc. Its
1332 // address may escape if referenced by a direct relocation. If relative
1333 // vtables are used then if the vtable is in a shared object the offsets will
1334 // be to the PLT entry. The condition is conservative.
1335 bool hasBti = btiHeader &&
1336 (sym.hasFlag(bit: NEEDS_COPY) || sym.isInIplt || sym.thunkAccessed);
1337 if (hasBti) {
1338 memcpy(dest: buf, src: btiData, n: sizeof(btiData));
1339 buf += sizeof(btiData);
1340 pltEntryAddr += sizeof(btiData);
1341 }
1342
1343 uint64_t gotPltEntryAddr = sym.getGotPltVA(ctx);
1344 memcpy(dest: buf, src: addrInst, n: sizeof(addrInst));
1345 relocateNoSym(loc: buf, type: R_AARCH64_ADR_PREL_PG_HI21,
1346 val: getAArch64Page(expr: gotPltEntryAddr) - getAArch64Page(expr: pltEntryAddr));
1347 relocateNoSym(loc: buf + 4, type: R_AARCH64_LDST64_ABS_LO12_NC, val: gotPltEntryAddr);
1348 relocateNoSym(loc: buf + 8, type: R_AARCH64_ADD_ABS_LO12_NC, val: gotPltEntryAddr);
1349
1350 if (pacEntryKind != PEK_NoAuth)
1351 memcpy(dest: buf + sizeof(addrInst),
1352 src: pacEntryKind == PEK_AuthHint ? pacHintBr : pacBr,
1353 n: sizeof(pacEntryKind == PEK_AuthHint ? pacHintBr : pacBr));
1354 else
1355 memcpy(dest: buf + sizeof(addrInst), src: stdBr, n: sizeof(stdBr));
1356 if (!hasBti)
1357 // We didn't add the BTI c instruction so round out size with NOP.
1358 memcpy(dest: buf + sizeof(addrInst) + sizeof(stdBr), src: nopData, n: sizeof(nopData));
1359}
1360
1361template <class ELFT>
1362static void
1363addTaggedSymbolReferences(Ctx &ctx, InputSectionBase &sec,
1364 DenseMap<Symbol *, unsigned> &referenceCount) {
1365 assert(sec.type == SHT_AARCH64_MEMTAG_GLOBALS_STATIC);
1366
1367 const RelsOrRelas<ELFT> rels = sec.relsOrRelas<ELFT>();
1368 if (rels.areRelocsRel())
1369 ErrAlways(ctx)
1370 << "non-RELA relocations are not allowed with memtag globals";
1371
1372 for (const typename ELFT::Rela &rel : rels.relas) {
1373 Symbol &sym = sec.file->getRelocTargetSym(rel);
1374 // Linker-synthesized symbols such as __executable_start may be referenced
1375 // as tagged in input objfiles, and we don't want them to be tagged. A
1376 // cheap way to exclude them is the type check, but their type is
1377 // STT_NOTYPE. In addition, this save us from checking untaggable symbols,
1378 // like functions or TLS symbols.
1379 if (sym.type != STT_OBJECT)
1380 continue;
1381 // STB_LOCAL symbols can't be referenced from outside the object file, and
1382 // thus don't need to be checked for references from other object files.
1383 if (sym.binding == STB_LOCAL) {
1384 sym.setIsTagged(true);
1385 continue;
1386 }
1387 ++referenceCount[&sym];
1388 }
1389 sec.markDead();
1390}
1391
1392// A tagged symbol must be denoted as being tagged by all references and the
1393// chosen definition. For simplicity, here, it must also be denoted as tagged
1394// for all definitions. Otherwise:
1395//
1396// 1. A tagged definition can be used by an untagged declaration, in which case
1397// the untagged access may be PC-relative, causing a tag mismatch at
1398// runtime.
1399// 2. An untagged definition can be used by a tagged declaration, where the
1400// compiler has taken advantage of the increased alignment of the tagged
1401// declaration, but the alignment at runtime is wrong, causing a fault.
1402//
1403// Ideally, this isn't a problem, as any TU that imports or exports tagged
1404// symbols should also be built with tagging. But, to handle these cases, we
1405// demote the symbol to be untagged.
1406void elf::createTaggedSymbols(Ctx &ctx) {
1407 assert(hasMemtag(ctx));
1408
1409 // First, collect all symbols that are marked as tagged, and count how many
1410 // times they're marked as tagged.
1411 DenseMap<Symbol *, unsigned> taggedSymbolReferenceCount;
1412 for (InputFile *file : ctx.objectFiles) {
1413 if (file->kind() != InputFile::ObjKind)
1414 continue;
1415 for (InputSectionBase *section : file->getSections()) {
1416 if (!section || section->type != SHT_AARCH64_MEMTAG_GLOBALS_STATIC ||
1417 section == &InputSection::discarded)
1418 continue;
1419 invokeELFT(addTaggedSymbolReferences, ctx, *section,
1420 taggedSymbolReferenceCount);
1421 }
1422 }
1423
1424 // Now, go through all the symbols. If the number of declarations +
1425 // definitions to a symbol exceeds the amount of times they're marked as
1426 // tagged, it means we have an objfile that uses the untagged variant of the
1427 // symbol.
1428 for (InputFile *file : ctx.objectFiles) {
1429 if (file->kind() != InputFile::BinaryKind &&
1430 file->kind() != InputFile::ObjKind)
1431 continue;
1432
1433 for (Symbol *symbol : file->getSymbols()) {
1434 // See `addTaggedSymbolReferences` for more details.
1435 if (symbol->type != STT_OBJECT ||
1436 symbol->binding == STB_LOCAL)
1437 continue;
1438 auto it = taggedSymbolReferenceCount.find(Val: symbol);
1439 if (it == taggedSymbolReferenceCount.end()) continue;
1440 unsigned &remainingAllowedTaggedRefs = it->second;
1441 if (remainingAllowedTaggedRefs == 0) {
1442 taggedSymbolReferenceCount.erase(I: it);
1443 continue;
1444 }
1445 --remainingAllowedTaggedRefs;
1446 }
1447 }
1448
1449 // `addTaggedSymbolReferences` has already checked that we have RELA
1450 // relocations, the only other way to get written addends is with
1451 // --apply-dynamic-relocs.
1452 if (!taggedSymbolReferenceCount.empty() && ctx.arg.writeAddends)
1453 ErrAlways(ctx) << "--apply-dynamic-relocs cannot be used with MTE globals";
1454
1455 // Now, `taggedSymbolReferenceCount` should only contain symbols that are
1456 // defined as tagged exactly the same amount as it's referenced, meaning all
1457 // uses are tagged.
1458 for (auto &[symbol, remainingTaggedRefs] : taggedSymbolReferenceCount) {
1459 assert(remainingTaggedRefs == 0 &&
1460 "Symbol is defined as tagged more times than it's used");
1461 symbol->setIsTagged(true);
1462 }
1463}
1464
1465void elf::setAArch64TargetInfo(Ctx &ctx) {
1466 if ((ctx.arg.andFeatures & GNU_PROPERTY_AARCH64_FEATURE_1_BTI) ||
1467 ctx.arg.zPacPlt)
1468 ctx.target.reset(p: new AArch64BtiPac(ctx));
1469 else
1470 ctx.target.reset(p: new AArch64(ctx));
1471}
1472