Update match branches

This updates all places where match branches check on StatementKind or UseContext.
This doesn't properly implement them, but adds TODOs where they are, and also adds some best
guesses to what they should be in some cases.
This commit is contained in:
kadmin 2020-10-05 22:53:00 +00:00
parent 72c734d001
commit 89f45ed9f3
19 changed files with 1346 additions and 24 deletions

View File

@ -293,8 +293,7 @@ impl<'mir, 'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> Visitor<'tcx>
| MutatingUseContext::AsmOutput
| MutatingUseContext::Borrow
| MutatingUseContext::AddressOf
| MutatingUseContext::Projection
| MutatingUseContext::CopyNonOverlapping,
| MutatingUseContext::Projection,
)
| PlaceContext::NonMutatingUse(
NonMutatingUseContext::Inspect
@ -302,8 +301,7 @@ impl<'mir, 'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> Visitor<'tcx>
| NonMutatingUseContext::UniqueBorrow
| NonMutatingUseContext::ShallowBorrow
| NonMutatingUseContext::AddressOf
| NonMutatingUseContext::Projection
| NonMutatingUseContext::CopyNonOverlapping,
| NonMutatingUseContext::Projection,
) => {
self.not_ssa(local);
}

View File

@ -120,18 +120,22 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
ref dst,
ref size,
}) => {
let dst_val = self.codegen_place(&mut bx, dst.as_ref());
let src_val = self.codegen_place(&mut bx, src.as_ref());
let dst_val = self.codegen_operand(&mut bx, dst);
let src_val = self.codegen_operand(&mut bx, src);
let size_val = self.codegen_operand(&mut bx, size);
let size = size_val.immediate_or_packed_pair(&mut bx);
let dst = dst_val.immediate_or_packed_pair(&mut bx);
let src = src_val.immediate_or_packed_pair(&mut bx);
use crate::MemFlags;
let flags =
(!MemFlags::UNALIGNED) & (!MemFlags::VOLATILE) & (!MemFlags::NONTEMPORAL);
bx.memcpy(
dst_val.llval,
dst_val.align,
src_val.llval,
src_val.align,
dst,
dst_val.layout.layout.align.pref,
src,
src_val.layout.layout.align.pref,
size,
// TODO probably want to have this change based on alignment above?
crate::MemFlags::empty(),
flags,
);
bx
}

View File

@ -1668,7 +1668,7 @@ impl Debug for Statement<'_> {
ref src,
ref dst,
ref size,
}) => write!(fmt, "copy_nonoverlapping(src={:?}, dst={:?},bytes={:?})", src, dst, size),
}) => write!(fmt, "copy_nonoverlapping(src={:?}, dst={:?}, size={:?})", src, dst, size),
Nop => write!(fmt, "nop"),
}
}
@ -1682,8 +1682,8 @@ pub struct Coverage {
#[derive(Clone, Debug, PartialEq, TyEncodable, TyDecodable, HashStable, TypeFoldable)]
pub struct CopyNonOverlapping<'tcx> {
pub src: Place<'tcx>,
pub dst: Place<'tcx>,
pub src: Operand<'tcx>,
pub dst: Operand<'tcx>,
pub size: Operand<'tcx>,
}

View File

@ -441,14 +441,12 @@ macro_rules! make_mir_visitor {
ref $($mutability)? dst,
ref $($mutability)? size,
}) => {
self.visit_place(
self.visit_operand(
src,
PlaceContext::NonMutatingUse(NonMutatingUseContext::CopyNonOverlapping),
location
);
self.visit_place(
self.visit_operand(
dst,
PlaceContext::MutatingUse(MutatingUseContext::CopyNonOverlapping),
location
);
self.visit_operand(size, location)
@ -1168,8 +1166,6 @@ pub enum NonMutatingUseContext {
/// f(&x.y);
///
Projection,
/// Source from copy_nonoverlapping.
CopyNonOverlapping,
}
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
@ -1199,8 +1195,6 @@ pub enum MutatingUseContext {
Projection,
/// Retagging, a "Stacked Borrows" shadow state operation
Retag,
/// Memory written to in copy_nonoverlapping.
CopyNonOverlapping,
}
#[derive(Copy, Clone, Debug, PartialEq, Eq)]

View File

@ -92,6 +92,21 @@ impl<'cx, 'tcx> Visitor<'tcx> for InvalidationGenerator<'cx, 'tcx> {
self.consume_operand(location, input);
}
}
StatementKind::CopyNonOverlapping(box rustc_middle::mir::CopyNonOverlapping {
ref src,
ref dst,
ref size,
}) => {
self.consume_operand(location, src);
self.consume_operand(location, dst);
self.consume_operand(location, size);
match dst {
Operand::Move(ref place) | Operand::Copy(ref place) => {
self.mutate_place(location, *place, Deep, JustWrite);
}
_ => {}
}
}
StatementKind::Nop
| StatementKind::Coverage(..)
| StatementKind::AscribeUserType(..)

View File

@ -626,6 +626,8 @@ impl<'cx, 'tcx> dataflow::ResultsVisitor<'cx, 'tcx> for MirBorrowckCtxt<'cx, 'tc
self.consume_operand(location, (input, span), flow_state);
}
}
StatementKind::CopyNonOverlapping(..) => todo!(),
StatementKind::Nop
| StatementKind::Coverage(..)
| StatementKind::AscribeUserType(..)

