Skip to content

Commit 247b29d

Browse files
committed
[Constraint solver] Treat downgraded errors as "disfavored overloads".
This allows us to still maintain them in the score kind, but not treat them as being as severe as an error requiring a fix.
1 parent 32ff69e commit 247b29d

File tree

5 files changed

+32
-19
lines changed

5 files changed

+32
-19
lines changed

include/swift/Sema/CSFix.h

Lines changed: 4 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@ class ConstraintSystem;
4646
class ConstraintLocator;
4747
class ConstraintLocatorBuilder;
4848
enum class ConversionRestrictionKind;
49+
enum ScoreKind: unsigned int;
4950
class Solution;
5051
struct MemberLookupResult;
5152

@@ -433,18 +434,9 @@ class ConstraintFix {
433434
}
434435
}
435436

436-
/// Whether this kind of fix affects the solution score.
437-
bool affectsSolutionScore() const {
438-
switch (fixBehavior) {
439-
case FixBehavior::AlwaysWarning:
440-
case FixBehavior::DowngradeToWarning:
441-
case FixBehavior::Suppress:
442-
return false;
443-
444-
case FixBehavior::Error:
445-
return true;
446-
}
447-
}
437+
/// Whether this kind of fix affects the solution score, and which score
438+
/// it affects.
439+
Optional<ScoreKind> affectsSolutionScore() const;
448440

449441
/// The diagnostic behavior limit that will be applied to any emitted
450442
/// diagnostics.

include/swift/Sema/ConstraintSystem.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -775,7 +775,7 @@ class FunctionArgApplyInfo {
775775

776776
/// Describes an aspect of a solution that affects its overall score, i.e., a
777777
/// user-defined conversions.
778-
enum ScoreKind {
778+
enum ScoreKind: unsigned int {
779779
// These values are used as indices into a Score value.
780780

781781
/// A fix needs to be applied to the source.

lib/Sema/CSApply.cpp

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -9105,16 +9105,23 @@ Optional<SolutionApplicationTarget> ConstraintSystem::applySolution(
91059105
Solution &solution, SolutionApplicationTarget target) {
91069106
// If any fixes needed to be applied to arrive at this solution, resolve
91079107
// them to specific expressions.
9108+
unsigned numResolvableFixes = 0;
91089109
if (!solution.Fixes.empty()) {
91099110
if (shouldSuppressDiagnostics())
91109111
return None;
91119112

91129113
bool diagnosedErrorsViaFixes = applySolutionFixes(solution);
9114+
bool canApplySolution = true;
9115+
for (const auto fix : solution.Fixes) {
9116+
if (!fix->canApplySolution())
9117+
canApplySolution = false;
9118+
if (fix->affectsSolutionScore() == SK_Fix && fix->canApplySolution())
9119+
++numResolvableFixes;
9120+
}
9121+
91139122
// If all of the available fixes would result in a warning,
91149123
// we can go ahead and apply this solution to AST.
9115-
if (!llvm::all_of(solution.Fixes, [](const ConstraintFix *fix) {
9116-
return fix->canApplySolution();
9117-
})) {
9124+
if (!canApplySolution) {
91189125
// If we already diagnosed any errors via fixes, that's it.
91199126
if (diagnosedErrorsViaFixes)
91209127
return None;
@@ -9131,7 +9138,7 @@ Optional<SolutionApplicationTarget> ConstraintSystem::applySolution(
91319138
// produce a fallback diagnostic to highlight the problem.
91329139
{
91339140
const auto &score = solution.getFixedScore();
9134-
if (score.Data[SK_Fix] > 0 || score.Data[SK_Hole] > 0) {
9141+
if (score.Data[SK_Fix] > numResolvableFixes || score.Data[SK_Hole] > 0) {
91359142
maybeProduceFallbackDiagnostic(target);
91369143
return None;
91379144
}

lib/Sema/CSFix.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,20 @@ using namespace constraints;
3737

3838
ConstraintFix::~ConstraintFix() {}
3939

40+
Optional<ScoreKind> ConstraintFix::affectsSolutionScore() const {
41+
switch (fixBehavior) {
42+
case FixBehavior::AlwaysWarning:
43+
return None;
44+
45+
case FixBehavior::Error:
46+
return SK_Fix;
47+
48+
case FixBehavior::DowngradeToWarning:
49+
case FixBehavior::Suppress:
50+
return SK_DisfavoredOverload;
51+
}
52+
}
53+
4054
ASTNode ConstraintFix::getAnchor() const { return getLocator()->getAnchor(); }
4155

4256
void ConstraintFix::print(llvm::raw_ostream &Out) const {

lib/Sema/CSSimplify.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12706,8 +12706,8 @@ bool ConstraintSystem::recordFix(ConstraintFix *fix, unsigned impact) {
1270612706
// Record the fix.
1270712707

1270812708
// If this should affect the solution score, do so.
12709-
if (fix->affectsSolutionScore())
12710-
increaseScore(SK_Fix, impact);
12709+
if (auto scoreKind = fix->affectsSolutionScore())
12710+
increaseScore(*scoreKind, impact);
1271112711

1271212712
// If we've made the current solution worse than the best solution we've seen
1271312713
// already, stop now.

0 commit comments

Comments
 (0)