]> git.lizzy.rs Git - rust.git/blob - src/librustc_mir/transform/deaggregator.rs
Rollup merge of #61750 - tmandry:fix-install, r=Mark-Simulacrum
[rust.git] / src / librustc_mir / transform / deaggregator.rs
1 use rustc::mir::*;
2 use rustc::ty::TyCtxt;
3 use crate::transform::{MirPass, MirSource};
4 use crate::util::expand_aggregate;
5
6 pub struct Deaggregator;
7
8 impl MirPass for Deaggregator {
9     fn run_pass<'tcx>(
10         &self,
11         tcx: TyCtxt<'tcx, 'tcx>,
12         _source: MirSource<'tcx>,
13         body: &mut Body<'tcx>,
14     ) {
15         let (basic_blocks, local_decls) = body.basic_blocks_and_local_decls_mut();
16         let local_decls = &*local_decls;
17         for bb in basic_blocks {
18             bb.expand_statements(|stmt| {
19                 // FIXME(eddyb) don't match twice on `stmt.kind` (post-NLL).
20                 if let StatementKind::Assign(_, ref rhs) = stmt.kind {
21                     if let Rvalue::Aggregate(ref kind, _) = **rhs {
22                         // FIXME(#48193) Deaggregate arrays when it's cheaper to do so.
23                         if let AggregateKind::Array(_) = **kind {
24                             return None;
25                         }
26                     } else {
27                         return None;
28                     }
29                 } else {
30                     return None;
31                 }
32
33                 let stmt = stmt.replace_nop();
34                 let source_info = stmt.source_info;
35                 let (lhs, kind, operands) = match stmt.kind {
36                     StatementKind::Assign(lhs, box rvalue) => {
37                         match rvalue {
38                             Rvalue::Aggregate(kind, operands) => (lhs, kind, operands),
39                             _ => bug!()
40                         }
41                     }
42                     _ => bug!()
43                 };
44
45                 Some(expand_aggregate(
46                     lhs,
47                     operands.into_iter().map(|op| {
48                         let ty = op.ty(local_decls, tcx);
49                         (op, ty)
50                     }),
51                     *kind,
52                     source_info,
53                 ))
54             });
55         }
56     }
57 }