Skip to content

Commit ec3a34c

Browse files
committed
[PAC][lld][AArch64][ELF] Support signed GOT with tiny code model
Support `R_AARCH64_AUTH_GOT_ADR_PREL_LO21` and `R_AARCH64_AUTH_GOT_LD_PREL19` GOT-generating relocations.
1 parent 03f9115 commit ec3a34c

File tree

5 files changed

+87
-4
lines changed

5 files changed

+87
-4
lines changed

lld/ELF/Arch/AArch64.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -205,6 +205,9 @@ RelExpr AArch64::getRelExpr(RelType type, const Symbol &s,
205205
case R_AARCH64_AUTH_LD64_GOT_LO12_NC:
206206
case R_AARCH64_AUTH_GOT_ADD_LO12_NC:
207207
return RE_AARCH64_AUTH_GOT;
208+
case R_AARCH64_AUTH_GOT_LD_PREL19:
209+
case R_AARCH64_AUTH_GOT_ADR_PREL_LO21:
210+
return RE_AARCH64_AUTH_GOT_PC;
208211
case R_AARCH64_LD64_GOTPAGE_LO15:
209212
return RE_AARCH64_GOT_PAGE;
210213
case R_AARCH64_ADR_GOT_PAGE:
@@ -548,6 +551,7 @@ void AArch64::relocate(uint8_t *loc, const Relocation &rel,
548551
write32AArch64Addr(loc, val >> 12);
549552
break;
550553
case R_AARCH64_ADR_PREL_LO21:
554+
case R_AARCH64_AUTH_GOT_ADR_PREL_LO21:
551555
checkInt(ctx, loc, val, 21, rel);
552556
write32AArch64Addr(loc, val);
553557
break;
@@ -568,6 +572,7 @@ void AArch64::relocate(uint8_t *loc, const Relocation &rel,
568572
case R_AARCH64_CONDBR19:
569573
case R_AARCH64_LD_PREL_LO19:
570574
case R_AARCH64_GOT_LD_PREL19:
575+
case R_AARCH64_AUTH_GOT_LD_PREL19:
571576
checkAlignment(ctx, loc, val, 4, rel);
572577
checkInt(ctx, loc, val, 21, rel);
573578
writeMaskedBits32le(loc, (val & 0x1FFFFC) << 3, 0x1FFFFC << 3);

lld/ELF/InputSection.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -817,6 +817,7 @@ uint64_t InputSectionBase::getRelocTargetVA(Ctx &ctx, const Relocation &r,
817817
case RE_AARCH64_GOT_PAGE:
818818
return r.sym->getGotVA(ctx) + a - getAArch64Page(ctx.in.got->getVA());
819819
case R_GOT_PC:
820+
case R_AARCH64_AUTH_GOT_PC:
820821
case R_RELAX_TLS_GD_TO_IE:
821822
return r.sym->getGotVA(ctx) + a - p;
822823
case R_GOTPLT_GOTREL:

lld/ELF/Relocations.cpp

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -197,8 +197,9 @@ static bool needsPlt(RelExpr expr) {
197197
}
198198

199199
bool lld::elf::needsGot(RelExpr expr) {
200-
return oneof<R_GOT, RE_AARCH64_AUTH_GOT, R_GOT_OFF, RE_MIPS_GOT_LOCAL_PAGE,
201-
RE_MIPS_GOT_OFF, RE_MIPS_GOT_OFF32, RE_AARCH64_GOT_PAGE_PC,
200+
return oneof<R_GOT, RE_AARCH64_AUTH_GOT, RE_AARCH64_AUTH_GOT_PC, R_GOT_OFF,
201+
RE_MIPS_GOT_LOCAL_PAGE, RE_MIPS_GOT_OFF, RE_MIPS_GOT_OFF32,
202+
RE_AARCH64_GOT_PAGE_PC, RE_AARCH64_AUTH_GOT_PAGE_PC,
202203
RE_AARCH64_AUTH_GOT_PAGE_PC, R_GOT_PC, R_GOTPLT,
203204
RE_AARCH64_GOT_PAGE, RE_LOONGARCH_GOT, RE_LOONGARCH_GOT_PAGE_PC>(
204205
expr);
@@ -981,7 +982,8 @@ bool RelocationScanner::isStaticLinkTimeConstant(RelExpr e, RelType type,
981982
R_GOTPLTONLY_PC, R_PLT_PC, R_PLT_GOTREL, R_PLT_GOTPLT,
982983
R_GOTPLT_GOTREL, R_GOTPLT_PC, RE_PPC32_PLTREL, RE_PPC64_CALL_PLT,
983984
RE_PPC64_RELAX_TOC, RE_RISCV_ADD, RE_AARCH64_GOT_PAGE,
984-
RE_AARCH64_AUTH_GOT, RE_LOONGARCH_PLT_PAGE_PC, RE_LOONGARCH_GOT,
985+
RE_AARCH64_AUTH_GOT, RE_AARCH64_AUTH_GOT_PC,
986+
RE_LOONGARCH_PLT_PAGE_PC, RE_LOONGARCH_GOT,
985987
RE_LOONGARCH_GOT_PAGE_PC>(e))
986988
return true;
987989

@@ -1096,7 +1098,8 @@ void RelocationScanner::processAux(RelExpr expr, RelType type, uint64_t offset,
10961098
} else if (!sym.isTls() || ctx.arg.emachine != EM_LOONGARCH) {
10971099
// Many LoongArch TLS relocs reuse the RE_LOONGARCH_GOT type, in which
10981100
// case the NEEDS_GOT flag shouldn't get set.
1099-
if (expr == RE_AARCH64_AUTH_GOT || expr == RE_AARCH64_AUTH_GOT_PAGE_PC)
1101+
if (expr == RE_AARCH64_AUTH_GOT || expr == RE_AARCH64_AUTH_GOT_PAGE_PC ||
1102+
expr == RE_AARCH64_AUTH_GOT_PAGE_PC)
11001103
sym.setFlags(NEEDS_GOT | NEEDS_GOT_AUTH);
11011104
else
11021105
sym.setFlags(NEEDS_GOT | NEEDS_GOT_NONAUTH);

lld/ELF/Relocations.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,7 @@ enum RelExpr {
9595
RE_AARCH64_AUTH_GOT_PAGE_PC,
9696
RE_AARCH64_GOT_PAGE,
9797
RE_AARCH64_AUTH_GOT,
98+
RE_AARCH64_AUTH_GOT_PC,
9899
RE_AARCH64_PAGE_PC,
99100
RE_AARCH64_RELAX_TLS_GD_TO_IE_PAGE_PC,
100101
RE_AARCH64_TLSDESC_PAGE,

lld/test/ELF/aarch64-got-relocations-pauth.s

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,79 @@ _start:
7777
adrp x1, :got_auth:zed
7878
add x1, x1, :got_auth_lo12:zed
7979

80+
#--- ok-tiny.s
81+
82+
# RUN: llvm-mc -filetype=obj -triple=aarch64-none-linux ok-tiny.s -o ok-tiny.o
83+
84+
# RUN: ld.lld ok-tiny.o a.so -pie -o external-tiny
85+
# RUN: llvm-readelf -r -S -x .got external-tiny | FileCheck %s --check-prefix=EXTERNAL-TINY
86+
87+
# RUN: ld.lld ok-tiny.o a.o -pie -o local-tiny
88+
# RUN: llvm-readelf -r -S -x .got -s local-tiny | FileCheck %s --check-prefix=LOCAL-TINY
89+
90+
# EXTERNAL-TINY: Offset Info Type Symbol's Value Symbol's Name + Addend
91+
# EXTERNAL-TINY-NEXT: 0000000000020380 000000010000e201 R_AARCH64_AUTH_GLOB_DAT 0000000000000000 bar + 0
92+
# EXTERNAL-TINY-NEXT: 0000000000020388 000000020000e201 R_AARCH64_AUTH_GLOB_DAT 0000000000000000 zed + 0
93+
94+
## Symbol's values for bar and zed are equal since they contain no content (see Inputs/shared.s)
95+
# LOCAL-TINY: Offset Info Type Symbol's Value Symbol's Name + Addend
96+
# LOCAL-TINY-NEXT: 0000000000020320 0000000000000411 R_AARCH64_AUTH_RELATIVE 10260
97+
# LOCAL-TINY-NEXT: 0000000000020328 0000000000000411 R_AARCH64_AUTH_RELATIVE 10260
98+
99+
# EXTERNAL-TINY: Hex dump of section '.got':
100+
# EXTERNAL-TINY-NEXT: 0x00020380 00000000 00000080 00000000 000000a0
101+
# ^^
102+
# 0b10000000 bit 63 address diversity = true, bits 61..60 key = IA
103+
# ^^
104+
# 0b10100000 bit 63 address diversity = true, bits 61..60 key = DA
105+
106+
# LOCAL-TINY: Symbol table '.symtab' contains {{.*}} entries:
107+
# LOCAL-TINY: Num: Value Size Type Bind Vis Ndx Name
108+
# LOCAL-TINY: 0000000000010260 0 FUNC GLOBAL DEFAULT 6 bar
109+
# LOCAL-TINY: 0000000000010260 0 NOTYPE GLOBAL DEFAULT 6 zed
110+
111+
# LOCAL-TINY: Hex dump of section '.got':
112+
# LOCAL-TINY-NEXT: 0x00020320 00000000 00000080 00000000 000000a0
113+
# ^^
114+
# 0b10000000 bit 63 address diversity = true, bits 61..60 key = IA
115+
# ^^
116+
# 0b10100000 bit 63 address diversity = true, bits 61..60 key = DA
117+
118+
# RUN: llvm-objdump -d external-tiny | FileCheck %s --check-prefix=EXTERNAL-TINY-ASM
119+
120+
# EXTERNAL-TINY-ASM: <_start>:
121+
# EXTERNAL-TINY-ASM-NEXT: adr x0, 0x20380
122+
# EXTERNAL-TINY-ASM-NEXT: ldr x1, [x0]
123+
# EXTERNAL-TINY-ASM-NEXT: adr x0, 0x20380
124+
# EXTERNAL-TINY-ASM-NEXT: ldr x1, 0x20380
125+
# EXTERNAL-TINY-ASM-NEXT: adr x0, 0x20388
126+
# EXTERNAL-TINY-ASM-NEXT: ldr x1, [x0]
127+
# EXTERNAL-TINY-ASM-NEXT: adr x0, 0x20388
128+
# EXTERNAL-TINY-ASM-NEXT: ldr x1, 0x20388
129+
130+
# RUN: llvm-objdump -d local-tiny | FileCheck %s --check-prefix=LOCAL-TINY-ASM
131+
132+
# LOCAL-TINY-ASM: <_start>:
133+
# LOCAL-TINY-ASM-NEXT: adr x0, 0x20320
134+
# LOCAL-TINY-ASM-NEXT: ldr x1, [x0]
135+
# LOCAL-TINY-ASM-NEXT: adr x0, 0x20320
136+
# LOCAL-TINY-ASM-NEXT: ldr x1, 0x20320
137+
# LOCAL-TINY-ASM-NEXT: adr x0, 0x20328
138+
# LOCAL-TINY-ASM-NEXT: ldr x1, [x0]
139+
# LOCAL-TINY-ASM-NEXT: adr x0, 0x20328
140+
# LOCAL-TINY-ASM-NEXT: ldr x1, 0x20328
141+
142+
.globl _start
143+
_start:
144+
adr x0, :got_auth:bar
145+
ldr x1, [x0]
146+
adr x0, :got_auth:bar
147+
ldr x1, :got_auth:bar
148+
adr x0, :got_auth:zed
149+
ldr x1, [x0]
150+
adr x0, :got_auth:zed
151+
ldr x1, :got_auth:zed
152+
80153
#--- err.s
81154
# RUN: llvm-mc -filetype=obj -triple=aarch64 err.s -o err.o
82155
# RUN: not ld.lld err.o a.so -pie -o /dev/null 2>&1 | FileCheck %s --check-prefix=ERR --implicit-check-not=error:

0 commit comments

Comments
 (0)