Skip to content

Commit ad1294d

Browse files
committed
threaded a ty::ParameterEnvironment for the current node id via the associated Ctxt item.
used this to address a long-standing wart/bug in how filtering-out of values with type impl'ing `Copy` was done.
1 parent fdf80bc commit ad1294d

File tree

5 files changed

+56
-44
lines changed

5 files changed

+56
-44
lines changed

src/librustc_borrowck/borrowck/mir/dataflow/graphviz.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ use std::marker::PhantomData;
2424
use std::mem;
2525
use std::path::Path;
2626

27-
use super::super::gather_moves::{MoveData};
27+
use super::super::MoveDataParamEnv;
2828
use super::super::MirBorrowckCtxtPreDataflow;
2929
use bitslice::bits_to_string;
3030
use indexed_set::{Idx, IdxSet};
@@ -79,15 +79,15 @@ impl<O: BitDenotation> DataflowState<O> {
7979
}
8080

8181
pub trait MirWithFlowState<'tcx> {
82-
type BD: BitDenotation<Ctxt=MoveData<'tcx>>;
82+
type BD: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>>;
8383
fn node_id(&self) -> NodeId;
8484
fn mir(&self) -> &Mir<'tcx>;
8585
fn analysis_ctxt(&self) -> &<Self::BD as BitDenotation>::Ctxt;
8686
fn flow_state(&self) -> &DataflowState<Self::BD>;
8787
}
8888

