From 86f3fe1680e6bb7078afc9dbc6739ed5696c3e49 Mon Sep 17 00:00:00 2001 From: Holly Borla Date: Tue, 9 Jul 2024 19:43:40 -0700 Subject: [PATCH] [Concurrency] Don't infer actor isolation from inherited conformances. If a conformance is inherited from a superclass, the isolation of the subclass should be inferred directly from the superclass. If the superclass has opted out of global actor inference from a protocol, such as by conforming to the protocol in an extension, then the subclass should not infer isolation from the protocol. --- lib/Sema/TypeCheckConcurrency.cpp | 15 +++++++++++++-- .../global_actor_inference_swift6.swift | 10 ++++++++++ 2 files changed, 23 insertions(+), 2 deletions(-) diff --git a/lib/Sema/TypeCheckConcurrency.cpp b/lib/Sema/TypeCheckConcurrency.cpp index a5a66790a1a4f..be7fc3a350663 100644 --- a/lib/Sema/TypeCheckConcurrency.cpp +++ b/lib/Sema/TypeCheckConcurrency.cpp @@ -4648,8 +4648,19 @@ getIsolationFromConformances(NominalTypeDecl *nominal) { return std::nullopt; std::optional foundIsolation; - for (auto proto : - nominal->getLocalProtocols(ConformanceLookupKind::NonStructural)) { + for (auto conformance : + nominal->getLocalConformances(ConformanceLookupKind::NonStructural)) { + + // Don't include inherited conformances. If a conformance is inherited + // from a superclass, the isolation of the subclass should be inferred + // from the superclass, which is done directly in ActorIsolationRequest. + // If the superclass has opted out of global actor inference, such as + // by conforming to the protocol in an extension, then the subclass should + // not infer isolation from the protocol. + if (conformance->getKind() == ProtocolConformanceKind::Inherited) + continue; + + auto *proto = conformance->getProtocol(); switch (auto protoIsolation = getActorIsolation(proto)) { case ActorIsolation::ActorInstance: case ActorIsolation::Unspecified: diff --git a/test/Concurrency/global_actor_inference_swift6.swift b/test/Concurrency/global_actor_inference_swift6.swift index eb0ac2b0a36e6..905ce18c97ff5 100644 --- a/test/Concurrency/global_actor_inference_swift6.swift +++ b/test/Concurrency/global_actor_inference_swift6.swift @@ -213,3 +213,13 @@ class C2: MainActorSuperclass, InferenceConflictWithSuperclass { } +class ConformInExtension {} +extension ConformInExtension: InferMainActor {} + +class InheritConformance: ConformInExtension { + func f() {} +} + +func testInheritedMainActorConformance() { + InheritConformance().f() // okay; this is not main actor isolated +}