Skip to content

Commit 0dab117

Browse files
committed
Remove DropAndReplace terminator
1 parent 03b9e1d commit 0dab117

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

52 files changed

+312
-396
lines changed

compiler/rustc_borrowck/src/diagnostics/conflict_errors.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2364,10 +2364,10 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
23642364
ProjectionElem::Deref => match kind {
23652365
StorageDeadOrDrop::LocalStorageDead
23662366
| StorageDeadOrDrop::BoxedStorageDead => {
2367-
assert!(
2368-
place_ty.ty.is_box(),
2369-
"Drop of value behind a reference or raw pointer"
2370-
);
2367+
// assert!(
2368+
// place_ty.ty.is_box(),
2369+
// "Drop of value behind a reference or raw pointer"
2370+
// );
23712371
StorageDeadOrDrop::BoxedStorageDead
23722372
}
23732373
StorageDeadOrDrop::Destructor(_) => kind,

compiler/rustc_borrowck/src/diagnostics/mod.rs

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -939,7 +939,22 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
939939
return OtherUse(use_span);
940940
}
941941

942-
for stmt in &self.body[location.block].statements[location.statement_index + 1..] {
942+
// drop and replace might have moved the assignment to the next block
943+
let maybe_additional_statement = if let Some(Terminator {
944+
kind: TerminatorKind::Drop { target: drop_target, is_replace: true, .. },
945+
..
946+
}) = self.body[location.block].terminator
947+
{
948+
self.body[drop_target].statements.iter().take(1)
949+
} else {
950+
[].iter().take(0)
951+
};
952+
953+
let statements = self.body[location.block].statements[location.statement_index + 1..]
954+
.iter()
955+
.chain(maybe_additional_statement);
956+
957+
for stmt in statements {
943958
if let StatementKind::Assign(box (_, Rvalue::Aggregate(kind, places))) = &stmt.kind {
944959
let (&def_id, is_generator) = match kind {
945960
box AggregateKind::Closure(def_id, _) => (def_id, false),

compiler/rustc_borrowck/src/invalidation.rs

Lines changed: 37 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,8 @@ use rustc_middle::ty::TyCtxt;
1010

1111
use crate::{
1212
borrow_set::BorrowSet, facts::AllFacts, location::LocationTable, path_utils::*, AccessDepth,
13-
Activation, ArtificialField, BorrowIndex, Deep, LocalMutationIsAllowed, Read, ReadKind,
14-
ReadOrWrite, Reservation, Shallow, Write, WriteKind,
13+
Activation, ArtificialField, BorrowIndex, Deep, FxHashSet, LocalMutationIsAllowed, Read,
14+
ReadKind, ReadOrWrite, Reservation, Shallow, Write, WriteKind,
1515
};
1616

1717
pub(super) fn generate_invalidates<'tcx>(
@@ -36,6 +36,7 @@ pub(super) fn generate_invalidates<'tcx>(
3636
location_table,
3737
body: &body,
3838
dominators,
39+
to_skip: Default::default(),
3940
};
4041
ig.visit_body(body);
4142
}
@@ -48,6 +49,7 @@ struct InvalidationGenerator<'cx, 'tcx> {
4849
body: &'cx Body<'tcx>,
4950
dominators: Dominators<BasicBlock>,
5051
borrow_set: &'cx BorrowSet<'tcx>,
52+
to_skip: FxHashSet<Location>,
5153
}
5254

5355
/// Visits the whole MIR and generates `invalidates()` facts.
@@ -60,7 +62,9 @@ impl<'cx, 'tcx> Visitor<'tcx> for InvalidationGenerator<'cx, 'tcx> {
6062
StatementKind::Assign(box (lhs, rhs)) => {
6163
self.consume_rvalue(location, rhs);
6264

63-
self.mutate_place(location, *lhs, Shallow(None));
65+
if !self.to_skip.contains(&location) {
66+
self.mutate_place(location, *lhs, Shallow(None));
67+
}
6468
}
6569
StatementKind::FakeRead(box (_, _)) => {
6670
// Only relevant for initialized/liveness/safety checks.
@@ -109,22 +113,36 @@ impl<'cx, 'tcx> Visitor<'tcx> for InvalidationGenerator<'cx, 'tcx> {
109113
TerminatorKind::SwitchInt { discr, targets: _ } => {
110114
self.consume_operand(location, discr);
111115
}
112-
TerminatorKind::Drop { place: drop_place, target: _, unwind: _ } => {
113-
self.access_place(
114-
location,
115-
*drop_place,
116-
(AccessDepth::Drop, Write(WriteKind::StorageDeadOrDrop)),
117-
LocalMutationIsAllowed::Yes,
118-
);
119-
}
120-
TerminatorKind::DropAndReplace {
121-
place: drop_place,
122-
value: new_value,
123-
target: _,
124-
unwind: _,
125-
} => {
126-
self.mutate_place(location, *drop_place, Deep);
127-
self.consume_operand(location, new_value);
116+
TerminatorKind::Drop { place: drop_place, target, unwind, is_replace } => {
117+
let next_statement = if *is_replace {
118+
self.body
119+
.basic_blocks
120+
.get(*target)
121+
.expect("MIR should be complete at this point")
122+
.statements
123+
.first()
124+
} else {
125+
None
126+
};
127+
128+
match next_statement {
129+
Some(Statement { kind: StatementKind::Assign(_), source_info: _ }) => {
130+
// this is a drop from a replace operation, for better diagnostic report
131+
// here possible conflicts and mute the assign statement errors
132+
self.to_skip.insert(Location { block: *target, statement_index: 0 });
133+
self.to_skip
134+
.insert(Location { block: unwind.unwrap(), statement_index: 0 });
135+
self.mutate_place(location, *drop_place, AccessDepth::Deep);
136+
}
137+
_ => {
138+
self.access_place(
139+
location,
140+
*drop_place,
141+
(AccessDepth::Drop, Write(WriteKind::StorageDeadOrDrop)),
142+
LocalMutationIsAllowed::Yes,
143+
);
144+
}
145+
}
128146
}
129147
TerminatorKind::Call {
130148
func,

compiler/rustc_borrowck/src/lib.rs

Lines changed: 40 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -340,6 +340,7 @@ fn do_mir_borrowck<'tcx>(
340340
next_region_name: RefCell::new(1),
341341
polonius_output: None,
342342
errors,
343+
to_skip: Default::default(),
343344
};
344345
promoted_mbcx.report_move_errors(move_errors);
345346
errors = promoted_mbcx.errors;
@@ -371,6 +372,7 @@ fn do_mir_borrowck<'tcx>(
371372
next_region_name: RefCell::new(1),
372373
polonius_output,
373374
errors,
375+
to_skip: Default::default(),
374376
};
375377

376378
// Compute and report region errors, if any.
@@ -553,6 +555,8 @@ struct MirBorrowckCtxt<'cx, 'tcx> {
553555
polonius_output: Option<Rc<PoloniusOutput>>,
554556

555557
errors: error::BorrowckErrors<'tcx>,
558+
559+
to_skip: FxHashSet<Location>,
556560
}
557561

558562
// Check that:
@@ -577,8 +581,9 @@ impl<'cx, 'tcx> rustc_mir_dataflow::ResultsVisitor<'cx, 'tcx> for MirBorrowckCtx
577581
match &stmt.kind {
578582
StatementKind::Assign(box (lhs, rhs)) => {
579583
self.consume_rvalue(location, (rhs, span), flow_state);
580-
581-
self.mutate_place(location, (*lhs, span), Shallow(None), flow_state);
584+
if !self.to_skip.contains(&location) {
585+
self.mutate_place(location, (*lhs, span), Shallow(None), flow_state);
586+
}
582587
}
583588
StatementKind::FakeRead(box (_, place)) => {
584589
// Read for match doesn't access any memory and is used to
@@ -644,29 +649,43 @@ impl<'cx, 'tcx> rustc_mir_dataflow::ResultsVisitor<'cx, 'tcx> for MirBorrowckCtx
644649
TerminatorKind::SwitchInt { discr, targets: _ } => {
645650
self.consume_operand(loc, (discr, span), flow_state);
646651
}
647-
TerminatorKind::Drop { place, target: _, unwind: _ } => {
652+
TerminatorKind::Drop { place, target, unwind, is_replace } => {
648653
debug!(
649654
"visit_terminator_drop \
650655
loc: {:?} term: {:?} place: {:?} span: {:?}",
651656
loc, term, place, span
652657
);
653658

654-
self.access_place(
655-
loc,
656-
(*place, span),
657-
(AccessDepth::Drop, Write(WriteKind::StorageDeadOrDrop)),
658-
LocalMutationIsAllowed::Yes,
659-
flow_state,
660-
);
661-
}
662-
TerminatorKind::DropAndReplace {
663-
place: drop_place,
664-
value: new_value,
665-
target: _,
666-
unwind: _,
667-
} => {
668-
self.mutate_place(loc, (*drop_place, span), Deep, flow_state);
669-
self.consume_operand(loc, (new_value, span), flow_state);
659+
let next_statement = if *is_replace {
660+
self.body()
661+
.basic_blocks
662+
.get(*target)
663+
.expect("MIR should be complete at this point")
664+
.statements
665+
.first()
666+
} else {
667+
None
668+
};
669+
670+
match next_statement {
671+
Some(Statement { kind: StatementKind::Assign(_), source_info: _ }) => {
672+
// this is a drop from a replace operation, for better diagnostic report
673+
// here possible conflicts and mute the assign statement errors
674+
self.to_skip.insert(Location { block: *target, statement_index: 0 });
675+
self.to_skip
676+
.insert(Location { block: unwind.unwrap(), statement_index: 0 });
677+
self.mutate_place(loc, (*place, span), AccessDepth::Deep, flow_state);
678+
}
679+
_ => {
680+
self.access_place(
681+
loc,
682+
(*place, span),
683+
(AccessDepth::Drop, Write(WriteKind::StorageDeadOrDrop)),
684+
LocalMutationIsAllowed::Yes,
685+
flow_state,
686+
);
687+
}
688+
}
670689
}
671690
TerminatorKind::Call {
672691
func,
@@ -782,7 +801,6 @@ impl<'cx, 'tcx> rustc_mir_dataflow::ResultsVisitor<'cx, 'tcx> for MirBorrowckCtx
782801
| TerminatorKind::Assert { .. }
783802
| TerminatorKind::Call { .. }
784803
| TerminatorKind::Drop { .. }
785-
| TerminatorKind::DropAndReplace { .. }
786804
| TerminatorKind::FalseEdge { real_target: _, imaginary_target: _ }
787805
| TerminatorKind::FalseUnwind { real_target: _, unwind: _ }
788806
| TerminatorKind::Goto { .. }
@@ -1592,7 +1610,8 @@ impl<'cx, 'tcx> MirBorrowckCtxt<'cx, 'tcx> {
15921610
(prefix, place_span.0, place_span.1),
15931611
mpi,
15941612
);
1595-
} // Only query longest prefix with a MovePath, not further
1613+
}
1614+
// Only query longest prefix with a MovePath, not further
15961615
// ancestors; dataflow recurs on children when parents
15971616
// move (to support partial (re)inits).
15981617
//

compiler/rustc_borrowck/src/type_check/mod.rs

Lines changed: 0 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1345,25 +1345,6 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
13451345
| TerminatorKind::InlineAsm { .. } => {
13461346
// no checks needed for these
13471347
}
1348-
1349-
TerminatorKind::DropAndReplace { place, value, target: _, unwind: _ } => {
1350-
let place_ty = place.ty(body, tcx).ty;
1351-
let rv_ty = value.ty(body, tcx);
1352-
1353-
let locations = term_location.to_locations();
1354-
if let Err(terr) =
1355-
self.sub_types(rv_ty, place_ty, locations, ConstraintCategory::Assignment)
1356-
{
1357-
span_mirbug!(
1358-
self,
1359-
term,
1360-
"bad DropAndReplace ({:?} = {:?}): {:?}",
1361-
place_ty,
1362-
rv_ty,
1363-
terr
1364-
);
1365-
}
1366-
}
13671348
TerminatorKind::SwitchInt { discr, .. } => {
13681349
self.check_operand(discr, term_location);
13691350

@@ -1637,7 +1618,6 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
16371618
}
16381619
TerminatorKind::Unreachable => {}
16391620
TerminatorKind::Drop { target, unwind, .. }
1640-
| TerminatorKind::DropAndReplace { target, unwind, .. }
16411621
| TerminatorKind::Assert { target, cleanup: unwind, .. } => {
16421622
self.assert_iscleanup(body, block_data, target, is_cleanup);
16431623
if let Some(unwind) = unwind {

compiler/rustc_borrowck/src/used_muts.rs

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -71,9 +71,10 @@ impl<'visit, 'cx, 'tcx> Visitor<'tcx> for GatherUsedMutsVisitor<'visit, 'cx, 'tc
7171
TerminatorKind::Call { destination, .. } => {
7272
self.remove_never_initialized_mut_locals(*destination);
7373
}
74-
TerminatorKind::DropAndReplace { place, .. } => {
75-
self.remove_never_initialized_mut_locals(*place);
76-
}
74+
// FIXME: ??
75+
// TerminatorKind::DropAndReplace { place, .. } => {
76+
// self.remove_never_initialized_mut_locals(*place);
77+
// }
7778
_ => {}
7879
}
7980

compiler/rustc_codegen_cranelift/src/base.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -474,11 +474,10 @@ fn codegen_fn_body(fx: &mut FunctionCx<'_, '_, '_>, start_block: Block) {
474474
TerminatorKind::Yield { .. }
475475
| TerminatorKind::FalseEdge { .. }
476476
| TerminatorKind::FalseUnwind { .. }
477-
| TerminatorKind::DropAndReplace { .. }
478477
| TerminatorKind::GeneratorDrop => {
479478
bug!("shouldn't exist at codegen {:?}", bb_data.terminator());
480479
}
481-
TerminatorKind::Drop { place, target, unwind: _ } => {
480+
TerminatorKind::Drop { place, target, unwind: _, is_replace: _ } => {
482481
let drop_place = codegen_place(fx, *place);
483482
crate::abi::codegen_drop(fx, source_info, drop_place);
484483

compiler/rustc_codegen_cranelift/src/constant.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -542,8 +542,7 @@ pub(crate) fn mir_operand_get_const_val<'tcx>(
542542
| TerminatorKind::Unreachable
543543
| TerminatorKind::Drop { .. }
544544
| TerminatorKind::Assert { .. } => {}
545-
TerminatorKind::DropAndReplace { .. }
546-
| TerminatorKind::Yield { .. }
545+
TerminatorKind::Yield { .. }
547546
| TerminatorKind::GeneratorDrop
548547
| TerminatorKind::FalseEdge { .. }
549548
| TerminatorKind::FalseUnwind { .. } => unreachable!(),

compiler/rustc_codegen_ssa/src/mir/analyze.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -281,7 +281,6 @@ pub fn cleanup_kinds(mir: &mir::Body<'_>) -> IndexVec<mir::BasicBlock, CleanupKi
281281
TerminatorKind::Call { cleanup: unwind, .. }
282282
| TerminatorKind::InlineAsm { cleanup: unwind, .. }
283283
| TerminatorKind::Assert { cleanup: unwind, .. }
284-
| TerminatorKind::DropAndReplace { unwind, .. }
285284
| TerminatorKind::Drop { unwind, .. } => {
286285
if let Some(unwind) = unwind {
287286
debug!(

compiler/rustc_codegen_ssa/src/mir/block.rs

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1305,7 +1305,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
13051305
MergingSucc::False
13061306
}
13071307

1308-
mir::TerminatorKind::Drop { place, target, unwind } => {
1308+
mir::TerminatorKind::Drop { place, target, unwind, is_replace: _ } => {
13091309
self.codegen_drop_terminator(helper, bx, place, target, unwind, mergeable_succ())
13101310
}
13111311

@@ -1322,10 +1322,6 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
13221322
mergeable_succ(),
13231323
),
13241324

1325-
mir::TerminatorKind::DropAndReplace { .. } => {
1326-
bug!("undesugared DropAndReplace in codegen: {:?}", terminator);
1327-
}
1328-
13291325
mir::TerminatorKind::Call {
13301326
ref func,
13311327
ref args,

compiler/rustc_const_eval/src/interpret/terminator.rs

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -118,7 +118,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
118118
}
119119
}
120120

121-
Drop { place, target, unwind } => {
121+
Drop { place, target, unwind, is_replace: _ } => {
122122
let frame = self.frame();
123123
let ty = place.ty(&frame.body.local_decls, *self.tcx).ty;
124124
let ty = self.subst_from_frame_and_normalize_erasing_regions(frame, ty)?;
@@ -164,11 +164,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
164164
Unreachable => throw_ub!(Unreachable),
165165

166166
// These should never occur for MIR we actually run.
167-
DropAndReplace { .. }
168-
| FalseEdge { .. }
169-
| FalseUnwind { .. }
170-
| Yield { .. }
171-
| GeneratorDrop => span_bug!(
167+
FalseEdge { .. } | FalseUnwind { .. } | Yield { .. } | GeneratorDrop => span_bug!(
172168
terminator.source_info.span,
173169
"{:#?} should have been eliminated by MIR pass",
174170
terminator.kind

compiler/rustc_const_eval/src/transform/check_consts/check.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -961,8 +961,7 @@ impl<'tcx> Visitor<'tcx> for Checker<'_, 'tcx> {
961961

962962
// Forbid all `Drop` terminators unless the place being dropped is a local with no
963963
// projections that cannot be `NeedsNonConstDrop`.
964-
TerminatorKind::Drop { place: dropped_place, .. }
965-
| TerminatorKind::DropAndReplace { place: dropped_place, .. } => {
964+
TerminatorKind::Drop { place: dropped_place, .. } => {
966965
// If we are checking live drops after drop-elaboration, don't emit duplicate
967966
// errors here.
968967
if super::post_drop_elaboration::checking_enabled(self.ccx) {

compiler/rustc_const_eval/src/transform/check_consts/post_drop_elaboration.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -80,8 +80,7 @@ impl<'tcx> Visitor<'tcx> for CheckLiveDrops<'_, 'tcx> {
8080
trace!("visit_terminator: terminator={:?} location={:?}", terminator, location);
8181

8282
match &terminator.kind {
83-
mir::TerminatorKind::Drop { place: dropped_place, .. }
84-
| mir::TerminatorKind::DropAndReplace { place: dropped_place, .. } => {
83+
mir::TerminatorKind::Drop { place: dropped_place, .. } => {
8584
let dropped_ty = dropped_place.ty(self.body, self.tcx).ty;
8685
if !NeedsNonConstDrop::in_any_value_of_ty(self.ccx, dropped_ty) {
8786
// Instead of throwing a bug, we just return here. This is because we have to

0 commit comments

Comments
 (0)