8989
impl<'a, 'tcx: 'a, BD> MirWithFlowState<'tcx> for MirBorrowckCtxtPreDataflow<'a, 'tcx, BD>
90-
where 'a, 'tcx: 'a, BD: BitDenotation<Ctxt=MoveData<'tcx>>
90+
where 'a, 'tcx: 'a, BD: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>>
9191
{
9292
type BD = BD;
9393
fn node_id(&self) -> NodeId { self.node_id }
@@ -109,7 +109,7 @@ pub fn print_borrowck_graph_to<'a, 'tcx, BD, P>(
109109
path: &Path,
110110
render_idx: P)
111111
-> io::Result<()>
112-
where BD: BitDenotation<Ctxt=MoveData<'tcx>>,
112+
where BD: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>>,
113113
P: for <'b> Fn(&'b BD::Ctxt, BD::Idx) -> &'b Debug
114114
{
115115
let g = Graph { mbcx: mbcx, phantom: PhantomData, render_idx: render_idx };

src/librustc_borrowck/borrowck/mir/dataflow/impls.rs

Lines changed: 19 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,8 @@ use rustc::ty::TyCtxt;
1212
use rustc::mir::repr::{self, Mir};
1313

1414
use super::super::gather_moves::{Location};
15-
use super::super::gather_moves::{MoveData, MoveOutIndex, MovePathIndex};
15+
use super::super::gather_moves::{MoveOutIndex, MovePathIndex};
16+
use super::super::MoveDataParamEnv;
1617
use super::super::DropFlagState;
1718
use super::super::drop_flag_effects_for_function_entry;
1819
use super::super::drop_flag_effects_for_location;
@@ -226,10 +227,10 @@ impl<'a, 'tcx> DefinitelyInitializedLvals<'a, 'tcx> {
226227

227228
impl<'a, 'tcx> BitDenotation for MaybeInitializedLvals<'a, 'tcx> {
228229
type Idx = MovePathIndex;
229-
type Ctxt = MoveData<'tcx>;
230+
type Ctxt = MoveDataParamEnv<'tcx>;
230231
fn name() -> &'static str { "maybe_init" }
231232
fn bits_per_block(&self, ctxt: &Self::Ctxt) -> usize {
232-
ctxt.move_paths.len()
233+
ctxt.move_data.move_paths.len()
233234
}
234235

235236
fn start_block_effect(&self, ctxt: &Self::Ctxt, sets: &mut BlockSets<MovePathIndex>)
@@ -276,19 +277,19 @@ impl<'a, 'tcx> BitDenotation for MaybeInitializedLvals<'a, 'tcx> {
276277
dest_lval: &repr::Lvalue) {
277278
// when a call returns successfully, that means we need to set
278279
// the bits for that dest_lval to 1 (initialized).
279-
let move_path_index = ctxt.rev_lookup.find(dest_lval);
280-
on_all_children_bits(self.tcx, self.mir, ctxt,
280+
let move_path_index = ctxt.move_data.rev_lookup.find(dest_lval);
281+
on_all_children_bits(self.tcx, self.mir, &ctxt.move_data,
281282
move_path_index,
282283
|mpi| { in_out.add(&mpi); });
283284
}
284285
}
285286

286287
impl<'a, 'tcx> BitDenotation for MaybeUninitializedLvals<'a, 'tcx> {
287288
type Idx = MovePathIndex;
288-
type Ctxt = MoveData<'tcx>;
289+
type Ctxt = MoveDataParamEnv<'tcx>;
289290
fn name() -> &'static str { "maybe_uninit" }
290291
fn bits_per_block(&self, ctxt: &Self::Ctxt) -> usize {
291-
ctxt.move_paths.len()
292+
ctxt.move_data.move_paths.len()
292293
}
293294

294295
// sets on_entry bits for Arg lvalues
@@ -338,19 +339,19 @@ impl<'a, 'tcx> BitDenotation for MaybeUninitializedLvals<'a, 'tcx> {
338339
dest_lval: &repr::Lvalue) {
339340
// when a call returns successfully, that means we need to set
340341
// the bits for that dest_lval to 1 (initialized).
341-
let move_path_index = ctxt.rev_lookup.find(dest_lval);
342-
on_all_children_bits(self.tcx, self.mir, ctxt,
342+
let move_path_index = ctxt.move_data.rev_lookup.find(dest_lval);
343+
on_all_children_bits(self.tcx, self.mir, &ctxt.move_data,
343344
move_path_index,
344345
|mpi| { in_out.remove(&mpi); });
345346
}
346347
}
347348

348349
impl<'a, 'tcx> BitDenotation for DefinitelyInitializedLvals<'a, 'tcx> {
349350
type Idx = MovePathIndex;
350-
type Ctxt = MoveData<'tcx>;
351+
type Ctxt = MoveDataParamEnv<'tcx>;
351352
fn name() -> &'static str { "definite_init" }
352353
fn bits_per_block(&self, ctxt: &Self::Ctxt) -> usize {
353-
ctxt.move_paths.len()
354+
ctxt.move_data.move_paths.len()
354355
}
355356

356357
// sets on_entry bits for Arg lvalues
@@ -399,19 +400,19 @@ impl<'a, 'tcx> BitDenotation for DefinitelyInitializedLvals<'a, 'tcx> {
399400
dest_lval: &repr::Lvalue) {
400401
// when a call returns successfully, that means we need to set
401402
// the bits for that dest_lval to 1 (initialized).
402-
let move_path_index = ctxt.rev_lookup.find(dest_lval);
403-
on_all_children_bits(self.tcx, self.mir, ctxt,
403+
let move_path_index = ctxt.move_data.rev_lookup.find(dest_lval);
404+
on_all_children_bits(self.tcx, self.mir, &ctxt.move_data,
404405
move_path_index,
405406
|mpi| { in_out.add(&mpi); });
406407
}
407408
}
408409

409410
impl<'a, 'tcx> BitDenotation for MovingOutStatements<'a, 'tcx> {
410411
type Idx = MoveOutIndex;
411-
type Ctxt = MoveData<'tcx>;
412+
type Ctxt = MoveDataParamEnv<'tcx>;
412413
fn name() -> &'static str { "moving_out" }
413414
fn bits_per_block(&self, ctxt: &Self::Ctxt) -> usize {
414-
ctxt.moves.len()
415+
ctxt.move_data.moves.len()
415416
}
416417

417418
fn start_block_effect(&self,_move_data: &Self::Ctxt, _sets: &mut BlockSets<MoveOutIndex>) {
@@ -423,7 +424,7 @@ impl<'a, 'tcx> BitDenotation for MovingOutStatements<'a, 'tcx> {
423424
sets: &mut BlockSets<MoveOutIndex>,
424425
bb: repr::BasicBlock,
425426
idx: usize) {
426-
let (tcx, mir, move_data) = (self.tcx, self.mir, ctxt);
427+
let (tcx, mir, move_data) = (self.tcx, self.mir, &ctxt.move_data);
427428
let stmt = &mir.basic_block_data(bb).statements[idx];
428429
let loc_map = &move_data.loc_map;
429430
let path_map = &move_data.path_map;
@@ -463,7 +464,7 @@ impl<'a, 'tcx> BitDenotation for MovingOutStatements<'a, 'tcx> {
463464
bb: repr::BasicBlock,
464465
statements_len: usize)
465466
{
466-
let (mir, move_data) = (self.mir, ctxt);
467+
let (mir, move_data) = (self.mir, &ctxt.move_data);
467468
let term = mir.basic_block_data(bb).terminator.as_ref().unwrap();
468469
let loc_map = &move_data.loc_map;
469470
let loc = Location { block: bb, index: statements_len };
@@ -482,7 +483,7 @@ impl<'a, 'tcx> BitDenotation for MovingOutStatements<'a, 'tcx> {
482483
_call_bb: repr::BasicBlock,
483484
_dest_bb: repr::BasicBlock,
484485
dest_lval: &repr::Lvalue) {
485-
let move_data = ctxt;
486+
let move_data = &ctxt.move_data;
486487
let move_path_index = move_data.rev_lookup.find(dest_lval);
487488
let bits_per_block = self.bits_per_block(ctxt);
488489

src/librustc_borrowck/borrowck/mir/dataflow/mod.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ use std::path::PathBuf;
1818
use std::usize;
1919

2020
use super::MirBorrowckCtxtPreDataflow;
21-
use super::gather_moves::{MoveData};
21+
use super::MoveDataParamEnv;
2222

2323
use bitslice::{bitwise, BitwiseOperator};
2424
use indexed_set::{Idx, IdxSet, OwnIdxSet};
@@ -36,7 +36,7 @@ pub trait Dataflow<BD: BitDenotation> {
3636
}
3737

3838
impl<'a, 'tcx: 'a, BD> Dataflow<BD> for MirBorrowckCtxtPreDataflow<'a, 'tcx, BD>
39-
where BD: BitDenotation<Ctxt=MoveData<'tcx>> + DataflowOperator
39+
where BD: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>> + DataflowOperator
4040
{
4141
fn dataflow<P>(&mut self, p: P) where P: Fn(&BD::Ctxt, BD::Idx) -> &Debug {
4242
self.flow_state.build_sets();
@@ -140,7 +140,7 @@ fn dataflow_path(context: &str, prepost: &str, path: &str) -> PathBuf {
140140
}
141141

142142
impl<'a, 'tcx: 'a, BD> MirBorrowckCtxtPreDataflow<'a, 'tcx, BD>
143-
where BD: BitDenotation<Ctxt=MoveData<'tcx>>
143+
where BD: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>>
144144
{
145145
fn pre_dataflow_instrumentation<P>(&self, p: P) -> io::Result<()>
146146
where P: Fn(&BD::Ctxt, BD::Idx) -> &Debug

src/librustc_borrowck/borrowck/mir/dataflow/sanity_check.rs

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,8 @@ use syntax::codemap::Span;
1515
use rustc::ty::{self, TyCtxt};
1616
use rustc::mir::repr::{self, Mir};
1717

18-
use super::super::gather_moves::{MoveData, MovePathIndex};
18+
use super::super::gather_moves::{MovePathIndex};
19+
use super::super::MoveDataParamEnv;
1920
use super::BitDenotation;
2021
use super::DataflowResults;
2122

@@ -41,7 +42,7 @@ pub fn sanity_check_via_rustc_peek<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
4142
_attributes: &[ast::Attribute],
4243
flow_ctxt: &O::Ctxt,
4344
results: &DataflowResults<O>)
44-
where O: BitDenotation<Ctxt=MoveData<'tcx>, Idx=MovePathIndex>
45+
where O: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>, Idx=MovePathIndex>
4546
{
4647
debug!("sanity_check_via_rustc_peek id: {:?}", id);
4748
// FIXME: this is not DRY. Figure out way to abstract this and
@@ -56,11 +57,12 @@ pub fn sanity_check_via_rustc_peek<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
5657

5758
fn each_block<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
5859
mir: &Mir<'tcx>,
59-
move_data: &O::Ctxt,
60+
ctxt: &O::Ctxt,
6061
results: &DataflowResults<O>,
6162
bb: repr::BasicBlock) where
62-
O: BitDenotation<Ctxt=MoveData<'tcx>, Idx=MovePathIndex>
63+
O: BitDenotation<Ctxt=MoveDataParamEnv<'tcx>, Idx=MovePathIndex>
6364
{
65+
let move_data = &ctxt.move_data;
6466
let bb_data = mir.basic_block_data(bb);
6567
let &repr::BasicBlockData { ref statements,
6668
ref terminator,
@@ -127,15 +129,15 @@ fn each_block<'a, 'tcx, O>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
127129
tcx.sess.span_err(span, msg);
128130
}
129131
}
130-
132+
131133
let lhs_mpi = move_data.rev_lookup.find(lvalue);
132134

133135
debug!("rustc_peek: computing effect on lvalue: {:?} ({:?}) in stmt: {:?}",
134136
lvalue, lhs_mpi, stmt);
135137
// reset GEN and KILL sets before emulating their effect.
136138
for e in sets.gen_set.words_mut() { *e = 0; }
137139
for e in sets.kill_set.words_mut() { *e = 0; }
138-
results.0.operator.statement_effect(move_data, &mut sets, bb, j);
140+
results.0.operator.statement_effect(ctxt, &mut sets, bb, j);
139141
sets.on_entry.union(sets.gen_set);
140142
sets.on_entry.subtract(sets.kill_set);
141143
}

src/librustc_borrowck/borrowck/mir/mod.rs

Lines changed: 22 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,11 @@ fn has_rustc_mir_with(attrs: &[ast::Attribute], name: &str) -> Option<P<MetaItem
5050
return None;
5151
}
5252

53+
pub struct MoveDataParamEnv<'tcx> {
54+
move_data: MoveData<'tcx>,
55+
param_env: ty::ParameterEnvironment<'tcx>,
56+
}
57+
5358
pub fn borrowck_mir<'a, 'tcx: 'a>(
5459
bcx: &mut BorrowckCtxt<'a, 'tcx>,
5560
fk: FnKind,
@@ -72,21 +77,23 @@ pub fn borrowck_mir<'a, 'tcx: 'a>(
7277
let tcx = bcx.tcx;
7378

7479
let move_data = MoveData::gather_moves(mir, tcx);
80+
let param_env = ty::ParameterEnvironment::for_item(tcx, id);
81+
let mdpe = MoveDataParamEnv { move_data: move_data, param_env: param_env };
7582
let flow_inits =
76-
do_dataflow(tcx, mir, id, attributes, &move_data, MaybeInitializedLvals::new(tcx, mir));
83+
do_dataflow(tcx, mir, id, attributes, &mdpe, MaybeInitializedLvals::new(tcx, mir));
7784
let flow_uninits =
78-
do_dataflow(tcx, mir, id, attributes, &move_data, MaybeUninitializedLvals::new(tcx, mir));
85+
do_dataflow(tcx, mir, id, attributes, &mdpe, MaybeUninitializedLvals::new(tcx, mir));
7986
let flow_def_inits =
80-
do_dataflow(tcx, mir, id, attributes, &move_data, DefinitelyInitializedLvals::new(tcx, mir));
87+
do_dataflow(tcx, mir, id, attributes, &mdpe, DefinitelyInitializedLvals::new(tcx, mir));
8188

8289
if has_rustc_mir_with(attributes, "rustc_peek_maybe_init").is_some() {
83-
dataflow::sanity_check_via_rustc_peek(bcx.tcx, mir, id, attributes, &move_data, &flow_inits);
90+
dataflow::sanity_check_via_rustc_peek(bcx.tcx, mir, id, attributes, &mdpe, &flow_inits);
8491
}
8592
if has_rustc_mir_with(attributes, "rustc_peek_maybe_uninit").is_some() {
86-
dataflow::sanity_check_via_rustc_peek(bcx.tcx, mir, id, attributes, &move_data, &flow_uninits);
93+
dataflow::sanity_check_via_rustc_peek(bcx.tcx, mir, id, attributes, &mdpe, &flow_uninits);
8794
}
8895
if has_rustc_mir_with(attributes, "rustc_peek_definite_init").is_some() {
89-
dataflow::sanity_check_via_rustc_peek(bcx.tcx, mir, id, attributes, &move_data, &flow_def_inits);
96+
dataflow::sanity_check_via_rustc_peek(bcx.tcx, mir, id, attributes, &mdpe, &flow_def_inits);
9097
}
9198

9299
if has_rustc_mir_with(attributes, "stop_after_dataflow").is_some() {
@@ -97,7 +104,7 @@ pub fn borrowck_mir<'a, 'tcx: 'a>(
97104
bcx: bcx,
98105
mir: mir,
99106
node_id: id,
100-
move_data: move_data,
107+
move_data: mdpe.move_data,
101108
flow_inits: flow_inits,
102109
flow_uninits: flow_uninits,
103110
};
@@ -115,7 +122,7 @@ fn do_dataflow<'a, 'tcx, BD>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
115122
attributes: &[ast::Attribute],
116123
ctxt: &BD::Ctxt,
117124
bd: BD) -> DataflowResults<BD>
118-
where BD: BitDenotation<Idx=MovePathIndex, Ctxt=MoveData<'tcx>> + DataflowOperator
125+
where BD: BitDenotation<Idx=MovePathIndex, Ctxt=MoveDataParamEnv<'tcx>> + DataflowOperator
119126
{
120127
use syntax::attr::AttrMetaMethods;
121128

@@ -145,7 +152,7 @@ fn do_dataflow<'a, 'tcx, BD>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
145152
flow_state: DataflowAnalysis::new(tcx, mir, ctxt, bd),
146153
};
147154

148-
mbcx.dataflow(|move_data, i| &move_data.move_paths[i]);
155+
mbcx.dataflow(|ctxt, i| &ctxt.move_data.move_paths[i]);
149156
mbcx.flow_state.results()
150157
}
151158

@@ -253,10 +260,11 @@ fn on_all_children_bits<'a, 'tcx, F>(
253260
fn drop_flag_effects_for_function_entry<'a, 'tcx, F>(
254261
tcx: TyCtxt<'a, 'tcx, 'tcx>,
255262
mir: &Mir<'tcx>,
256-
move_data: &MoveData<'tcx>,
263+
ctxt: &MoveDataParamEnv<'tcx>,
257264
mut callback: F)
258265
where F: FnMut(MovePathIndex, DropFlagState)
259266
{
267+
let move_data = &ctxt.move_data;
260268
for i in 0..(mir.arg_decls.len() as u32) {
261269
let lvalue = repr::Lvalue::Arg(i);
262270
let move_path_index = move_data.rev_lookup.find(&lvalue);
@@ -269,11 +277,13 @@ fn drop_flag_effects_for_function_entry<'a, 'tcx, F>(
269277
fn drop_flag_effects_for_location<'a, 'tcx, F>(
270278
tcx: TyCtxt<'a, 'tcx, 'tcx>,
271279
mir: &Mir<'tcx>,
272-
move_data: &MoveData<'tcx>,
280+
ctxt: &MoveDataParamEnv<'tcx>,
273281
loc: Location,
274282
mut callback: F)
275283
where F: FnMut(MovePathIndex, DropFlagState)
276284
{
285+
let move_data = &ctxt.move_data;
286+
let param_env = &ctxt.param_env;
277287
debug!("drop_flag_effects_for_location({:?})", loc);
278288

279289
// first, move out of the RHS
@@ -284,8 +294,7 @@ fn drop_flag_effects_for_location<'a, 'tcx, F>(
284294
// don't move out of non-Copy things
285295
if let MovePathContent::Lvalue(ref lvalue) = move_data.move_paths[path].content {
286296
let ty = mir.lvalue_ty(tcx, lvalue).to_ty(tcx);
287-
let empty_param_env = tcx.empty_parameter_environment();
288-
if !ty.moves_by_default(tcx, &empty_param_env, DUMMY_SP) {
297+
if !ty.moves_by_default(tcx, param_env, DUMMY_SP) {
289298
continue;
290299
}
291300
}

0 commit comments

Comments
 (0)