1515//
1616// ===----------------------------------------------------------------------===//
1717
18+ #include " CodeSynthesis.h"
1819#include " TypeChecker.h"
1920#include " swift/AST/Decl.h"
2021#include " swift/AST/Stmt.h"
@@ -45,9 +46,16 @@ static bool canDeriveConformance(DeclContext *DC,
4546 if (auto structDecl = dyn_cast<StructDecl>(target)) {
4647 // All stored properties of the struct must conform to the protocol. If
4748 // there are no stored properties, we will vaccously return true.
48- return DerivedConformance::storedPropertiesNotConformingToProtocol (
49- DC, structDecl, protocol)
50- .empty ();
49+ if (!DerivedConformance::storedPropertiesNotConformingToProtocol (
50+ DC, structDecl, protocol).empty ())
51+ return false ;
52+
53+ // If the struct is actor-isolated, we cannot derive Equatable/Hashable
54+ // conformance if any of the stored properties are mutable.
55+ if (memberwiseAccessorsRequireActorIsolation (structDecl))
56+ return false ;
57+
58+ return true ;
5159 }
5260
5361 return false ;
@@ -426,6 +434,8 @@ deriveEquatable_eq(
426434 return nullptr ;
427435 }
428436
437+ addNonIsolatedToSynthesized (derived.Nominal , eqDecl);
438+
429439 eqDecl->setBodySynthesizer (bodySynthesizer);
430440
431441 eqDecl->copyFormalAccessFrom (derived.Nominal , /* sourceIsParentContext*/ true );
@@ -544,7 +554,7 @@ deriveHashable_hashInto(
544554 /* Throws=*/ false ,
545555 /* GenericParams=*/ nullptr , params, returnType, parentDC);
546556 hashDecl->setBodySynthesizer (bodySynthesizer);
547-
557+ addNonIsolatedToSynthesized (derived. Nominal , hashDecl);
548558 hashDecl->copyFormalAccessFrom (derived.Nominal ,
549559 /* sourceIsParentContext=*/ true );
550560
@@ -881,6 +891,7 @@ static ValueDecl *deriveHashable_hashValue(DerivedConformance &derived) {
881891 SourceLoc (), C.Id_hashValue , parentDC);
882892 hashValueDecl->setInterfaceType (intType);
883893 hashValueDecl->setSynthesized ();
894+ addNonIsolatedToSynthesized (derived.Nominal , hashValueDecl);
884895
885896 ParameterList *params = ParameterList::createEmpty (C);
886897
@@ -896,7 +907,6 @@ static ValueDecl *deriveHashable_hashValue(DerivedConformance &derived) {
896907 getterDecl->setBodySynthesizer (&deriveBodyHashable_hashValue);
897908 getterDecl->setSynthesized ();
898909 getterDecl->setIsTransparent (false );
899-
900910 getterDecl->copyFormalAccessFrom (derived.Nominal ,
901911 /* sourceIsParentContext*/ true );
902912
0 commit comments