@@ -17,6 +17,7 @@ use crate::constants::TRAIT_PATHS;
17
17
18
18
pub ( crate ) struct MutablyUsedVariablesCtxt < ' tcx > {
19
19
mutably_used_vars : hir:: HirIdSet ,
20
+ locally_bind_vars : hir:: HirIdSet ,
20
21
all_vars : FxHashSet < Ty < ' tcx > > ,
21
22
prev_bind : Option < hir:: HirId > ,
22
23
/// In async functions, the inner AST is composed of multiple layers until we reach the code
@@ -34,14 +35,17 @@ pub(crate) fn check_variables<'tcx>(
34
35
body_owner : hir:: def_id:: LocalDefId ,
35
36
body : & hir:: Body < ' tcx > ,
36
37
mut_params : & hir:: HirIdSet ,
38
+ params : & hir:: HirIdSet ,
37
39
) -> bool {
38
40
let MutablyUsedVariablesCtxt {
39
41
mut mutably_used_vars,
40
42
all_vars,
43
+ mut locally_bind_vars,
41
44
..
42
45
} = {
43
46
let mut ctx = MutablyUsedVariablesCtxt {
44
47
mutably_used_vars : hir:: HirIdSet :: default ( ) ,
48
+ locally_bind_vars : hir:: HirIdSet :: default ( ) ,
45
49
all_vars : FxHashSet :: default ( ) ,
46
50
prev_bind : None ,
47
51
prev_move_to_closure : hir:: HirIdSet :: default ( ) ,
@@ -78,7 +82,9 @@ pub(crate) fn check_variables<'tcx>(
78
82
for ty in all_vars {
79
83
res &= is_type_valid ( cx, ty) ;
80
84
}
85
+ locally_bind_vars. retain ( |& item| !params. contains ( & item) ) ;
81
86
mutably_used_vars. retain ( |& item| !mut_params. contains ( & item) ) ;
87
+ mutably_used_vars. retain ( |& item| !locally_bind_vars. contains ( & item) ) ;
82
88
83
89
res &= mutably_used_vars. is_empty ( ) ;
84
90
@@ -315,11 +321,10 @@ impl<'tcx> euv::Delegate<'tcx> for MutablyUsedVariablesCtxt<'tcx> {
315
321
var_path : UpvarPath { hir_id : vid } ,
316
322
..
317
323
} ) ,
318
- base_ty,
319
324
..
320
325
} = & cmt. place
321
326
{
322
- self . all_vars . insert ( * base_ty ) ;
327
+ self . locally_bind_vars . insert ( * vid ) ;
323
328
if self . is_in_unsafe_block ( id) {
324
329
self . add_mutably_used_var ( * vid) ;
325
330
}
0 commit comments