@@ -1035,6 +1035,8 @@ impl<'tcx> LifetimeContext<'_, 'tcx> {
10351035 lifetime_names : & FxHashSet < ast:: Ident > ,
10361036 params : & [ ElisionFailureInfo ] ,
10371037 ) {
1038+ let snippet = self . tcx . sess . source_map ( ) . span_to_snippet ( span) . ok ( ) ;
1039+
10381040 err. span_label (
10391041 span,
10401042 & format ! (
@@ -1044,11 +1046,10 @@ impl<'tcx> LifetimeContext<'_, 'tcx> {
10441046 ) ,
10451047 ) ;
10461048
1047- let snippet = self . tcx . sess . source_map ( ) . span_to_snippet ( span) . ok ( ) ;
10481049 let suggest_existing = |err : & mut DiagnosticBuilder < ' _ > , sugg| {
10491050 err. span_suggestion_verbose (
10501051 span,
1051- "consider using the named lifetime" ,
1052+ & format ! ( "consider using the `{}` lifetime" , lifetime_names . iter ( ) . next ( ) . unwrap ( ) ) ,
10521053 sugg,
10531054 Applicability :: MaybeIncorrect ,
10541055 ) ;
@@ -1138,6 +1139,20 @@ impl<'tcx> LifetimeContext<'_, 'tcx> {
11381139 ( 0 , _, Some ( snippet) ) if !snippet. ends_with ( '>' ) && count == 1 => {
11391140 suggest_new ( err, & format ! ( "{}<'a>" , snippet) ) ;
11401141 }
1142+ ( n, ..) if n > 1 => {
1143+ let spans: Vec < Span > = lifetime_names. iter ( ) . map ( |lt| lt. span ) . collect ( ) ;
1144+ err. span_note ( spans, "these named lifetimes are available to use" ) ;
1145+ if Some ( "" ) == snippet. as_deref ( ) {
1146+ // This happens when we have `Foo<T>` where we point at the space before `T`,
1147+ // but this can be confusing so we give a suggestion with placeholders.
1148+ err. span_suggestion_verbose (
1149+ span,
1150+ "consider using one of the available lifetimes here" ,
1151+ "'lifetime, " . repeat ( count) ,
1152+ Applicability :: HasPlaceholders ,
1153+ ) ;
1154+ }
1155+ }
11411156 _ => { }
11421157 }
11431158 }
0 commit comments