diff --git a/lib/Sema/TypeCheckConcurrency.cpp b/lib/Sema/TypeCheckConcurrency.cpp index 4737591f2e15a..8c188fe83e67a 100644 --- a/lib/Sema/TypeCheckConcurrency.cpp +++ b/lib/Sema/TypeCheckConcurrency.cpp @@ -3344,6 +3344,13 @@ ActorIsolation ActorIsolationRequest::evaluate( return inferredIsolation(isolation); } + // If this is a dynamic replacement for another function, use the + // actor isolation of the function it replaces. + if (auto replacedDecl = value->getDynamicallyReplacedDecl()) { + if (auto isolation = getActorIsolation(replacedDecl)) + return inferredIsolation(isolation); + } + if (shouldInferAttributeInContext(value->getDeclContext())) { // If the declaration witnesses a protocol requirement that is isolated, // use that. diff --git a/test/Concurrency/Inputs/dynamically_replaceable.swift b/test/Concurrency/Inputs/dynamically_replaceable.swift new file mode 100644 index 0000000000000..08632d00bee2a --- /dev/null +++ b/test/Concurrency/Inputs/dynamically_replaceable.swift @@ -0,0 +1,2 @@ +@MainActor +public dynamic func dynamicOnMainActor() { } diff --git a/test/Concurrency/global_actor_inference.swift b/test/Concurrency/global_actor_inference.swift index 84de2be68f223..d23cc3992c586 100644 --- a/test/Concurrency/global_actor_inference.swift +++ b/test/Concurrency/global_actor_inference.swift @@ -1,5 +1,8 @@ -// RUN: %target-typecheck-verify-swift -disable-availability-checking +// RUN: %empty-directory(%t) +// RUN: %target-swift-frontend -emit-module -emit-module-path %t/dynamically_replaceable.swiftmodule -module-name dynamically_replaceable -warn-concurrency %S/Inputs/dynamically_replaceable.swift +// RUN: %target-typecheck-verify-swift -I %t -disable-availability-checking // REQUIRES: concurrency +import dynamically_replaceable actor SomeActor { } @@ -552,3 +555,11 @@ func useFooInADefer() -> String { return "hello" } + +// ---------------------------------------------------------------------- +// Dynamic replacement +// ---------------------------------------------------------------------- +@_dynamicReplacement(for: dynamicOnMainActor) +func replacesDynamicOnMainActor() { + onlyOnMainActor() +}