Skip to content

Commit 3a1847b

Browse files
committed
implement outlive suggestions
1 parent b7176b4 commit 3a1847b

39 files changed

+807
-6
lines changed

src/librustc_errors/diagnostic.rs

+15-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ use crate::Applicability;
66
use crate::Level;
77
use crate::snippet::Style;
88
use std::fmt;
9-
use syntax_pos::{MultiSpan, Span};
9+
use syntax_pos::{MultiSpan, Span, DUMMY_SP};
1010

1111
#[must_use]
1212
#[derive(Clone, Debug, PartialEq, Hash, RustcEncodable, RustcDecodable)]
@@ -17,6 +17,11 @@ pub struct Diagnostic {
1717
pub span: MultiSpan,
1818
pub children: Vec<SubDiagnostic>,
1919
pub suggestions: Vec<CodeSuggestion>,
20+
21+
/// This is not used for highlighting or rendering any error message. Rather, it can be used
22+
/// as a sort key to sort a buffer of diagnostics. By default, it is the primary span of
23+
/// `span` if there is one. Otherwise, it is `DUMMY_SP`.
24+
pub sort_span: Span,
2025
}
2126

2227
#[derive(Clone, Debug, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable)]
@@ -87,6 +92,7 @@ impl Diagnostic {
8792
span: MultiSpan::new(),
8893
children: vec![],
8994
suggestions: vec![],
95+
sort_span: DUMMY_SP,
9096
}
9197
}
9298

@@ -118,6 +124,11 @@ impl Diagnostic {
118124
self.level == Level::Cancelled
119125
}
120126

127+
/// Set the sorting span.
128+
pub fn set_sort_span(&mut self, sp: Span) {
129+
self.sort_span = sp;
130+
}
131+
121132
/// Adds a span/label to be included in the resulting snippet.
122133
/// This label will be shown together with the original span/label used when creating the
123134
/// diagnostic, *not* a span added by one of the `span_*` methods.
@@ -457,6 +468,9 @@ impl Diagnostic {
457468

458469
pub fn set_span<S: Into<MultiSpan>>(&mut self, sp: S) -> &mut Self {
459470
self.span = sp.into();
471+
if let Some(span) = self.span.primary_span() {
472+
self.sort_span = span;
473+
}
460474
self
461475
}
462476

src/librustc_mir/borrow_check/mod.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -367,7 +367,7 @@ fn do_mir_borrowck<'a, 'tcx>(
367367
}
368368

369369
if !mbcx.errors_buffer.is_empty() {
370-
mbcx.errors_buffer.sort_by_key(|diag| diag.span.primary_span());
370+
mbcx.errors_buffer.sort_by_key(|diag| diag.sort_span);
371371

372372
for diag in mbcx.errors_buffer.drain(..) {
373373
mbcx.infcx.tcx.sess.diagnostic().emit_diagnostic(&diag);

src/librustc_mir/borrow_check/nll/region_infer/error_reporting/mod.rs

+21-4
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,10 @@ use syntax::errors::Applicability;
1818
use syntax::symbol::kw;
1919
use syntax_pos::Span;
2020

21+
use self::outlives_suggestion::OutlivesSuggestionBuilder;
22+
23+
pub mod outlives_suggestion;
24+
2125
mod region_name;
2226
mod var_name;
2327

@@ -56,7 +60,6 @@ enum Trace {
5660
/// Various pieces of state used when reporting borrow checker errors.
5761
pub struct ErrorReportingCtx<'a, 'b, 'tcx> {
5862
/// The region inference context used for borrow chekcing this MIR body.
59-
#[allow(dead_code)] // FIXME(mark-i-m): used by outlives suggestions
6063
region_infcx: &'b RegionInferenceContext<'tcx>,
6164

6265
/// The inference context used for type checking.
@@ -370,6 +373,7 @@ impl<'tcx> RegionInferenceContext<'tcx> {
370373
fr: RegionVid,
371374
fr_origin: NLLRegionVariableOrigin,
372375
outlived_fr: RegionVid,
376+
outlives_suggestion: &mut OutlivesSuggestionBuilder,
373377
renctx: &mut RegionErrorNamingCtx,
374378
) -> DiagnosticBuilder<'a> {
375379
debug!("report_error(fr={:?}, outlived_fr={:?})", fr, outlived_fr);
@@ -415,9 +419,22 @@ impl<'tcx> RegionInferenceContext<'tcx> {
415419
self.report_fnmut_error(&errctx, &errci, renctx)
416420
}
417421
(ConstraintCategory::Assignment, true, false)
418-
| (ConstraintCategory::CallArgument, true, false) =>
419-
self.report_escaping_data_error(&errctx, &errci, renctx),
420-
_ => self.report_general_error(&errctx, &errci, renctx),
422+
| (ConstraintCategory::CallArgument, true, false) => {
423+
let mut db = self.report_escaping_data_error(&errctx, &errci, renctx);
424+
425+
outlives_suggestion.intermediate_suggestion(&errctx, &errci, renctx, &mut db);
426+
outlives_suggestion.collect_constraint(fr, outlived_fr);
427+
428+
db
429+
}
430+
_ => {
431+
let mut db = self.report_general_error(&errctx, &errci, renctx);
432+
433+
outlives_suggestion.intermediate_suggestion(&errctx, &errci, renctx, &mut db);
434+
outlives_suggestion.collect_constraint(fr, outlived_fr);
435+
436+
db
437+
}
421438
}
422439
}
423440

0 commit comments

Comments
 (0)