Add `-Z borrowck=migrate` flag, use it to link NLL up to AST-borrowck.
This commit is contained in:
parent
655894baf9
commit
a23e8a726c
|
@ -455,15 +455,28 @@ pub enum BorrowckMode {
|
|||
Ast,
|
||||
Mir,
|
||||
Compare,
|
||||
Migrate,
|
||||
}
|
||||
|
||||
impl BorrowckMode {
|
||||
/// Should we run the MIR-based borrow check, but also fall back
|
||||
/// on the AST borrow check if the MIR-based one errors.
|
||||
pub fn migrate(self) -> bool {
|
||||
match self {
|
||||
BorrowckMode::Ast => false,
|
||||
BorrowckMode::Compare => false,
|
||||
BorrowckMode::Mir => false,
|
||||
BorrowckMode::Migrate => true,
|
||||
}
|
||||
}
|
||||
|
||||
/// Should we emit the AST-based borrow checker errors?
|
||||
pub fn use_ast(self) -> bool {
|
||||
match self {
|
||||
BorrowckMode::Ast => true,
|
||||
BorrowckMode::Compare => true,
|
||||
BorrowckMode::Mir => false,
|
||||
BorrowckMode::Migrate => false,
|
||||
}
|
||||
}
|
||||
/// Should we emit the MIR-based borrow checker errors?
|
||||
|
@ -472,6 +485,7 @@ impl BorrowckMode {
|
|||
BorrowckMode::Ast => false,
|
||||
BorrowckMode::Compare => true,
|
||||
BorrowckMode::Mir => true,
|
||||
BorrowckMode::Migrate => true,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2166,6 +2180,7 @@ pub fn build_session_options_and_crate_config(
|
|||
None | Some("ast") => BorrowckMode::Ast,
|
||||
Some("mir") => BorrowckMode::Mir,
|
||||
Some("compare") => BorrowckMode::Compare,
|
||||
Some("migrate") => BorrowckMode::Migrate,
|
||||
Some(m) => early_error(error_format, &format!("unknown borrowck mode `{}`", m)),
|
||||
};
|
||||
|
||||
|
|
|
@ -1366,6 +1366,12 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
|
|||
self.borrowck_mode().use_mir()
|
||||
}
|
||||
|
||||
/// If true, we should use the MIR-based borrow check, but also
|
||||
/// fall back on the AST borrow check if the MIR-based one errors.
|
||||
pub fn migrate_borrowck(self) -> bool {
|
||||
self.borrowck_mode().migrate()
|
||||
}
|
||||
|
||||
/// If true, make MIR codegen for `match` emit a temp that holds a
|
||||
/// borrow of the input to the match expression.
|
||||
pub fn generate_borrow_of_any_match_input(&self) -> bool {
|
||||
|
@ -1399,6 +1405,7 @@ impl<'a, 'gcx, 'tcx> TyCtxt<'a, 'gcx, 'tcx> {
|
|||
pub fn borrowck_mode(&self) -> BorrowckMode {
|
||||
match self.sess.opts.borrowck_mode {
|
||||
mode @ BorrowckMode::Mir |
|
||||
mode @ BorrowckMode::Migrate |
|
||||
mode @ BorrowckMode::Compare => mode,
|
||||
|
||||
mode @ BorrowckMode::Ast => {
|
||||
|
|
|
@ -90,7 +90,7 @@ pub struct AnalysisData<'a, 'tcx: 'a> {
|
|||
fn borrowck<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, owner_def_id: DefId)
|
||||
-> Lrc<BorrowCheckResult>
|
||||
{
|
||||
assert!(tcx.use_ast_borrowck());
|
||||
assert!(tcx.use_ast_borrowck() || tcx.migrate_borrowck());
|
||||
|
||||
debug!("borrowck(body_owner_def_id={:?})", owner_def_id);
|
||||
|
||||
|
|
|
@ -99,6 +99,25 @@ impl Diagnostic {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn is_error(&self) -> bool {
|
||||
match self.level {
|
||||
Level::Bug |
|
||||
Level::Fatal |
|
||||
Level::PhaseFatal |
|
||||
Level::Error |
|
||||
Level::FailureNote => {
|
||||
true
|
||||
}
|
||||
|
||||
Level::Warning |
|
||||
Level::Note |
|
||||
Level::Help |
|
||||
Level::Cancelled => {
|
||||
false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Cancel the diagnostic (a structured diagnostic must either be emitted or
|
||||
/// canceled or it will panic when dropped).
|
||||
pub fn cancel(&mut self) {
|
||||
|
|
|
@ -100,25 +100,6 @@ impl<'a> DiagnosticBuilder<'a> {
|
|||
buffered_diagnostics.push(diagnostic);
|
||||
}
|
||||
|
||||
pub fn is_error(&self) -> bool {
|
||||
match self.level {
|
||||
Level::Bug |
|
||||
Level::Fatal |
|
||||
Level::PhaseFatal |
|
||||
Level::Error |
|
||||
Level::FailureNote => {
|
||||
true
|
||||
}
|
||||
|
||||
Level::Warning |
|
||||
Level::Note |
|
||||
Level::Help |
|
||||
Level::Cancelled => {
|
||||
false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Convenience function for internal use, clients should use one of the
|
||||
/// span_* methods instead.
|
||||
pub fn sub<S: Into<MultiSpan>>(
|
||||
|
|
|
@ -16,6 +16,7 @@ use rustc::hir::def_id::DefId;
|
|||
use rustc::hir::map::definitions::DefPathData;
|
||||
use rustc::infer::InferCtxt;
|
||||
use rustc::lint::builtin::UNUSED_MUT;
|
||||
use rustc::middle::borrowck::SignalledError;
|
||||
use rustc::mir::{AggregateKind, BasicBlock, BorrowCheckResult, BorrowKind};
|
||||
use rustc::mir::{ClearCrossCrate, Local, Location, Mir, Mutability, Operand, Place};
|
||||
use rustc::mir::{Field, Projection, ProjectionElem, Rvalue, Statement, StatementKind};
|
||||
|
@ -23,7 +24,7 @@ use rustc::mir::{Terminator, TerminatorKind};
|
|||
use rustc::ty::query::Providers;
|
||||
use rustc::ty::{self, ParamEnv, TyCtxt};
|
||||
|
||||
use rustc_errors::{Diagnostic, DiagnosticBuilder};
|
||||
use rustc_errors::{Diagnostic, DiagnosticBuilder, Level};
|
||||
use rustc_data_structures::graph::dominators::Dominators;
|
||||
use rustc_data_structures::fx::FxHashSet;
|
||||
use rustc_data_structures::indexed_set::IdxSetBuf;
|
||||
|
@ -329,8 +330,28 @@ fn do_mir_borrowck<'a, 'gcx, 'tcx>(
|
|||
}
|
||||
}
|
||||
|
||||
for diag in mbcx.errors_buffer.drain(..) {
|
||||
DiagnosticBuilder::new_diagnostic(mbcx.tcx.sess.diagnostic(), diag).emit();
|
||||
if mbcx.errors_buffer.len() > 0 {
|
||||
if tcx.migrate_borrowck() {
|
||||
match tcx.borrowck(def_id).signalled_any_error {
|
||||
SignalledError::NoErrorsSeen => {
|
||||
// if AST-borrowck signalled no errors, then
|
||||
// downgrade all the buffered MIR-borrowck errors
|
||||
// to warnings.
|
||||
for err in &mut mbcx.errors_buffer {
|
||||
if err.is_error() { err.level = Level::Warning; }
|
||||
}
|
||||
}
|
||||
SignalledError::SawSomeError => {
|
||||
// if AST-borrowck signalled a (cancelled) error,
|
||||
// then we will just emit the buffered
|
||||
// MIR-borrowck errors as normal.
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for diag in mbcx.errors_buffer.drain(..) {
|
||||
DiagnosticBuilder::new_diagnostic(mbcx.tcx.sess.diagnostic(), diag).emit();
|
||||
}
|
||||
}
|
||||
|
||||
let result = BorrowCheckResult {
|
||||
|
|
Loading…
Reference in New Issue