Skip to content

Commit 486562a

Browse files
committed
Sema: Optimize ConstraintSystem::is{Decl,Conformance}Unavailable
Let's avoid creating an ExportContext, which computes a bunch of irrelevant stuff. Also, delay the expensive call to overApproximateAvailabilityAtLocation() unless we know the declaration is conditionally unavailable.
1 parent bf23faa commit 486562a

File tree

1 file changed

+24
-22
lines changed

1 file changed

+24
-22
lines changed

lib/Sema/ConstraintSystem.cpp

Lines changed: 24 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -5089,17 +5089,36 @@ bool ConstraintSystem::isDeclUnavailable(const Decl *D,
50895089
if (D->getAttrs().isUnavailable(ctx))
50905090
return true;
50915091

5092+
if (ctx.LangOpts.DisableAvailabilityChecking)
5093+
return false;
5094+
5095+
if (!DC->getParentSourceFile()) {
5096+
// We only check availability if this reference is in a source file; we do
5097+
// not check in other kinds of FileUnits.
5098+
return false;
5099+
}
5100+
5101+
AvailabilityContext safeRangeUnderApprox{
5102+
AvailabilityInference::availableRange(D, ctx)};
5103+
if (safeRangeUnderApprox.isAlwaysAvailable())
5104+
return false;
5105+
50925106
SourceLoc loc;
50935107

50945108
if (locator) {
50955109
if (auto anchor = locator->getAnchor())
50965110
loc = getLoc(anchor);
50975111
}
50985112

5099-
// If not, let's check contextual unavailability.
5100-
ExportContext where = ExportContext::forFunctionBody(DC, loc);
5101-
auto result = TypeChecker::checkDeclarationAvailability(D, where);
5102-
return result.hasValue();
5113+
AvailabilityContext runningOSOverApprox =
5114+
TypeChecker::overApproximateAvailabilityAtLocation(loc, DC);
5115+
5116+
// The reference is safe if an over-approximation of the running OS
5117+
// versions is fully contained within an under-approximation
5118+
// of the versions on which the declaration is available. If this
5119+
// containment cannot be guaranteed, we say the reference is
5120+
// not available.
5121+
return !runningOSOverApprox.isContainedIn(safeRangeUnderApprox);
51035122
}
51045123

51055124
bool ConstraintSystem::isConformanceUnavailable(ProtocolConformanceRef conformance,
@@ -5113,24 +5132,7 @@ bool ConstraintSystem::isConformanceUnavailable(ProtocolConformanceRef conforman
51135132
if (ext == nullptr)
51145133
return false;
51155134

5116-
auto &ctx = getASTContext();
5117-
5118-
// First check whether this declaration is universally unavailable.
5119-
if (ext->getAttrs().isUnavailable(ctx))
5120-
return true;
5121-
5122-
SourceLoc loc;
5123-
5124-
if (locator) {
5125-
if (auto anchor = locator->getAnchor())
5126-
loc = getLoc(anchor);
5127-
}
5128-
5129-
// If not, let's check contextual unavailability.
5130-
ExportContext where = ExportContext::forFunctionBody(DC, loc);
5131-
auto result = TypeChecker::checkConformanceAvailability(
5132-
rootConf, ext, where);
5133-
return result.hasValue();
5135+
return isDeclUnavailable(ext, locator);
51345136
}
51355137

51365138
/// If we aren't certain that we've emitted a diagnostic, emit a fallback

0 commit comments

Comments
 (0)