@@ -52,16 +52,20 @@ bool FailureDiagnostic::diagnoseAsNote() {
52
52
}
53
53
54
54
ASTNode FailureDiagnostic::getAnchor () const {
55
- auto &cs = getConstraintSystem ();
56
-
57
55
auto *locator = getLocator ();
58
56
// Resolve the locator to a specific expression.
59
- SourceRange range;
60
- ConstraintLocator *resolved = simplifyLocator (cs, locator, range);
61
- if (!resolved || !resolved->getAnchor ())
62
- return locator->getAnchor ();
63
57
64
- auto anchor = resolved->getAnchor ();
58
+ auto anchor = locator->getAnchor ();
59
+
60
+ {
61
+ SourceRange range;
62
+ auto path = locator->getPath ();
63
+
64
+ simplifyLocator (anchor, path, range);
65
+ if (!anchor)
66
+ return locator->getAnchor ();
67
+ }
68
+
65
69
// FIXME: Work around an odd locator representation that doesn't separate the
66
70
// base of a subscript member from the member access.
67
71
if (locator->isLastElement <LocatorPathElt::SubscriptMember>()) {
@@ -73,7 +77,11 @@ ASTNode FailureDiagnostic::getAnchor() const {
73
77
}
74
78
75
79
Type FailureDiagnostic::getType (ASTNode node, bool wantRValue) const {
76
- return resolveType (S.getType (node), /* reconstituteSugar=*/ false , wantRValue);
80
+ return resolveType (getRawType (node), /* reconstituteSugar=*/ false , wantRValue);
81
+ }
82
+
83
+ Type FailureDiagnostic::getRawType (ASTNode node) const {
84
+ return S.getType (node);
77
85
}
78
86
79
87
template <typename ... ArgTypes>
@@ -146,6 +154,18 @@ Type FailureDiagnostic::restoreGenericParameters(
146
154
});
147
155
}
148
156
157
+ bool FailureDiagnostic::conformsToKnownProtocol (
158
+ Type type, KnownProtocolKind protocol) const {
159
+ auto &cs = getConstraintSystem ();
160
+ return constraints::conformsToKnownProtocol (cs, type, protocol);
161
+ }
162
+
163
+ Type FailureDiagnostic::isRawRepresentable (Type type,
164
+ KnownProtocolKind protocol) const {
165
+ auto &cs = getConstraintSystem ();
166
+ return constraints::isRawRepresentable (cs, type, protocol);
167
+ }
168
+
149
169
Type RequirementFailure::getOwnerType () const {
150
170
auto anchor = getRawAnchor ();
151
171
@@ -183,7 +203,7 @@ const Requirement &RequirementFailure::getRequirement() const {
183
203
184
204
ProtocolConformance *RequirementFailure::getConformanceForConditionalReq (
185
205
ConstraintLocator *locator) {
186
- auto &cs = getConstraintSystem ();
206
+ auto &solution = getSolution ();
187
207
auto reqElt = locator->castLastElementTo <LocatorPathElt::AnyRequirement>();
188
208
if (!reqElt.isConditionalRequirement ())
189
209
return nullptr ;
@@ -192,10 +212,10 @@ ProtocolConformance *RequirementFailure::getConformanceForConditionalReq(
192
212
auto *typeReqLoc = getConstraintLocator (getRawAnchor (), path.drop_back ());
193
213
194
214
auto result = llvm::find_if (
195
- cs. CheckedConformances ,
215
+ solution. Conformances ,
196
216
[&](const std::pair<ConstraintLocator *, ProtocolConformanceRef>
197
217
&conformance) { return conformance.first == typeReqLoc; });
198
- assert (result != cs. CheckedConformances .end ());
218
+ assert (result != solution. Conformances .end ());
199
219
200
220
auto conformance = result->second ;
201
221
assert (conformance.isConcrete ());
@@ -407,9 +427,8 @@ bool MissingConformanceFailure::diagnoseAsError() {
407
427
if (auto *binaryOp = dyn_cast_or_null<BinaryExpr>(findParentExpr (anchor))) {
408
428
auto *caseExpr = binaryOp->getArg ()->getElement (0 );
409
429
410
- auto &cs = getConstraintSystem ();
411
430
llvm::SmallPtrSet<Expr *, 4 > anchors;
412
- for (const auto *fix : cs. getFixes () ) {
431
+ for (const auto *fix : getSolution (). Fixes ) {
413
432
if (auto anchor = fix->getAnchor ()) {
414
433
if (anchor.is <Expr *>())
415
434
anchors.insert (getAsExpr (anchor));
@@ -1262,12 +1281,11 @@ bool RValueTreatedAsLValueFailure::diagnoseAsError() {
1262
1281
ParameterTypeFlags ())});
1263
1282
1264
1283
if (auto info = getFunctionArgApplyInfo (argLoc)) {
1265
- auto &cs = getConstraintSystem ();
1266
1284
auto paramType = info->getParamType ();
1267
1285
auto argType = getType (inoutExpr)->getWithoutSpecifierType ();
1268
1286
1269
1287
PointerTypeKind ptr;
1270
- if (cs. isArrayType (argType) &&
1288
+ if (isArrayType (argType) &&
1271
1289
paramType->getAnyPointerElementType (ptr) &&
1272
1290
(ptr == PTK_UnsafePointer || ptr == PTK_UnsafeRawPointer)) {
1273
1291
emitDiagnosticAt (inoutExpr->getLoc (),
@@ -2021,8 +2039,7 @@ bool ContextualFailure::diagnoseAsError() {
2021
2039
}
2022
2040
2023
2041
case ConstraintLocator::RValueAdjustment: {
2024
- auto &cs = getConstraintSystem ();
2025
-
2042
+ auto &solution = getSolution ();
2026
2043
auto overload = getOverloadChoiceIfAvailable (
2027
2044
getConstraintLocator (anchor, ConstraintLocator::UnresolvedMember));
2028
2045
if (!(overload && overload->choice .isDecl ()))
@@ -2048,8 +2065,11 @@ bool ContextualFailure::diagnoseAsError() {
2048
2065
2049
2066
auto params = fnType->getParams ();
2050
2067
2051
- ParameterListInfo info (params, choice,
2052
- hasAppliedSelf (cs, overload->choice ));
2068
+ ParameterListInfo info (
2069
+ params, choice,
2070
+ hasAppliedSelf (overload->choice , [&solution](Type type) {
2071
+ return solution.simplifyType (type);
2072
+ }));
2053
2073
auto numMissingArgs = llvm::count_if (
2054
2074
indices (params), [&info](const unsigned paramIdx) -> bool {
2055
2075
return !info.hasDefaultArgument (paramIdx);
@@ -2402,9 +2422,8 @@ bool ContextualFailure::diagnoseConversionToBool() const {
2402
2422
2403
2423
// If we're trying to convert something from optional type to an integer, then
2404
2424
// a comparison against nil was probably expected.
2405
- auto &cs = getConstraintSystem ();
2406
- if (conformsToKnownProtocol (cs, fromType, KnownProtocolKind::BinaryInteger) &&
2407
- conformsToKnownProtocol (cs, fromType,
2425
+ if (conformsToKnownProtocol (fromType, KnownProtocolKind::BinaryInteger) &&
2426
+ conformsToKnownProtocol (fromType,
2408
2427
KnownProtocolKind::ExpressibleByIntegerLiteral)) {
2409
2428
StringRef prefix = " ((" ;
2410
2429
StringRef suffix;
@@ -2499,7 +2518,6 @@ bool ContextualFailure::diagnoseYieldByReferenceMismatch() const {
2499
2518
bool ContextualFailure::tryRawRepresentableFixIts (
2500
2519
InFlightDiagnostic &diagnostic,
2501
2520
KnownProtocolKind rawRepresentableProtocol) const {
2502
- auto &CS = getConstraintSystem ();
2503
2521
auto anchor = getAnchor ();
2504
2522
auto fromType = getFromType ();
2505
2523
auto toType = getToType ();
@@ -2554,14 +2572,14 @@ bool ContextualFailure::tryRawRepresentableFixIts(
2554
2572
}
2555
2573
};
2556
2574
2557
- if (conformsToKnownProtocol (CS, fromType, rawRepresentableProtocol)) {
2558
- if (conformsToKnownProtocol (CS, fromType, KnownProtocolKind::OptionSet) &&
2575
+ if (conformsToKnownProtocol (fromType, rawRepresentableProtocol)) {
2576
+ if (conformsToKnownProtocol (fromType, KnownProtocolKind::OptionSet) &&
2559
2577
isExpr<IntegerLiteralExpr>(anchor) &&
2560
2578
castToExpr<IntegerLiteralExpr>(anchor)->getDigitsText () == " 0" ) {
2561
2579
diagnostic.fixItReplace (::getSourceRange (anchor), " []" );
2562
2580
return true ;
2563
2581
}
2564
- if (auto rawTy = isRawRepresentable (CS, toType, rawRepresentableProtocol)) {
2582
+ if (auto rawTy = isRawRepresentable (toType, rawRepresentableProtocol)) {
2565
2583
// Produce before/after strings like 'Result(rawValue: RawType(<expr>))'
2566
2584
// or just 'Result(rawValue: <expr>)'.
2567
2585
std::string convWrapBefore = toType.getString ();
@@ -2591,8 +2609,8 @@ bool ContextualFailure::tryRawRepresentableFixIts(
2591
2609
}
2592
2610
}
2593
2611
2594
- if (auto rawTy = isRawRepresentable (CS, fromType, rawRepresentableProtocol)) {
2595
- if (conformsToKnownProtocol (CS, toType, rawRepresentableProtocol)) {
2612
+ if (auto rawTy = isRawRepresentable (fromType, rawRepresentableProtocol)) {
2613
+ if (conformsToKnownProtocol (toType, rawRepresentableProtocol)) {
2596
2614
std::string convWrapBefore;
2597
2615
std::string convWrapAfter = " .rawValue" ;
2598
2616
if (!TypeChecker::isConvertibleTo (rawTy, toType, getDC ())) {
@@ -2873,12 +2891,11 @@ void ContextualFailure::tryComputedPropertyFixIts() const {
2873
2891
}
2874
2892
2875
2893
bool ContextualFailure::isIntegerToStringIndexConversion () const {
2876
- auto &cs = getConstraintSystem ();
2877
2894
auto kind = KnownProtocolKind::ExpressibleByIntegerLiteral;
2878
2895
2879
2896
auto fromType = getFromType ();
2880
2897
auto toType = getToType ()->getCanonicalType ();
2881
- return (conformsToKnownProtocol (cs, fromType, kind) &&
2898
+ return (conformsToKnownProtocol (fromType, kind) &&
2882
2899
toType.getString () == " String.CharacterView.Index" );
2883
2900
}
2884
2901
@@ -3135,12 +3152,18 @@ bool MissingPropertyWrapperUnwrapFailure::diagnoseAsError() {
3135
3152
}
3136
3153
3137
3154
bool SubscriptMisuseFailure::diagnoseAsError () {
3155
+ auto *locator = getLocator ();
3138
3156
auto &sourceMgr = getASTContext ().SourceMgr ;
3139
3157
3140
3158
auto *memberExpr = castToExpr<UnresolvedDotExpr>(getRawAnchor ());
3141
3159
3142
3160
auto memberRange = getSourceRange ();
3143
- (void )simplifyLocator (getConstraintSystem (), getLocator (), memberRange);
3161
+
3162
+ {
3163
+ auto rawAnchor = getRawAnchor ();
3164
+ auto path = locator->getPath ();
3165
+ simplifyLocator (rawAnchor, path, memberRange);
3166
+ }
3144
3167
3145
3168
auto nameLoc = DeclNameLoc (memberRange.Start );
3146
3169
@@ -3170,7 +3193,7 @@ bool SubscriptMisuseFailure::diagnoseAsError() {
3170
3193
}
3171
3194
diag.flush ();
3172
3195
3173
- if (auto overload = getOverloadChoiceIfAvailable (getLocator () )) {
3196
+ if (auto overload = getOverloadChoiceIfAvailable (locator )) {
3174
3197
emitDiagnosticAt (overload->choice .getDecl (), diag::kind_declared_here,
3175
3198
DescriptiveDeclKind::Subscript);
3176
3199
}
@@ -3402,27 +3425,26 @@ bool MissingMemberFailure::diagnoseForDynamicCallable() const {
3402
3425
}
3403
3426
3404
3427
bool MissingMemberFailure::diagnoseInLiteralCollectionContext () const {
3405
- auto &cs = getConstraintSystem ();
3406
3428
auto *expr = castToExpr (getAnchor ());
3407
- auto *parentExpr = cs. getParentExpr (expr);
3429
+ auto *parentExpr = findParentExpr (expr);
3408
3430
auto &solution = getSolution ();
3409
3431
3410
3432
if (!(parentExpr && isa<UnresolvedMemberExpr>(expr)))
3411
3433
return false ;
3412
3434
3413
3435
auto parentType = getType (parentExpr);
3414
3436
3415
- if (!cs. isCollectionType (parentType) && !parentType->is <TupleType>())
3437
+ if (!isCollectionType (parentType) && !parentType->is <TupleType>())
3416
3438
return false ;
3417
3439
3418
3440
if (isa<TupleExpr>(parentExpr)) {
3419
- parentExpr = cs. getParentExpr (parentExpr);
3441
+ parentExpr = findParentExpr (parentExpr);
3420
3442
if (!parentExpr)
3421
3443
return false ;
3422
3444
}
3423
3445
3424
3446
if (auto *defaultableVar =
3425
- cs. getType (parentExpr)->getAs <TypeVariableType>()) {
3447
+ getRawType (parentExpr)->getAs <TypeVariableType>()) {
3426
3448
if (solution.DefaultedConstraints .count (
3427
3449
defaultableVar->getImpl ().getLocator ()) != 0 ) {
3428
3450
emitDiagnostic (diag::unresolved_member_no_inference, getName ());
@@ -4261,12 +4283,11 @@ bool MissingArgumentsFailure::isMisplacedMissingArgument(
4261
4283
return (*fix)->getKind () == kind;
4262
4284
};
4263
4285
4264
- auto &cs = solution.getConstraintSystem ();
4265
4286
auto *callLocator =
4266
- cs .getConstraintLocator (anchor, ConstraintLocator::ApplyArgument);
4287
+ solution .getConstraintLocator (anchor, { ConstraintLocator::ApplyArgument} );
4267
4288
4268
4289
auto argFlags = fnType->getParams ()[0 ].getParameterFlags ();
4269
- auto *argLoc = cs .getConstraintLocator (
4290
+ auto *argLoc = solution .getConstraintLocator (
4270
4291
callLocator, LocatorPathElt::ApplyArgToParam (0 , 0 , argFlags));
4271
4292
4272
4293
if (!(hasFixFor (FixKind::AllowArgumentTypeMismatch, argLoc) &&
@@ -4295,7 +4316,7 @@ bool MissingArgumentsFailure::isMisplacedMissingArgument(
4295
4316
auto argType = solution.simplifyType (solution.getType (argument));
4296
4317
auto paramType = fnType->getParams ()[1 ].getPlainType ();
4297
4318
4298
- return TypeChecker::isConvertibleTo (argType, paramType, cs. DC );
4319
+ return TypeChecker::isConvertibleTo (argType, paramType, solution. getDC () );
4299
4320
}
4300
4321
4301
4322
std::tuple<Expr *, Expr *, unsigned , bool >
@@ -5053,7 +5074,7 @@ bool MissingGenericArgumentsFailure::diagnoseForAnchor(
5053
5074
5054
5075
bool MissingGenericArgumentsFailure::diagnoseParameter (
5055
5076
Anchor anchor, GenericTypeParamType *GP) const {
5056
- auto &cs = getConstraintSystem ();
5077
+ auto &solution = getSolution ();
5057
5078
5058
5079
auto loc = anchor.is <Expr *>() ? anchor.get <Expr *>()->getLoc ()
5059
5080
: anchor.get <TypeRepr *>()->getLoc ();
@@ -5063,7 +5084,7 @@ bool MissingGenericArgumentsFailure::diagnoseParameter(
5063
5084
// going to be completely cut off from the rest of constraint system,
5064
5085
// that's why we'd get two fixes in this case which is not ideal.
5065
5086
if (locator->isForContextualType () &&
5066
- llvm::count_if (cs .DefaultedConstraints ,
5087
+ llvm::count_if (solution .DefaultedConstraints ,
5067
5088
[&GP](const ConstraintLocator *locator) {
5068
5089
return locator->getGenericParameter () == GP;
5069
5090
}) > 1 ) {
@@ -5103,7 +5124,7 @@ bool MissingGenericArgumentsFailure::diagnoseParameter(
5103
5124
5104
5125
void MissingGenericArgumentsFailure::emitGenericSignatureNote (
5105
5126
Anchor anchor) const {
5106
- auto &cs = getConstraintSystem ();
5127
+ auto &solution = getSolution ();
5107
5128
auto *paramDC = getDeclContext ();
5108
5129
5109
5130
if (!paramDC)
@@ -5121,7 +5142,9 @@ void MissingGenericArgumentsFailure::emitGenericSignatureNote(
5121
5142
};
5122
5143
5123
5144
llvm::SmallDenseMap<GenericTypeParamDecl *, Type> params;
5124
- for (auto *typeVar : cs.getTypeVariables ()) {
5145
+ for (auto &entry : solution.typeBindings ) {
5146
+ auto *typeVar = entry.first ;
5147
+
5125
5148
auto *GP = typeVar->getImpl ().getGenericParameter ();
5126
5149
if (!GP)
5127
5150
continue ;
@@ -5131,7 +5154,7 @@ void MissingGenericArgumentsFailure::emitGenericSignatureNote(
5131
5154
5132
5155
// If this is one of the defaulted parameter types, attempt
5133
5156
// to emit placeholder for it instead of `Any`.
5134
- if (llvm::any_of (cs .DefaultedConstraints ,
5157
+ if (llvm::any_of (solution .DefaultedConstraints ,
5135
5158
[&](const ConstraintLocator *locator) {
5136
5159
return GP->getDecl () == getParamDecl (locator);
5137
5160
}))
@@ -5558,11 +5581,14 @@ bool ArgumentMismatchFailure::diagnoseUseOfReferenceEqualityOperator() const {
5558
5581
// let's avoid producing a diagnostic second time, because first
5559
5582
// one would cover both arguments.
5560
5583
if (getAsExpr (getAnchor ()) == rhs && rhsType->is <FunctionType>()) {
5561
- auto &cs = getConstraintSystem ();
5562
- if (cs.hasFixFor (getConstraintLocator (
5563
- binaryOp, {ConstraintLocator::ApplyArgument,
5564
- LocatorPathElt::ApplyArgToParam (
5565
- 0 , 0 , getParameterFlagsAtIndex (0 ))})))
5584
+ auto *argLoc = getConstraintLocator (
5585
+ binaryOp,
5586
+ {ConstraintLocator::ApplyArgument,
5587
+ LocatorPathElt::ApplyArgToParam (0 , 0 , getParameterFlagsAtIndex (0 ))});
5588
+
5589
+ if (llvm::any_of (getSolution ().Fixes , [&argLoc](const ConstraintFix *fix) {
5590
+ return fix->getLocator () == argLoc;
5591
+ }))
5566
5592
return true ;
5567
5593
}
5568
5594
0 commit comments