Skip to content

Commit 678d41a

Browse files
authored
Merge pull request #74607 from hborla/isolation-from-superclass-requirement
[Concurrency] Infer protocol isolation from superclass requirements.
2 parents a079c5c + 13f0c0c commit 678d41a

File tree

2 files changed

+54
-7
lines changed

2 files changed

+54
-7
lines changed

lib/Sema/TypeCheckConcurrency.cpp

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4603,30 +4603,43 @@ getIsolationFromConformances(NominalTypeDecl *nominal) {
46034603
static std::optional<ActorIsolation>
46044604
getIsolationFromInheritedProtocols(ProtocolDecl *protocol) {
46054605
std::optional<ActorIsolation> foundIsolation;
4606-
for (auto inherited : protocol->getInheritedProtocols()) {
4607-
switch (auto protoIsolation = getActorIsolation(inherited)) {
4606+
bool conflict = false;
4607+
4608+
auto inferIsolation = [&](ValueDecl *decl) {
4609+
switch (auto protoIsolation = getActorIsolation(decl)) {
46084610
case ActorIsolation::ActorInstance:
46094611
case ActorIsolation::Unspecified:
46104612
case ActorIsolation::Nonisolated:
46114613
case ActorIsolation::NonisolatedUnsafe:
4612-
break;
4614+
return;
46134615

46144616
case ActorIsolation::Erased:
46154617
llvm_unreachable("protocol cannot have erased isolation");
46164618

46174619
case ActorIsolation::GlobalActor:
46184620
if (!foundIsolation) {
46194621
foundIsolation = protoIsolation;
4620-
continue;
4622+
return;
46214623
}
46224624

46234625
if (*foundIsolation != protoIsolation)
4624-
return std::nullopt;
4626+
conflict = true;
46254627

4626-
break;
4628+
return;
46274629
}
4630+
};
4631+
4632+
for (auto inherited : protocol->getInheritedProtocols()) {
4633+
inferIsolation(inherited);
46284634
}
46294635

4636+
if (auto *superclass = protocol->getSuperclassDecl()) {
4637+
inferIsolation(superclass);
4638+
}
4639+
4640+
if (conflict)
4641+
return std::nullopt;
4642+
46304643
return foundIsolation;
46314644
}
46324645

test/Concurrency/global_actor_inference_swift6.swift

Lines changed: 35 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
// RUN: %target-swift-frontend -swift-version 6 -emit-module -emit-module-path %t/other_global_actor_inference.swiftmodule -module-name other_global_actor_inference -strict-concurrency=complete %S/Inputs/other_global_actor_inference.swift
44

5-
// RUN: %target-swift-frontend -swift-version 6 -I %t -disable-availability-checking %s -emit-sil -o /dev/null -verify -enable-upcoming-feature GlobalActorIsolatedTypesUsability
5+
// RUN: %target-swift-frontend -swift-version 6 -I %t -disable-availability-checking %s -emit-sil -o /dev/null -verify
66

77
// REQUIRES: concurrency
88

@@ -179,3 +179,37 @@ extension S3 {
179179
// expected-error@-1{{global actor 'SomeGlobalActor'-isolated instance method 'f()' cannot be used to satisfy main actor-isolated protocol requirement}}
180180
//expected-note@-2{{add 'nonisolated' to 'f()' to make this instance method not isolated to the actor}}
181181
}
182+
183+
@MainActor
184+
func onMain() {}
185+
186+
@MainActor
187+
class MainActorSuperclass {}
188+
189+
protocol InferMainFromSuperclass: MainActorSuperclass {
190+
func f()
191+
}
192+
193+
class C1: MainActorSuperclass, InferMainFromSuperclass {
194+
func f() {
195+
onMain() // okay
196+
}
197+
}
198+
199+
protocol InferenceConflictWithSuperclass: MainActorSuperclass, InferSomeGlobalActor {
200+
func g()
201+
// expected-note@-1 {{mark the protocol requirement 'g()' 'async' to allow actor-isolated conformances}}
202+
}
203+
204+
205+
class C2: MainActorSuperclass, InferenceConflictWithSuperclass {
206+
//expected-note@-1 {{add '@preconcurrency' to the 'InferenceConflictWithSuperclass' conformance to defer isolation checking to run time}}
207+
208+
func f() {}
209+
210+
func g() {}
211+
// expected-error@-1 {{main actor-isolated instance method 'g()' cannot be used to satisfy nonisolated protocol requirement}}
212+
// expected-note@-2 {{add 'nonisolated' to 'g()' to make this instance method not isolated to the actor}}
213+
}
214+
215+

0 commit comments

Comments
 (0)