From 3ff93177cf7976c1db072cdcb4bc3f23e5f6b78c Mon Sep 17 00:00:00 2001 From: Dylan MacKenzie Date: Wed, 13 May 2020 09:45:00 -0700 Subject: [PATCH] Document why we don't look at storage liveness ...when determining what locals are live. A local cannot be borrowed before it is `storage_live` and `MaybeBorrowedLocals` already invalidates borrows on `StorageDead`. Likewise, a local cannot be initialized before it is marked StorageLive and is marked as uninitialized after `StorageDead`. --- src/librustc_mir/transform/generator.rs | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/librustc_mir/transform/generator.rs b/src/librustc_mir/transform/generator.rs index bee129b8749..5f8104e7934 100644 --- a/src/librustc_mir/transform/generator.rs +++ b/src/librustc_mir/transform/generator.rs @@ -505,6 +505,12 @@ fn locals_live_across_suspend_points( let mut live_locals = locals_live_across_yield_point(block); + // The combination of `MaybeInitializedLocals` and `MaybeBorrowedLocals` should be strictly + // more precise than `MaybeStorageLive` because they handle `StorageDead` themselves. This + // assumes that the MIR forbids locals from being initialized/borrowed before reaching + // `StorageLive`. + debug_assert!(storage_live.get().superset(&live_locals)); + // Ignore the generator's `self` argument since it is handled seperately. live_locals.remove(SELF_ARG); debug!("block = {:?}, live_locals = {:?}", block, live_locals); @@ -571,6 +577,9 @@ fn record_conflicts_at_curr_loc( // // requires_storage := init | borrowed // + // Just like when determining what locals are live at yield points, there is no need + // to look at storage liveness here, since `init | borrowed` is strictly more precise. + // // FIXME: This function is called in a loop, so it might be better to pass in a temporary // bitset rather than cloning here. let mut requires_storage = init.get().clone();