Skip to content

Commit c3e9676

Browse files
authored
Merge pull request #38261 from ahoppen/pr/check-semantics-expr-for-completion-handler-call
[Async Refactoring] Get semantics providing expr to decide if call is to completion handler
2 parents d69f0df + ec89579 commit c3e9676

File tree

3 files changed

+24
-11
lines changed

3 files changed

+24
-11
lines changed

lib/IDE/Refactoring.cpp

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4258,10 +4258,12 @@ struct AsyncHandlerDesc {
42584258
if (!isValid())
42594259
return nullptr;
42604260

4261-
if (Node.isExpr(swift::ExprKind::Call)) {
4262-
CallExpr *CE = cast<CallExpr>(Node.dyn_cast<Expr *>());
4263-
if (CE->getFn()->getReferencedDecl().getDecl() == getHandler())
4264-
return CE;
4261+
if (auto E = Node.dyn_cast<Expr *>()) {
4262+
if (auto *CE = dyn_cast<CallExpr>(E->getSemanticsProvidingExpr())) {
4263+
if (CE->getFn()->getReferencedDecl().getDecl() == getHandler()) {
4264+
return CE;
4265+
}
4266+
}
42654267
}
42664268
return nullptr;
42674269
}
@@ -6357,10 +6359,10 @@ class AsyncConverter : private SourceEntityWalker {
63576359
}
63586360
} else if (CallExpr *CE = TopHandler.getAsHandlerCall(E)) {
63596361
if (Scopes.back().isWrappedInContination()) {
6360-
return addCustom(CE->getSourceRange(),
6362+
return addCustom(E->getSourceRange(),
63616363
[&]() { addHandlerCallToContinuation(CE); });
63626364
} else if (NestedExprCount == 0) {
6363-
return addCustom(CE->getSourceRange(), [&]() { addHandlerCall(CE); });
6365+
return addCustom(E->getSourceRange(), [&]() { addHandlerCall(CE); });
63646366
}
63656367
} else if (auto *CE = dyn_cast<CallExpr>(E)) {
63666368
// Try and hoist a call's completion handler. Don't do so if

test/refactoring/ConvertAsync/convert_function.swift

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -287,15 +287,12 @@ func testReturnHandling2(completion: @escaping (String) -> ()) {
287287
// RETURN-HANDLING2-NEXT: }
288288
// RETURN-HANDLING2-NEXT: }
289289

290-
// FIXME: We should arguably be able to handle transforming this completion handler call (rdar://78011350).
291-
// RUN: %refactor -add-async-alternative -dump-text -source-filename %s -pos=%(line+1):1 | %FileCheck -check-prefix=RETURN-HANDLING3 %s
290+
// RUN: %refactor-check-compiles -add-async-alternative -dump-text -source-filename %s -pos=%(line+1):1 | %FileCheck -check-prefix=RETURN-HANDLING3 %s
292291
func testReturnHandling3(_ completion: (String?, Error?) -> Void) {
293292
return (completion("", nil))
294293
}
295294
// RETURN-HANDLING3: func testReturnHandling3() async throws -> String {
296-
// RETURN-HANDLING3-NEXT: return try await withCheckedThrowingContinuation { continuation in
297-
// RETURN-HANDLING3-NEXT: (continuation.resume(returning: ""))
298-
// RETURN-HANDLING3-NEXT: }
295+
// RETURN-HANDLING3-NEXT: {{^}} return ""{{$}}
299296
// RETURN-HANDLING3-NEXT: }
300297

301298
// RUN: %refactor -convert-to-async -dump-text -source-filename %s -pos=%(line+1):1 | %FileCheck -check-prefix=RDAR78693050 %s

test/refactoring/ConvertAsync/convert_to_continuation.swift

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,20 @@ func testCreateContinuation(completionHandler: (Int) -> Void) {
2626
// CREATE-CONTINUATION-NEXT: }
2727
// CREATE-CONTINUATION-NEXT: }
2828

29+
// RUN: %refactor-check-compiles -convert-to-async -dump-text -source-filename %s -pos=%(line+1):1 | %FileCheck -check-prefix=CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS %s
30+
func testCreateContinuationWithCompletionHandlerCallInParens(completionHandler: (Int) -> Void) {
31+
withoutAsyncAlternativeBecauseOfMismatchedCompletionHandlerName {
32+
(completionHandler($0))
33+
}
34+
}
35+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS: func testCreateContinuationWithCompletionHandlerCallInParens() async -> Int {
36+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS-NEXT: return await withCheckedContinuation { continuation in
37+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS-NEXT: withoutAsyncAlternativeBecauseOfMismatchedCompletionHandlerName {
38+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS-NEXT: continuation.resume(returning: $0)
39+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS-NEXT: }
40+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS-NEXT: }
41+
// CREATE-CONTINUATION-HANDLER-CALL-IN-PARENS-NEXT: }
42+
2943
// RUN: %refactor-check-compiles -convert-to-async -dump-text -source-filename %s -pos=%(line+1):1 | %FileCheck -check-prefix=CREATE-CONTINUATION-BECAUSE-RETURN-VALUE %s
3044
func testCreateContinuationBecauseOfReturnValue(completionHandler: (Int) -> Void) {
3145
_ = withoutAsyncAlternativeBecauseOfReturnValue {

0 commit comments

Comments
 (0)