Skip to content

Commit 7047559

Browse files
committed
[CGObjC] Allow clang.arc.attachedcall on -O0 on AArch64
It is supported in GlobalISel there. It is not supported on X86 GlobalISel.
1 parent 2de905d commit 7047559

File tree

5 files changed

+293
-30
lines changed

5 files changed

+293
-30
lines changed

clang/lib/CodeGen/CGObjC.cpp

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2415,9 +2415,7 @@ static llvm::Value *emitOptimizedARCReturnCall(llvm::Value *value,
24152415
emitAutoreleasedReturnValueMarker(CGF);
24162416

24172417
// Add operand bundle "clang.arc.attachedcall" to the call instead of emitting
2418-
// retainRV or claimRV calls in the IR. We currently do this only when the
2419-
// optimization level isn't -O0 since global-isel, which is currently run at
2420-
// -O0, doesn't know about the operand bundle.
2418+
// retainRV or claimRV calls in the IR.
24212419
ObjCEntrypoints &EPs = CGF.CGM.getObjCEntrypoints();
24222420
llvm::Function *&EP = IsRetainRV
24232421
? EPs.objc_retainAutoreleasedReturnValue
@@ -2429,11 +2427,9 @@ static llvm::Value *emitOptimizedARCReturnCall(llvm::Value *value,
24292427

24302428
llvm::Triple::ArchType Arch = CGF.CGM.getTriple().getArch();
24312429

2432-
// FIXME: Do this on all targets and at -O0 too. This can be enabled only if
2433-
// the target backend knows how to handle the operand bundle.
2434-
if (CGF.CGM.getCodeGenOpts().OptimizationLevel > 0 &&
2435-
(Arch == llvm::Triple::aarch64 || Arch == llvm::Triple::aarch64_32 ||
2436-
Arch == llvm::Triple::x86_64)) {
2430+
if ((CGF.CGM.getCodeGenOpts().OptimizationLevel > 0 &&
2431+
Arch == llvm::Triple::x86_64) ||
2432+
Arch == llvm::Triple::aarch64 || Arch == llvm::Triple::aarch64_32) {
24372433
llvm::Value *bundleArgs[] = {EP};
24382434
llvm::OperandBundleDef OB("clang.arc.attachedcall", bundleArgs);
24392435
auto *oldCall = cast<llvm::CallBase>(value);

clang/test/CodeGenObjC/arc-arm.m

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,17 @@
11
// RUN: %clang_cc1 -triple armv7-apple-darwin10 -emit-llvm -fblocks -fobjc-arc -o - %s | FileCheck %s
2-
// RUN: %clang_cc1 -triple arm64-apple-ios -emit-llvm -fblocks -fobjc-arc -o - %s | FileCheck %s
2+
// RUN: %clang_cc1 -triple arm64-apple-ios -emit-llvm -fblocks -fobjc-arc -o - %s | FileCheck %s -check-prefix=ARM64-ATTACHED
33

44
// use an autorelease marker on ARM64.
55

66
id test0(void) {
77
extern id test0_helper(void);
88
// CHECK: [[T0:%.*]] = call [[CC:(arm_aapcscc )?]]ptr @test0_helper()
99
// CHECK-NEXT: ret ptr [[T0]]
10+
// ARM64-ATTACHED: %call1 = call ptr @test0_helper() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
11+
// ARM64-ATTACHED: call void asm sideeffect "mov\09fp, fp\09\09// marker for objc_retainAutoreleaseReturnValue", ""()
12+
// ARM64-ATTACHED: call void (...) @llvm.objc.clang.arc.noop.use(ptr %call1) #2
13+
// ARM64-ATTACHED: %0 = tail call ptr @llvm.objc.autoreleaseReturnValue(ptr %call1) #2
14+
// ARM64-ATTACHED: ret ptr %0
1015
return test0_helper();
1116
}
1217

@@ -18,6 +23,12 @@ void test1(void) {
1823
// CHECK-NEXT: store ptr [[T1]],
1924
// CHECK-NEXT: call [[CC]]void @llvm.objc.storeStrong(
2025
// CHECK-NEXT: ret void
26+
// ARM64-ATTACHED: %call1 = call ptr @test1_helper() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
27+
// ARM64-ATTACHED: call void asm sideeffect "mov\09fp, fp\09\09// marker for objc_retainAutoreleaseReturnValue", ""()
28+
// ARM64-ATTACHED: call void (...) @llvm.objc.clang.arc.noop.use(ptr %call1) #2
29+
// ARM64-ATTACHED: store ptr %call1,
30+
// ARM64-ATTACHED: call void @llvm.objc.storeStrong(
31+
// ARM64-ATTACHED: ret void
2132
id x = test1_helper();
2233
}
2334

@@ -26,12 +37,22 @@ void test1(void) {
2637
extern A *test2_helper(void);
2738
// CHECK: [[T0:%.*]] = call [[CC]]ptr @test2_helper()
2839
// CHECK-NEXT: ret ptr [[T0]]
40+
// ARM64-ATTACHED: %call1 = call ptr @test2_helper() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
41+
// ARM64-ATTACHED: call void asm sideeffect "mov\09fp, fp\09\09// marker for objc_retainAutoreleaseReturnValue", ""()
42+
// ARM64-ATTACHED: call void (...) @llvm.objc.clang.arc.noop.use(ptr %call1) #2
43+
// ARM64-ATTACHED: %0 = tail call ptr @llvm.objc.autoreleaseReturnValue(ptr %call1) #2
44+
// ARM64-ATTACHED: ret ptr %0
2945
return test2_helper();
3046
}
3147

3248
id test3(void) {
3349
extern A *test3_helper(void);
3450
// CHECK: [[T0:%.*]] = call [[CC]]ptr @test3_helper()
3551
// CHECK-NEXT: ret ptr [[T0]]
52+
// ARM64-ATTACHED: %call1 = call ptr @test3_helper() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
53+
// ARM64-ATTACHED: call void asm sideeffect "mov\09fp, fp\09\09// marker for objc_retainAutoreleaseReturnValue", ""()
54+
// ARM64-ATTACHED: call void (...) @llvm.objc.clang.arc.noop.use(ptr %call1) #2
55+
// ARM64-ATTACHED: %0 = tail call ptr @llvm.objc.autoreleaseReturnValue(ptr %call1) #2
56+
// ARM64-ATTACHED: ret ptr %0
3657
return test3_helper();
3758
}

clang/test/CodeGenObjC/arc-unsafeclaim.m

Lines changed: 31 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
// RUN: %clang_cc1 -triple i386-apple-darwin11 -fobjc-runtime=macosx-fragile-10.11 -fobjc-arc -emit-llvm -o - %s | FileCheck %s -check-prefix=CHECK -check-prefix=CHECK-UNOPTIMIZED -check-prefix=CHECK-MARKED -check-prefix=CALL
88

99
// Make sure it works on ARM64.
10-
// RUN: %clang_cc1 -triple arm64-apple-ios9 -fobjc-runtime=ios-9.0 -fobjc-arc -emit-llvm -o - %s | FileCheck %s -check-prefix=CHECK -check-prefix=CHECK-UNOPTIMIZED -check-prefix=CHECK-MARKED -check-prefix=CALL
10+
// RUN: %clang_cc1 -triple arm64-apple-ios9 -fobjc-runtime=ios-9.0 -fobjc-arc -emit-llvm -o - %s | FileCheck %s -check-prefix=ATTACHED-CALL
1111

1212
// Make sure it works on ARM.
1313
// RUN: %clang_cc1 -triple armv7-apple-ios9 -fobjc-runtime=ios-9.0 -fobjc-arc -emit-llvm -o - %s | FileCheck %s -check-prefix=CHECK -check-prefix=CHECK-UNOPTIMIZED -check-prefix=CHECK-MARKED -check-prefix=CALL
@@ -41,8 +41,9 @@ void test_assign(void) {
4141
// DISABLED-NEXT: [[T2:%.*]] = {{.*}}call ptr @llvm.objc.retainAutoreleasedReturnValue(ptr [[T0]])
4242

4343
// ATTACHED-CALL-LABEL: define{{.*}} void @test_assign()
44-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ],
45-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
44+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ]
45+
// ATTACHED-CALL-DAG: call void asm sideeffect
46+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
4647

4748
void test_assign_assign(void) {
4849
__unsafe_unretained id x, y;
@@ -62,8 +63,9 @@ void test_assign_assign(void) {
6263
// CHECK-NEXT: ret void
6364

6465
// ATTACHED-CALL-LABEL: define{{.*}} void @test_assign_assign()
65-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ],
66-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
66+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ]
67+
// ATTACHED-CALL-DAG: call void asm sideeffect
68+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
6769

6870
void test_strong_assign_assign(void) {
6971
__strong id x;
@@ -88,8 +90,9 @@ void test_strong_assign_assign(void) {
8890
// CHECK-NEXT: ret void
8991

9092
// ATTACHED-CALL-LABEL: define{{.*}} void @test_strong_assign_assign()
91-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ],
92-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
93+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
94+
// ATTACHED-CALL-DAG: call void asm sideeffect
95+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
9396

9497
void test_assign_strong_assign(void) {
9598
__unsafe_unretained id x;
@@ -114,8 +117,9 @@ void test_assign_strong_assign(void) {
114117
// CHECK-NEXT: ret void
115118

116119
// ATTACHED-CALL-LABEL: define{{.*}} void @test_assign_strong_assign()
117-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ],
118-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
120+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
121+
// ATTACHED-CALL-DAG: call void asm sideeffect
122+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
119123

120124
void test_init(void) {
121125
__unsafe_unretained id x = makeA();
@@ -131,8 +135,9 @@ void test_init(void) {
131135
// CHECK-NEXT: ret void
132136

133137
// ATTACHED-CALL-LABEL: define{{.*}} void @test_init()
134-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ],
135-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
138+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ]
139+
// ATTACHED-CALL-DAG: call void asm sideeffect
140+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
136141

137142
void test_init_assignment(void) {
138143
__unsafe_unretained id x;
@@ -152,8 +157,9 @@ void test_init_assignment(void) {
152157
// CHECK-NEXT: ret void
153158

154159
// ATTACHED-CALL-LABEL: define{{.*}} void @test_init_assignment()
155-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ],
156-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
160+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ]
161+
// ATTACHED-CALL-DAG: call void asm sideeffect
162+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
157163

158164
void test_strong_init_assignment(void) {
159165
__unsafe_unretained id x;
@@ -175,8 +181,9 @@ void test_strong_init_assignment(void) {
175181
// CHECK-NEXT: ret void
176182

177183
// ATTACHED-CALL-LABEL: define{{.*}} void @test_strong_init_assignment()
178-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ],
179-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
184+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
185+
// ATTACHED-CALL-DAG: call void asm sideeffect
186+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
180187

181188
void test_init_strong_assignment(void) {
182189
__strong id x;
@@ -200,8 +207,9 @@ void test_init_strong_assignment(void) {
200207
// CHECK-NEXT: ret void
201208

202209
// ATTACHED-CALL-LABEL: define{{.*}} void @test_init_strong_assignment()
203-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ],
204-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
210+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.retainAutoreleasedReturnValue) ]
211+
// ATTACHED-CALL-DAG: call void asm sideeffect
212+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
205213

206214
void test_ignored(void) {
207215
makeA();
@@ -214,8 +222,9 @@ void test_ignored(void) {
214222
// CHECK-NEXT: ret void
215223

216224
// ATTACHED-CALL-LABEL: define{{.*}} void @test_ignored()
217-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ],
218-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
225+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ]
226+
// ATTACHED-CALL-DAG: call void asm sideeffect
227+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
219228

220229
void test_cast_to_void(void) {
221230
(void) makeA();
@@ -228,8 +237,9 @@ void test_cast_to_void(void) {
228237
// CHECK-NEXT: ret void
229238

230239
// ATTACHED-CALL-LABEL: define{{.*}} void @test_cast_to_void()
231-
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ],
232-
// ATTACHED-CALL: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
240+
// ATTACHED-CALL: [[T0:%.*]] = call ptr @makeA() [ "clang.arc.attachedcall"(ptr @llvm.objc.unsafeClaimAutoreleasedReturnValue) ]
241+
// ATTACHED-CALL-DAG: call void asm sideeffect
242+
// ATTACHED-CALL-NEXT: call void (...) @llvm.objc.clang.arc.noop.use(ptr [[T0]])
233243

234244

235245
// This is always at the end of the module.

llvm/lib/Target/AArch64/AArch64FastISel.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
#include "llvm/ADT/DenseMap.h"
2626
#include "llvm/ADT/SmallVector.h"
2727
#include "llvm/Analysis/BranchProbabilityInfo.h"
28+
#include "llvm/Analysis/ObjCARCUtil.h"
2829
#include "llvm/CodeGen/CallingConvLower.h"
2930
#include "llvm/CodeGen/FastISel.h"
3031
#include "llvm/CodeGen/FunctionLoweringInfo.h"
@@ -3159,6 +3160,10 @@ bool AArch64FastISel::fastLowerCall(CallLoweringInfo &CLI) {
31593160
CLI.CB->getOperandBundle(LLVMContext::OB_kcfi))
31603161
return false;
31613162

3163+
// Allow SelectionDAG isel to handle clang.arc.attachedcall operand bundle.
3164+
if (CLI.CB && objcarc::hasAttachedCallOpBundle(CLI.CB))
3165+
return false;
3166+
31623167
// Allow SelectionDAG isel to handle tail calls.
31633168
if (IsTailCall)
31643169
return false;

0 commit comments

Comments
 (0)