From 27adb31fcc2e31ca5528112260a5981fa91d687e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?John=20K=C3=A5re=20Alsaker?= Date: Sun, 1 Apr 2018 08:17:53 +0200 Subject: [PATCH] Combine Session.entry_fn and Session.entry_type and make them thread-safe --- src/librustc/middle/dead.rs | 2 +- src/librustc/middle/entry.rs | 19 +++++++++---------- src/librustc/session/config.rs | 4 +--- src/librustc/session/mod.rs | 6 ++---- src/librustc_mir/monomorphize/collector.rs | 4 ++-- src/librustc_mir/monomorphize/item.rs | 2 +- src/librustc_trans/base.rs | 10 +++++----- src/librustc_trans/debuginfo/mod.rs | 2 +- src/librustc_trans_utils/lib.rs | 2 +- src/librustc_typeck/check/mod.rs | 8 ++++---- src/librustc_typeck/lib.rs | 10 ++++------ 11 files changed, 31 insertions(+), 38 deletions(-) diff --git a/src/librustc/middle/dead.rs b/src/librustc/middle/dead.rs index abd52624c30d..a0cd231bb704 100644 --- a/src/librustc/middle/dead.rs +++ b/src/librustc/middle/dead.rs @@ -408,7 +408,7 @@ fn create_and_seed_worklist<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, } // Seed entry point - if let Some((id, _)) = *tcx.sess.entry_fn.borrow() { + if let Some((id, _, _)) = *tcx.sess.entry_fn.borrow() { worklist.push(id); } diff --git a/src/librustc/middle/entry.rs b/src/librustc/middle/entry.rs index 37d79f408f3f..ebc796466629 100644 --- a/src/librustc/middle/entry.rs +++ b/src/librustc/middle/entry.rs @@ -63,12 +63,13 @@ pub fn find_entry_point(session: &Session, }); if !any_exe { // No need to find a main function + session.entry_fn.set(None); return } // If the user wants no main function at all, then stop here. if attr::contains_name(&hir_map.krate().attrs, "no_main") { - session.entry_type.set(Some(config::EntryNone)); + session.entry_fn.set(None); return } @@ -153,17 +154,15 @@ fn find_item(item: &Item, ctxt: &mut EntryContext, at_root: bool) { } fn configure_main(this: &mut EntryContext, crate_name: &str) { - if this.start_fn.is_some() { - *this.session.entry_fn.borrow_mut() = this.start_fn; - this.session.entry_type.set(Some(config::EntryStart)); - } else if this.attr_main_fn.is_some() { - *this.session.entry_fn.borrow_mut() = this.attr_main_fn; - this.session.entry_type.set(Some(config::EntryMain)); - } else if this.main_fn.is_some() { - *this.session.entry_fn.borrow_mut() = this.main_fn; - this.session.entry_type.set(Some(config::EntryMain)); + if let Some((node_id, span)) = this.start_fn { + this.session.entry_fn.set(Some((node_id, span, config::EntryStart))); + } else if let Some((node_id, span)) = this.attr_main_fn { + this.session.entry_fn.set(Some((node_id, span, config::EntryMain))); + } else if let Some((node_id, span)) = this.main_fn { + this.session.entry_fn.set(Some((node_id, span, config::EntryMain))); } 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() { diff --git a/src/librustc/session/config.rs b/src/librustc/session/config.rs index a07370e1e42a..afe4442799b2 100644 --- a/src/librustc/session/config.rs +++ b/src/librustc/session/config.rs @@ -614,13 +614,11 @@ impl Options { // The type of entry function, so // users can have their own entry -// functions that don't start a -// scheduler +// functions #[derive(Copy, Clone, PartialEq)] pub enum EntryFnType { EntryMain, EntryStart, - EntryNone, } #[derive(Copy, PartialEq, PartialOrd, Clone, Ord, Eq, Hash, Debug)] diff --git a/src/librustc/session/mod.rs b/src/librustc/session/mod.rs index c084c8684817..97b73fac1a42 100644 --- a/src/librustc/session/mod.rs +++ b/src/librustc/session/mod.rs @@ -70,8 +70,7 @@ pub struct Session { pub opts: config::Options, pub parse_sess: ParseSess, /// For a library crate, this is always none - pub entry_fn: RefCell>, - pub entry_type: Cell>, + pub entry_fn: Once>, pub plugin_registrar_fn: Cell>, pub derive_registrar_fn: Cell>, pub default_sysroot: Option, @@ -1094,8 +1093,7 @@ pub fn build_session_( opts: sopts, parse_sess: p_s, // For a library crate, this is always none - entry_fn: RefCell::new(None), - entry_type: Cell::new(None), + entry_fn: Once::new(), plugin_registrar_fn: Cell::new(None), derive_registrar_fn: Cell::new(None), default_sysroot, diff --git a/src/librustc_mir/monomorphize/collector.rs b/src/librustc_mir/monomorphize/collector.rs index 1189da109299..83ef28e4f156 100644 --- a/src/librustc_mir/monomorphize/collector.rs +++ b/src/librustc_mir/monomorphize/collector.rs @@ -325,7 +325,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, _)| { + let entry_fn = tcx.sess.entry_fn.borrow().map(|(node_id, _, _)| { tcx.hir.local_def_id(node_id) }); @@ -1038,7 +1038,7 @@ 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_type.get() != Some(config::EntryMain) { + if self.tcx.sess.entry_fn.get().map(|e| e.2) != Some(config::EntryMain) { return } diff --git a/src/librustc_mir/monomorphize/item.rs b/src/librustc_mir/monomorphize/item.rs index c2f4359c0082..181751f17770 100644 --- a/src/librustc_mir/monomorphize/item.rs +++ b/src/librustc_mir/monomorphize/item.rs @@ -92,7 +92,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)); + tcx.sess.entry_fn.borrow().map(|(id, _, _)| tcx.hir.local_def_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_trans/base.rs b/src/librustc_trans/base.rs index 0329264a3125..dd51ffcf3136 100644 --- a/src/librustc_trans/base.rs +++ b/src/librustc_trans/base.rs @@ -517,7 +517,7 @@ pub fn set_link_section(cx: &CodegenCx, /// users main function. fn maybe_create_entry_wrapper(cx: &CodegenCx) { let (main_def_id, span) = match *cx.sess().entry_fn.borrow() { - Some((id, span)) => { + Some((id, span, _)) => { (cx.tcx.hir.local_def_id(id), span) } None => return, @@ -533,11 +533,11 @@ fn maybe_create_entry_wrapper(cx: &CodegenCx) { let main_llfn = callee::get_fn(cx, instance); - let et = cx.sess().entry_type.get().unwrap(); + let et = cx.sess().entry_fn.get().map(|e| e.2); match et { - config::EntryMain => create_entry_fn(cx, span, main_llfn, main_def_id, true), - config::EntryStart => create_entry_fn(cx, span, main_llfn, main_def_id, false), - config::EntryNone => {} // Do nothing. + Some(config::EntryMain) => create_entry_fn(cx, span, main_llfn, main_def_id, true), + Some(config::EntryStart) => create_entry_fn(cx, span, main_llfn, main_def_id, false), + None => {} // Do nothing. } fn create_entry_fn<'cx>(cx: &'cx CodegenCx, diff --git a/src/librustc_trans/debuginfo/mod.rs b/src/librustc_trans/debuginfo/mod.rs index 7664c88679e0..0ba11a1785ba 100644 --- a/src/librustc_trans/debuginfo/mod.rs +++ b/src/librustc_trans/debuginfo/mod.rs @@ -263,7 +263,7 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CodegenCx<'a, 'tcx>, let local_id = cx.tcx.hir.as_local_node_id(def_id); match *cx.sess().entry_fn.borrow() { - Some((id, _)) => { + Some((id, _, _)) => { if local_id == Some(id) { flags = flags | DIFlags::FlagMainSubprogram; } diff --git a/src/librustc_trans_utils/lib.rs b/src/librustc_trans_utils/lib.rs index cf47d9b62a94..a33978eeb62f 100644 --- a/src/librustc_trans_utils/lib.rs +++ b/src/librustc_trans_utils/lib.rs @@ -52,7 +52,7 @@ 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() { + 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") { diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 1308f9ef2cd0..fc60e984ea14 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -1128,10 +1128,10 @@ 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, _)) = *fcx.tcx.sess.entry_fn.borrow() { + if let Some((id, _, entry_type)) = *fcx.tcx.sess.entry_fn.borrow() { if id == fn_id { - match fcx.sess().entry_type.get() { - Some(config::EntryMain) => { + match entry_type { + config::EntryMain => { let substs = fcx.tcx.mk_substs(iter::once(Kind::from(ret_ty))); let trait_ref = ty::TraitRef::new(term_id, substs); let return_ty_span = decl.output.span(); @@ -1142,7 +1142,7 @@ fn check_fn<'a, 'gcx, 'tcx>(inherited: &'a Inherited<'a, 'gcx, 'tcx>, traits::Obligation::new( cause, param_env, trait_ref.to_predicate())); }, - _ => {}, + config::EntryStart => {}, } } } diff --git a/src/librustc_typeck/lib.rs b/src/librustc_typeck/lib.rs index 6f71db998bd4..7891cc4471ff 100644 --- a/src/librustc_typeck/lib.rs +++ b/src/librustc_typeck/lib.rs @@ -289,12 +289,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)) = *tcx.sess.entry_fn.borrow() { - match tcx.sess.entry_type.get() { - Some(config::EntryMain) => check_main_fn_ty(tcx, id, sp), - Some(config::EntryStart) => check_start_fn_ty(tcx, id, sp), - Some(config::EntryNone) => {} - None => bug!("entry function without a type") + if let Some((id, sp, entry_type)) = *tcx.sess.entry_fn.borrow() { + match entry_type { + config::EntryMain => check_main_fn_ty(tcx, id, sp), + config::EntryStart => check_start_fn_ty(tcx, id, sp), } } }