Auto merge of #36388 - pcwalton:copy-propagation, r=nikomatsakis

librustc_mir: Implement def-use chains and trivial copy propagation on MIR.

This only supports trivial cases in which there is exactly one def and
one use.

Currently, some random unrelated MIR tests are failing, probably just because they haven't been updated.

r? @eddyb
This commit is contained in:
bors 2016-09-20 08:01:01 -07:00 committed by GitHub
commit c772948b68
20 changed files with 593 additions and 37 deletions

View file

@ -23,9 +23,9 @@ fn helper(_: usize) {
pub fn ref_dst(s: &[u8]) {
// We used to generate an extra alloca and memcpy to ref the dst, so check that we copy
// directly to the alloca for "x"
// CHECK: [[X0:%[0-9]+]] = getelementptr {{.*}} { i8*, [[USIZE]] }* %x, i32 0, i32 0
// CHECK: [[X0:%[0-9]+]] = getelementptr {{.*}} { i8*, [[USIZE]] }* %s, i32 0, i32 0
// CHECK: store i8* %0, i8** [[X0]]
// CHECK: [[X1:%[0-9]+]] = getelementptr {{.*}} { i8*, [[USIZE]] }* %x, i32 0, i32 1
// CHECK: [[X1:%[0-9]+]] = getelementptr {{.*}} { i8*, [[USIZE]] }* %s, i32 0, i32 1
// CHECK: store [[USIZE]] %1, [[USIZE]]* [[X1]]
let x = &*s;

View file

@ -21,27 +21,27 @@ fn main() {
// END RUST SOURCE
// START rustc.node4.PreTrans.after.mir
// bb0: {
// StorageLive(var0); // scope 0 at storage_ranges.rs:12:9: 12:10
// var0 = const 0i32; // scope 0 at storage_ranges.rs:12:13: 12:14
// StorageLive(var1); // scope 1 at storage_ranges.rs:14:13: 14:14
// StorageLive(tmp1); // scope 1 at storage_ranges.rs:14:18: 14:25
// StorageLive(tmp2); // scope 1 at storage_ranges.rs:14:23: 14:24
// tmp2 = var0; // scope 1 at storage_ranges.rs:14:23: 14:24
// tmp1 = std::option::Option<i32>::Some(tmp2,); // scope 1 at storage_ranges.rs:14:18: 14:25
// var1 = &tmp1; // scope 1 at storage_ranges.rs:14:17: 14:25
// StorageDead(tmp2); // scope 1 at storage_ranges.rs:14:23: 14:24
// tmp0 = (); // scope 2 at storage_ranges.rs:13:5: 15:6
// StorageDead(tmp1); // scope 1 at storage_ranges.rs:14:18: 14:25
// StorageDead(var1); // scope 1 at storage_ranges.rs:14:13: 14:14
// StorageLive(var2); // scope 1 at storage_ranges.rs:16:9: 16:10
// var2 = const 1i32; // scope 1 at storage_ranges.rs:16:13: 16:14
// return = (); // scope 3 at storage_ranges.rs:11:11: 17:2
// StorageDead(var2); // scope 1 at storage_ranges.rs:16:9: 16:10
// StorageDead(var0); // scope 0 at storage_ranges.rs:12:9: 12:10
// goto -> bb1; // scope 0 at storage_ranges.rs:11:1: 17:2
// nop; // scope 0 at storage_ranges.rs:14:9: 14:10
// var0 = const 0i32; // scope 0 at storage_ranges.rs:14:13: 14:14
// StorageLive(var1); // scope 1 at storage_ranges.rs:16:13: 16:14
// StorageLive(tmp1); // scope 1 at storage_ranges.rs:16:18: 16:25
// nop; // scope 1 at storage_ranges.rs:16:23: 16:24
// nop; // scope 1 at storage_ranges.rs:16:23: 16:24
// tmp1 = std::option::Option<i32>::Some(var0,); // scope 1 at storage_ranges.rs:16:18: 16:25
// var1 = &tmp1; // scope 1 at storage_ranges.rs:16:17: 16:25
// nop; // scope 1 at storage_ranges.rs:16:23: 16:24
// tmp0 = (); // scope 2 at storage_ranges.rs:15:5: 17:6
// StorageDead(tmp1); // scope 1 at storage_ranges.rs:16:18: 16:25
// StorageDead(var1); // scope 1 at storage_ranges.rs:16:13: 16:14
// StorageLive(var2); // scope 1 at storage_ranges.rs:18:9: 18:10
// var2 = const 1i32; // scope 1 at storage_ranges.rs:18:13: 18:14
// return = (); // scope 3 at storage_ranges.rs:13:11: 19:2
// StorageDead(var2); // scope 1 at storage_ranges.rs:18:9: 18:10
// nop; // scope 0 at storage_ranges.rs:14:9: 14:10
// goto -> bb1; // scope 0 at storage_ranges.rs:13:1: 19:2
// }
//
// bb1: {
// return; // scope 0 at storage_ranges.rs:11:1: 17:2
// return; // scope 0 at storage_ranges.rs:13:1: 19:2
// }
// END rustc.node4.PreTrans.after.mir