@@ -17,6 +17,7 @@ use crate::dataflow::DataflowResultsCursor;
17
17
use crate :: dataflow:: {
18
18
DefinitelyInitializedPlaces , MaybeInitializedPlaces , MaybeUninitializedPlaces
19
19
} ;
20
+ use crate :: dataflow:: IndirectlyMutableLocals ;
20
21
use crate :: dataflow:: move_paths:: { MovePathIndex , LookupResult } ;
21
22
use crate :: dataflow:: move_paths:: { HasMoveData , MoveData } ;
22
23
@@ -51,6 +52,10 @@ impl<'tcx> MirPass<'tcx> for SanityCheck {
51
52
do_dataflow ( tcx, body, def_id, & attributes, & dead_unwinds,
52
53
DefinitelyInitializedPlaces :: new ( tcx, body, & mdpe) ,
53
54
|bd, i| DebugFormatted :: new ( & bd. move_data ( ) . move_paths [ i] ) ) ;
55
+ let flow_indirectly_mut =
56
+ do_dataflow ( tcx, body, def_id, & attributes, & dead_unwinds,
57
+ IndirectlyMutableLocals :: new ( tcx, body, param_env) ,
58
+ |_, i| DebugFormatted :: new ( & i) ) ;
54
59
55
60
if has_rustc_mir_with ( & attributes, sym:: rustc_peek_maybe_init) . is_some ( ) {
56
61
sanity_check_via_rustc_peek ( tcx, body, def_id, & attributes, & flow_inits) ;
@@ -61,6 +66,9 @@ impl<'tcx> MirPass<'tcx> for SanityCheck {
61
66
if has_rustc_mir_with ( & attributes, sym:: rustc_peek_definite_init) . is_some ( ) {
62
67
sanity_check_via_rustc_peek ( tcx, body, def_id, & attributes, & flow_def_inits) ;
63
68
}
69
+ if has_rustc_mir_with ( & attributes, sym:: rustc_peek_indirectly_mutable) . is_some ( ) {
70
+ sanity_check_via_rustc_peek ( tcx, body, def_id, & attributes, & flow_indirectly_mut) ;
71
+ }
64
72
if has_rustc_mir_with ( & attributes, sym:: stop_after_dataflow) . is_some ( ) {
65
73
tcx. sess . fatal ( "stop_after_dataflow ended compilation" ) ;
66
74
}
@@ -252,9 +260,33 @@ impl<'tcx, O> RustcPeekAt<'tcx> for O
252
260
tcx. sess . span_err ( call. span , "rustc_peek: bit not set" ) ;
253
261
}
254
262
}
263
+
255
264
LookupResult :: Parent ( ..) => {
256
265
tcx. sess . span_err ( call. span , "rustc_peek: argument untracked" ) ;
257
266
}
258
267
}
259
268
}
260
269
}
270
+
271
+ impl < ' tcx > RustcPeekAt < ' tcx > for IndirectlyMutableLocals < ' _ , ' tcx > {
272
+ fn peek_at (
273
+ & self ,
274
+ tcx : TyCtxt < ' tcx > ,
275
+ place : & mir:: Place < ' tcx > ,
276
+ flow_state : & BitSet < Local > ,
277
+ call : PeekCall ,
278
+ ) {
279
+ warn ! ( "peek_at: place={:?}" , place) ;
280
+ let local = match place {
281
+ mir:: Place { base : mir:: PlaceBase :: Local ( l) , projection : box [ ] } => * l,
282
+ _ => {
283
+ tcx. sess . span_err ( call. span , "rustc_peek: argument was not a local" ) ;
284
+ return ;
285
+ }
286
+ } ;
287
+
288
+ if !flow_state. contains ( local) {
289
+ tcx. sess . span_err ( call. span , "rustc_peek: bit not set" ) ;
290
+ }
291
+ }
292
+ }
0 commit comments