]> git.lizzy.rs Git - rust.git/blob - src/librustc_mir/dataflow/impls/storage_liveness.rs
Rollup merge of #61237 - DevQps:expand-iterator-docs, r=Mark-Simulacrum
[rust.git] / src / librustc_mir / dataflow / impls / storage_liveness.rs
1 pub use super::*;
2
3 use rustc::mir::*;
4 use crate::dataflow::BitDenotation;
5
6 #[derive(Copy, Clone)]
7 pub struct MaybeStorageLive<'a, 'tcx: 'a> {
8     mir: &'a Mir<'tcx>,
9 }
10
11 impl<'a, 'tcx: 'a> MaybeStorageLive<'a, 'tcx> {
12     pub fn new(mir: &'a Mir<'tcx>)
13                -> Self {
14         MaybeStorageLive { mir }
15     }
16
17     pub fn mir(&self) -> &Mir<'tcx> {
18         self.mir
19     }
20 }
21
22 impl<'a, 'tcx> BitDenotation<'tcx> for MaybeStorageLive<'a, 'tcx> {
23     type Idx = Local;
24     fn name() -> &'static str { "maybe_storage_live" }
25     fn bits_per_block(&self) -> usize {
26         self.mir.local_decls.len()
27     }
28
29     fn start_block_effect(&self, _sets: &mut BitSet<Local>) {
30         // Nothing is live on function entry
31     }
32
33     fn statement_effect(&self,
34                         sets: &mut BlockSets<'_, Local>,
35                         loc: Location) {
36         let stmt = &self.mir[loc.block].statements[loc.statement_index];
37
38         match stmt.kind {
39             StatementKind::StorageLive(l) => sets.gen(l),
40             StatementKind::StorageDead(l) => sets.kill(l),
41             _ => (),
42         }
43     }
44
45     fn terminator_effect(&self,
46                          sets: &mut BlockSets<'_, Local>,
47                          loc: Location) {
48         match &self.mir[loc.block].terminator().kind {
49             TerminatorKind::Drop { location, .. } => if let Some(l) = location.local() {
50                 sets.kill(l);
51             }
52             _ => (),
53         }
54     }
55
56     fn propagate_call_return(
57         &self,
58         _in_out: &mut BitSet<Local>,
59         _call_bb: mir::BasicBlock,
60         _dest_bb: mir::BasicBlock,
61         _dest_place: &mir::Place<'tcx>,
62     ) {
63         // Nothing to do when a call returns successfully
64     }
65 }
66
67 impl<'a, 'tcx> BitSetOperator for MaybeStorageLive<'a, 'tcx> {
68     #[inline]
69     fn join<T: Idx>(&self, inout_set: &mut BitSet<T>, in_set: &BitSet<T>) -> bool {
70         inout_set.union(in_set) // "maybe" means we union effects of both preds
71     }
72 }
73
74 impl<'a, 'tcx> InitialFlow for MaybeStorageLive<'a, 'tcx> {
75     #[inline]
76     fn bottom_value() -> bool {
77         false // bottom = dead
78     }
79 }