From b0d303479188a7880f253a28bf9d8ddd981b6ca6 Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 12:21:28 -0500 Subject: [PATCH 1/8] librustc*: Moved RefCell out of the definition of DefMap --- src/librustc/middle/check_static_recursion.rs | 10 ++++---- src/librustc/middle/def.rs | 4 +--- src/librustc/middle/pat_util.rs | 24 ++++++++++--------- src/librustc/middle/resolve_lifetime.rs | 6 +++-- src/librustc/middle/ty.rs | 4 ++-- src/librustc_resolve/lib.rs | 4 ++-- src/librustc_trans/trans/_match.rs | 11 +++++---- 7 files changed, 34 insertions(+), 29 deletions(-) diff --git a/src/librustc/middle/check_static_recursion.rs b/src/librustc/middle/check_static_recursion.rs index b97978fc03fff..199982dd11a9a 100644 --- a/src/librustc/middle/check_static_recursion.rs +++ b/src/librustc/middle/check_static_recursion.rs @@ -19,9 +19,11 @@ use syntax::{ast_util, ast_map}; use syntax::visit::Visitor; use syntax::visit; +use std::cell::RefCell; + struct CheckCrateVisitor<'a, 'ast: 'a> { sess: &'a Session, - def_map: &'a DefMap, + def_map: &'a RefCell, ast_map: &'a ast_map::Map<'ast> } @@ -33,7 +35,7 @@ impl<'v, 'a, 'ast> Visitor<'v> for CheckCrateVisitor<'a, 'ast> { pub fn check_crate<'ast>(sess: &Session, krate: &ast::Crate, - def_map: &DefMap, + def_map: &RefCell, ast_map: &ast_map::Map<'ast>) { let mut visitor = CheckCrateVisitor { sess: sess, @@ -59,7 +61,7 @@ struct CheckItemRecursionVisitor<'a, 'ast: 'a> { root_it: &'a ast::Item, sess: &'a Session, ast_map: &'a ast_map::Map<'ast>, - def_map: &'a DefMap, + def_map: &'a RefCell, idstack: Vec } @@ -67,7 +69,7 @@ struct CheckItemRecursionVisitor<'a, 'ast: 'a> { // FIXME: Should use the dependency graph when it's available (#1356) pub fn check_item_recursion<'a>(sess: &'a Session, ast_map: &'a ast_map::Map, - def_map: &'a DefMap, + def_map: &'a RefCell, it: &'a ast::Item) { let mut visitor = CheckItemRecursionVisitor { diff --git a/src/librustc/middle/def.rs b/src/librustc/middle/def.rs index 6707a4d3fd775..29275c50c407c 100644 --- a/src/librustc/middle/def.rs +++ b/src/librustc/middle/def.rs @@ -17,8 +17,6 @@ use util::nodemap::NodeMap; use syntax::ast; use syntax::ast_util::local_def; -use std::cell::RefCell; - #[derive(Clone, Copy, PartialEq, Eq, RustcEncodable, RustcDecodable, Hash, Debug)] pub enum Def { DefFn(ast::DefId, bool /* is_ctor */), @@ -99,7 +97,7 @@ impl PathResolution { } // Definition mapping -pub type DefMap = RefCell>; +pub type DefMap = NodeMap; // This is the replacement export map. It maps a module to all of the exports // within. pub type ExportMap = NodeMap>; diff --git a/src/librustc/middle/pat_util.rs b/src/librustc/middle/pat_util.rs index 12b56562c84d6..06bf619804c37 100644 --- a/src/librustc/middle/pat_util.rs +++ b/src/librustc/middle/pat_util.rs @@ -16,11 +16,13 @@ use syntax::ast; use syntax::ast_util::walk_pat; use syntax::codemap::{Span, DUMMY_SP}; +use std::cell::RefCell; + pub type PatIdMap = FnvHashMap; // This is used because same-named variables in alternative patterns need to // use the NodeId of their namesake in the first pattern. -pub fn pat_id_map(dm: &DefMap, pat: &ast::Pat) -> PatIdMap { +pub fn pat_id_map(dm: &RefCell, pat: &ast::Pat) -> PatIdMap { let mut map = FnvHashMap(); pat_bindings(dm, pat, |_bm, p_id, _s, path1| { map.insert(path1.node, p_id); @@ -28,7 +30,7 @@ pub fn pat_id_map(dm: &DefMap, pat: &ast::Pat) -> PatIdMap { map } -pub fn pat_is_refutable(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_is_refutable(dm: &RefCell, pat: &ast::Pat) -> bool { match pat.node { ast::PatLit(_) | ast::PatRange(_, _) => true, ast::PatEnum(_, _) | @@ -44,7 +46,7 @@ pub fn pat_is_refutable(dm: &DefMap, pat: &ast::Pat) -> bool { } } -pub fn pat_is_variant_or_struct(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_is_variant_or_struct(dm: &RefCell, pat: &ast::Pat) -> bool { match pat.node { ast::PatEnum(_, _) | ast::PatIdent(_, _, None) | @@ -58,7 +60,7 @@ pub fn pat_is_variant_or_struct(dm: &DefMap, pat: &ast::Pat) -> bool { } } -pub fn pat_is_const(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_is_const(dm: &RefCell, pat: &ast::Pat) -> bool { match pat.node { ast::PatIdent(_, _, None) | ast::PatEnum(..) => { match dm.borrow().get(&pat.id).map(|d| d.full_def()) { @@ -70,7 +72,7 @@ pub fn pat_is_const(dm: &DefMap, pat: &ast::Pat) -> bool { } } -pub fn pat_is_binding(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_is_binding(dm: &RefCell, pat: &ast::Pat) -> bool { match pat.node { ast::PatIdent(..) => { !pat_is_variant_or_struct(dm, pat) && @@ -80,7 +82,7 @@ pub fn pat_is_binding(dm: &DefMap, pat: &ast::Pat) -> bool { } } -pub fn pat_is_binding_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_is_binding_or_wild(dm: &RefCell, pat: &ast::Pat) -> bool { match pat.node { ast::PatIdent(..) => pat_is_binding(dm, pat), ast::PatWild(_) => true, @@ -90,7 +92,7 @@ pub fn pat_is_binding_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool { /// Call `it` on every "binding" in a pattern, e.g., on `a` in /// `match foo() { Some(a) => (), None => () }` -pub fn pat_bindings(dm: &DefMap, pat: &ast::Pat, mut it: I) where +pub fn pat_bindings(dm: &RefCell, pat: &ast::Pat, mut it: I) where I: FnMut(ast::BindingMode, ast::NodeId, Span, &ast::SpannedIdent), { walk_pat(pat, |p| { @@ -106,7 +108,7 @@ pub fn pat_bindings(dm: &DefMap, pat: &ast::Pat, mut it: I) where /// Checks if the pattern contains any patterns that bind something to /// an ident, e.g. `foo`, or `Foo(foo)` or `foo @ Bar(..)`. -pub fn pat_contains_bindings(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_contains_bindings(dm: &RefCell, pat: &ast::Pat) -> bool { let mut contains_bindings = false; walk_pat(pat, |p| { if pat_is_binding(dm, p) { @@ -120,7 +122,7 @@ pub fn pat_contains_bindings(dm: &DefMap, pat: &ast::Pat) -> bool { } /// Checks if the pattern contains any `ref` or `ref mut` bindings. -pub fn pat_contains_ref_binding(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_contains_ref_binding(dm: &RefCell, pat: &ast::Pat) -> bool { let mut result = false; pat_bindings(dm, pat, |mode, _, _, _| { match mode { @@ -133,13 +135,13 @@ pub fn pat_contains_ref_binding(dm: &DefMap, pat: &ast::Pat) -> bool { /// Checks if the patterns for this arm contain any `ref` or `ref mut` /// bindings. -pub fn arm_contains_ref_binding(dm: &DefMap, arm: &ast::Arm) -> bool { +pub fn arm_contains_ref_binding(dm: &RefCell, arm: &ast::Arm) -> bool { arm.pats.iter().any(|pat| pat_contains_ref_binding(dm, pat)) } /// Checks if the pattern contains any patterns that bind something to /// an ident or wildcard, e.g. `foo`, or `Foo(_)`, `foo @ Bar(..)`, -pub fn pat_contains_bindings_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool { +pub fn pat_contains_bindings_or_wild(dm: &RefCell, pat: &ast::Pat) -> bool { let mut contains_bindings = false; walk_pat(pat, |p| { if pat_is_binding_or_wild(dm, p) { diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index a3d71c989bfdf..4d5716c6dbfa5 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -33,6 +33,8 @@ use syntax::visit; use syntax::visit::Visitor; use util::nodemap::NodeMap; +use std::cell::RefCell; + #[derive(Clone, Copy, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, Debug)] pub enum DefRegion { DefStaticRegion, @@ -53,7 +55,7 @@ struct LifetimeContext<'a> { sess: &'a Session, named_region_map: &'a mut NamedRegionMap, scope: Scope<'a>, - def_map: &'a DefMap, + def_map: &'a RefCell, // Deep breath. Our representation for poly trait refs contains a single // binder and thus we only allow a single level of quantification. However, // the syntax of Rust permits quantification in two places, e.g., `T: for <'a> Foo<'a>` @@ -89,7 +91,7 @@ type Scope<'a> = &'a ScopeChain<'a>; static ROOT_SCOPE: ScopeChain<'static> = RootScope; -pub fn krate(sess: &Session, krate: &ast::Crate, def_map: &DefMap) -> NamedRegionMap { +pub fn krate(sess: &Session, krate: &ast::Crate, def_map: &RefCell) -> NamedRegionMap { let mut named_region_map = NodeMap(); visit::walk_crate(&mut LifetimeContext { sess: sess, diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index 1123c9236312a..a8ce3f87f17ef 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -680,7 +680,7 @@ pub struct ctxt<'tcx> { pub types: CommonTypes<'tcx>, pub sess: Session, - pub def_map: DefMap, + pub def_map: RefCell, pub named_region_map: resolve_lifetime::NamedRegionMap, @@ -2589,7 +2589,7 @@ impl<'tcx> CommonTypes<'tcx> { pub fn mk_ctxt<'tcx>(s: Session, arenas: &'tcx CtxtArenas<'tcx>, - def_map: DefMap, + def_map: RefCell, named_region_map: resolve_lifetime::NamedRegionMap, map: ast_map::Map<'tcx>, freevars: RefCell, diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs index 045320e4fa425..197b56f6eda86 100644 --- a/src/librustc_resolve/lib.rs +++ b/src/librustc_resolve/lib.rs @@ -801,7 +801,7 @@ pub struct Resolver<'a, 'tcx:'a> { // The idents for the primitive types. primitive_type_table: PrimitiveTypeTable, - def_map: DefMap, + def_map: RefCell, freevars: RefCell, freevars_seen: RefCell>, export_map: ExportMap, @@ -3519,7 +3519,7 @@ fn module_to_string(module: &Module) -> String { pub struct CrateMap { - pub def_map: DefMap, + pub def_map: RefCell, pub freevars: RefCell, pub export_map: ExportMap, pub trait_map: TraitMap, diff --git a/src/librustc_trans/trans/_match.rs b/src/librustc_trans/trans/_match.rs index ef599a01e7c40..26a5d90ab82d4 100644 --- a/src/librustc_trans/trans/_match.rs +++ b/src/librustc_trans/trans/_match.rs @@ -219,6 +219,7 @@ use util::nodemap::FnvHashMap; use util::ppaux::{Repr, vec_map_to_string}; use std; +use std::cell::RefCell; use std::cmp::Ordering; use std::iter::AdditiveIterator; use std::rc::Rc; @@ -428,7 +429,7 @@ fn expand_nested_bindings<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, } fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>, - dm: &DefMap, + dm: &RefCell, m: &[Match<'a, 'p, 'blk, 'tcx>], col: usize, val: ValueRef, @@ -474,7 +475,7 @@ fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>, } fn enter_default<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, - dm: &DefMap, + dm: &RefCell, m: &[Match<'a, 'p, 'blk, 'tcx>], col: usize, val: ValueRef) @@ -529,7 +530,7 @@ fn enter_default<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, fn enter_opt<'a, 'p, 'blk, 'tcx>( bcx: Block<'blk, 'tcx>, _: ast::NodeId, - dm: &DefMap, + dm: &RefCell, m: &[Match<'a, 'p, 'blk, 'tcx>], opt: &Opt, col: usize, @@ -772,8 +773,8 @@ impl FailureHandler { } } -fn pick_column_to_specialize(def_map: &DefMap, m: &[Match]) -> Option { - fn pat_score(def_map: &DefMap, pat: &ast::Pat) -> usize { +fn pick_column_to_specialize(def_map: &RefCell, m: &[Match]) -> Option { + fn pat_score(def_map: &RefCell, pat: &ast::Pat) -> usize { match pat.node { ast::PatIdent(_, _, Some(ref inner)) => pat_score(def_map, &**inner), _ if pat_is_refutable(def_map, pat) => 1, From 87cb97b237b90227b5c102b80408d697c45d7b7e Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 13:21:00 -0500 Subject: [PATCH 2/8] librustc*: Removed RefCell from pat_util --- src/librustc/middle/cfg/construct.rs | 2 +- src/librustc/middle/check_match.rs | 10 ++++----- src/librustc/middle/dead.rs | 2 +- src/librustc/middle/expr_use_visitor.rs | 6 ++--- src/librustc/middle/liveness.rs | 10 ++++----- src/librustc/middle/pat_util.rs | 30 ++++++++++++------------- src/librustc/middle/ty.rs | 4 ++-- src/librustc_lint/builtin.rs | 2 +- src/librustc_resolve/lib.rs | 2 +- src/librustc_trans/trans/_match.rs | 12 +++++----- src/librustc_trans/trans/debuginfo.rs | 8 +++---- src/librustc_typeck/check/_match.rs | 8 +++---- src/librustc_typeck/check/mod.rs | 8 +++---- src/librustc_typeck/check/regionck.rs | 2 +- src/librustc_typeck/check/writeback.rs | 2 +- 15 files changed, 53 insertions(+), 55 deletions(-) diff --git a/src/librustc/middle/cfg/construct.rs b/src/librustc/middle/cfg/construct.rs index cbc2ef1535ea6..60acf9de2df42 100644 --- a/src/librustc/middle/cfg/construct.rs +++ b/src/librustc/middle/cfg/construct.rs @@ -494,7 +494,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> { let guard_exit = self.expr(&**guard, guard_start); let this_has_bindings = pat_util::pat_contains_bindings_or_wild( - &self.tcx.def_map, &**pat); + &self.tcx.def_map.borrow(), &**pat); // If both this pattern and the previous pattern // were free of bindings, they must consist only diff --git a/src/librustc/middle/check_match.rs b/src/librustc/middle/check_match.rs index 79f4d62b45e75..86ebca2c3f338 100644 --- a/src/librustc/middle/check_match.rs +++ b/src/librustc/middle/check_match.rs @@ -692,7 +692,7 @@ fn is_useful(cx: &MatchCheckCtxt, Some(constructor) => { let matrix = rows.iter().filter_map(|r| { - if pat_is_binding_or_wild(&cx.tcx.def_map, raw_pat(r[0])) { + if pat_is_binding_or_wild(&cx.tcx.def_map.borrow(), raw_pat(r[0])) { Some(r.tail().to_vec()) } else { None @@ -1069,7 +1069,7 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt, let def_map = &tcx.def_map; let mut by_ref_span = None; for pat in pats { - pat_bindings(def_map, &**pat, |bm, _, span, _path| { + pat_bindings(&def_map.borrow(), &**pat, |bm, _, span, _path| { match bm { ast::BindByRef(_) => { by_ref_span = Some(span); @@ -1084,7 +1084,7 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt, // check legality of moving out of the enum // x @ Foo(..) is legal, but x @ Foo(y) isn't. - if sub.map_or(false, |p| pat_contains_bindings(def_map, &*p)) { + if sub.map_or(false, |p| pat_contains_bindings(&def_map.borrow(), &*p)) { span_err!(cx.tcx.sess, p.span, E0007, "cannot bind by-move with sub-bindings"); } else if has_guard { span_err!(cx.tcx.sess, p.span, E0008, "cannot bind by-move into a pattern guard"); @@ -1097,7 +1097,7 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt, for pat in pats { ast_util::walk_pat(&**pat, |p| { - if pat_is_binding(def_map, &*p) { + if pat_is_binding(&def_map.borrow(), &*p) { match p.node { ast::PatIdent(ast::BindByValue(_), _, ref sub) => { let pat_ty = ty::node_id_to_type(tcx, p.id); @@ -1182,7 +1182,7 @@ struct AtBindingPatternVisitor<'a, 'b:'a, 'tcx:'b> { impl<'a, 'b, 'tcx, 'v> Visitor<'v> for AtBindingPatternVisitor<'a, 'b, 'tcx> { fn visit_pat(&mut self, pat: &Pat) { - if !self.bindings_allowed && pat_is_binding(&self.cx.tcx.def_map, pat) { + if !self.bindings_allowed && pat_is_binding(&self.cx.tcx.def_map.borrow(), pat) { span_err!(self.cx.tcx.sess, pat.span, E0303, "pattern bindings are not allowed \ after an `@`"); diff --git a/src/librustc/middle/dead.rs b/src/librustc/middle/dead.rs index 568375597c0de..25d33d4aceddc 100644 --- a/src/librustc/middle/dead.rs +++ b/src/librustc/middle/dead.rs @@ -284,7 +284,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for MarkSymbolVisitor<'a, 'tcx> { ast::PatStruct(_, ref fields, _) => { self.handle_field_pattern_match(pat, fields); } - _ if pat_util::pat_is_const(def_map, pat) => { + _ if pat_util::pat_is_const(&def_map.borrow(), pat) => { // it might be the only use of a const self.lookup_and_handle_definition(&pat.id) } diff --git a/src/librustc/middle/expr_use_visitor.rs b/src/librustc/middle/expr_use_visitor.rs index 2fa9c7c8fbebb..525b807d8073a 100644 --- a/src/librustc/middle/expr_use_visitor.rs +++ b/src/librustc/middle/expr_use_visitor.rs @@ -688,7 +688,7 @@ impl<'d,'t,'tcx,TYPER:mc::Typer<'tcx>> ExprUseVisitor<'d,'t,'tcx,TYPER> { match local.init { None => { let delegate = &mut self.delegate; - pat_util::pat_bindings(&self.typer.tcx().def_map, &*local.pat, + pat_util::pat_bindings(&self.typer.tcx().def_map.borrow(), &*local.pat, |_, id, span, _| { delegate.decl_without_init(id, span); }) @@ -969,7 +969,7 @@ impl<'d,'t,'tcx,TYPER:mc::Typer<'tcx>> ExprUseVisitor<'d,'t,'tcx,TYPER> { return_if_err!(self.mc.cat_pattern(cmt_discr, pat, |_mc, cmt_pat, pat| { let tcx = self.tcx(); let def_map = &self.tcx().def_map; - if pat_util::pat_is_binding(def_map, pat) { + if pat_util::pat_is_binding(&def_map.borrow(), pat) { match pat.node { ast::PatIdent(ast::BindByRef(_), _, _) => mode.lub(BorrowingMatch), @@ -1004,7 +1004,7 @@ impl<'d,'t,'tcx,TYPER:mc::Typer<'tcx>> ExprUseVisitor<'d,'t,'tcx,TYPER> { let def_map = &self.tcx().def_map; let delegate = &mut self.delegate; return_if_err!(mc.cat_pattern(cmt_discr.clone(), pat, |mc, cmt_pat, pat| { - if pat_util::pat_is_binding(def_map, pat) { + if pat_util::pat_is_binding(&def_map.borrow(), pat) { let tcx = typer.tcx(); debug!("binding cmt_pat={} pat={} match_mode={:?}", diff --git a/src/librustc/middle/liveness.rs b/src/librustc/middle/liveness.rs index d7161607b61eb..cb82d226b6aba 100644 --- a/src/librustc/middle/liveness.rs +++ b/src/librustc/middle/liveness.rs @@ -381,7 +381,7 @@ fn visit_fn(ir: &mut IrMaps, debug!("creating fn_maps: {:?}", &fn_maps as *const IrMaps); for arg in &decl.inputs { - pat_util::pat_bindings(&ir.tcx.def_map, + pat_util::pat_bindings(&ir.tcx.def_map.borrow(), &*arg.pat, |_bm, arg_id, _x, path1| { debug!("adding argument {}", arg_id); @@ -416,7 +416,7 @@ fn visit_fn(ir: &mut IrMaps, } fn visit_local(ir: &mut IrMaps, local: &ast::Local) { - pat_util::pat_bindings(&ir.tcx.def_map, &*local.pat, |_, p_id, sp, path1| { + pat_util::pat_bindings(&ir.tcx.def_map.borrow(), &*local.pat, |_, p_id, sp, path1| { debug!("adding local variable {}", p_id); let name = path1.node; ir.add_live_node_for_node(p_id, VarDefNode(sp)); @@ -430,7 +430,7 @@ fn visit_local(ir: &mut IrMaps, local: &ast::Local) { fn visit_arm(ir: &mut IrMaps, arm: &ast::Arm) { for pat in &arm.pats { - pat_util::pat_bindings(&ir.tcx.def_map, &**pat, |bm, p_id, sp, path1| { + pat_util::pat_bindings(&ir.tcx.def_map.borrow(), &**pat, |bm, p_id, sp, path1| { debug!("adding local variable {} from match with bm {:?}", p_id, bm); let name = path1.node; @@ -599,7 +599,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> { fn pat_bindings(&mut self, pat: &ast::Pat, mut f: F) where F: FnMut(&mut Liveness<'a, 'tcx>, LiveNode, Variable, Span, NodeId), { - pat_util::pat_bindings(&self.ir.tcx.def_map, pat, |_bm, p_id, sp, _n| { + pat_util::pat_bindings(&self.ir.tcx.def_map.borrow(), pat, |_bm, p_id, sp, _n| { let ln = self.live_node(p_id, sp); let var = self.variable(p_id, sp); f(self, ln, var, sp, p_id); @@ -1595,7 +1595,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> { fn warn_about_unused_args(&self, decl: &ast::FnDecl, entry_ln: LiveNode) { for arg in &decl.inputs { - pat_util::pat_bindings(&self.ir.tcx.def_map, + pat_util::pat_bindings(&self.ir.tcx.def_map.borrow(), &*arg.pat, |_bm, p_id, sp, path1| { let var = self.variable(p_id, sp); diff --git a/src/librustc/middle/pat_util.rs b/src/librustc/middle/pat_util.rs index 06bf619804c37..1802222edf12e 100644 --- a/src/librustc/middle/pat_util.rs +++ b/src/librustc/middle/pat_util.rs @@ -16,13 +16,11 @@ use syntax::ast; use syntax::ast_util::walk_pat; use syntax::codemap::{Span, DUMMY_SP}; -use std::cell::RefCell; - pub type PatIdMap = FnvHashMap; // This is used because same-named variables in alternative patterns need to // use the NodeId of their namesake in the first pattern. -pub fn pat_id_map(dm: &RefCell, pat: &ast::Pat) -> PatIdMap { +pub fn pat_id_map(dm: &DefMap, pat: &ast::Pat) -> PatIdMap { let mut map = FnvHashMap(); pat_bindings(dm, pat, |_bm, p_id, _s, path1| { map.insert(path1.node, p_id); @@ -30,13 +28,13 @@ pub fn pat_id_map(dm: &RefCell, pat: &ast::Pat) -> PatIdMap { map } -pub fn pat_is_refutable(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_is_refutable(dm: &DefMap, pat: &ast::Pat) -> bool { match pat.node { ast::PatLit(_) | ast::PatRange(_, _) => true, ast::PatEnum(_, _) | ast::PatIdent(_, _, None) | ast::PatStruct(..) => { - match dm.borrow().get(&pat.id).map(|d| d.full_def()) { + match dm.get(&pat.id).map(|d| d.full_def()) { Some(DefVariant(..)) => true, _ => false } @@ -46,12 +44,12 @@ pub fn pat_is_refutable(dm: &RefCell, pat: &ast::Pat) -> bool { } } -pub fn pat_is_variant_or_struct(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_is_variant_or_struct(dm: &DefMap, pat: &ast::Pat) -> bool { match pat.node { ast::PatEnum(_, _) | ast::PatIdent(_, _, None) | ast::PatStruct(..) => { - match dm.borrow().get(&pat.id).map(|d| d.full_def()) { + match dm.get(&pat.id).map(|d| d.full_def()) { Some(DefVariant(..)) | Some(DefStruct(..)) => true, _ => false } @@ -60,10 +58,10 @@ pub fn pat_is_variant_or_struct(dm: &RefCell, pat: &ast::Pat) -> bool { } } -pub fn pat_is_const(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_is_const(dm: &DefMap, pat: &ast::Pat) -> bool { match pat.node { ast::PatIdent(_, _, None) | ast::PatEnum(..) => { - match dm.borrow().get(&pat.id).map(|d| d.full_def()) { + match dm.get(&pat.id).map(|d| d.full_def()) { Some(DefConst(..)) => true, _ => false } @@ -72,7 +70,7 @@ pub fn pat_is_const(dm: &RefCell, pat: &ast::Pat) -> bool { } } -pub fn pat_is_binding(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_is_binding(dm: &DefMap, pat: &ast::Pat) -> bool { match pat.node { ast::PatIdent(..) => { !pat_is_variant_or_struct(dm, pat) && @@ -82,7 +80,7 @@ pub fn pat_is_binding(dm: &RefCell, pat: &ast::Pat) -> bool { } } -pub fn pat_is_binding_or_wild(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_is_binding_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool { match pat.node { ast::PatIdent(..) => pat_is_binding(dm, pat), ast::PatWild(_) => true, @@ -92,7 +90,7 @@ pub fn pat_is_binding_or_wild(dm: &RefCell, pat: &ast::Pat) -> bool { /// Call `it` on every "binding" in a pattern, e.g., on `a` in /// `match foo() { Some(a) => (), None => () }` -pub fn pat_bindings(dm: &RefCell, pat: &ast::Pat, mut it: I) where +pub fn pat_bindings(dm: &DefMap, pat: &ast::Pat, mut it: I) where I: FnMut(ast::BindingMode, ast::NodeId, Span, &ast::SpannedIdent), { walk_pat(pat, |p| { @@ -108,7 +106,7 @@ pub fn pat_bindings(dm: &RefCell, pat: &ast::Pat, mut it: I) where /// Checks if the pattern contains any patterns that bind something to /// an ident, e.g. `foo`, or `Foo(foo)` or `foo @ Bar(..)`. -pub fn pat_contains_bindings(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_contains_bindings(dm: &DefMap, pat: &ast::Pat) -> bool { let mut contains_bindings = false; walk_pat(pat, |p| { if pat_is_binding(dm, p) { @@ -122,7 +120,7 @@ pub fn pat_contains_bindings(dm: &RefCell, pat: &ast::Pat) -> bool { } /// Checks if the pattern contains any `ref` or `ref mut` bindings. -pub fn pat_contains_ref_binding(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_contains_ref_binding(dm: &DefMap, pat: &ast::Pat) -> bool { let mut result = false; pat_bindings(dm, pat, |mode, _, _, _| { match mode { @@ -135,13 +133,13 @@ pub fn pat_contains_ref_binding(dm: &RefCell, pat: &ast::Pat) -> bool { /// Checks if the patterns for this arm contain any `ref` or `ref mut` /// bindings. -pub fn arm_contains_ref_binding(dm: &RefCell, arm: &ast::Arm) -> bool { +pub fn arm_contains_ref_binding(dm: &DefMap, arm: &ast::Arm) -> bool { arm.pats.iter().any(|pat| pat_contains_ref_binding(dm, pat)) } /// Checks if the pattern contains any patterns that bind something to /// an ident or wildcard, e.g. `foo`, or `Foo(_)`, `foo @ Bar(..)`, -pub fn pat_contains_bindings_or_wild(dm: &RefCell, pat: &ast::Pat) -> bool { +pub fn pat_contains_bindings_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool { let mut contains_bindings = false; walk_pat(pat, |p| { if pat_is_binding_or_wild(dm, p) { diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index a8ce3f87f17ef..d5736bd349d01 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -2733,11 +2733,11 @@ impl<'tcx> ctxt<'tcx> { } pub fn pat_contains_ref_binding(&self, pat: &ast::Pat) -> bool { - pat_util::pat_contains_ref_binding(&self.def_map, pat) + pat_util::pat_contains_ref_binding(&self.def_map.borrow(), pat) } pub fn arm_contains_ref_binding(&self, arm: &ast::Arm) -> bool { - pat_util::arm_contains_ref_binding(&self.def_map, arm) + pat_util::arm_contains_ref_binding(&self.def_map.borrow(), arm) } } diff --git a/src/librustc_lint/builtin.rs b/src/librustc_lint/builtin.rs index 3bb737ddc1279..0eb6225c1e940 100644 --- a/src/librustc_lint/builtin.rs +++ b/src/librustc_lint/builtin.rs @@ -1329,7 +1329,7 @@ impl UnusedMut { let mut mutables = FnvHashMap(); for p in pats { - pat_util::pat_bindings(&cx.tcx.def_map, &**p, |mode, id, _, path1| { + pat_util::pat_bindings(&cx.tcx.def_map.borrow(), &**p, |mode, id, _, path1| { let ident = path1.node; if let ast::BindByValue(ast::MutMutable) = mode { if !token::get_ident(ident).starts_with("_") { diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs index 197b56f6eda86..b07aa2f1753f4 100644 --- a/src/librustc_resolve/lib.rs +++ b/src/librustc_resolve/lib.rs @@ -2148,7 +2148,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> { // user and one 'x' came from the macro. fn binding_mode_map(&mut self, pat: &Pat) -> BindingMap { let mut result = HashMap::new(); - pat_bindings(&self.def_map, pat, |binding_mode, _id, sp, path1| { + pat_bindings(&self.def_map.borrow(), pat, |binding_mode, _id, sp, path1| { let name = mtwt::resolve(path1.node); result.insert(name, BindingInfo { span: sp, diff --git a/src/librustc_trans/trans/_match.rs b/src/librustc_trans/trans/_match.rs index 26a5d90ab82d4..572c0ea81d244 100644 --- a/src/librustc_trans/trans/_match.rs +++ b/src/librustc_trans/trans/_match.rs @@ -450,7 +450,7 @@ fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>, let mut bound_ptrs = br.bound_ptrs.clone(); match this.node { ast::PatIdent(_, ref path, None) => { - if pat_is_binding(dm, &*this) { + if pat_is_binding(&dm.borrow(), &*this) { bound_ptrs.push((path.node, val)); } } @@ -489,7 +489,7 @@ fn enter_default<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, // Collect all of the matches that can match against anything. enter_match(bcx, dm, m, col, val, |pats| { - if pat_is_binding_or_wild(dm, &*pats[col]) { + if pat_is_binding_or_wild(&dm.borrow(), &*pats[col]) { let mut r = pats[..col].to_vec(); r.push_all(&pats[col + 1..]); Some(r) @@ -777,7 +777,7 @@ fn pick_column_to_specialize(def_map: &RefCell, m: &[Match]) -> Option, pat: &ast::Pat) -> usize { match pat.node { ast::PatIdent(_, _, Some(ref inner)) => pat_score(def_map, &**inner), - _ if pat_is_refutable(def_map, pat) => 1, + _ if pat_is_refutable(&def_map.borrow(), pat) => 1, _ => 0 } } @@ -1379,7 +1379,7 @@ fn create_bindings_map<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, pat: &ast::Pat, let tcx = bcx.tcx(); let reassigned = is_discr_reassigned(bcx, discr, body); let mut bindings_map = FnvHashMap(); - pat_bindings(&tcx.def_map, &*pat, |bm, p_id, span, path1| { + pat_bindings(&tcx.def_map.borrow(), &*pat, |bm, p_id, span, path1| { let ident = path1.node; let variable_ty = node_id_type(bcx, p_id); let llvariable_ty = type_of::type_of(ccx, variable_ty); @@ -1525,7 +1525,7 @@ pub fn store_local<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, // create dummy memory for the variables if we have no // value to store into them immediately let tcx = bcx.tcx(); - pat_bindings(&tcx.def_map, pat, |_, p_id, _, path1| { + pat_bindings(&tcx.def_map.borrow(), pat, |_, p_id, _, path1| { let scope = cleanup::var_scope(tcx, p_id); bcx = mk_binding_alloca( bcx, p_id, &path1.node, scope, (), @@ -1682,7 +1682,7 @@ fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, let ccx = bcx.ccx(); match pat.node { ast::PatIdent(pat_binding_mode, ref path1, ref inner) => { - if pat_is_binding(&tcx.def_map, &*pat) { + if pat_is_binding(&tcx.def_map.borrow(), &*pat) { // Allocate the stack slot where the value of this // binding will live and place it into the appropriate // map. diff --git a/src/librustc_trans/trans/debuginfo.rs b/src/librustc_trans/trans/debuginfo.rs index 2747288b60755..9ba23016ed163 100644 --- a/src/librustc_trans/trans/debuginfo.rs +++ b/src/librustc_trans/trans/debuginfo.rs @@ -843,7 +843,7 @@ pub fn create_local_var_metadata(bcx: Block, local: &ast::Local) { let def_map = &cx.tcx().def_map; let locals = bcx.fcx.lllocals.borrow(); - pat_util::pat_bindings(def_map, &*local.pat, |_, node_id, span, var_ident| { + pat_util::pat_bindings(&def_map.borrow(), &*local.pat, |_, node_id, span, var_ident| { let datum = match locals.get(&node_id) { Some(datum) => datum, None => { @@ -1021,7 +1021,7 @@ pub fn create_argument_metadata(bcx: Block, arg: &ast::Arg) { .fn_metadata; let locals = bcx.fcx.lllocals.borrow(); - pat_util::pat_bindings(def_map, &*arg.pat, |_, node_id, span, var_ident| { + pat_util::pat_bindings(&def_map.borrow(), &*arg.pat, |_, node_id, span, var_ident| { let datum = match locals.get(&node_id) { Some(v) => v, None => { @@ -3255,7 +3255,7 @@ fn create_scope_map(cx: &CrateContext, // Push argument identifiers onto the stack so arguments integrate nicely // with variable shadowing. for arg in args { - pat_util::pat_bindings(def_map, &*arg.pat, |_, node_id, _, path1| { + pat_util::pat_bindings(&def_map.borrow(), &*arg.pat, |_, node_id, _, path1| { scope_stack.push(ScopeStackEntry { scope_metadata: fn_metadata, ident: Some(path1.node) }); scope_map.insert(node_id, fn_metadata); @@ -3372,7 +3372,7 @@ fn create_scope_map(cx: &CrateContext, // Check if this is a binding. If so we need to put it on the // scope stack and maybe introduce an artificial scope - if pat_util::pat_is_binding(def_map, &*pat) { + if pat_util::pat_is_binding(&def_map.borrow(), &*pat) { let ident = path1.node; diff --git a/src/librustc_typeck/check/_match.rs b/src/librustc_typeck/check/_match.rs index 8f1a67723cb79..655b6d18af35b 100644 --- a/src/librustc_typeck/check/_match.rs +++ b/src/librustc_typeck/check/_match.rs @@ -118,7 +118,7 @@ pub fn check_pat<'a, 'tcx>(pcx: &pat_ctxt<'a, 'tcx>, // subtyping doesn't matter here, as the value is some kind of scalar demand::eqtype(fcx, pat.span, expected, lhs_ty); } - ast::PatEnum(..) | ast::PatIdent(..) if pat_is_const(&tcx.def_map, pat) => { + ast::PatEnum(..) | ast::PatIdent(..) if pat_is_const(&tcx.def_map.borrow(), pat) => { let const_did = tcx.def_map.borrow().get(&pat.id).unwrap().def_id(); let const_scheme = ty::lookup_item_type(tcx, const_did); assert!(const_scheme.generics.is_empty()); @@ -134,7 +134,7 @@ pub fn check_pat<'a, 'tcx>(pcx: &pat_ctxt<'a, 'tcx>, // is good enough. demand::suptype(fcx, pat.span, expected, const_ty); } - ast::PatIdent(bm, ref path, ref sub) if pat_is_binding(&tcx.def_map, pat) => { + ast::PatIdent(bm, ref path, ref sub) if pat_is_binding(&tcx.def_map.borrow(), pat) => { let typ = fcx.local_ty(pat.span, pat.id); match bm { ast::BindByRef(mutbl) => { @@ -336,7 +336,7 @@ pub fn check_dereferencable<'a, 'tcx>(pcx: &pat_ctxt<'a, 'tcx>, inner: &ast::Pat) -> bool { let fcx = pcx.fcx; let tcx = pcx.fcx.ccx.tcx; - if pat_is_binding(&tcx.def_map, inner) { + if pat_is_binding(&tcx.def_map.borrow(), inner) { let expected = fcx.infcx().shallow_resolve(expected); ty::deref(expected, true).map_or(true, |mt| match mt.ty.sty { ty::ty_trait(_) => { @@ -383,7 +383,7 @@ pub fn check_match<'a, 'tcx>(fcx: &FnCtxt<'a, 'tcx>, for arm in arms { let mut pcx = pat_ctxt { fcx: fcx, - map: pat_id_map(&tcx.def_map, &*arm.pats[0]), + map: pat_id_map(&tcx.def_map.borrow(), &*arm.pats[0]), }; for p in &arm.pats { check_pat(&mut pcx, &**p, discrim_ty); diff --git a/src/librustc_typeck/check/mod.rs b/src/librustc_typeck/check/mod.rs index 156fbfede9c98..5dc3200663f97 100644 --- a/src/librustc_typeck/check/mod.rs +++ b/src/librustc_typeck/check/mod.rs @@ -574,7 +574,7 @@ impl<'a, 'tcx> Visitor<'tcx> for GatherLocalsVisitor<'a, 'tcx> { // Add pattern bindings. fn visit_pat(&mut self, p: &'tcx ast::Pat) { if let ast::PatIdent(_, ref path1, _) = p.node { - if pat_util::pat_is_binding(&self.fcx.ccx.tcx.def_map, p) { + if pat_util::pat_is_binding(&self.fcx.ccx.tcx.def_map.borrow(), p) { let var_ty = self.assign(p.span, p.id, None); self.fcx.require_type_is_sized(var_ty, p.span, @@ -679,7 +679,7 @@ fn check_fn<'a, 'tcx>(ccx: &'a CrateCtxt<'a, 'tcx>, for (arg_ty, input) in arg_tys.iter().zip(decl.inputs.iter()) { // Create type variables for each argument. pat_util::pat_bindings( - &tcx.def_map, + &tcx.def_map.borrow(), &*input.pat, |_bm, pat_id, sp, _path| { let var_ty = visit.assign(sp, pat_id, None); @@ -690,7 +690,7 @@ fn check_fn<'a, 'tcx>(ccx: &'a CrateCtxt<'a, 'tcx>, // Check the pattern. let pcx = pat_ctxt { fcx: &fcx, - map: pat_id_map(&tcx.def_map, &*input.pat), + map: pat_id_map(&tcx.def_map.borrow(), &*input.pat), }; _match::check_pat(&pcx, &*input.pat, *arg_ty); } @@ -3989,7 +3989,7 @@ pub fn check_decl_local<'a,'tcx>(fcx: &FnCtxt<'a,'tcx>, local: &'tcx ast::Local) let pcx = pat_ctxt { fcx: fcx, - map: pat_id_map(&tcx.def_map, &*local.pat), + map: pat_id_map(&tcx.def_map.borrow(), &*local.pat), }; _match::check_pat(&pcx, &*local.pat, t); let pat_ty = fcx.node_ty(local.pat.id); diff --git a/src/librustc_typeck/check/regionck.rs b/src/librustc_typeck/check/regionck.rs index 9171367468026..fff2cfdab75ac 100644 --- a/src/librustc_typeck/check/regionck.rs +++ b/src/librustc_typeck/check/regionck.rs @@ -446,7 +446,7 @@ fn visit_local(rcx: &mut Rcx, l: &ast::Local) { fn constrain_bindings_in_pat(pat: &ast::Pat, rcx: &mut Rcx) { let tcx = rcx.fcx.tcx(); debug!("regionck::visit_pat(pat={})", pat.repr(tcx)); - pat_util::pat_bindings(&tcx.def_map, pat, |_, id, span, _| { + pat_util::pat_bindings(&tcx.def_map.borrow(), pat, |_, id, span, _| { // If we have a variable that contains region'd data, that // data will be accessible from anywhere that the variable is // accessed. We must be wary of loops like this: diff --git a/src/librustc_typeck/check/writeback.rs b/src/librustc_typeck/check/writeback.rs index 37f43252483aa..2135e5c53c046 100644 --- a/src/librustc_typeck/check/writeback.rs +++ b/src/librustc_typeck/check/writeback.rs @@ -55,7 +55,7 @@ pub fn resolve_type_vars_in_fn(fcx: &FnCtxt, wbcx.visit_pat(&*arg.pat); // Privacy needs the type for the whole pattern, not just each binding - if !pat_util::pat_is_binding(&fcx.tcx().def_map, &*arg.pat) { + if !pat_util::pat_is_binding(&fcx.tcx().def_map.borrow(), &*arg.pat) { wbcx.visit_node_id(ResolvingPattern(arg.pat.span), arg.pat.id); } From 447e0a29503045d258b0c0b7de745c79350bf8a9 Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 13:26:40 -0500 Subject: [PATCH 3/8] librustc_resolve: Removed the RefCell around the DefMap in Resolver --- src/librustc_resolve/check_unused.rs | 7 +++---- src/librustc_resolve/lib.rs | 14 +++++++------- src/librustc_resolve/resolve_imports.rs | 6 +++--- 3 files changed, 13 insertions(+), 14 deletions(-) diff --git a/src/librustc_resolve/check_unused.rs b/src/librustc_resolve/check_unused.rs index aebbe14407380..070f1d5436090 100644 --- a/src/librustc_resolve/check_unused.rs +++ b/src/librustc_resolve/check_unused.rs @@ -68,8 +68,7 @@ impl<'a, 'b, 'tcx> UnusedImportCheckVisitor<'a, 'b, 'tcx> { "unused import".to_string()); } - let mut def_map = self.def_map.borrow_mut(); - let path_res = if let Some(r) = def_map.get_mut(&id) { + let path_res = if let Some(r) = self.resolver.def_map.get_mut(&id) { r } else { return; @@ -81,12 +80,12 @@ impl<'a, 'b, 'tcx> UnusedImportCheckVisitor<'a, 'b, 'tcx> { } }; - let mut v_used = if self.used_imports.contains(&(id, ValueNS)) { + let mut v_used = if self.resolver.used_imports.contains(&(id, ValueNS)) { Used } else { Unused }; - let t_used = if self.used_imports.contains(&(id, TypeNS)) { + let t_used = if self.resolver.used_imports.contains(&(id, TypeNS)) { Used } else { Unused diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs index b07aa2f1753f4..e7d30a1b5236a 100644 --- a/src/librustc_resolve/lib.rs +++ b/src/librustc_resolve/lib.rs @@ -801,7 +801,7 @@ pub struct Resolver<'a, 'tcx:'a> { // The idents for the primitive types. primitive_type_table: PrimitiveTypeTable, - def_map: RefCell, + def_map: DefMap, freevars: RefCell, freevars_seen: RefCell>, export_map: ExportMap, @@ -869,7 +869,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> { primitive_type_table: PrimitiveTypeTable::new(), - def_map: RefCell::new(NodeMap()), + def_map: NodeMap(), freevars: RefCell::new(NodeMap()), freevars_seen: RefCell::new(NodeMap()), export_map: NodeMap(), @@ -1871,7 +1871,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> { ItemUse(ref view_path) => { // check for imports shadowing primitive types if let ast::ViewPathSimple(ident, _) = view_path.node { - match self.def_map.borrow().get(&item.id).map(|d| d.full_def()) { + match self.def_map.get(&item.id).map(|d| d.full_def()) { Some(DefTy(..)) | Some(DefStruct(..)) | Some(DefTrait(..)) | None => { self.check_if_primitive_type_name(ident.name, item.span); } @@ -2148,7 +2148,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> { // user and one 'x' came from the macro. fn binding_mode_map(&mut self, pat: &Pat) -> BindingMap { let mut result = HashMap::new(); - pat_bindings(&self.def_map.borrow(), pat, |binding_mode, _id, sp, path1| { + pat_bindings(&self.def_map, pat, |binding_mode, _id, sp, path1| { let name = mtwt::resolve(path1.node); result.insert(name, BindingInfo { span: sp, @@ -2991,7 +2991,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> { if allowed == Everything { // Look for a field with the same name in the current self_type. - match self.def_map.borrow().get(&node_id).map(|d| d.full_def()) { + match self.def_map.get(&node_id).map(|d| d.full_def()) { Some(DefTy(did, _)) | Some(DefStruct(did)) | Some(DefVariant(_, did, _)) => match self.structs.get(&did) { @@ -3402,7 +3402,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> { assert!(match resolution.last_private {LastImport{..} => false, _ => true}, "Import should only be used for `use` directives"); - if let Some(prev_res) = self.def_map.borrow_mut().insert(node_id, resolution) { + if let Some(prev_res) = self.def_map.insert(node_id, resolution) { let span = self.ast_map.opt_span(node_id).unwrap_or(codemap::DUMMY_SP); self.session.span_bug(span, &format!("path resolved multiple times \ ({:?} before, {:?} now)", @@ -3557,7 +3557,7 @@ pub fn resolve_crate<'a, 'tcx>(session: &'a Session, check_unused::check_crate(&mut resolver, krate); CrateMap { - def_map: resolver.def_map, + def_map: RefCell::new(resolver.def_map), freevars: resolver.freevars, export_map: resolver.export_map, trait_map: resolver.trait_map, diff --git a/src/librustc_resolve/resolve_imports.rs b/src/librustc_resolve/resolve_imports.rs index f1a8507b17811..d1136376ec1e4 100644 --- a/src/librustc_resolve/resolve_imports.rs +++ b/src/librustc_resolve/resolve_imports.rs @@ -684,14 +684,14 @@ impl<'a, 'b:'a, 'tcx:'b> ImportResolver<'a, 'b, 'tcx> { }; if let Some((def, _)) = value_def_and_priv { - self.resolver.def_map.borrow_mut().insert(directive.id, PathResolution { + self.resolver.def_map.insert(directive.id, PathResolution { base_def: def, last_private: import_lp, depth: 0 }); } if let Some((def, _)) = type_def_and_priv { - self.resolver.def_map.borrow_mut().insert(directive.id, PathResolution { + self.resolver.def_map.insert(directive.id, PathResolution { base_def: def, last_private: import_lp, depth: 0 @@ -815,7 +815,7 @@ impl<'a, 'b:'a, 'tcx:'b> ImportResolver<'a, 'b, 'tcx> { // Record the destination of this import if let Some(did) = target_module.def_id.get() { - self.resolver.def_map.borrow_mut().insert(id, PathResolution { + self.resolver.def_map.insert(id, PathResolution { base_def: DefMod(did), last_private: lp, depth: 0 From 70e77c7046a9207944bc4e0d9ef4c358002b00f6 Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 14:20:03 -0500 Subject: [PATCH 4/8] librustc: Removed the RefCell around DefMap in check_static_recursion --- src/librustc/middle/check_static_recursion.rs | 12 +++++------- src/librustc_driver/driver.rs | 2 +- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/src/librustc/middle/check_static_recursion.rs b/src/librustc/middle/check_static_recursion.rs index 199982dd11a9a..2e29e2c5872b2 100644 --- a/src/librustc/middle/check_static_recursion.rs +++ b/src/librustc/middle/check_static_recursion.rs @@ -19,11 +19,9 @@ use syntax::{ast_util, ast_map}; use syntax::visit::Visitor; use syntax::visit; -use std::cell::RefCell; - struct CheckCrateVisitor<'a, 'ast: 'a> { sess: &'a Session, - def_map: &'a RefCell, + def_map: &'a DefMap, ast_map: &'a ast_map::Map<'ast> } @@ -35,7 +33,7 @@ impl<'v, 'a, 'ast> Visitor<'v> for CheckCrateVisitor<'a, 'ast> { pub fn check_crate<'ast>(sess: &Session, krate: &ast::Crate, - def_map: &RefCell, + def_map: &DefMap, ast_map: &ast_map::Map<'ast>) { let mut visitor = CheckCrateVisitor { sess: sess, @@ -61,7 +59,7 @@ struct CheckItemRecursionVisitor<'a, 'ast: 'a> { root_it: &'a ast::Item, sess: &'a Session, ast_map: &'a ast_map::Map<'ast>, - def_map: &'a RefCell, + def_map: &'a DefMap, idstack: Vec } @@ -69,7 +67,7 @@ struct CheckItemRecursionVisitor<'a, 'ast: 'a> { // FIXME: Should use the dependency graph when it's available (#1356) pub fn check_item_recursion<'a>(sess: &'a Session, ast_map: &'a ast_map::Map, - def_map: &'a RefCell, + def_map: &'a DefMap, it: &'a ast::Item) { let mut visitor = CheckItemRecursionVisitor { @@ -96,7 +94,7 @@ impl<'a, 'ast, 'v> Visitor<'v> for CheckItemRecursionVisitor<'a, 'ast> { fn visit_expr(&mut self, e: &ast::Expr) { match e.node { ast::ExprPath(..) => { - match self.def_map.borrow().get(&e.id).map(|d| d.base_def) { + match self.def_map.get(&e.id).map(|d| d.base_def) { Some(DefStatic(def_id, _)) | Some(DefConst(def_id)) if ast_util::is_local(def_id) => { diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index fe05b489229ad..b64d4d36f2151 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -617,7 +617,7 @@ pub fn phase_3_run_analysis_passes<'tcx>(sess: Session, middle::check_loop::check_crate(&sess, krate)); time(time_passes, "static item recursion checking", (), |_| - middle::check_static_recursion::check_crate(&sess, krate, &def_map, &ast_map)); + middle::check_static_recursion::check_crate(&sess, krate, &def_map.borrow(), &ast_map)); let ty_cx = ty::mk_ctxt(sess, arenas, From fd3a387c74c82b4efd0b530bd76d4c9da0c3cacc Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 14:26:16 -0500 Subject: [PATCH 5/8] librustc: removed the RefCell around DefMap in resolve_lifetime --- src/librustc/middle/resolve_lifetime.rs | 8 +++----- src/librustc_driver/driver.rs | 3 ++- 2 files changed, 5 insertions(+), 6 deletions(-) diff --git a/src/librustc/middle/resolve_lifetime.rs b/src/librustc/middle/resolve_lifetime.rs index 4d5716c6dbfa5..2a070ef4c7777 100644 --- a/src/librustc/middle/resolve_lifetime.rs +++ b/src/librustc/middle/resolve_lifetime.rs @@ -33,8 +33,6 @@ use syntax::visit; use syntax::visit::Visitor; use util::nodemap::NodeMap; -use std::cell::RefCell; - #[derive(Clone, Copy, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, Debug)] pub enum DefRegion { DefStaticRegion, @@ -55,7 +53,7 @@ struct LifetimeContext<'a> { sess: &'a Session, named_region_map: &'a mut NamedRegionMap, scope: Scope<'a>, - def_map: &'a RefCell, + def_map: &'a DefMap, // Deep breath. Our representation for poly trait refs contains a single // binder and thus we only allow a single level of quantification. However, // the syntax of Rust permits quantification in two places, e.g., `T: for <'a> Foo<'a>` @@ -91,7 +89,7 @@ type Scope<'a> = &'a ScopeChain<'a>; static ROOT_SCOPE: ScopeChain<'static> = RootScope; -pub fn krate(sess: &Session, krate: &ast::Crate, def_map: &RefCell) -> NamedRegionMap { +pub fn krate(sess: &Session, krate: &ast::Crate, def_map: &DefMap) -> NamedRegionMap { let mut named_region_map = NodeMap(); visit::walk_crate(&mut LifetimeContext { sess: sess, @@ -174,7 +172,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> { ast::TyPath(None, ref path) => { // if this path references a trait, then this will resolve to // a trait ref, which introduces a binding scope. - match self.def_map.borrow().get(&ty.id).map(|d| (d.base_def, d.depth)) { + match self.def_map.get(&ty.id).map(|d| (d.base_def, d.depth)) { Some((def::DefTrait(..), 0)) => { self.with(LateScope(&Vec::new(), self.scope), |_, this| { this.visit_path(path, ty.id); diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index b64d4d36f2151..d9812eb336a56 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -600,7 +600,8 @@ pub fn phase_3_run_analysis_passes<'tcx>(sess: Session, syntax::ext::mtwt::clear_tables(); let named_region_map = time(time_passes, "lifetime resolution", (), - |_| middle::resolve_lifetime::krate(&sess, krate, &def_map)); + |_| middle::resolve_lifetime::krate(&sess, krate, + &def_map.borrow())); time(time_passes, "looking for entry point", (), |_| middle::entry::find_entry_point(&sess, &ast_map)); From fa26f545c96aa707a7cfaf5b1de0a7a6542001f7 Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 14:36:49 -0500 Subject: [PATCH 6/8] librustc: Make ty::mk_ctxt take an unwrapped DefMap (no RefCell) --- src/librustc/middle/ty.rs | 4 ++-- src/librustc_driver/driver.rs | 2 +- src/librustc_driver/test.rs | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index d5736bd349d01..90430f216e472 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -2589,7 +2589,7 @@ impl<'tcx> CommonTypes<'tcx> { pub fn mk_ctxt<'tcx>(s: Session, arenas: &'tcx CtxtArenas<'tcx>, - def_map: RefCell, + def_map: DefMap, named_region_map: resolve_lifetime::NamedRegionMap, map: ast_map::Map<'tcx>, freevars: RefCell, @@ -2611,7 +2611,7 @@ pub fn mk_ctxt<'tcx>(s: Session, item_variance_map: RefCell::new(DefIdMap()), variance_computed: Cell::new(false), sess: s, - def_map: def_map, + def_map: RefCell::new(def_map), region_maps: region_maps, node_types: RefCell::new(FnvHashMap()), item_substs: RefCell::new(NodeMap()), diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index d9812eb336a56..1702d0a51c989 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -622,7 +622,7 @@ pub fn phase_3_run_analysis_passes<'tcx>(sess: Session, let ty_cx = ty::mk_ctxt(sess, arenas, - def_map, + def_map.into_inner(), named_region_map, ast_map, freevars, diff --git a/src/librustc_driver/test.rs b/src/librustc_driver/test.rs index f9be71561e384..a4d655f806d1c 100644 --- a/src/librustc_driver/test.rs +++ b/src/librustc_driver/test.rs @@ -129,7 +129,7 @@ fn test_env(source_string: &str, let region_map = region::resolve_crate(&sess, krate); let tcx = ty::mk_ctxt(sess, &arenas, - def_map, + def_map.into_inner(), named_region_map, ast_map, freevars, From 0362ba8a1e81aae475351bad5f820c71fed60b69 Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 14:41:47 -0500 Subject: [PATCH 7/8] librustc: Removed the RefCell wrapping DefMap in CrateMap --- src/librustc_driver/driver.rs | 7 +++---- src/librustc_driver/test.rs | 2 +- src/librustc_resolve/lib.rs | 4 ++-- 3 files changed, 6 insertions(+), 7 deletions(-) diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index 1702d0a51c989..fe05b489229ad 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -600,8 +600,7 @@ pub fn phase_3_run_analysis_passes<'tcx>(sess: Session, syntax::ext::mtwt::clear_tables(); let named_region_map = time(time_passes, "lifetime resolution", (), - |_| middle::resolve_lifetime::krate(&sess, krate, - &def_map.borrow())); + |_| middle::resolve_lifetime::krate(&sess, krate, &def_map)); time(time_passes, "looking for entry point", (), |_| middle::entry::find_entry_point(&sess, &ast_map)); @@ -618,11 +617,11 @@ pub fn phase_3_run_analysis_passes<'tcx>(sess: Session, middle::check_loop::check_crate(&sess, krate)); time(time_passes, "static item recursion checking", (), |_| - middle::check_static_recursion::check_crate(&sess, krate, &def_map.borrow(), &ast_map)); + middle::check_static_recursion::check_crate(&sess, krate, &def_map, &ast_map)); let ty_cx = ty::mk_ctxt(sess, arenas, - def_map.into_inner(), + def_map, named_region_map, ast_map, freevars, diff --git a/src/librustc_driver/test.rs b/src/librustc_driver/test.rs index a4d655f806d1c..f9be71561e384 100644 --- a/src/librustc_driver/test.rs +++ b/src/librustc_driver/test.rs @@ -129,7 +129,7 @@ fn test_env(source_string: &str, let region_map = region::resolve_crate(&sess, krate); let tcx = ty::mk_ctxt(sess, &arenas, - def_map.into_inner(), + def_map, named_region_map, ast_map, freevars, diff --git a/src/librustc_resolve/lib.rs b/src/librustc_resolve/lib.rs index e7d30a1b5236a..968996ab2f686 100644 --- a/src/librustc_resolve/lib.rs +++ b/src/librustc_resolve/lib.rs @@ -3519,7 +3519,7 @@ fn module_to_string(module: &Module) -> String { pub struct CrateMap { - pub def_map: RefCell, + pub def_map: DefMap, pub freevars: RefCell, pub export_map: ExportMap, pub trait_map: TraitMap, @@ -3557,7 +3557,7 @@ pub fn resolve_crate<'a, 'tcx>(session: &'a Session, check_unused::check_crate(&mut resolver, krate); CrateMap { - def_map: RefCell::new(resolver.def_map), + def_map: resolver.def_map, freevars: resolver.freevars, export_map: resolver.export_map, trait_map: resolver.trait_map, From 0105960d8379609e1b392f3dbf652f044d78e364 Mon Sep 17 00:00:00 2001 From: Jonathan S Date: Sun, 5 Apr 2015 15:16:41 -0500 Subject: [PATCH 8/8] librustc_trans: Cleaned up some usage of DefMap by removing the wrapping RefCell in _match --- src/librustc_trans/trans/_match.rs | 29 ++++++++++++++--------------- 1 file changed, 14 insertions(+), 15 deletions(-) diff --git a/src/librustc_trans/trans/_match.rs b/src/librustc_trans/trans/_match.rs index 572c0ea81d244..e28c758e63ec1 100644 --- a/src/librustc_trans/trans/_match.rs +++ b/src/librustc_trans/trans/_match.rs @@ -219,7 +219,6 @@ use util::nodemap::FnvHashMap; use util::ppaux::{Repr, vec_map_to_string}; use std; -use std::cell::RefCell; use std::cmp::Ordering; use std::iter::AdditiveIterator; use std::rc::Rc; @@ -429,7 +428,7 @@ fn expand_nested_bindings<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, } fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>, - dm: &RefCell, + dm: &DefMap, m: &[Match<'a, 'p, 'blk, 'tcx>], col: usize, val: ValueRef, @@ -450,7 +449,7 @@ fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>, let mut bound_ptrs = br.bound_ptrs.clone(); match this.node { ast::PatIdent(_, ref path, None) => { - if pat_is_binding(&dm.borrow(), &*this) { + if pat_is_binding(&dm, &*this) { bound_ptrs.push((path.node, val)); } } @@ -475,7 +474,7 @@ fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>, } fn enter_default<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, - dm: &RefCell, + dm: &DefMap, m: &[Match<'a, 'p, 'blk, 'tcx>], col: usize, val: ValueRef) @@ -489,7 +488,7 @@ fn enter_default<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, // Collect all of the matches that can match against anything. enter_match(bcx, dm, m, col, val, |pats| { - if pat_is_binding_or_wild(&dm.borrow(), &*pats[col]) { + if pat_is_binding_or_wild(&dm, &*pats[col]) { let mut r = pats[..col].to_vec(); r.push_all(&pats[col + 1..]); Some(r) @@ -530,7 +529,7 @@ fn enter_default<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, fn enter_opt<'a, 'p, 'blk, 'tcx>( bcx: Block<'blk, 'tcx>, _: ast::NodeId, - dm: &RefCell, + dm: &DefMap, m: &[Match<'a, 'p, 'blk, 'tcx>], opt: &Opt, col: usize, @@ -773,11 +772,11 @@ impl FailureHandler { } } -fn pick_column_to_specialize(def_map: &RefCell, m: &[Match]) -> Option { - fn pat_score(def_map: &RefCell, pat: &ast::Pat) -> usize { +fn pick_column_to_specialize(def_map: &DefMap, m: &[Match]) -> Option { + fn pat_score(def_map: &DefMap, pat: &ast::Pat) -> usize { match pat.node { ast::PatIdent(_, _, Some(ref inner)) => pat_score(def_map, &**inner), - _ if pat_is_refutable(&def_map.borrow(), pat) => 1, + _ if pat_is_refutable(&def_map, pat) => 1, _ => 0 } } @@ -997,9 +996,9 @@ fn compile_submatch<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>, return; } - let tcx = bcx.tcx(); - let def_map = &tcx.def_map; - match pick_column_to_specialize(def_map, m) { + // On a separate line to limit the lifetime of the borrow + let col_opt = pick_column_to_specialize(&bcx.tcx().def_map.borrow(), m); + match col_opt { Some(col) => { let val = vals[col]; if has_nested_bindings(m, col) { @@ -1095,7 +1094,7 @@ fn compile_submatch_continue<'a, 'p, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>, }; match adt_vals { Some(field_vals) => { - let pats = enter_match(bcx, dm, m, col, val, |pats| + let pats = enter_match(bcx, &dm.borrow(), m, col, val, |pats| check_match::specialize(&mcx, pats, &check_match::Single, col, field_vals.len()) @@ -1153,7 +1152,7 @@ fn compile_submatch_continue<'a, 'p, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>, C_int(ccx, 0) // Placeholder for when not using a switch }; - let defaults = enter_default(else_cx, dm, m, col, val); + let defaults = enter_default(else_cx, &dm.borrow(), m, col, val); let exhaustive = chk.is_infallible() && defaults.len() == 0; let len = opts.len(); @@ -1253,7 +1252,7 @@ fn compile_submatch_continue<'a, 'p, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>, } ConstantValue(..) | ConstantRange(..) => () } - let opt_ms = enter_opt(opt_cx, pat_id, dm, m, opt, col, size, val); + let opt_ms = enter_opt(opt_cx, pat_id, &dm.borrow(), m, opt, col, size, val); let mut opt_vals = unpacked; opt_vals.push_all(&vals_left[..]); compile_submatch(opt_cx,