// large chunks of memory alive and we want to free them as soon as
// possible to keep the peak memory usage low
let (outputs, trans) = {
- let (outputs, expanded_crate, id) = {
- let krate = match phase_1_parse_input(sess, cfg, input) {
- Ok(krate) => krate,
- Err(mut parse_error) => {
- parse_error.emit();
- return Err(1);
- }
- };
+ let krate = match phase_1_parse_input(sess, cfg, input) {
+ Ok(krate) => krate,
+ Err(mut parse_error) => {
+ parse_error.emit();
+ return Err(1);
+ }
+ };
+ let krate = {
let mut compile_state = CompileState::state_after_parse(input,
sess,
outdir,
sess,
compile_state,
Ok(()));
- let krate = compile_state.krate.unwrap();
- let outputs = build_output_filenames(input, outdir, output, &krate.attrs, sess);
- let id = link::find_crate_name(Some(sess), &krate.attrs, input);
- let expanded_crate = phase_2_configure_and_expand(sess,
- &cstore,
- krate,
- &id,
- addl_plugins)?;
+ compile_state.krate.unwrap()
+ };
- (outputs, expanded_crate, id)
+ let outputs = build_output_filenames(input, outdir, output, &krate.attrs, sess);
+ let id = link::find_crate_name(Some(sess), &krate.attrs, input);
+ let ExpansionResult { expanded_crate, defs, analysis, resolutions, mut hir_forest } = {
+ let make_glob_map = control.make_glob_map;
+ phase_2_configure_and_expand(sess, &cstore, krate, &id, addl_plugins, make_glob_map)?
};
controller_entry_point!(after_expand,
&id),
Ok(()));
- let expanded_crate = assign_node_ids(sess, expanded_crate);
-
- // Collect defintions for def ids.
- let mut defs = time(sess.time_passes(),
- "collecting defs",
- || hir_map::collect_definitions(&expanded_crate));
-
- time(sess.time_passes(),
- "external crate/lib resolution",
- || read_local_crates(sess, &cstore, &defs, &expanded_crate, &id, &sess.dep_graph));
-
- time(sess.time_passes(),
- "early lint checks",
- || lint::check_ast_crate(sess, &expanded_crate));
-
- time(sess.time_passes(),
- "AST validation",
- || ast_validation::check_crate(sess, &expanded_crate));
-
- let (analysis, resolutions, mut hir_forest) = {
- lower_and_resolve(sess, &id, &mut defs, &expanded_crate,
- &sess.dep_graph, control.make_glob_map)
- };
-
- // Discard MTWT tables that aren't required past lowering to HIR.
- if !keep_mtwt_tables(sess) {
- syntax::ext::mtwt::clear_tables();
- }
-
let arenas = ty::CtxtArenas::new();
// Construct the HIR map
- let hir_forest = &mut hir_forest;
let hir_map = time(sess.time_passes(),
"indexing hir",
- move || hir_map::map_crate(hir_forest, defs));
+ || hir_map::map_crate(&mut hir_forest, defs));
{
let _ignore = hir_map.dep_graph.in_ignore();
// For continuing compilation after a parsed crate has been
// modified
+pub struct ExpansionResult<'a> {
+ pub expanded_crate: ast::Crate,
+ pub defs: hir_map::Definitions,
+ pub analysis: ty::CrateAnalysis<'a>,
+ pub resolutions: Resolutions,
+ pub hir_forest: hir_map::Forest,
+}
+
/// Run the "early phases" of the compiler: initial `cfg` processing,
/// loading compiler plugins (including those from `addl_plugins`),
/// syntax expansion, secondary `cfg` expansion, synthesis of a test
-/// harness if one is to be provided and injection of a dependency on the
-/// standard library and prelude.
+/// harness if one is to be provided, injection of a dependency on the
+/// standard library and prelude, and name resolution.
///
/// Returns `None` if we're aborting after handling -W help.
-pub fn phase_2_configure_and_expand(sess: &Session,
- cstore: &CStore,
- mut krate: ast::Crate,
- crate_name: &str,
- addl_plugins: Option<Vec<String>>)
- -> Result<ast::Crate, usize> {
+pub fn phase_2_configure_and_expand<'a>(sess: &Session,
+ cstore: &CStore,
+ mut krate: ast::Crate,
+ crate_name: &'a str,
+ addl_plugins: Option<Vec<String>>,
+ make_glob_map: resolve::MakeGlobMap)
+ -> Result<ExpansionResult<'a>, usize> {
let time_passes = sess.time_passes();
// strip before anything else because crate metadata may use #[cfg_attr]
"prelude injection",
|| syntax::std_inject::maybe_inject_prelude(&sess.parse_sess, krate));
- time(time_passes,
- "checking that all macro invocations are gone",
- || syntax::ext::expand::check_for_macros(&sess.parse_sess, &krate));
-
time(time_passes,
"checking for inline asm in case the target doesn't support it",
|| no_asm::check_crate(sess, &krate));
println!("Post-expansion node count: {}", count_nodes(&krate));
}
- Ok(krate)
+ krate = assign_node_ids(sess, krate);
+
+ // Collect defintions for def ids.
+ let mut defs =
+ time(sess.time_passes(), "collecting defs", || hir_map::collect_definitions(&krate));
+
+ time(sess.time_passes(),
+ "external crate/lib resolution",
+ || read_local_crates(sess, &cstore, &defs, &krate, crate_name, &sess.dep_graph));
+
+ time(sess.time_passes(),
+ "early lint checks",
+ || lint::check_ast_crate(sess, &krate));
+
+ time(sess.time_passes(),
+ "AST validation",
+ || ast_validation::check_crate(sess, &krate));
+
+ let (analysis, resolutions, hir_forest) =
+ lower_and_resolve(sess, crate_name, &mut defs, &krate, &sess.dep_graph, make_glob_map);
+
+ // Discard MTWT tables that aren't required past lowering to HIR.
+ if !keep_mtwt_tables(sess) {
+ syntax::ext::mtwt::clear_tables();
+ }
+
+ Ok(ExpansionResult {
+ expanded_crate: krate,
+ defs: defs,
+ analysis: analysis,
+ resolutions: resolutions,
+ hir_forest: hir_forest
+ })
}
pub fn assign_node_ids(sess: &Session, krate: ast::Crate) -> ast::Crate {
use rustc::ty::{self, Ty, TyCtxt, TypeFoldable};
use rustc::infer::{self, InferOk, InferResult, TypeOrigin};
use rustc_metadata::cstore::CStore;
-use rustc_metadata::creader::read_local_crates;
use rustc::hir::map as hir_map;
use rustc::session::{self, config};
use std::rc::Rc;
input: source_string.to_string(),
};
let krate = driver::phase_1_parse_input(&sess, krate_config, &input).unwrap();
- let krate = driver::phase_2_configure_and_expand(&sess, &cstore, krate, "test", None)
- .expect("phase 2 aborted");
-
- let krate = driver::assign_node_ids(&sess, krate);
- let mut defs = hir_map::collect_definitions(&krate);
- read_local_crates(&sess, &cstore, &defs, &krate, "test_crate", &dep_graph);
+ let driver::ExpansionResult { defs, resolutions, mut hir_forest, .. } =
+ driver::phase_2_configure_and_expand(&sess, &cstore, krate, "test", None, MakeGlobMap::No)
+ .expect("phase 2 aborted");
let _ignore = dep_graph.in_ignore();
- let (_, resolutions, mut hir_forest) = {
- driver::lower_and_resolve(&sess, "test-crate", &mut defs, &krate,
- &sess.dep_graph, MakeGlobMap::No)
- };
-
let arenas = ty::CtxtArenas::new();
let ast_map = hir_map::map_crate(&mut hir_forest, defs);
use rustc_trans::back::link;
use rustc_resolve as resolve;
use rustc_metadata::cstore::CStore;
-use rustc_metadata::creader::read_local_crates;
use syntax::{ast, codemap, errors};
use syntax::errors::emitter::ColorConfig;
let krate = panictry!(driver::phase_1_parse_input(&sess, cfg, &input));
- let name = link::find_crate_name(Some(&sess), &krate.attrs,
- &input);
+ let name = link::find_crate_name(Some(&sess), &krate.attrs, &input);
- let krate = driver::phase_2_configure_and_expand(&sess, &cstore, krate, &name, None)
- .expect("phase_2_configure_and_expand aborted in rustdoc!");
-
- let krate = driver::assign_node_ids(&sess, krate);
-
- let mut defs = hir_map::collect_definitions(&krate);
- read_local_crates(&sess, &cstore, &defs, &krate, &name, &dep_graph);
-
- // Lower ast -> hir and resolve.
- let (analysis, resolutions, mut hir_forest) = {
- driver::lower_and_resolve(&sess, &name, &mut defs, &krate,
- &sess.dep_graph, resolve::MakeGlobMap::No)
+ let driver::ExpansionResult { defs, analysis, resolutions, mut hir_forest, .. } = {
+ let make_glob_map = resolve::MakeGlobMap::No;
+ driver::phase_2_configure_and_expand(&sess, &cstore, krate, &name, None, make_glob_map)
+ .expect("phase_2_configure_and_expand aborted in rustdoc!")
};
let arenas = ty::CtxtArenas::new();
use rustc::session::{self, config};
use rustc::session::config::{get_unstable_features_setting, OutputType};
use rustc::session::search_paths::{SearchPaths, PathKind};
-use rustc::hir::lowering::{lower_crate, DummyResolver};
use rustc_back::dynamic_lib::DynamicLibrary;
use rustc_back::tempdir::TempDir;
use rustc_driver::{driver, Compilation};
+use rustc_driver::driver::phase_2_configure_and_expand;
use rustc_metadata::cstore::CStore;
+use rustc_resolve::MakeGlobMap;
use syntax::codemap::CodeMap;
use syntax::errors;
use syntax::errors::emitter::ColorConfig;
let mut cfg = config::build_configuration(&sess);
cfg.extend(config::parse_cfgspecs(cfgs.clone()));
let krate = panictry!(driver::phase_1_parse_input(&sess, cfg, &input));
- let krate = driver::phase_2_configure_and_expand(&sess, &cstore, krate,
- "rustdoc-test", None)
- .expect("phase_2_configure_and_expand aborted in rustdoc!");
- let krate = driver::assign_node_ids(&sess, krate);
- let dep_graph = DepGraph::new(false);
- let defs = hir_map::collect_definitions(&krate);
-
- let mut dummy_resolver = DummyResolver;
- let krate = lower_crate(&sess, &krate, &sess, &mut dummy_resolver);
-
- let opts = scrape_test_config(&krate);
+ let driver::ExpansionResult { defs, mut hir_forest, .. } = {
+ let make_glob_map = MakeGlobMap::No;
+ phase_2_configure_and_expand(&sess, &cstore, krate, "rustdoc-test", None, make_glob_map)
+ .expect("phase_2_configure_and_expand aborted in rustdoc!")
+ };
+ let dep_graph = DepGraph::new(false);
+ let opts = scrape_test_config(hir_forest.krate());
let _ignore = dep_graph.in_ignore();
- let mut forest = hir_map::Forest::new(krate, &dep_graph);
- let map = hir_map::map_crate(&mut forest, defs);
+ let map = hir_map::map_crate(&mut hir_forest, defs);
let ctx = core::DocContext {
map: &map,
use fold;
use fold::*;
use util::move_map::MoveMap;
-use parse;
use parse::token::{fresh_mark, fresh_name, intern, keywords};
use ptr::P;
use util::small_vector::SmallVector;
noop_fold_tts(tts, &mut Marker{mark:m, expn_id: None})
}
-/// Check that there are no macro invocations left in the AST:
-pub fn check_for_macros(sess: &parse::ParseSess, krate: &ast::Crate) {
- visit::walk_crate(&mut MacroExterminator{sess:sess}, krate);
-}
-
-/// A visitor that ensures that no macro invocations remain in an AST.
-struct MacroExterminator<'a>{
- sess: &'a parse::ParseSess
-}
-
-impl<'a, 'v> Visitor<'v> for MacroExterminator<'a> {
- fn visit_mac(&mut self, mac: &ast::Mac) {
- self.sess.span_diagnostic.span_bug(mac.span,
- "macro exterminator: expected AST \
- with no macro invocations");
- }
-}
-
#[cfg(test)]
mod tests {
+++ /dev/null
--include ../tools.mk
-
-all:
- $(RUSTC) -o $(TMPDIR)/input.dd -Z no-analysis --emit dep-info input.rs
- sed -i'.bak' 's/^.*input.dd/input.dd/g' $(TMPDIR)/input.dd
- diff -u $(TMPDIR)/input.dd input.dd
+++ /dev/null
-input.dd: input.rs
-
-input.rs:
+++ /dev/null
-// Copyright 2014 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-// Tests that dep info can be emitted without resolving external crates.
-extern crate not_there;
-
-fn main() {}
let krate = panictry!(driver::phase_1_parse_input(&sess, cfg, &input));
- let krate = driver::phase_2_configure_and_expand(&sess, &cstore, krate, &id, None)
- .expect("phase_2 returned `None`");
-
- let krate = driver::assign_node_ids(&sess, krate);
- let mut defs = ast_map::collect_definitions(&krate);
- read_local_crates(&sess, &cstore, &defs, &krate, &id, &dep_graph);
- let (analysis, resolutions, mut hir_forest) = {
- driver::lower_and_resolve(&sess, &id, &mut defs, &krate,
- &sess.dep_graph, MakeGlobMap::No)
+ let driver::ExpansionResult { defs, analysis, resolutions, mut hir_forest, .. } = {
+ driver::phase_2_configure_and_expand(&sess, &cstore, krate, &id, None, MakeGlobMap::No)
+ .expect("phase_2 returned `None`")
};
let arenas = ty::CtxtArenas::new();