use PlaceRef abstractions more consistently
This commit is contained in:
parent
0c2c243342
commit
c07c10d1e4
10 changed files with 40 additions and 93 deletions
|
@ -123,13 +123,7 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
|
|||
item_msg = access_place_desc;
|
||||
debug_assert!(self.body.local_decls[ty::CAPTURE_STRUCT_LOCAL].ty.is_ref());
|
||||
debug_assert!(is_closure_or_generator(
|
||||
Place::ty_from(
|
||||
the_place_err.local,
|
||||
the_place_err.projection,
|
||||
self.body,
|
||||
self.infcx.tcx
|
||||
)
|
||||
.ty
|
||||
the_place_err.ty(self.body, self.infcx.tcx).ty
|
||||
));
|
||||
|
||||
reason = if self.is_upvar_field_projection(access_place.as_ref()).is_some() {
|
||||
|
|
|
@ -46,11 +46,9 @@ impl<'tcx> PlaceExt<'tcx> for Place<'tcx> {
|
|||
}
|
||||
}
|
||||
|
||||
for (i, elem) in self.projection.iter().enumerate() {
|
||||
let proj_base = &self.projection[..i];
|
||||
|
||||
for (i, (proj_base, elem)) in self.iter_projections().enumerate() {
|
||||
if elem == ProjectionElem::Deref {
|
||||
let ty = Place::ty_from(self.local, proj_base, body, tcx).ty;
|
||||
let ty = proj_base.ty(body, tcx).ty;
|
||||
match ty.kind() {
|
||||
ty::Ref(_, _, hir::Mutability::Not) if i == 0 => {
|
||||
// For references to thread-local statics, we do need
|
||||
|
|
|
@ -135,13 +135,11 @@ fn place_components_conflict<'tcx>(
|
|||
}
|
||||
|
||||
// loop invariant: borrow_c is always either equal to access_c or disjoint from it.
|
||||
for (i, (borrow_c, &access_c)) in
|
||||
iter::zip(borrow_place.projection, access_place.projection).enumerate()
|
||||
for ((borrow_place, borrow_c), &access_c) in
|
||||
iter::zip(borrow_place.iter_projections(), access_place.projection)
|
||||
{
|
||||
debug!(?borrow_c, ?access_c);
|
||||
|
||||
let borrow_proj_base = &borrow_place.projection[..i];
|
||||
|
||||
// Borrow and access path both have more components.
|
||||
//
|
||||
// Examples:
|
||||
|
@ -154,15 +152,7 @@ fn place_components_conflict<'tcx>(
|
|||
// check whether the components being borrowed vs
|
||||
// accessed are disjoint (as in the second example,
|
||||
// but not the first).
|
||||
match place_projection_conflict(
|
||||
tcx,
|
||||
body,
|
||||
borrow_local,
|
||||
borrow_proj_base,
|
||||
borrow_c,
|
||||
access_c,
|
||||
bias,
|
||||
) {
|
||||
match place_projection_conflict(tcx, body, borrow_place, borrow_c, access_c, bias) {
|
||||
Overlap::Arbitrary => {
|
||||
// We have encountered different fields of potentially
|
||||
// the same union - the borrow now partially overlaps.
|
||||
|
@ -193,8 +183,7 @@ fn place_components_conflict<'tcx>(
|
|||
}
|
||||
|
||||
if borrow_place.projection.len() > access_place.projection.len() {
|
||||
for (i, elem) in borrow_place.projection[access_place.projection.len()..].iter().enumerate()
|
||||
{
|
||||
for (base, elem) in borrow_place.iter_projections().skip(access_place.projection.len()) {
|
||||
// Borrow path is longer than the access path. Examples:
|
||||
//
|
||||
// - borrow of `a.b.c`, access to `a.b`
|
||||
|
@ -203,8 +192,7 @@ fn place_components_conflict<'tcx>(
|
|||
// our place. This is a conflict if that is a part our
|
||||
// access cares about.
|
||||
|
||||
let proj_base = &borrow_place.projection[..access_place.projection.len() + i];
|
||||
let base_ty = Place::ty_from(borrow_local, proj_base, body, tcx).ty;
|
||||
let base_ty = base.ty(body, tcx).ty;
|
||||
|
||||
match (elem, &base_ty.kind(), access) {
|
||||
(_, _, Shallow(Some(ArtificialField::ArrayLength)))
|
||||
|
@ -308,8 +296,7 @@ fn place_base_conflict(l1: Local, l2: Local) -> Overlap {
|
|||
fn place_projection_conflict<'tcx>(
|
||||
tcx: TyCtxt<'tcx>,
|
||||
body: &Body<'tcx>,
|
||||
pi1_local: Local,
|
||||
pi1_proj_base: &[PlaceElem<'tcx>],
|
||||
pi1: PlaceRef<'tcx>,
|
||||
pi1_elem: PlaceElem<'tcx>,
|
||||
pi2_elem: PlaceElem<'tcx>,
|
||||
bias: PlaceConflictBias,
|
||||
|
@ -331,7 +318,7 @@ fn place_projection_conflict<'tcx>(
|
|||
debug!("place_element_conflict: DISJOINT-OR-EQ-FIELD");
|
||||
Overlap::EqualOrDisjoint
|
||||
} else {
|
||||
let ty = Place::ty_from(pi1_local, pi1_proj_base, body, tcx).ty;
|
||||
let ty = pi1.ty(body, tcx).ty;
|
||||
if ty.is_union() {
|
||||
// Different fields of a union, we are basically stuck.
|
||||
debug!("place_element_conflict: STUCK-UNION");
|
||||
|
|
|
@ -2499,7 +2499,6 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
|||
location, borrow_region, borrowed_place
|
||||
);
|
||||
|
||||
let mut cursor = borrowed_place.projection.as_ref();
|
||||
let tcx = self.infcx.tcx;
|
||||
let field = path_utils::is_upvar_field_projection(
|
||||
tcx,
|
||||
|
@ -2513,14 +2512,12 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
|||
ConstraintCategory::Boring
|
||||
};
|
||||
|
||||
while let [proj_base @ .., elem] = cursor {
|
||||
cursor = proj_base;
|
||||
|
||||
for (base, elem) in borrowed_place.as_ref().iter_projections().rev() {
|
||||
debug!("add_reborrow_constraint - iteration {:?}", elem);
|
||||
|
||||
match elem {
|
||||
ProjectionElem::Deref => {
|
||||
let base_ty = Place::ty_from(borrowed_place.local, proj_base, body, tcx).ty;
|
||||
let base_ty = base.ty(body, tcx).ty;
|
||||
|
||||
debug!("add_reborrow_constraint - base_ty = {:?}", base_ty);
|
||||
match base_ty.kind() {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue