@@ -53,7 +53,8 @@ concreteSyntaxDeclForAvailableAttribute(const Decl *AbstractSyntaxDecl);
5353static bool diagnoseExplicitUnavailability (
5454 SourceLoc loc, const RootProtocolConformance *rootConf,
5555 const ExtensionDecl *ext, const ExportContext &where,
56- bool warnIfConformanceUnavailablePreSwift6 = false );
56+ bool warnIfConformanceUnavailablePreSwift6 = false ,
57+ bool preconcurrency = false );
5758
5859// / Emit a diagnostic for references to declarations that have been
5960// / marked as unavailable, either through "unavailable" or "obsoleted:".
@@ -66,7 +67,8 @@ static bool diagnoseSubstitutionMapAvailability(
6667 SourceLoc loc, SubstitutionMap subs, const ExportContext &where,
6768 Type depTy = Type(), Type replacementTy = Type(),
6869 bool warnIfConformanceUnavailablePreSwift6 = false,
69- bool suppressParameterizationCheckForOptional = false);
70+ bool suppressParameterizationCheckForOptional = false,
71+ bool preconcurrency = false);
7072
7173// / Diagnose uses of unavailable declarations in types.
7274static bool
@@ -2985,7 +2987,8 @@ getExplicitUnavailabilityDiagnosticInfo(const Decl *decl,
29852987bool diagnoseExplicitUnavailability (
29862988 SourceLoc loc, const RootProtocolConformance *rootConf,
29872989 const ExtensionDecl *ext, const ExportContext &where,
2988- bool warnIfConformanceUnavailablePreSwift6) {
2990+ bool warnIfConformanceUnavailablePreSwift6,
2991+ bool preconcurrency) {
29892992 // Invertible protocols are never unavailable.
29902993 if (rootConf->getProtocol ()->getInvertibleProtocolKind ())
29912994 return false ;
@@ -3011,7 +3014,7 @@ bool diagnoseExplicitUnavailability(
30113014 diags
30123015 .diagnose (loc, diag::conformance_availability_unavailable, type, proto,
30133016 platform.empty (), platform, EncodedMessage.Message )
3014- .limitBehaviorUntilSwiftVersion (behavior, 6 )
3017+ .limitBehaviorWithPreconcurrency (behavior, preconcurrency )
30153018 .warnUntilSwiftVersionIf (warnIfConformanceUnavailablePreSwift6, 6 );
30163019
30173020 switch (diagnosticInfo->getStatus ()) {
@@ -3523,6 +3526,7 @@ class ExprAvailabilityWalker : public ASTWalker {
35233526 ASTContext &Context;
35243527 MemberAccessContext AccessContext = MemberAccessContext::Default;
35253528 SmallVector<const Expr *, 16 > ExprStack;
3529+ SmallVector<bool , 4 > PreconcurrencyCalleeStack;
35263530 const ExportContext &Where;
35273531
35283532public:
@@ -3546,6 +3550,15 @@ class ExprAvailabilityWalker : public ASTWalker {
35463550
35473551 ExprStack.push_back (E);
35483552
3553+ if (auto *apply = dyn_cast<ApplyExpr>(E)) {
3554+ bool preconcurrency = false ;
3555+ auto declRef = apply->getFn ()->getReferencedDecl ();
3556+ if (auto *decl = declRef.getDecl ()) {
3557+ preconcurrency = decl->preconcurrency ();
3558+ }
3559+ PreconcurrencyCalleeStack.push_back (preconcurrency);
3560+ }
3561+
35493562 if (auto DR = dyn_cast<DeclRefExpr>(E)) {
35503563 diagnoseDeclRefAvailability (DR->getDeclRef (), DR->getSourceRange (),
35513564 getEnclosingApplyExpr (), std::nullopt );
@@ -3668,9 +3681,15 @@ class ExprAvailabilityWalker : public ASTWalker {
36683681 EE->getLoc (),
36693682 Where.getDeclContext ());
36703683
3684+ bool preconcurrency = false ;
3685+ if (!PreconcurrencyCalleeStack.empty ()) {
3686+ preconcurrency = PreconcurrencyCalleeStack.back ();
3687+ }
3688+
36713689 for (ProtocolConformanceRef C : EE->getConformances ()) {
36723690 diagnoseConformanceAvailability (E->getLoc (), C, Where, Type (), Type (),
3673- /* useConformanceAvailabilityErrorsOpt=*/ true );
3691+ /* useConformanceAvailabilityErrorsOpt=*/ true ,
3692+ /* preconcurrency=*/ preconcurrency);
36743693 }
36753694 }
36763695
@@ -3696,6 +3715,10 @@ class ExprAvailabilityWalker : public ASTWalker {
36963715 assert (ExprStack.back () == E);
36973716 ExprStack.pop_back ();
36983717
3718+ if (auto *apply = dyn_cast<ApplyExpr>(E)) {
3719+ PreconcurrencyCalleeStack.pop_back ();
3720+ }
3721+
36993722 return Action::Continue (E);
37003723 }
37013724
@@ -3990,8 +4013,12 @@ bool ExprAvailabilityWalker::diagnoseDeclRefAvailability(
39904013 }
39914014
39924015 if (R.isValid ()) {
3993- if (diagnoseSubstitutionMapAvailability (R.Start , declRef.getSubstitutions (),
3994- Where)) {
4016+ if (diagnoseSubstitutionMapAvailability (
4017+ R.Start , declRef.getSubstitutions (), Where,
4018+ Type (), Type (),
4019+ /* warnIfConformanceUnavailablePreSwift6*/ false ,
4020+ /* suppressParameterizationCheckForOptional*/ false ,
4021+ /* preconcurrency*/ D->preconcurrency ())) {
39954022 return true ;
39964023 }
39974024 }
@@ -4489,7 +4516,8 @@ class ProblematicTypeFinder : public TypeDeclFinder {
44894516 /* depTy=*/ Type (),
44904517 /* replacementTy=*/ Type (),
44914518 /* warnIfConformanceUnavailablePreSwift6=*/ false ,
4492- /* suppressParameterizationCheckForOptional=*/ ty->isOptional ());
4519+ /* suppressParameterizationCheckForOptional=*/ ty->isOptional (),
4520+ /* preconcurrency*/ ty->getAnyNominal ()->preconcurrency ());
44934521 return Action::Continue;
44944522 }
44954523
@@ -4539,17 +4567,19 @@ void swift::diagnoseTypeAvailability(const TypeRepr *TR, Type T, SourceLoc loc,
45394567}
45404568
45414569static void diagnoseMissingConformance (
4542- SourceLoc loc, Type type, ProtocolDecl *proto, const DeclContext *fromDC) {
4570+ SourceLoc loc, Type type, ProtocolDecl *proto, const DeclContext *fromDC,
4571+ bool preconcurrency) {
45434572 assert (proto->isSpecificProtocol (KnownProtocolKind::Sendable));
4544- diagnoseMissingSendableConformance (loc, type, fromDC);
4573+ diagnoseMissingSendableConformance (loc, type, fromDC, preconcurrency );
45454574}
45464575
45474576bool
45484577swift::diagnoseConformanceAvailability (SourceLoc loc,
45494578 ProtocolConformanceRef conformance,
45504579 const ExportContext &where,
45514580 Type depTy, Type replacementTy,
4552- bool warnIfConformanceUnavailablePreSwift6) {
4581+ bool warnIfConformanceUnavailablePreSwift6,
4582+ bool preconcurrency) {
45534583 assert (!where.isImplicit ());
45544584
45554585 if (conformance.isInvalid () || conformance.isAbstract ())
@@ -4561,7 +4591,8 @@ swift::diagnoseConformanceAvailability(SourceLoc loc,
45614591 for (auto patternConf : pack->getPatternConformances ()) {
45624592 diagnosed |= diagnoseConformanceAvailability (
45634593 loc, patternConf, where, depTy, replacementTy,
4564- warnIfConformanceUnavailablePreSwift6);
4594+ warnIfConformanceUnavailablePreSwift6,
4595+ preconcurrency);
45654596 }
45664597 return diagnosed;
45674598 }
@@ -4581,7 +4612,8 @@ swift::diagnoseConformanceAvailability(SourceLoc loc,
45814612 if (auto builtinConformance = dyn_cast<BuiltinProtocolConformance>(rootConf)){
45824613 if (builtinConformance->isMissing ()) {
45834614 diagnoseMissingConformance (loc, builtinConformance->getType (),
4584- builtinConformance->getProtocol (), DC);
4615+ builtinConformance->getProtocol (), DC,
4616+ preconcurrency);
45854617 }
45864618 }
45874619
@@ -4611,7 +4643,8 @@ swift::diagnoseConformanceAvailability(SourceLoc loc,
46114643 // FIXME: diagnoseExplicitUnavailability() should take unmet requirement
46124644 if (diagnoseExplicitUnavailability (
46134645 loc, rootConf, ext, where,
4614- warnIfConformanceUnavailablePreSwift6)) {
4646+ warnIfConformanceUnavailablePreSwift6,
4647+ preconcurrency)) {
46154648 maybeEmitAssociatedTypeNote ();
46164649 return true ;
46174650 }
@@ -4640,7 +4673,8 @@ swift::diagnoseConformanceAvailability(SourceLoc loc,
46404673 SubstitutionMap subConformanceSubs = concreteConf->getSubstitutionMap ();
46414674 if (diagnoseSubstitutionMapAvailability (loc, subConformanceSubs, where,
46424675 depTy, replacementTy,
4643- warnIfConformanceUnavailablePreSwift6))
4676+ warnIfConformanceUnavailablePreSwift6,
4677+ preconcurrency))
46444678 return true ;
46454679
46464680 return false ;
@@ -4649,12 +4683,14 @@ swift::diagnoseConformanceAvailability(SourceLoc loc,
46494683bool diagnoseSubstitutionMapAvailability (
46504684 SourceLoc loc, SubstitutionMap subs, const ExportContext &where, Type depTy,
46514685 Type replacementTy, bool warnIfConformanceUnavailablePreSwift6,
4652- bool suppressParameterizationCheckForOptional) {
4686+ bool suppressParameterizationCheckForOptional,
4687+ bool preconcurrency) {
46534688 bool hadAnyIssues = false ;
46544689 for (ProtocolConformanceRef conformance : subs.getConformances ()) {
46554690 if (diagnoseConformanceAvailability (loc, conformance, where,
46564691 depTy, replacementTy,
4657- warnIfConformanceUnavailablePreSwift6))
4692+ warnIfConformanceUnavailablePreSwift6,
4693+ preconcurrency))
46584694 hadAnyIssues = true ;
46594695 }
46604696
0 commit comments