Skip to content

Commit ae1b06b

Browse files
committed
[Sema] Display simplified conditional conformance fixits on the command line.
Fixes rdar://problem/39170601 and SR-7352.
1 parent 11d67b5 commit ae1b06b

File tree

5 files changed

+19
-7
lines changed

5 files changed

+19
-7
lines changed

include/swift/AST/DiagnosticsSema.def

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1453,6 +1453,9 @@ NOTE(note_explicitly_state_conditional_conformance_relaxed,none,
14531453
"did you mean to explicitly state the conformance with relaxed bounds?", ())
14541454
NOTE(note_explicitly_state_conditional_conformance_same,none,
14551455
"did you mean to explicitly state the conformance with the same bounds?", ())
1456+
NOTE(note_explicitly_state_conditional_conformance_noneditor,none,
1457+
"did you mean to explicitly state the conformance like '%0where ...'?",
1458+
(StringRef))
14561459
ERROR(protocol_has_missing_requirements,none,
14571460
"type %0 cannot conform to protocol %1 because it has requirements that "
14581461
"cannot be satisfied", (Type, Type))

lib/Sema/TypeCheckProtocol.cpp

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1300,8 +1300,9 @@ static void diagnoseConformanceImpliedByConditionalConformance(
13001300
// want to encourage it.
13011301

13021302
auto ext = cast<ExtensionDecl>(implyingConf->getDeclContext());
1303+
auto &ctxt = ext->getASTContext();
13031304

1304-
auto &SM = ext->getASTContext().SourceMgr;
1305+
auto &SM = ctxt.SourceMgr;
13051306
StringRef extraIndent;
13061307
StringRef indent = Lexer::getIndentationForLine(SM, loc, &extraIndent);
13071308

@@ -1324,6 +1325,16 @@ static void diagnoseConformanceImpliedByConditionalConformance(
13241325
<< indent;
13251326
}
13261327

1328+
if (!ctxt.LangOpts.DiagnosticsEditorMode) {
1329+
// The fixits below are too complicated for the command line: the suggested
1330+
// code ends up not being displayed, and the text by itself doesn't help. So
1331+
// instead we skip all that and just have some text.
1332+
Diags.diagnose(loc,
1333+
diag::note_explicitly_state_conditional_conformance_noneditor,
1334+
prefix.str());
1335+
return;
1336+
}
1337+
13271338
// First, we do the fixit for "matching" requirements (i.e. X: P where T: P).
13281339
bool matchingIsValid = true;
13291340
llvm::SmallString<128> matchingFixit = prefix;

test/Generics/conditional_conformances.swift

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -279,16 +279,14 @@ struct InheritImplicitOne<T> {}
279279
// incorrect/insufficiently general).
280280
extension InheritImplicitOne: P5 where T: P1 {}
281281
// expected-error@-1{{conditional conformance of type 'InheritImplicitOne<T>' to protocol 'P5' does not imply conformance to inherited protocol 'P2'}}
282-
// expected-note@-2{{did you mean to explicitly state the conformance with the same bounds?}}
283-
// expected-note@-3{{did you mean to explicitly state the conformance with different bounds?}}
282+
// expected-note@-2{{did you mean to explicitly state the conformance like 'extension InheritImplicitOne: P2 where ...'?}}
284283

285284
struct InheritImplicitTwo<T> {}
286285
// Even if we relax the rule about implication, this double-up should still be
287286
// an error, because either conformance could imply InheritImplicitTwo: P2.
288287
extension InheritImplicitTwo: P5 where T: P1 {}
289288
// expected-error@-1{{conditional conformance of type 'InheritImplicitTwo<T>' to protocol 'P5' does not imply conformance to inherited protocol 'P2'}}
290-
// expected-note@-2{{did you mean to explicitly state the conformance with the same bounds?}}
291-
// expected-note@-3{{did you mean to explicitly state the conformance with different bounds?}}
289+
// expected-note@-2{{did you mean to explicitly state the conformance like 'extension InheritImplicitTwo: P2 where ...'?}}
292290
extension InheritImplicitTwo: P6 where T: P1 {}
293291

294292
// However, if there's a non-conditional conformance that implies something, we

test/Generics/conditional_conformances_fixit.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// RUN: %target-typecheck-verify-swift -emit-fixits-path %t.remap -fixit-all
1+
// RUN: %target-typecheck-verify-swift -emit-fixits-path %t.remap -fixit-all -diagnostics-editor-mode
22
// RUN: c-arcmt-test %t.remap | arcmt-test -verify-transformed-files %s.result
33

44
protocol P1 {}

test/Generics/conditional_conformances_fixit.swift.result

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// RUN: %target-typecheck-verify-swift -emit-fixits-path %t.remap -fixit-all
1+
// RUN: %target-typecheck-verify-swift -emit-fixits-path %t.remap -fixit-all -diagnostics-editor-mode
22
// RUN: c-arcmt-test %t.remap | arcmt-test -verify-transformed-files %s.result
33

44
protocol P1 {}

0 commit comments

Comments
 (0)