@@ -106,7 +106,7 @@ pub trait TypeErrCtxtExt<'tcx> {
106
106
obligation : & PredicateObligation < ' tcx > ,
107
107
trait_ref : ty:: TraitRef < ' tcx > ,
108
108
err : & mut Diagnostic ,
109
- ) ;
109
+ ) -> bool ;
110
110
111
111
fn report_const_param_not_wf (
112
112
& self ,
@@ -507,8 +507,9 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
507
507
508
508
let mut err = struct_span_err ! ( self . tcx. sess, span, E0277 , "{}" , err_msg) ;
509
509
510
+ let mut suggested = false ;
510
511
if is_try_conversion {
511
- self . try_conversion_context ( & obligation, trait_ref. skip_binder ( ) , & mut err) ;
512
+ suggested = self . try_conversion_context ( & obligation, trait_ref. skip_binder ( ) , & mut err) ;
512
513
}
513
514
514
515
if is_try_conversion && let Some ( ret_span) = self . return_type_span ( & obligation) {
@@ -611,8 +612,7 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
611
612
612
613
self . suggest_floating_point_literal ( & obligation, & mut err, & trait_ref) ;
613
614
self . suggest_dereferencing_index ( & obligation, & mut err, trait_predicate) ;
614
- let mut suggested =
615
- self . suggest_dereferences ( & obligation, & mut err, trait_predicate) ;
615
+ suggested |= self . suggest_dereferences ( & obligation, & mut err, trait_predicate) ;
616
616
suggested |= self . suggest_fn_call ( & obligation, & mut err, trait_predicate) ;
617
617
let impl_candidates = self . find_similar_impl_candidates ( trait_predicate) ;
618
618
suggested = if let & [ cand] = & impl_candidates[ ..] {
@@ -967,7 +967,7 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
967
967
obligation : & PredicateObligation < ' tcx > ,
968
968
trait_ref : ty:: TraitRef < ' tcx > ,
969
969
err : & mut Diagnostic ,
970
- ) {
970
+ ) -> bool {
971
971
let span = obligation. cause . span ;
972
972
struct V < ' v > {
973
973
search_span : Span ,
@@ -992,22 +992,22 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
992
992
Some ( hir:: Node :: Item ( hir:: Item { kind : hir:: ItemKind :: Fn ( _, _, body_id) , .. } ) ) => {
993
993
body_id
994
994
}
995
- _ => return ,
995
+ _ => return false ,
996
996
} ;
997
997
let mut v = V { search_span : span, found : None } ;
998
998
v. visit_body ( self . tcx . hir ( ) . body ( * body_id) ) ;
999
999
let Some ( expr) = v. found else {
1000
- return ;
1000
+ return false ;
1001
1001
} ;
1002
1002
let Some ( typeck) = & self . typeck_results else {
1003
- return ;
1003
+ return false ;
1004
1004
} ;
1005
1005
let Some ( ( ObligationCauseCode :: QuestionMark , Some ( y) ) ) = obligation. cause . code ( ) . parent ( )
1006
1006
else {
1007
- return ;
1007
+ return false ;
1008
1008
} ;
1009
1009
if !self . tcx . is_diagnostic_item ( sym:: FromResidual , y. def_id ( ) ) {
1010
- return ;
1010
+ return false ;
1011
1011
}
1012
1012
let self_ty = trait_ref. self_ty ( ) ;
1013
1013
let found_ty = trait_ref. args . get ( 1 ) . and_then ( |a| a. as_type ( ) ) ;
@@ -1032,6 +1032,7 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
1032
1032
Some ( arg. as_type ( ) ?)
1033
1033
} ;
1034
1034
1035
+ let mut suggested = false ;
1035
1036
let mut chain = vec ! [ ] ;
1036
1037
1037
1038
// The following logic is simlar to `point_at_chain`, but that's focused on associated types
@@ -1096,6 +1097,7 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
1096
1097
)
1097
1098
. must_apply_modulo_regions ( )
1098
1099
{
1100
+ suggested = true ;
1099
1101
err. span_suggestion_short (
1100
1102
stmt. span . with_lo ( expr. span . hi ( ) ) ,
1101
1103
"remove this semicolon" ,
@@ -1152,17 +1154,20 @@ impl<'tcx> TypeErrCtxtExt<'tcx> for TypeErrCtxt<'_, 'tcx> {
1152
1154
)
1153
1155
. must_apply_modulo_regions ( )
1154
1156
{
1155
- err. span_label ( span, format ! ( "this has type `Result<_, {err_ty}>`" ) ) ;
1157
+ if !suggested {
1158
+ err. span_label ( span, format ! ( "this has type `Result<_, {err_ty}>`" ) ) ;
1159
+ }
1156
1160
} else {
1157
1161
err. span_label (
1158
- span,
1159
- format ! (
1160
- "this can't be annotated with `?` because it has type `Result<_, {err_ty}>`" ,
1161
- ) ,
1162
- ) ;
1162
+ span,
1163
+ format ! (
1164
+ "this can't be annotated with `?` because it has type `Result<_, {err_ty}>`" ,
1165
+ ) ,
1166
+ ) ;
1163
1167
}
1164
1168
prev = Some ( err_ty) ;
1165
1169
}
1170
+ suggested
1166
1171
}
1167
1172
1168
1173
fn report_const_param_not_wf (
0 commit comments