diff --git a/src/librustc/dep_graph/dep_node.rs b/src/librustc/dep_graph/dep_node.rs index 427fe51e6ff9c..9df41c981eb7b 100644 --- a/src/librustc/dep_graph/dep_node.rs +++ b/src/librustc/dep_graph/dep_node.rs @@ -583,6 +583,7 @@ define_dep_nodes!( <'tcx> [] CheckImplItemWellFormed(DefId), [] ReachableNonGenerics(CrateNum), [] NativeLibraries(CrateNum), + [] EntryFn(CrateNum), [] PluginRegistrarFn(CrateNum), [] ProcMacroDeclsStatic(CrateNum), [input] CrateDisambiguator(CrateNum), diff --git a/src/librustc/middle/dead.rs b/src/librustc/middle/dead.rs index 0c769c91801b8..abbf0ae210c25 100644 --- a/src/librustc/middle/dead.rs +++ b/src/librustc/middle/dead.rs @@ -409,7 +409,7 @@ fn create_and_seed_worklist<'a, 'tcx>( } }).chain( // Seed entry point - tcx.sess.entry_fn.borrow().map(|(id, _, _)| id) + tcx.entry_fn(LOCAL_CRATE).map(|(def_id, _)| tcx.hir().as_local_node_id(def_id).unwrap()) ).collect::>(); // Seed implemented trait items diff --git a/src/librustc/middle/entry.rs b/src/librustc/middle/entry.rs index 6b593a1a9f9b2..218ca3b7553c0 100644 --- a/src/librustc/middle/entry.rs +++ b/src/librustc/middle/entry.rs @@ -1,5 +1,5 @@ use hir::map as hir_map; -use hir::def_id::{CRATE_DEF_INDEX}; +use hir::def_id::{CrateNum, CRATE_DEF_INDEX, DefId, LOCAL_CRATE}; use session::{config, Session}; use session::config::EntryFnType; use syntax::ast::NodeId; @@ -8,6 +8,8 @@ use syntax::entry::EntryPointType; use syntax_pos::Span; use hir::{Item, ItemKind, ImplItem, TraitItem}; use hir::itemlikevisit::ItemLikeVisitor; +use ty::TyCtxt; +use ty::query::Providers; struct EntryContext<'a, 'tcx: 'a> { session: &'a Session, @@ -45,36 +47,34 @@ impl<'a, 'tcx> ItemLikeVisitor<'tcx> for EntryContext<'a, 'tcx> { } } -pub fn find_entry_point(session: &Session, - hir_map: &hir_map::Map<'_>, - crate_name: &str) { - let any_exe = session.crate_types.borrow().iter().any(|ty| { +fn entry_fn(tcx: TyCtxt<'_, '_, '_>, cnum: CrateNum) -> Option<(DefId, EntryFnType)> { + assert_eq!(cnum, LOCAL_CRATE); + + let any_exe = tcx.sess.crate_types.borrow().iter().any(|ty| { *ty == config::CrateType::Executable }); if !any_exe { // No need to find a main function - session.entry_fn.set(None); - return + return None; } // If the user wants no main function at all, then stop here. - if attr::contains_name(&hir_map.krate().attrs, "no_main") { - session.entry_fn.set(None); - return + if attr::contains_name(&tcx.hir().krate().attrs, "no_main") { + return None; } let mut ctxt = EntryContext { - session, - map: hir_map, + session: tcx.sess, + map: tcx.hir(), main_fn: None, attr_main_fn: None, start_fn: None, non_main_fns: Vec::new(), }; - hir_map.krate().visit_all_item_likes(&mut ctxt); + tcx.hir().krate().visit_all_item_likes(&mut ctxt); - configure_main(&mut ctxt, crate_name); + configure_main(tcx, &ctxt) } // Beware, this is duplicated in `libsyntax/entry.rs`, so make sure to keep @@ -135,43 +135,58 @@ fn find_item(item: &Item, ctxt: &mut EntryContext<'_, '_>, at_root: bool) { .span_label(item.span, "multiple `start` functions") .emit(); } - }, - EntryPointType::None => () + } + EntryPointType::None => (), } } -fn configure_main(this: &mut EntryContext<'_, '_>, crate_name: &str) { - if let Some((node_id, span)) = this.start_fn { - this.session.entry_fn.set(Some((node_id, span, EntryFnType::Start))); - } else if let Some((node_id, span)) = this.attr_main_fn { - this.session.entry_fn.set(Some((node_id, span, EntryFnType::Main))); - } else if let Some((node_id, span)) = this.main_fn { - this.session.entry_fn.set(Some((node_id, span, EntryFnType::Main))); +fn configure_main( + tcx: TyCtxt<'_, '_, '_>, + visitor: &EntryContext<'_, '_>, +) -> Option<(DefId, EntryFnType)> { + if let Some((node_id, _)) = visitor.start_fn { + Some((tcx.hir().local_def_id(node_id), EntryFnType::Start)) + } else if let Some((node_id, _)) = visitor.attr_main_fn { + Some((tcx.hir().local_def_id(node_id), EntryFnType::Main)) + } else if let Some((node_id, _)) = visitor.main_fn { + Some((tcx.hir().local_def_id(node_id), EntryFnType::Main)) } else { // No main function - this.session.entry_fn.set(None); - let mut err = struct_err!(this.session, E0601, - "`main` function not found in crate `{}`", crate_name); - if !this.non_main_fns.is_empty() { + let mut err = struct_err!(tcx.sess, E0601, + "`main` function not found in crate `{}`", tcx.crate_name(LOCAL_CRATE)); + if !visitor.non_main_fns.is_empty() { // There were some functions named 'main' though. Try to give the user a hint. err.note("the main function must be defined at the crate level \ but you have one or more functions named 'main' that are not \ defined at the crate level. Either move the definition or \ attach the `#[main]` attribute to override this behavior."); - for &(_, span) in &this.non_main_fns { + for &(_, span) in &visitor.non_main_fns { err.span_note(span, "here is a function named 'main'"); } err.emit(); - this.session.abort_if_errors(); + tcx.sess.abort_if_errors(); } else { - if let Some(ref filename) = this.session.local_crate_source_file { + if let Some(ref filename) = tcx.sess.local_crate_source_file { err.note(&format!("consider adding a `main` function to `{}`", filename.display())); } - if this.session.teach(&err.get_code().unwrap()) { + if tcx.sess.teach(&err.get_code().unwrap()) { err.note("If you don't know the basics of Rust, you can go look to the Rust Book \ to get started: https://doc.rust-lang.org/book/"); } err.emit(); } + + None } } + +pub fn find_entry_point(tcx: TyCtxt<'_, '_, '_>) -> Option<(DefId, EntryFnType)> { + tcx.entry_fn(LOCAL_CRATE) +} + +pub fn provide(providers: &mut Providers<'_>) { + *providers = Providers { + entry_fn, + ..*providers + }; +} diff --git a/src/librustc/session/config.rs b/src/librustc/session/config.rs index 42adc6a87fdba..41e75aa32effc 100644 --- a/src/librustc/session/config.rs +++ b/src/librustc/session/config.rs @@ -649,15 +649,15 @@ impl Options { } } -// The type of entry function, so -// users can have their own entry -// functions -#[derive(Copy, Clone, PartialEq)] +// The type of entry function, so users can have their own entry functions +#[derive(Copy, Clone, PartialEq, Hash, Debug)] pub enum EntryFnType { Main, Start, } +impl_stable_hash_via_hash!(EntryFnType); + #[derive(Copy, PartialEq, PartialOrd, Clone, Ord, Eq, Hash, Debug)] pub enum CrateType { Executable, diff --git a/src/librustc/session/mod.rs b/src/librustc/session/mod.rs index 7363b8b3a78fa..cf00bf330deea 100644 --- a/src/librustc/session/mod.rs +++ b/src/librustc/session/mod.rs @@ -67,8 +67,6 @@ pub struct Session { /// This is `None` if the host and target are the same. pub target_tlib_path: Option, pub parse_sess: ParseSess, - /// For a library crate, this is always none - pub entry_fn: Once>, pub sysroot: PathBuf, /// The name of the root source file of the crate, in the local file system. /// `None` means that there is no source file. @@ -1173,8 +1171,6 @@ pub fn build_session_( host_tlib_path, target_tlib_path, parse_sess: p_s, - // For a library crate, this is always none - entry_fn: Once::new(), sysroot, local_crate_source_file, working_dir, diff --git a/src/librustc/ty/query/config.rs b/src/librustc/ty/query/config.rs index ca5d1f6bd3203..38e90d6d823b2 100644 --- a/src/librustc/ty/query/config.rs +++ b/src/librustc/ty/query/config.rs @@ -629,6 +629,12 @@ impl<'tcx> QueryDescription<'tcx> for queries::foreign_modules<'tcx> { } } +impl<'tcx> QueryDescription<'tcx> for queries::entry_fn<'tcx> { + fn describe(_tcx: TyCtxt<'_, '_, '_>, _: CrateNum) -> Cow<'static, str> { + "looking up the entry function of a crate".into() + } +} + impl<'tcx> QueryDescription<'tcx> for queries::plugin_registrar_fn<'tcx> { fn describe(_tcx: TyCtxt<'_, '_, '_>, _: CrateNum) -> Cow<'static, str> { "looking up the plugin registrar for a crate".into() diff --git a/src/librustc/ty/query/mod.rs b/src/librustc/ty/query/mod.rs index 39d76ceed9507..6bf99a98d4eff 100644 --- a/src/librustc/ty/query/mod.rs +++ b/src/librustc/ty/query/mod.rs @@ -22,7 +22,7 @@ use mir::mono::CodegenUnit; use mir; use mir::interpret::GlobalId; use session::{CompileResult, CrateDisambiguator}; -use session::config::OutputFilenames; +use session::config::{EntryFnType, OutputFilenames}; use traits::{self, Vtable}; use traits::query::{ CanonicalPredicateGoal, CanonicalProjectionGoal, @@ -476,6 +476,9 @@ define_queries! { <'tcx> [] fn foreign_modules: ForeignModules(CrateNum) -> Lrc>, + /// Identifies the entry-point (e.g. the `main` function) for a given + /// crate, returning `None` if there is no entry point (such as for library crates). + [] fn entry_fn: EntryFn(CrateNum) -> Option<(DefId, EntryFnType)>, [] fn plugin_registrar_fn: PluginRegistrarFn(CrateNum) -> Option, [] fn proc_macro_decls_static: ProcMacroDeclsStatic(CrateNum) -> Option, [] fn crate_disambiguator: CrateDisambiguator(CrateNum) -> CrateDisambiguator, diff --git a/src/librustc/ty/query/plumbing.rs b/src/librustc/ty/query/plumbing.rs index 562cd75a75ff4..bb47d9a9db970 100644 --- a/src/librustc/ty/query/plumbing.rs +++ b/src/librustc/ty/query/plumbing.rs @@ -1362,6 +1362,7 @@ pub fn force_from_dep_node<'a, 'gcx, 'lcx>(tcx: TyCtxt<'a, 'gcx, 'lcx>, DepKind::CheckImplItemWellFormed => { force!(check_impl_item_well_formed, def_id!()); } DepKind::ReachableNonGenerics => { force!(reachable_non_generics, krate!()); } DepKind::NativeLibraries => { force!(native_libraries, krate!()); } + DepKind::EntryFn => { force!(entry_fn, krate!()); } DepKind::PluginRegistrarFn => { force!(plugin_registrar_fn, krate!()); } DepKind::ProcMacroDeclsStatic => { force!(proc_macro_decls_static, krate!()); } DepKind::CrateDisambiguator => { force!(crate_disambiguator, krate!()); } diff --git a/src/librustc_codegen_llvm/debuginfo/mod.rs b/src/librustc_codegen_llvm/debuginfo/mod.rs index 2eab626ae8e6e..b504aa515fd44 100644 --- a/src/librustc_codegen_llvm/debuginfo/mod.rs +++ b/src/librustc_codegen_llvm/debuginfo/mod.rs @@ -14,7 +14,7 @@ use llvm; use llvm::debuginfo::{DIFile, DIType, DIScope, DIBuilder, DISubprogram, DIArray, DIFlags, DILexicalBlock}; use rustc::hir::CodegenFnAttrFlags; -use rustc::hir::def_id::{DefId, CrateNum}; +use rustc::hir::def_id::{DefId, CrateNum, LOCAL_CRATE}; use rustc::ty::subst::{Substs, UnpackedKind}; use abi::Abi; @@ -290,9 +290,8 @@ impl DebugInfoMethods<'tcx> for CodegenCx<'ll, 'tcx> { let mut flags = DIFlags::FlagPrototyped; - let local_id = self.tcx().hir().as_local_node_id(def_id); - if let Some((id, _, _)) = *self.sess().entry_fn.borrow() { - if local_id == Some(id) { + if let Some((id, _)) = self.tcx.entry_fn(LOCAL_CRATE) { + if id == def_id { flags |= DIFlags::FlagMainSubprogram; } } diff --git a/src/librustc_codegen_ssa/back/symbol_export.rs b/src/librustc_codegen_ssa/back/symbol_export.rs index bf69089a254a4..c372892c521be 100644 --- a/src/librustc_codegen_ssa/back/symbol_export.rs +++ b/src/librustc_codegen_ssa/back/symbol_export.rs @@ -194,7 +194,7 @@ fn exported_symbols_provider_local<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }) .collect(); - if tcx.sess.entry_fn.borrow().is_some() { + if tcx.entry_fn(LOCAL_CRATE).is_some() { let exported_symbol = ExportedSymbol::NoDefId(SymbolName::new("main")); symbols.push((exported_symbol, SymbolExportLevel::C)); diff --git a/src/librustc_codegen_ssa/base.rs b/src/librustc_codegen_ssa/base.rs index b88ec075653ba..38caacba4d069 100644 --- a/src/librustc_codegen_ssa/base.rs +++ b/src/librustc_codegen_ssa/base.rs @@ -441,10 +441,8 @@ pub fn codegen_instance<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>( pub fn maybe_create_entry_wrapper<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>( cx: &'a Bx::CodegenCx ) { - let (main_def_id, span) = match *cx.sess().entry_fn.borrow() { - Some((id, span, _)) => { - (cx.tcx().hir().local_def_id(id), span) - } + let (main_def_id, span) = match cx.tcx().entry_fn(LOCAL_CRATE) { + Some((def_id, _)) => { (def_id, cx.tcx().def_span(def_id)) }, None => return, }; @@ -458,7 +456,7 @@ pub fn maybe_create_entry_wrapper<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>( let main_llfn = cx.get_fn(instance); - let et = cx.sess().entry_fn.get().map(|e| e.2); + let et = cx.tcx().entry_fn(LOCAL_CRATE).map(|e| e.1); match et { Some(EntryFnType::Main) => create_entry_fn::(cx, span, main_llfn, main_def_id, true), Some(EntryFnType::Start) => create_entry_fn::(cx, span, main_llfn, main_def_id, false), diff --git a/src/librustc_codegen_utils/lib.rs b/src/librustc_codegen_utils/lib.rs index b59bca0ae0edb..5f61852178d0f 100644 --- a/src/librustc_codegen_utils/lib.rs +++ b/src/librustc_codegen_utils/lib.rs @@ -31,6 +31,7 @@ extern crate syntax_pos; #[macro_use] extern crate rustc_data_structures; use rustc::ty::TyCtxt; +use rustc::hir::def_id::LOCAL_CRATE; pub mod link; pub mod codegen_backend; @@ -42,11 +43,9 @@ pub mod symbol_names_test; /// that actually test that compilation succeeds without /// reporting an error. pub fn check_for_rustc_errors_attr(tcx: TyCtxt) { - if let Some((id, span, _)) = *tcx.sess.entry_fn.borrow() { - let main_def_id = tcx.hir().local_def_id(id); - - if tcx.has_attr(main_def_id, "rustc_error") { - tcx.sess.span_fatal(span, "compilation successful"); + if let Some((def_id, _)) = tcx.entry_fn(LOCAL_CRATE) { + if tcx.has_attr(def_id, "rustc_error") { + tcx.sess.span_fatal(tcx.def_span(def_id), "compilation successful"); } } } diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index 3b7de37ae4b3f..4244110072305 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -1174,6 +1174,7 @@ pub fn default_provide(providers: &mut ty::query::Providers) { rustc_passes::provide(providers); rustc_traits::provide(providers); middle::region::provide(providers); + middle::entry::provide(providers); cstore::provide(providers); lint::provide(providers); } @@ -1210,10 +1211,6 @@ where rustc_incremental::load_query_result_cache(sess) }); - time(sess, "looking for entry point", || { - middle::entry::find_entry_point(sess, &hir_map, name) - }); - let mut local_providers = ty::query::Providers::default(); default_provide(&mut local_providers); codegen_backend.provide(&mut local_providers); @@ -1243,6 +1240,10 @@ where // tcx available. time(sess, "dep graph tcx init", || rustc_incremental::dep_graph_tcx_init(tcx)); + time(sess, "looking for entry point", || { + middle::entry::find_entry_point(tcx) + }); + time(sess, "looking for plugin registrar", || { plugin::build::find_plugin_registrar(tcx) }); diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index a6a8fe5ade56c..eb49547e9bf52 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -177,13 +177,13 @@ use rustc::hir::{self, CodegenFnAttrFlags}; use rustc::hir::itemlikevisit::ItemLikeVisitor; -use rustc::hir::def_id::DefId; +use rustc::hir::def_id::{DefId, LOCAL_CRATE}; use rustc::mir::interpret::{AllocId, ConstValue}; use rustc::middle::lang_items::{ExchangeMallocFnLangItem, StartFnLangItem}; use rustc::ty::subst::Substs; use rustc::ty::{self, TypeFoldable, Ty, TyCtxt, GenericParamDefKind}; use rustc::ty::adjustment::CustomCoerceUnsized; -use rustc::session::config; +use rustc::session::config::EntryFnType; use rustc::mir::{self, Location, Promoted}; use rustc::mir::visit::Visitor as MirVisitor; use rustc::mir::mono::MonoItem; @@ -321,9 +321,7 @@ fn collect_roots<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, let mut roots = Vec::new(); { - let entry_fn = tcx.sess.entry_fn.borrow().map(|(node_id, _, _)| { - tcx.hir().local_def_id(node_id) - }); + let entry_fn = tcx.entry_fn(LOCAL_CRATE); debug!("collect_roots: entry_fn = {:?}", entry_fn); @@ -924,7 +922,7 @@ struct RootCollector<'b, 'a: 'b, 'tcx: 'a + 'b> { tcx: TyCtxt<'a, 'tcx, 'tcx>, mode: MonoItemCollectionMode, output: &'b mut Vec>, - entry_fn: Option, + entry_fn: Option<(DefId, EntryFnType)>, } impl<'b, 'a, 'v> ItemLikeVisitor<'v> for RootCollector<'b, 'a, 'v> { @@ -1023,7 +1021,7 @@ impl<'b, 'a, 'v> RootCollector<'b, 'a, 'v> { true } MonoItemCollectionMode::Lazy => { - self.entry_fn == Some(def_id) || + self.entry_fn.map(|(id, _)| id) == Some(def_id) || self.tcx.is_reachable_non_generic(def_id) || self.tcx.codegen_fn_attrs(def_id).flags.contains( CodegenFnAttrFlags::RUSTC_STD_INTERNAL_SYMBOL) @@ -1048,14 +1046,9 @@ impl<'b, 'a, 'v> RootCollector<'b, 'a, 'v> { /// the return type of `main`. This is not needed when /// the user writes their own `start` manually. fn push_extra_entry_roots(&mut self) { - if self.tcx.sess.entry_fn.get().map(|e| e.2) != Some(config::EntryFnType::Main) { - return - } - - let main_def_id = if let Some(def_id) = self.entry_fn { - def_id - } else { - return + let main_def_id = match self.entry_fn { + Some((def_id, EntryFnType::Main)) => def_id, + _ => return, }; let start_def_id = match self.tcx.lang_items().require(StartFnLangItem) { diff --git a/src/librustc_mir/monomorphize/item.rs b/src/librustc_mir/monomorphize/item.rs index 7014f539d5754..c831cbd98299c 100644 --- a/src/librustc_mir/monomorphize/item.rs +++ b/src/librustc_mir/monomorphize/item.rs @@ -1,6 +1,6 @@ use monomorphize::Instance; use rustc::hir; -use rustc::hir::def_id::DefId; +use rustc::hir::def_id::{DefId, LOCAL_CRATE}; use rustc::session::config::OptLevel; use rustc::ty::{self, Ty, TyCtxt, ClosureSubsts, GeneratorSubsts}; use rustc::ty::subst::Substs; @@ -75,8 +75,7 @@ pub trait MonoItemExt<'a, 'tcx>: fmt::Debug { match *self.as_mono_item() { MonoItem::Fn(ref instance) => { - let entry_def_id = - tcx.sess.entry_fn.borrow().map(|(id, _, _)| tcx.hir().local_def_id(id)); + let entry_def_id = tcx.entry_fn(LOCAL_CRATE).map(|(id, _)| id); // If this function isn't inlined or otherwise has explicit // linkage, then we'll be creating a globally shared version. if self.explicit_linkage(tcx).is_some() || diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 1b07385d4d1f4..cb7e83985874c 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -132,7 +132,8 @@ use std::ops::{self, Deref}; use std::slice; use require_c_abi_if_variadic; -use session::{CompileIncomplete, config, Session}; +use session::{CompileIncomplete, Session}; +use session::config::EntryFnType; use TypeAndSubsts; use lint; use util::captures::Captures; @@ -1163,19 +1164,18 @@ fn check_fn<'a, 'gcx, 'tcx>(inherited: &'a Inherited<'a, 'gcx, 'tcx>, // Check that the main return type implements the termination trait. if let Some(term_id) = fcx.tcx.lang_items().termination() { - if let Some((id, _, entry_type)) = *fcx.tcx.sess.entry_fn.borrow() { - if id == fn_id { - if let config::EntryFnType::Main = entry_type { - let substs = fcx.tcx.mk_substs_trait(declared_ret_ty, &[]); - let trait_ref = ty::TraitRef::new(term_id, substs); - let return_ty_span = decl.output.span(); - let cause = traits::ObligationCause::new( - return_ty_span, fn_id, ObligationCauseCode::MainFunctionType); - - inherited.register_predicate( - traits::Obligation::new( - cause, param_env, trait_ref.to_predicate())); - } + if let Some((def_id, EntryFnType::Main)) = fcx.tcx.entry_fn(LOCAL_CRATE) { + let main_id = fcx.tcx.hir().as_local_node_id(def_id).unwrap(); + if main_id == fn_id { + let substs = fcx.tcx.mk_substs_trait(declared_ret_ty, &[]); + let trait_ref = ty::TraitRef::new(term_id, substs); + let return_ty_span = decl.output.span(); + let cause = traits::ObligationCause::new( + return_ty_span, fn_id, ObligationCauseCode::MainFunctionType); + + inherited.register_predicate( + traits::Obligation::new( + cause, param_env, trait_ref.to_predicate())); } } } diff --git a/src/librustc_typeck/lib.rs b/src/librustc_typeck/lib.rs index c55a1258ce955..fb5b28c55da29 100644 --- a/src/librustc_typeck/lib.rs +++ b/src/librustc_typeck/lib.rs @@ -104,23 +104,22 @@ mod namespace; mod outlives; mod variance; -use hir::Node; use rustc_target::spec::abi::Abi; -use rustc::hir; +use rustc::hir::{self, Node}; +use rustc::hir::def_id::{DefId, LOCAL_CRATE}; use rustc::infer::InferOk; use rustc::lint; use rustc::middle; use rustc::session; -use rustc::session::config::nightly_options; +use rustc::session::CompileIncomplete; +use rustc::session::config::{EntryFnType, nightly_options}; use rustc::traits::{ObligationCause, ObligationCauseCode, TraitEngine, TraitEngineExt}; use rustc::ty::subst::Substs; use rustc::ty::{self, Ty, TyCtxt}; use rustc::ty::query::Providers; use rustc::util; use rustc::util::profiling::ProfileCategory; -use session::{CompileIncomplete, config}; use syntax_pos::Span; -use syntax::ast; use util::common::time; use std::iter; @@ -185,10 +184,9 @@ fn require_same_types<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, }) } -fn check_main_fn_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, - main_id: ast::NodeId, - main_span: Span) { - let main_def_id = tcx.hir().local_def_id(main_id); +fn check_main_fn_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, main_def_id: DefId) { + let main_id = tcx.hir().as_local_node_id(main_def_id).unwrap(); + let main_span = tcx.def_span(main_def_id); let main_t = tcx.type_of(main_def_id); match main_t.sty { ty::FnDef(..) => { @@ -251,10 +249,9 @@ fn check_main_fn_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } } -fn check_start_fn_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, - start_id: ast::NodeId, - start_span: Span) { - let start_def_id = tcx.hir().local_def_id(start_id); +fn check_start_fn_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, start_def_id: DefId) { + let start_id = tcx.hir().as_local_node_id(start_def_id).unwrap(); + let start_span = tcx.def_span(start_def_id); let start_t = tcx.type_of(start_def_id); match start_t.sty { ty::FnDef(..) => { @@ -310,11 +307,10 @@ fn check_start_fn_ty<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } fn check_for_entry_fn<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) { - if let Some((id, sp, entry_type)) = *tcx.sess.entry_fn.borrow() { - match entry_type { - config::EntryFnType::Main => check_main_fn_ty(tcx, id, sp), - config::EntryFnType::Start => check_start_fn_ty(tcx, id, sp), - } + match tcx.entry_fn(LOCAL_CRATE) { + Some((def_id, EntryFnType::Main)) => check_main_fn_ty(tcx, def_id), + Some((def_id, EntryFnType::Start)) => check_start_fn_ty(tcx, def_id), + _ => {} } }