Skip to content

Commit cbbd70d

Browse files
committed
Auto merge of #54941 - pnkfelix:issue-21232-reject-partial-reinit, r=nikomatsakis
reject partial init and reinit of uninitialized data Reject partial initialization of uninitialized structured types (i.e. structs and tuples) and also reject partial *reinitialization* of such types. Fix #54986 Fix #54499 cc #21232
2 parents 9d7f0da + 233fdb4 commit cbbd70d

File tree

53 files changed

+1689
-206
lines changed

Some content is hidden

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

53 files changed

+1689
-206
lines changed

Diff for: src/librustc/mir/mod.rs

+13-1
Original file line numberDiff line numberDiff line change
@@ -1967,7 +1967,10 @@ impl<'tcx> Place<'tcx> {
19671967
Place::Projection(Box::new(PlaceProjection { base: self, elem }))
19681968
}
19691969

1970-
/// Find the innermost `Local` from this `Place`.
1970+
/// Find the innermost `Local` from this `Place`, *if* it is either a local itself or
1971+
/// a single deref of a local.
1972+
///
1973+
/// FIXME: can we safely swap the semantics of `fn base_local` below in here instead?
19711974
pub fn local(&self) -> Option<Local> {
19721975
match self {
19731976
Place::Local(local) |
@@ -1978,6 +1981,15 @@ impl<'tcx> Place<'tcx> {
19781981
_ => None,
19791982
}
19801983
}
1984+
1985+
/// Find the innermost `Local` from this `Place`.
1986+
pub fn base_local(&self) -> Option<Local> {
1987+
match self {
1988+
Place::Local(local) => Some(*local),
1989+
Place::Projection(box Projection { base, elem: _ }) => base.base_local(),
1990+
Place::Promoted(..) | Place::Static(..) => None,
1991+
}
1992+
}
19811993
}
19821994

19831995
impl<'tcx> Debug for Place<'tcx> {

Diff for: src/librustc_mir/borrow_check/error_reporting.rs

+13-12
Original file line numberDiff line numberDiff line change
@@ -51,16 +51,16 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
5151
&mut self,
5252
context: Context,
5353
desired_action: InitializationRequiringAction,
54-
(place, span): (&Place<'tcx>, Span),
54+
(moved_place, used_place, span): (&Place<'tcx>, &Place<'tcx>, Span),
5555
mpi: MovePathIndex,
5656
) {
5757
debug!(
58-
"report_use_of_moved_or_uninitialized: context={:?} desired_action={:?} place={:?} \
59-
span={:?} mpi={:?}",
60-
context, desired_action, place, span, mpi
58+
"report_use_of_moved_or_uninitialized: context={:?} desired_action={:?} \
59+
moved_place={:?} used_place={:?} span={:?} mpi={:?}",
60+
context, desired_action, moved_place, used_place, span, mpi
6161
);
6262

63-
let use_spans = self.move_spans(place, context.loc)
63+
let use_spans = self.move_spans(moved_place, context.loc)
6464
.or_else(|| self.borrow_spans(span, context.loc));
6565
let span = use_spans.args_or_use();
6666

@@ -75,7 +75,7 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
7575
.collect();
7676

7777
if move_out_indices.is_empty() {
78-
let root_place = self.prefixes(&place, PrefixSet::All).last().unwrap();
78+
let root_place = self.prefixes(&used_place, PrefixSet::All).last().unwrap();
7979

8080
if self.uninitialized_error_reported
8181
.contains(&root_place.clone())
@@ -89,14 +89,15 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
8989

9090
self.uninitialized_error_reported.insert(root_place.clone());
9191

92-
let item_msg = match self.describe_place_with_options(place, IncludingDowncast(true)) {
92+
let item_msg = match self.describe_place_with_options(used_place,
93+
IncludingDowncast(true)) {
9394
Some(name) => format!("`{}`", name),
9495
None => "value".to_owned(),
9596
};
9697
let mut err = self.infcx.tcx.cannot_act_on_uninitialized_variable(
9798
span,
9899
desired_action.as_noun(),
99-
&self.describe_place_with_options(place, IncludingDowncast(true))
100+
&self.describe_place_with_options(moved_place, IncludingDowncast(true))
100101
.unwrap_or("_".to_owned()),
101102
Origin::Mir,
102103
);
@@ -111,7 +112,7 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
111112
} else {
112113
if let Some((reported_place, _)) = self.move_error_reported.get(&move_out_indices) {
113114
if self.prefixes(&reported_place, PrefixSet::All)
114-
.any(|p| p == place)
115+
.any(|p| p == used_place)
115116
{
116117
debug!(
117118
"report_use_of_moved_or_uninitialized place: error suppressed \
@@ -128,7 +129,7 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
128129
span,
129130
desired_action.as_noun(),
130131
msg,
131-
self.describe_place_with_options(&place, IncludingDowncast(true)),
132+
self.describe_place_with_options(&moved_place, IncludingDowncast(true)),
132133
Origin::Mir,
133134
);
134135

@@ -181,7 +182,7 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
181182
);
182183
}
183184

184-
if let Some(ty) = self.retrieve_type_for_place(place) {
185+
if let Some(ty) = self.retrieve_type_for_place(used_place) {
185186
let needs_note = match ty.sty {
186187
ty::Closure(id, _) => {
187188
let tables = self.infcx.tcx.typeck_tables_of(id);
@@ -219,7 +220,7 @@ impl<'cx, 'gcx, 'tcx> MirBorrowckCtxt<'cx, 'gcx, 'tcx> {
219220
}
220221

221222
if let Some((_, mut old_err)) = self.move_error_reported
222-
.insert(move_out_indices, (place.clone(), err))
223+
.insert(move_out_indices, (used_place.clone(), err))
223224
{
224225
// Cancel the old error so it doesn't ICE.
225226
old_err.cancel();

0 commit comments

Comments
 (0)