@@ -724,6 +724,12 @@ class ApplyClassifier {
724
724
DeclContext *RethrowsDC = nullptr ;
725
725
DeclContext *ReasyncDC = nullptr ;
726
726
727
+ // Indicates if `classifyApply` will attempt to classify SelfApplyExpr
728
+ // because that should be done only in certain contexts like when infering
729
+ // if "async let" implicit auto closure wrapping initialize expression can
730
+ // throw.
731
+ bool ClassifySelfApplyExpr = false ;
732
+
727
733
DeclContext *getPolymorphicEffectDeclContext (EffectKind kind) const {
728
734
switch (kind) {
729
735
case EffectKind::Throws: return RethrowsDC;
@@ -745,16 +751,29 @@ class ApplyClassifier {
745
751
746
752
// / Check to see if the given function application throws or is async.
747
753
Classification classifyApply (ApplyExpr *E) {
748
- if (isa<SelfApplyExpr>(E)) {
749
- assert (!E->isImplicitlyAsync ());
750
- return Classification ();
751
- }
752
-
753
754
// An apply expression is a potential throw site if the function throws.
754
755
// But if the expression didn't type-check, suppress diagnostics.
755
756
if (!E->getType () || E->getType ()->hasError ())
756
757
return Classification::forInvalidCode ();
757
758
759
+ if (auto *SAE = dyn_cast<SelfApplyExpr>(E)) {
760
+ assert (!E->isImplicitlyAsync ());
761
+
762
+ if (ClassifySelfApplyExpr) {
763
+ // Do not consider throw properties in SelfAssignExpr with an implicit
764
+ // conversion base.
765
+ if (isa<ImplicitConversionExpr>(SAE->getBase ()))
766
+ return Classification ();
767
+
768
+ auto fnType = E->getType ()->getAs <AnyFunctionType>();
769
+ if (fnType && fnType->isThrowing ()) {
770
+ return Classification::forUnconditional (
771
+ EffectKind::Throws, PotentialEffectReason::forApply ());
772
+ }
773
+ }
774
+ return Classification ();
775
+ }
776
+
758
777
auto type = E->getFn ()->getType ();
759
778
if (!type) return Classification::forInvalidCode ();
760
779
auto fnType = type->getAs <AnyFunctionType>();
@@ -2957,6 +2976,8 @@ void TypeChecker::checkPropertyWrapperEffects(
2957
2976
}
2958
2977
2959
2978
bool TypeChecker::canThrow (Expr *expr) {
2960
- return (ApplyClassifier ().classifyExpr (expr, EffectKind::Throws)
2961
- == ConditionalEffectKind::Always);
2979
+ ApplyClassifier classifier;
2980
+ classifier.ClassifySelfApplyExpr = true ;
2981
+ return (classifier.classifyExpr (expr, EffectKind::Throws) ==
2982
+ ConditionalEffectKind::Always);
2962
2983
}
0 commit comments