View File

@ -1520,6 +1520,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
);
}
}
StatementKind::CopyNonOverlapping(..) => todo!(),
StatementKind::FakeRead(..)
| StatementKind::StorageLive(..)
| StatementKind::StorageDead(..)

View File

@ -306,6 +306,8 @@ impl<'tcx> dataflow::GenKillAnalysis<'tcx> for Borrows<'_, 'tcx> {
| mir::StatementKind::AscribeUserType(..)
| mir::StatementKind::Coverage(..)
| mir::StatementKind::Nop => {}
mir::StatementKind::CopyNonOverlapping(..) => todo!(),
}
}

View File

@ -150,6 +150,8 @@ impl<'mir, 'tcx> dataflow::GenKillAnalysis<'tcx> for MaybeRequiresStorage<'mir,
| StatementKind::Nop
| StatementKind::Retag(..)
| StatementKind::StorageLive(..) => {}
StatementKind::CopyNonOverlapping(..) => todo!(),
}
}

View File

@ -319,6 +319,8 @@ impl<'b, 'a, 'tcx> Gatherer<'b, 'a, 'tcx> {
| StatementKind::AscribeUserType(..)
| StatementKind::Coverage(..)
| StatementKind::Nop => {}
StatementKind::CopyNonOverlapping(..) => todo!(),
}
}

View File

@ -113,6 +113,23 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
M::retag(self, *kind, &dest)?;
}
// Call CopyNonOverlapping
CopyNonOverlapping(box rustc_middle::mir::CopyNonOverlapping { dst, src, size }) => {
let size = self.eval_operand(size, None)?;
let dst = {
let dst = self.eval_operand(dst, None)?;
dst.assert_mem_place(self)
};
let src = {
let src = self.eval_operand(src, None)?;
src.assert_mem_place(self)
};
// Not sure how to convert an MPlaceTy<'_, <M as Machine<'_, '_>>::PointerTag>
// to a pointer, or OpTy to a size
self.memory.copy(src, dst, size, /*nonoverlapping*/ true)?;
}
// Statements we do not track.
AscribeUserType(..) => {}

View File

@ -808,6 +808,7 @@ impl Visitor<'tcx> for Validator<'mir, 'tcx> {
| StatementKind::Retag { .. }
| StatementKind::AscribeUserType(..)
| StatementKind::Coverage(..)
| StatementKind::CopyNonOverlapping(..)
| StatementKind::Nop => {}
}
}

View File

@ -115,6 +115,7 @@ impl<'a, 'tcx> Visitor<'tcx> for UnsafetyChecker<'a, 'tcx> {
| StatementKind::Retag { .. }
| StatementKind::AscribeUserType(..)
| StatementKind::Coverage(..)
| StatementKind::CopyNonOverlapping(..)
| StatementKind::Nop => {
// safe (at least as emitted during MIR construction)
}

View File

@ -587,6 +587,7 @@ impl Conflicts<'a> {
| StatementKind::FakeRead(..)
| StatementKind::AscribeUserType(..)
| StatementKind::Coverage(..)
| StatementKind::CopyNonOverlapping(..)
| StatementKind::Nop => {}
}
}

View File

@ -1454,6 +1454,7 @@ impl Visitor<'tcx> for EnsureGeneratorFieldAssignmentsNeverAlias<'_> {
| StatementKind::Retag(..)
| StatementKind::AscribeUserType(..)
| StatementKind::Coverage(..)
| StatementKind::CopyNonOverlapping(..)
| StatementKind::Nop => {}
}
}

File diff suppressed because it is too large Load Diff

View File

@ -39,6 +39,7 @@ impl RemoveNoopLandingPads {
| StatementKind::StorageDead(_)
| StatementKind::AscribeUserType(..)
| StatementKind::Coverage(..)
| StatementKind::CopyNonOverlapping(..)
| StatementKind::Nop => {
// These are all nops in a landing pad
}

View File

@ -245,6 +245,7 @@ pub fn statement_kind_name(statement: &Statement<'_>) -> &'static str {
Retag(..) => "Retag",
AscribeUserType(..) => "AscribeUserType",
Coverage(..) => "Coverage",
CopyNonOverlapping(..) => "CopyNonOverlapping",
Nop => "Nop",
}
}

View File

@ -210,7 +210,7 @@ fn check_statement(tcx: TyCtxt<'tcx>, body: &Body<'tcx>, def_id: DefId, statemen
StatementKind::Assign(box (place, rval)) => {
check_place(tcx, *place, span, body)?;
check_rvalue(tcx, body, def_id, rval, span)
},
}
StatementKind::FakeRead(_, place) |
// just an assignment
@ -218,6 +218,13 @@ fn check_statement(tcx: TyCtxt<'tcx>, body: &Body<'tcx>, def_id: DefId, statemen
StatementKind::LlvmInlineAsm { .. } => Err((span, "cannot use inline assembly in const fn".into())),
StatementKind::CopyNonOverlapping(box rustc_middle::mir::CopyNonOverlapping{
dst, src, size,
}) => {
check_operand(tcx, dst, span, body)?;
check_operand(tcx, src, span, body)?;
check_operand(tcx, size, span, body)
},
// These are all NOPs
StatementKind::StorageLive(_)
| StatementKind::StorageDead(_)