Skip to content

Commit 083b3a8

Browse files
authored
Merge pull request #37228 from jckarter/objc-async-bridge-block-captures-5.5
[5.5] SILGen: Copy the block before detaching a task for async methods called from ObjC.
2 parents 3cbec1c + 217df8b commit 083b3a8

File tree

5 files changed

+32
-5
lines changed

5 files changed

+32
-5
lines changed

lib/SILGen/SILGenBridging.cpp

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1460,8 +1460,15 @@ SILFunction *SILGenFunction::emitNativeAsyncToForeignThunk(SILDeclRef thunk) {
14601460
for (auto input : objcFnTy->getParameters()) {
14611461
SILType argTy = getSILType(input, objcFnTy);
14621462
SILValue arg = F.begin()->createFunctionArgument(argTy);
1463-
1464-
if (!input.isConsumed()) {
1463+
// Copy block arguments.
1464+
if (argTy.isBlockPointerCompatible()) {
1465+
auto argCopy = B.createCopyBlock(loc, arg);
1466+
// If the argument is consumed, we're still responsible for releasing the
1467+
// original.
1468+
if (input.isConsumed())
1469+
emitManagedRValueWithCleanup(arg);
1470+
arg = argCopy;
1471+
} else if (!input.isConsumed()) {
14651472
arg = emitObjCUnconsumedArgument(*this, loc, arg);
14661473
}
14671474
auto managedArg = emitManagedRValueWithCleanup(arg);

test/Concurrency/Runtime/Inputs/objc_async.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,3 +17,5 @@
1717
__attribute__((swift_async_name("getter:catto()")));
1818

1919
@end
20+
21+
void scheduleButt(Butt *b, NSString *s);

test/Concurrency/Runtime/Inputs/objc_async.m

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,4 +26,11 @@ -(void)obtainCat:(void (^ _Nonnull)(NSInteger, NSError* _Nullable))completionHan
2626
completionHandler(nil, [NSError errorWithDomain:@"obtainCat" code:456 userInfo:nil]);
2727
}
2828

29-
@end
29+
@end
30+
31+
void scheduleButt(Butt *b, NSString *s) {
32+
[b butt: 1738 completionHandler: ^(NSInteger i) {
33+
printf("butt %p named %s occurred at %zd", b, [s UTF8String], (ssize_t)i);
34+
fflush(stdout);
35+
}];
36+
}

test/Concurrency/Runtime/objc_async.swift

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
// RUN: %empty-directory(%t)
2-
// RUN: %target-clang %S/Inputs/objc_async.m -c -o %t/objc_async_objc.o
2+
// RUN: %target-clang -fobjc-arc %S/Inputs/objc_async.m -c -o %t/objc_async_objc.o
33
// RUN: %target-build-swift -Xfrontend -enable-experimental-concurrency -parse-as-library -module-name main -import-objc-header %S/Inputs/objc_async.h %s %t/objc_async_objc.o -o %t/objc_async
44
// RUN: %target-run %t/objc_async | %FileCheck %s
55

@@ -28,6 +28,13 @@ func farmTest() async {
2828
}
2929
}
3030

31+
class Clbuttic: Butt {
32+
override func butt(_ x: Int) async -> Int {
33+
print("called into override")
34+
return 679
35+
}
36+
}
37+
3138
@main struct Main {
3239
static func main() async {
3340
// CHECK: starting 1738
@@ -39,6 +46,10 @@ func farmTest() async {
3946
// CHECK-NEXT: obtaining cat has failed!
4047
// CHECK-NEXT: caught exception
4148
await farmTest()
49+
50+
// CHECK-NEXT: called into override
51+
// CHECK-NEXT: butt {{.*}} named clbuttic occurred at 679
52+
scheduleButt(Clbuttic(), "clbuttic")
4253
}
4354
}
4455

test/SILGen/objc_async_from_swift.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ func testSlowServing(p: SlowServing) async throws {
2929

3030
class SlowSwiftServer: NSObject, SlowServing {
3131
// CHECK-LABEL: sil {{.*}} @${{.*}}10requestInt{{.*}}To :
32-
// CHECK: [[BLOCK_COPY:%.*]] = copy_value %0
32+
// CHECK: [[BLOCK_COPY:%.*]] = copy_block %0
3333
// CHECK: [[SELF:%.*]] = copy_value %1
3434
// CHECK: [[CLOSURE_REF:%.*]] = function_ref [[CLOSURE_IMP:@\$.*10requestInt.*U_To]] :
3535
// CHECK: [[CLOSURE:%.*]] = partial_apply [callee_guaranteed] [[CLOSURE_REF]]([[BLOCK_COPY]], [[SELF]])

0 commit comments

Comments
 (0)