Skip to content

Commit abec50c

Browse files
authored
[BOLT][AArch64] Fix strict usage during ADR Relax (#71377)
Currently strict mode is used to expand number of optimized functions, not to shrink it. Revert the option usage in the pass, so passing strict option would relax adr instruction even if there are no nops around it. Also add check for nop after adr instruction.
1 parent 9bb69c1 commit abec50c

File tree

4 files changed

+26
-16
lines changed

4 files changed

+26
-16
lines changed

bolt/lib/Passes/ADRRelaxationPass.cpp

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -72,14 +72,17 @@ void ADRRelaxationPass::runOnFunction(BinaryFunction &BF) {
7272

7373
if (It != BB.begin() && BC.MIB->isNoop(*std::prev(It))) {
7474
It = BB.eraseInstruction(std::prev(It));
75-
} else if (opts::StrictMode && !BF.isSimple()) {
75+
} else if (std::next(It) != BB.end() && BC.MIB->isNoop(*std::next(It))) {
76+
BB.eraseInstruction(std::next(It));
77+
} else if (!opts::StrictMode && !BF.isSimple()) {
7678
// If the function is not simple, it may contain a jump table undetected
7779
// by us. This jump table may use an offset from the branch instruction
7880
// to land in the desired place. If we add new instructions, we
7981
// invalidate this offset, so we have to rely on linker-inserted NOP to
8082
// replace it with ADRP, and abort if it is not present.
83+
auto L = BC.scopeLock();
8184
errs() << formatv("BOLT-ERROR: Cannot relax adr in non-simple function "
82-
"{0}. Can't proceed in current mode.\n",
85+
"{0}. Use --strict option to override\n",
8386
BF.getOneName());
8487
PassFailed = true;
8588
return;

bolt/test/AArch64/r_aarch64_prelxx.s

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
// CHECKPREL-NEXT: R_AARCH64_PREL32 {{.*}} _start + 4
1313
// CHECKPREL-NEXT: R_AARCH64_PREL64 {{.*}} _start + 8
1414

15-
// RUN: llvm-bolt %t.exe -o %t.bolt
15+
// RUN: llvm-bolt %t.exe -o %t.bolt --strict
1616
// RUN: llvm-objdump -D %t.bolt | FileCheck %s --check-prefix=CHECKPREL32
1717

1818
// CHECKPREL32: [[#%x,DATATABLEADDR:]] <datatable>:
Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,33 +1,27 @@
11
# The second and third ADR instructions are non-local to functions
22
# and must be replaced with ADRP + ADD by BOLT
3-
# Also since main is non-simple, we can't change it's length so we have to
4-
# replace NOP with adrp, and if there is no nop before adr in non-simple
3+
# Also since main and test are non-simple, we can't change it's length so we
4+
# have to replace NOP with adrp, and if there is no nop before adr in non-simple
55
# function, we can't guarantee we didn't break possible jump tables, so we
6-
# fail in strict mode
6+
# fail in non-strict mode
77

88
# REQUIRES: system-linux
99

1010
# RUN: llvm-mc -filetype=obj -triple aarch64-unknown-unknown \
1111
# RUN: %s -o %t.o
1212
# RUN: %clang %cflags %t.o -o %t.exe -Wl,-q
13-
# RUN: llvm-bolt %t.exe -o %t.bolt --adr-relaxation=true
13+
# RUN: llvm-bolt %t.exe -o %t.bolt --adr-relaxation=true --strict
1414
# RUN: llvm-objdump --no-print-imm-hex -d --disassemble-symbols=main %t.bolt | FileCheck %s
1515
# RUN: %t.bolt
16-
# RUN: not llvm-bolt %t.exe -o %t.bolt --adr-relaxation=true --strict \
16+
# RUN: not llvm-bolt %t.exe -o %t.bolt --adr-relaxation=true \
1717
# RUN: 2>&1 | FileCheck %s --check-prefix CHECK-ERROR
1818

19-
.data
20-
.align 8
21-
.global Gvar
22-
Gvar: .xword 0x0
23-
.global Gvar2
24-
Gvar2: .xword 0x42
25-
2619
.text
2720
.align 4
2821
.global test
2922
.type test, %function
3023
test:
24+
adr x2, Gvar
3125
mov x0, xzr
3226
ret
3327
.size test, .-test
@@ -47,11 +41,22 @@ br:
4741
.CI:
4842
.word 0xff
4943

44+
.data
45+
.align 8
46+
.global Gvar
47+
Gvar: .xword 0x0
48+
.global Gvar2
49+
Gvar2: .xword 0x42
50+
.balign 4
51+
jmptable:
52+
.word 0
53+
.word test - jmptable
54+
5055
# CHECK: <main>:
5156
# CHECK-NEXT: adr x0, 0x{{[1-8a-f][0-9a-f]*}}
5257
# CHECK-NEXT: adrp x1, 0x{{[1-8a-f][0-9a-f]*}}
5358
# CHECK-NEXT: add x1, x1, #{{[1-8a-f][0-9a-f]*}}
5459
# CHECK-NEXT: adrp x2, 0x{{[1-8a-f][0-9a-f]*}}
5560
# CHECK-NEXT: add x2, x2, #{{[1-8a-f][0-9a-f]*}}
5661
# CHECK-NEXT: adr x3, 0x{{[1-8a-f][0-9a-f]*}}
57-
# CHECK-ERROR: BOLT-ERROR: Cannot relax adr in non-simple function main
62+
# CHECK-ERROR: BOLT-ERROR: Cannot relax adr in non-simple function

bolt/test/runtime/AArch64/controlflow.s

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@ test_cond_branch:
4848
.global test_branch_reg
4949
.type test_branch_reg, %function
5050
test_branch_reg:
51+
nop
5152
adr x0, test_branch_zero
5253
br x0
5354
panic
@@ -97,6 +98,7 @@ test_call:
9798
.global test_call_reg
9899
.type test_call_reg, %function
99100
test_call_reg:
101+
nop
100102
adr x0, test_call_foo
101103
blr x0
102104
panic

0 commit comments

Comments
 (0)