use syntax_pos::Span;
use dataflow::indexes::BorrowIndex;
-use dataflow::move_paths::{HasMoveData, LookupResult, MoveData, MovePathIndex};
+use dataflow::move_paths::{HasMoveData, LookupResult, MoveData, MoveError, MovePathIndex};
use dataflow::Borrows;
use dataflow::DataflowResultsConsumer;
use dataflow::FlowAtLocation;
let mir = &mir; // no further changes
let location_table = &LocationTable::new(mir);
- let move_data: MoveData<'tcx> = match MoveData::gather_moves(mir, tcx) {
- Ok(move_data) => move_data,
- Err((move_data, move_errors)) => {
- move_errors::report_move_errors(&mir, tcx, move_errors, &move_data);
- move_data
- }
- };
+ let (move_data, move_errors): (MoveData<'tcx>, Option<Vec<MoveError<'tcx>>>) =
+ match MoveData::gather_moves(mir, tcx) {
+ Ok(move_data) => (move_data, None),
+ Err((move_data, move_errors)) => (move_data, Some(move_errors)),
+ };
let mdpe = MoveDataParamEnv {
move_data: move_data,
polonius_output,
);
+ if let Some(errors) = move_errors {
+ mbcx.report_move_errors(errors);
+ }
mbcx.analyze_results(&mut state); // entry point for DataflowResultsConsumer
// For each non-user used mutable variable, check if it's been assigned from
ProjectionElem::Field(field, _ty) => {
let base_ty = proj.base.ty(self.mir, self.tcx).to_ty(self.tcx);
- if base_ty.is_closure() || base_ty.is_generator() {
+ if base_ty.is_closure() || base_ty.is_generator() {
Some(field)
} else {
None
use rustc::hir;
use rustc::mir::*;
-use rustc::ty::{self, TyCtxt};
+use rustc::ty;
use rustc_errors::DiagnosticBuilder;
use syntax_pos::Span;
-use dataflow::move_paths::{IllegalMoveOrigin, IllegalMoveOriginKind, MoveData};
+use borrow_check::MirBorrowckCtxt;
+use dataflow::move_paths::{IllegalMoveOrigin, IllegalMoveOriginKind};
use dataflow::move_paths::{LookupResult, MoveError, MovePathIndex};
use util::borrowck_errors::{BorrowckErrors, Origin};
-pub(crate) fn report_move_errors<'gcx, 'tcx>(
- mir: &Mir<'tcx>,
- tcx: TyCtxt<'_, 'gcx, 'tcx>,
- move_errors: Vec<MoveError<'tcx>>,
- move_data: &MoveData<'tcx>,
-) {
- MoveErrorCtxt {
- mir,
- tcx,
- move_data,
- }.report_errors(move_errors);
-}
-
-#[derive(Copy, Clone)]
-struct MoveErrorCtxt<'a, 'gcx: 'tcx, 'tcx: 'a> {
- mir: &'a Mir<'tcx>,
- tcx: TyCtxt<'a, 'gcx, 'tcx>,
- move_data: &'a MoveData<'tcx>,
-}
-
// Often when desugaring a pattern match we may have many individual moves in
// MIR that are all part of one operation from the user's point-of-view. For
// example:
},
}
-impl<'a, 'gcx, 'tcx> MoveErrorCtxt<'a, 'gcx, 'tcx> {
- fn report_errors(self, move_errors: Vec<MoveError<'tcx>>) {
+impl<'a, 'gcx, 'tcx> MirBorrowckCtxt<'a, 'gcx, 'tcx> {
+ pub(crate) fn report_move_errors(&self, move_errors: Vec<MoveError<'tcx>>) {
let grouped_errors = self.group_move_errors(move_errors);
for error in grouped_errors {
self.report(error);
}
}
- fn group_move_errors(self, errors: Vec<MoveError<'tcx>>) -> Vec<GroupedMoveError<'tcx>> {
+ fn group_move_errors(&self, errors: Vec<MoveError<'tcx>>) -> Vec<GroupedMoveError<'tcx>> {
let mut grouped_errors = Vec::new();
for error in errors {
self.append_to_grouped_errors(&mut grouped_errors, error);
}
fn append_to_grouped_errors(
- self,
+ &self,
grouped_errors: &mut Vec<GroupedMoveError<'tcx>>,
error: MoveError<'tcx>,
) {
}
fn append_binding_error(
- self,
+ &self,
grouped_errors: &mut Vec<GroupedMoveError<'tcx>>,
kind: IllegalMoveOriginKind<'tcx>,
move_from: &Place<'tcx>,
};
}
- fn report(self, error: GroupedMoveError<'tcx>) {
+ fn report(&self, error: GroupedMoveError<'tcx>) {
let (mut err, err_span) = {
let (span, kind): (Span, &IllegalMoveOriginKind) = match error {
GroupedMoveError::MovesFromMatchPlace { span, ref kind, .. }
}
fn add_move_hints(
- self,
+ &self,
error: GroupedMoveError<'tcx>,
err: &mut DiagnosticBuilder<'a>,
span: Span,
}
}
- fn suitable_to_remove_deref(self, proj: &PlaceProjection<'tcx>, snippet: &str) -> bool {
+ fn suitable_to_remove_deref(&self, proj: &PlaceProjection<'tcx>, snippet: &str) -> bool {
let is_shared_ref = |ty: ty::Ty| match ty.sty {
ty::TypeVariants::TyRef(.., hir::Mutability::MutImmutable) => true,
_ => false,