Description
Building on #44870, once we have a vector of values, we will want to know what they are. I think the best idea is to include that information in the MIR dump. The MIR pretty-printing code is found in pretty.rs
.
Currently, this is invoked by the "Dump MIR" code found in dump_mir.rs
. This is part of the MIR pass setup -- basically this visitor gets invoked in between every MIR pass. However, we don't really want to touch this "Dump MIR" code -- this is because it runs in between passes, and the intention with the NLL inference is that the non-lexical lifetime information will be allocated and destroyed by the NLL pass itself, and hence it will be freed by the time this code runs.
Instead, what I think we ought to do is invoke the pretty-printer directly from within the NLL pass itself. This is easy enough, we just have to invoke the dump_mir()
function independently from the pass infrastructure, much like the mir-builder function does. Basically inserting a line like the following right in between line 142 and line 143 in NLL:
mir_util::dump_mir(tcx, None, "nll", &0, source, &mir);
However, this still won't do anything particularly interesting right now, because it doesn't have access to the region values! So I think we should extend dump_mir
to take an extra argument, or perhaps a callback, that lets us add extra information into the dump. Let's suppose we take the callback approach. Then we might do something like:
mir_util::dump_mir(tcx, None, "nll", &0, source, &mir, |out| {
for (index, value) in self.region_values.iter().enumerate() {
write!(out, "Region {:03}: {:?}", index, value)?;
}
Ok(())
});
and we would modify dump_mir()
to say something like:
pub fn dump_mir<'a, 'tcx, F>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
pass_num: Option<(MirSuite, MirPassIndex)>,
pass_name: &str,
disambiguator: &Display,
source: MirSource,
mir: &Mir<'tcx>,
extra_data: F)
where
F: FnMut(&mut Write) -> io::Result<()>
{
...
}
this callback extra_data
would be threaded down to the code that actually does the writing and invoked at the end or something.
One minor annoyance I see is that dump_mir
also iterates over the "promoted" values associated with Mir
. These are basically constant expressions that got extracted. We probably don't want to be dumping those. We could add a flag to disable this loop. But I think better yet would be to remove the loop altogether, and move it to this caller here, since I think that is the only one that actually wants this loop. That is, we would tranformat that code from:
if mir_util::dump_enabled(tcx, pass_name, source) {
mir_util::dump_mir(tcx,
Some((suite, pass_num)),
pass_name,
&Disambiguator { is_after },
source,
mir);
}
to something like:
if mir_util::dump_enabled(tcx, pass_name, source) {
mir_util::dump_mir(tcx,
Some((suite, pass_num)),
pass_name,
&Disambiguator { is_after },
source,
mir);
for (index, promoted_mir) in mir.promoted.iter_enumerated() {
let promoted_source = MirSource::Promoted(source.item_id(), index);
mir_util::dump_mir(tcx,
Some((suite, pass_num)),
pass_name,
&Disambiguator { is_after },
promoted_source,
promoted_mir);
}
}