Skip to content

Commit e155add

Browse files
spastorinonikomatsakis
authored andcommitted
Move categorize logic out of visit_local function
1 parent d0f1f07 commit e155add

File tree

1 file changed

+77
-55
lines changed

1 file changed

+77
-55
lines changed

src/librustc_mir/util/liveness.rs

Lines changed: 77 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -220,6 +220,78 @@ impl LivenessResult {
220220
}
221221
}
222222

223+
#[derive(Eq, PartialEq, Clone)]
224+
pub enum DefUse {
225+
Def,
226+
Use,
227+
}
228+
229+
pub fn categorize<'tcx>(context: PlaceContext<'tcx>, mode: LivenessMode) -> Option<DefUse> {
230+
match context {
231+
///////////////////////////////////////////////////////////////////////////
232+
// DEFS
233+
234+
PlaceContext::Store |
235+
236+
// We let Call define the result in both the success and
237+
// unwind cases. This is not really correct, however it
238+
// does not seem to be observable due to the way that we
239+
// generate MIR. See the test case
240+
// `mir-opt/nll/liveness-call-subtlety.rs`. To do things
241+
// properly, we would apply the def in call only to the
242+
// input from the success path and not the unwind
243+
// path. -nmatsakis
244+
PlaceContext::Call |
245+
246+
// Storage live and storage dead aren't proper defines, but we can ignore
247+
// values that come before them.
248+
PlaceContext::StorageLive |
249+
PlaceContext::StorageDead => Some(DefUse::Def),
250+
251+
///////////////////////////////////////////////////////////////////////////
252+
// REGULAR USES
253+
//
254+
// These are uses that occur *outside* of a drop. For the
255+
// purposes of NLL, these are special in that **all** the
256+
// lifetimes appearing in the variable must be live for each regular use.
257+
258+
PlaceContext::Projection(..) |
259+
260+
// Borrows only consider their local used at the point of the borrow.
261+
// This won't affect the results since we use this analysis for generators
262+
// and we only care about the result at suspension points. Borrows cannot
263+
// cross suspension points so this behavior is unproblematic.
264+
PlaceContext::Borrow { .. } |
265+
266+
PlaceContext::Inspect |
267+
PlaceContext::Copy |
268+
PlaceContext::Move |
269+
PlaceContext::Validate => {
270+
if mode.include_regular_use {
271+
Some(DefUse::Use)
272+
} else {
273+
None
274+
}
275+
}
276+
277+
///////////////////////////////////////////////////////////////////////////
278+
// DROP USES
279+
//
280+
// These are uses that occur in a DROP (a MIR drop, not a
281+
// call to `std::mem::drop()`). For the purposes of NLL,
282+
// uses in drop are special because `#[may_dangle]`
283+
// attributes can affect whether lifetimes must be live.
284+
285+
PlaceContext::Drop => {
286+
if mode.include_drops {
287+
Some(DefUse::Use)
288+
} else {
289+
None
290+
}
291+
}
292+
}
293+
}
294+
223295
struct DefsUsesVisitor {
224296
mode: LivenessMode,
225297
defs_uses: DefsUses,
@@ -268,66 +340,16 @@ impl DefsUses {
268340

269341
impl<'tcx> Visitor<'tcx> for DefsUsesVisitor {
270342
fn visit_local(&mut self, &local: &Local, context: PlaceContext<'tcx>, _: Location) {
271-
match context {
272-
///////////////////////////////////////////////////////////////////////////
273-
// DEFS
274-
275-
PlaceContext::Store |
276-
277-
// We let Call define the result in both the success and
278-
// unwind cases. This is not really correct, however it
279-
// does not seem to be observable due to the way that we
280-
// generate MIR. See the test case
281-
// `mir-opt/nll/liveness-call-subtlety.rs`. To do things
282-
// properly, we would apply the def in call only to the
283-
// input from the success path and not the unwind
284-
// path. -nmatsakis
285-
PlaceContext::Call |
286-
287-
// Storage live and storage dead aren't proper defines, but we can ignore
288-
// values that come before them.
289-
PlaceContext::StorageLive |
290-
PlaceContext::StorageDead => {
343+
match categorize(context, self.mode) {
344+
Some(DefUse::Def) => {
291345
self.defs_uses.add_def(local);
292346
}
293347

294-
///////////////////////////////////////////////////////////////////////////
295-
// REGULAR USES
296-
//
297-
// These are uses that occur *outside* of a drop. For the
298-
// purposes of NLL, these are special in that **all** the
299-
// lifetimes appearing in the variable must be live for each regular use.
300-
301-
PlaceContext::Projection(..) |
302-
303-
// Borrows only consider their local used at the point of the borrow.
304-
// This won't affect the results since we use this analysis for generators
305-
// and we only care about the result at suspension points. Borrows cannot
306-
// cross suspension points so this behavior is unproblematic.
307-
PlaceContext::Borrow { .. } |
308-
309-
PlaceContext::Inspect |
310-
PlaceContext::Copy |
311-
PlaceContext::Move |
312-
PlaceContext::Validate => {
313-
if self.mode.include_regular_use {
314-
self.defs_uses.add_use(local);
315-
}
348+
Some(DefUse::Use) => {
349+
self.defs_uses.add_use(local);
316350
}
317351

318-
///////////////////////////////////////////////////////////////////////////
319-
// DROP USES
320-
//
321-
// These are uses that occur in a DROP (a MIR drop, not a
322-
// call to `std::mem::drop()`). For the purposes of NLL,
323-
// uses in drop are special because `#[may_dangle]`
324-
// attributes can affect whether lifetimes must be live.
325-
326-
PlaceContext::Drop => {
327-
if self.mode.include_drops {
328-
self.defs_uses.add_use(local);
329-
}
330-
}
352+
None => {}
331353
}
332354
}
333355
}

0 commit comments

Comments
 (0)