save-analysis-json: thread through -z option
In fact, we make JSOn the default and add an option for save-analysis-csv for the legacy behaviour. We also rename some bits and pieces `dxr` -> `save-analysis`
This commit is contained in:
parent
91b5ed5ce3
commit
5065f0c2a2
5 changed files with 92 additions and 19 deletions
|
|
@ -618,7 +618,9 @@ options! {DebuggingOptions, DebuggingSetter, basic_debugging_options,
|
|||
ls: bool = (false, parse_bool,
|
||||
"list the symbols defined by a library crate"),
|
||||
save_analysis: bool = (false, parse_bool,
|
||||
"write syntax and type analysis information in addition to normal output"),
|
||||
"write syntax and type analysis (in JSON format) information in addition to normal output"),
|
||||
save_analysis_csv: bool = (false, parse_bool,
|
||||
"write syntax and type analysis (in CSV format) information in addition to normal output"),
|
||||
print_move_fragments: bool = (false, parse_bool,
|
||||
"print out move-fragment data for every fn"),
|
||||
flowgraph_print_loans: bool = (false, parse_bool,
|
||||
|
|
|
|||
|
|
@ -141,8 +141,7 @@ pub fn compile_input(sess: &Session,
|
|||
dep_graph));
|
||||
|
||||
// Discard MTWT tables that aren't required past lowering to HIR.
|
||||
if !sess.opts.debugging_opts.keep_mtwt_tables &&
|
||||
!sess.opts.debugging_opts.save_analysis {
|
||||
if !keep_mtwt_tables(sess) {
|
||||
syntax::ext::mtwt::clear_tables();
|
||||
}
|
||||
|
||||
|
|
@ -179,8 +178,7 @@ pub fn compile_input(sess: &Session,
|
|||
"early lint checks",
|
||||
|| lint::check_ast_crate(sess, &expanded_crate));
|
||||
|
||||
let opt_crate = if sess.opts.debugging_opts.keep_ast ||
|
||||
sess.opts.debugging_opts.save_analysis {
|
||||
let opt_crate = if keep_ast(sess) {
|
||||
Some(&expanded_crate)
|
||||
} else {
|
||||
drop(expanded_crate);
|
||||
|
|
@ -249,6 +247,18 @@ pub fn compile_input(sess: &Session,
|
|||
Ok(())
|
||||
}
|
||||
|
||||
fn keep_mtwt_tables(sess: &Session) -> bool {
|
||||
sess.opts.debugging_opts.keep_mtwt_tables ||
|
||||
sess.opts.debugging_opts.save_analysis ||
|
||||
sess.opts.debugging_opts.save_analysis_csv
|
||||
}
|
||||
|
||||
fn keep_ast(sess: &Session) -> bool {
|
||||
sess.opts.debugging_opts.keep_ast ||
|
||||
sess.opts.debugging_opts.save_analysis ||
|
||||
sess.opts.debugging_opts.save_analysis_csv
|
||||
}
|
||||
|
||||
/// The name used for source code that doesn't originate in a file
|
||||
/// (e.g. source from stdin or a string)
|
||||
pub fn anon_src() -> String {
|
||||
|
|
|
|||
|
|
@ -483,7 +483,7 @@ impl<'a> CompilerCalls<'a> for RustcDefaultCalls {
|
|||
control.after_llvm.stop = Compilation::Stop;
|
||||
}
|
||||
|
||||
if sess.opts.debugging_opts.save_analysis {
|
||||
if save_analysis(sess) {
|
||||
control.after_analysis.callback = box |state| {
|
||||
time(state.session.time_passes(), "save analysis", || {
|
||||
save::process_crate(state.tcx.unwrap(),
|
||||
|
|
@ -491,7 +491,8 @@ impl<'a> CompilerCalls<'a> for RustcDefaultCalls {
|
|||
state.krate.unwrap(),
|
||||
state.analysis.unwrap(),
|
||||
state.crate_name.unwrap(),
|
||||
state.out_dir)
|
||||
state.out_dir,
|
||||
save_analysis_format(state.session))
|
||||
});
|
||||
};
|
||||
control.after_analysis.run_callback_on_error = true;
|
||||
|
|
@ -502,6 +503,21 @@ impl<'a> CompilerCalls<'a> for RustcDefaultCalls {
|
|||
}
|
||||
}
|
||||
|
||||
fn save_analysis(sess: &Session) -> bool {
|
||||
sess.opts.debugging_opts.save_analysis ||
|
||||
sess.opts.debugging_opts.save_analysis_csv
|
||||
}
|
||||
|
||||
fn save_analysis_format(sess: &Session) -> save::Format {
|
||||
if sess.opts.debugging_opts.save_analysis {
|
||||
save::Format::Json
|
||||
} else if sess.opts.debugging_opts.save_analysis_csv {
|
||||
save::Format::Csv
|
||||
} else {
|
||||
unreachable!();
|
||||
}
|
||||
}
|
||||
|
||||
impl RustcDefaultCalls {
|
||||
pub fn list_metadata(sess: &Session, matches: &getopts::Matches, input: &Input) -> Compilation {
|
||||
let r = matches.opt_strs("Z");
|
||||
|
|
|
|||
|
|
@ -19,20 +19,39 @@ use syntax::ast::{CrateNum, NodeId};
|
|||
use super::data::{self, SpanData};
|
||||
use super::dump::Dump;
|
||||
|
||||
pub struct JsonDumper<'a, 'b, W: 'b> {
|
||||
pub struct JsonDumper<'a, 'b, W: Write + 'b> {
|
||||
output: &'b mut W,
|
||||
codemap: &'a CodeMap,
|
||||
first: bool,
|
||||
}
|
||||
|
||||
impl<'a, 'b, W: Write> JsonDumper<'a, 'b, W> {
|
||||
pub fn new(writer: &'b mut W, codemap: &'a CodeMap) -> JsonDumper<'a, 'b, W> {
|
||||
JsonDumper { output: writer, codemap:codemap }
|
||||
if let Err(_) = write!(writer, "[") {
|
||||
error!("Error writing output");
|
||||
}
|
||||
JsonDumper { output: writer, codemap:codemap, first: true }
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a, 'b, W: Write> Drop for JsonDumper<'a, 'b, W> {
|
||||
fn drop(&mut self) {
|
||||
if let Err(_) = write!(self.output, "]") {
|
||||
error!("Error writing output");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! impl_fn {
|
||||
($fn_name: ident, $data_type: ident) => {
|
||||
fn $fn_name(&mut self, data: data::$data_type) {
|
||||
if self.first {
|
||||
self.first = false;
|
||||
} else {
|
||||
if let Err(_) = write!(self.output, ",") {
|
||||
error!("Error writing output");
|
||||
}
|
||||
}
|
||||
let data = data.lower(self.codemap);
|
||||
if let Err(_) = write!(self.output, "{}", as_json(&data)) {
|
||||
error!("Error writing output '{}'", as_json(&data));
|
||||
|
|
|
|||
|
|
@ -688,12 +688,28 @@ impl<'v> Visitor<'v> for PathCollector {
|
|||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum Format {
|
||||
Csv,
|
||||
Json,
|
||||
}
|
||||
|
||||
impl Format {
|
||||
fn extension(&self) -> &'static str {
|
||||
match *self {
|
||||
Format::Csv => ".csv",
|
||||
Format::Json => ".json",
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn process_crate<'l, 'tcx>(tcx: &'l TyCtxt<'tcx>,
|
||||
lcx: &'l lowering::LoweringContext<'l>,
|
||||
krate: &ast::Crate,
|
||||
analysis: &'l ty::CrateAnalysis<'l>,
|
||||
cratename: &str,
|
||||
odir: Option<&Path>) {
|
||||
odir: Option<&Path>,
|
||||
format: Format) {
|
||||
let _ignore = tcx.dep_graph.in_ignore();
|
||||
|
||||
assert!(analysis.glob_map.is_some());
|
||||
|
|
@ -701,11 +717,11 @@ pub fn process_crate<'l, 'tcx>(tcx: &'l TyCtxt<'tcx>,
|
|||
info!("Dumping crate {}", cratename);
|
||||
|
||||
// find a path to dump our data to
|
||||
let mut root_path = match env::var_os("DXR_RUST_TEMP_FOLDER") {
|
||||
let mut root_path = match env::var_os("RUST_SAVE_ANALYSIS_FOLDER") {
|
||||
Some(val) => PathBuf::from(val),
|
||||
None => match odir {
|
||||
Some(val) => val.join("dxr"),
|
||||
None => PathBuf::from("dxr-temp"),
|
||||
Some(val) => val.join("save-analysis"),
|
||||
None => PathBuf::from("save-analysis-temp"),
|
||||
},
|
||||
};
|
||||
|
||||
|
|
@ -729,22 +745,32 @@ pub fn process_crate<'l, 'tcx>(tcx: &'l TyCtxt<'tcx>,
|
|||
};
|
||||
out_name.push_str(&cratename);
|
||||
out_name.push_str(&tcx.sess.opts.cg.extra_filename);
|
||||
out_name.push_str(".csv");
|
||||
out_name.push_str(format.extension());
|
||||
root_path.push(&out_name);
|
||||
let mut output_file = File::create(&root_path).unwrap_or_else(|e| {
|
||||
let disp = root_path.display();
|
||||
tcx.sess.fatal(&format!("Could not open {}: {}", disp, e));
|
||||
});
|
||||
root_path.pop();
|
||||
let output = &mut output_file;
|
||||
|
||||
let utils: SpanUtils<'tcx> = SpanUtils::new(&tcx.sess);
|
||||
let save_ctxt = SaveContext::new(tcx, lcx);
|
||||
let mut dumper = CsvDumper::new(&mut output_file, utils);
|
||||
let mut visitor = DumpVisitor::new(tcx, save_ctxt, analysis, &mut dumper);
|
||||
// FIXME: we don't write anything!
|
||||
|
||||
visitor.dump_crate_info(cratename, krate);
|
||||
visit::walk_crate(&mut visitor, krate);
|
||||
macro_rules! dump {
|
||||
($new_dumper: expr) => {{
|
||||
let mut dumper = $new_dumper;
|
||||
let mut visitor = DumpVisitor::new(tcx, save_ctxt, analysis, &mut dumper);
|
||||
|
||||
visitor.dump_crate_info(cratename, krate);
|
||||
visit::walk_crate(&mut visitor, krate);
|
||||
}}
|
||||
}
|
||||
|
||||
match format {
|
||||
Format::Csv => dump!(CsvDumper::new(output, utils)),
|
||||
Format::Json => dump!(JsonDumper::new(output, utils.sess.codemap())),
|
||||
}
|
||||
}
|
||||
|
||||
// Utility functions for the module.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue