@@ -134,8 +134,7 @@ pub(crate) fn check_liveness<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> Den
134
134
. iterate_to_fixpoint ( tcx, body, None )
135
135
. into_results_cursor ( body) ;
136
136
137
- let mut assignments =
138
- AssignmentResult :: find_dead_assignments ( tcx, & checked_places, & mut live, body) ;
137
+ let mut assignments = AssignmentResult :: find_dead_assignments ( & checked_places, & mut live, body) ;
139
138
140
139
assignments. merge_guards ( & checked_places, body) ;
141
140
@@ -197,6 +196,33 @@ fn maybe_suggest_literal_matching_name(
197
196
finder. found
198
197
}
199
198
199
+ /// Return whether we should consider the current place as a drop guard and skip reporting.
200
+ fn maybe_drop_guard < ' tcx > (
201
+ tcx : TyCtxt < ' tcx > ,
202
+ typing_env : ty:: TypingEnv < ' tcx > ,
203
+ index : PlaceIndex ,
204
+ ever_dropped : & DenseBitSet < PlaceIndex > ,
205
+ checked_places : & PlaceSet < ' tcx > ,
206
+ body : & Body < ' tcx > ,
207
+ ) -> bool {
208
+ if ever_dropped. contains ( index) {
209
+ let ty = checked_places. places [ index] . ty ( & body. local_decls , tcx) . ty ;
210
+ matches ! (
211
+ ty. kind( ) ,
212
+ ty:: Closure ( ..)
213
+ | ty:: Coroutine ( ..)
214
+ | ty:: Tuple ( ..)
215
+ | ty:: Adt ( ..)
216
+ | ty:: Dynamic ( ..)
217
+ | ty:: Array ( ..)
218
+ | ty:: Slice ( ..)
219
+ | ty:: Alias ( ty:: Opaque , ..)
220
+ ) && ty. needs_drop ( tcx, typing_env)
221
+ } else {
222
+ false
223
+ }
224
+ }
225
+
200
226
/// Detect the following case
201
227
///
202
228
/// ```text
@@ -578,7 +604,6 @@ impl AssignmentResult {
578
604
/// Assignments are collected, even if they are live. Dead assignments are reported, and live
579
605
/// assignments are used to make diagnostics correct for match guards.
580
606
fn find_dead_assignments < ' tcx > (
581
- tcx : TyCtxt < ' tcx > ,
582
607
checked_places : & PlaceSet < ' tcx > ,
583
608
cursor : & mut ResultsCursor < ' _ , ' tcx , MaybeLivePlaces < ' _ , ' tcx > > ,
584
609
body : & Body < ' tcx > ,
@@ -609,24 +634,9 @@ impl AssignmentResult {
609
634
}
610
635
} ;
611
636
612
- let typing_env = ty:: TypingEnv :: post_analysis ( tcx, body. source . def_id ( ) ) ;
613
637
let mut record_drop = |place : Place < ' tcx > | {
614
638
if let Some ( ( index, & [ ] ) ) = checked_places. get ( place. as_ref ( ) ) {
615
- let ty = place. ty ( & body. local_decls , tcx) . ty ;
616
- let needs_drop = matches ! (
617
- ty. kind( ) ,
618
- ty:: Closure ( ..)
619
- | ty:: Coroutine ( ..)
620
- | ty:: Tuple ( ..)
621
- | ty:: Adt ( ..)
622
- | ty:: Dynamic ( ..)
623
- | ty:: Array ( ..)
624
- | ty:: Slice ( ..)
625
- | ty:: Alias ( ty:: Opaque , ..)
626
- ) && ty. needs_drop ( tcx, typing_env) ;
627
- if needs_drop {
628
- ever_dropped. insert ( index) ;
629
- }
639
+ ever_dropped. insert ( index) ;
630
640
}
631
641
} ;
632
642
@@ -799,6 +809,8 @@ impl AssignmentResult {
799
809
checked_places : & PlaceSet < ' tcx > ,
800
810
body : & Body < ' tcx > ,
801
811
) {
812
+ let typing_env = ty:: TypingEnv :: post_analysis ( tcx, body. source . def_id ( ) ) ;
813
+
802
814
// First, report fully unused locals.
803
815
for ( index, place) in checked_places. iter ( ) {
804
816
if self . ever_live . contains ( index) {
@@ -874,7 +886,15 @@ impl AssignmentResult {
874
886
if !statements. is_empty ( ) {
875
887
// We have a dead local with outstanding assignments and with non-trivial drop.
876
888
// This is probably a drop-guard, so we do not issue a warning there.
877
- if self . ever_dropped . contains ( index) {
889
+ if maybe_drop_guard (
890
+ tcx,
891
+ typing_env,
892
+ index,
893
+ & self . ever_dropped ,
894
+ checked_places,
895
+ body,
896
+ ) {
897
+ statements. clear ( ) ;
878
898
continue ;
879
899
}
880
900
@@ -940,6 +960,8 @@ impl AssignmentResult {
940
960
checked_places : & PlaceSet < ' tcx > ,
941
961
body : & Body < ' tcx > ,
942
962
) {
963
+ let typing_env = ty:: TypingEnv :: post_analysis ( tcx, body. source . def_id ( ) ) ;
964
+
943
965
for ( index, statements) in self . assignments . into_iter_enumerated ( ) {
944
966
if statements. is_empty ( ) {
945
967
continue ;
@@ -949,7 +971,7 @@ impl AssignmentResult {
949
971
950
972
// We have outstanding assignments and with non-trivial drop.
951
973
// This is probably a drop-guard, so we do not issue a warning there.
952
- if self . ever_dropped . contains ( index ) {
974
+ if maybe_drop_guard ( tcx , typing_env , index , & self . ever_dropped , checked_places , body ) {
953
975
continue ;
954
976
}
955
977
0 commit comments