@@ -1740,6 +1740,8 @@ checkWitnessAvailability(ValueDecl *requirement,
17401740
17411741RequirementCheck WitnessChecker::checkWitness (ValueDecl *requirement,
17421742 const RequirementMatch &match) {
1743+ auto &ctx = getASTContext ();
1744+
17431745 if (!match.OptionalAdjustments .empty ())
17441746 return CheckKind::OptionalityConflict;
17451747
@@ -1769,7 +1771,7 @@ RequirementCheck WitnessChecker::checkWitness(ValueDecl *requirement,
17691771 return RequirementCheck (CheckKind::Availability, requiredAvailability);
17701772 }
17711773
1772- if (requirement->getAttrs ().isUnavailable (getASTContext () ) &&
1774+ if (requirement->getAttrs ().isUnavailable (ctx ) &&
17731775 match.Witness ->getDeclContext () == DC) {
17741776 return RequirementCheck (CheckKind::Unavailable);
17751777 }
@@ -1792,11 +1794,11 @@ RequirementCheck WitnessChecker::checkWitness(ValueDecl *requirement,
17921794 }
17931795 }
17941796
1795- if (match.Witness ->getAttrs ().isUnavailable (getASTContext () ) &&
1796- !requirement->getAttrs ().isUnavailable (getASTContext () )) {
1797+ if (match.Witness ->getAttrs ().isUnavailable (ctx ) &&
1798+ !requirement->getAttrs ().isUnavailable (ctx )) {
17971799 auto nominalOrExtensionIsUnavailable = [&]() {
17981800 if (auto extension = dyn_cast<ExtensionDecl>(DC)) {
1799- if (extension->getAttrs ().isUnavailable (getASTContext () ))
1801+ if (extension->getAttrs ().isUnavailable (ctx ))
18001802 return true ;
18011803 }
18021804
@@ -1813,6 +1815,20 @@ RequirementCheck WitnessChecker::checkWitness(ValueDecl *requirement,
18131815 return CheckKind::WitnessUnavailable;
18141816 }
18151817
1818+ // Warn about deprecated default implementations if the requirement is
1819+ // not deprecated, and the conformance is not deprecated.
1820+ bool isDefaultWitness = false ;
1821+ if (auto *nominal = match.Witness ->getDeclContext ()->getSelfNominalTypeDecl ())
1822+ isDefaultWitness = isa<ProtocolDecl>(nominal);
1823+ if (isDefaultWitness &&
1824+ match.Witness ->getAttrs ().isDeprecated (ctx) &&
1825+ !requirement->getAttrs ().isDeprecated (ctx)) {
1826+ auto conformanceContext = ExportContext::forConformance (DC, Proto);
1827+ if (!conformanceContext.isDeprecated ()) {
1828+ return RequirementCheck (CheckKind::DefaultWitnessDeprecated);
1829+ }
1830+ }
1831+
18161832 return CheckKind::Success;
18171833}
18181834
@@ -4374,6 +4390,25 @@ ConformanceChecker::resolveWitnessViaLookup(ValueDecl *requirement) {
43744390 requirement->getName ());
43754391 });
43764392 break ;
4393+
4394+ case CheckKind::DefaultWitnessDeprecated:
4395+ getASTContext ().addDelayedConformanceDiag (
4396+ Conformance, /* isError=*/ false ,
4397+ [witness, requirement](NormalProtocolConformance *conformance) {
4398+ auto &ctx = witness->getASTContext ();
4399+ auto &diags = ctx.Diags ;
4400+ SourceLoc diagLoc = getLocForDiagnosingWitness (conformance, witness);
4401+ auto *attr = witness->getAttrs ().getDeprecated (ctx);
4402+ EncodedDiagnosticMessage EncodedMessage (attr->Message );
4403+ diags.diagnose (diagLoc, diag::witness_deprecated,
4404+ witness, conformance->getProtocol ()->getName (),
4405+ EncodedMessage.Message );
4406+ emitDeclaredHereIfNeeded (diags, diagLoc, witness);
4407+ diags.diagnose (requirement, diag::kind_declname_declared_here,
4408+ DescriptiveDeclKind::Requirement,
4409+ requirement->getName ());
4410+ });
4411+ break ;
43774412 }
43784413
43794414 if (auto *classDecl = DC->getSelfClassDecl ()) {
0 commit comments