]> git.lizzy.rs Git - rust.git/commitdiff
Refactor away `ParentLink`.
authorJeffrey Seyfried <jeffrey.seyfried@gmail.com>
Sun, 18 Sep 2016 09:45:06 +0000 (09:45 +0000)
committerJeffrey Seyfried <jeffrey.seyfried@gmail.com>
Thu, 22 Sep 2016 07:13:54 +0000 (07:13 +0000)
src/librustc_resolve/build_reduced_graph.rs
src/librustc_resolve/lib.rs
src/librustc_resolve/resolve_imports.rs

index c9591c31831a850fe0ec7b30051ead1eac0ba45e..8c36d712a0dd7cd8e53ce2846e1abecddd5eecbc 100644 (file)
 //! any imports resolved.
 
 use resolve_imports::ImportDirectiveSubclass::{self, GlobImport};
-use Module;
+use {Module, ModuleKind};
 use Namespace::{self, TypeNS, ValueNS};
 use {NameBinding, NameBindingKind, ToNameBinding};
-use ParentLink::{ModuleParentLink, BlockParentLink};
 use Resolver;
 use {resolve_error, resolve_struct_error, ResolutionError};
 
@@ -196,9 +195,8 @@ fn build_reduced_graph_for_item(&mut self, item: &Item) {
                         krate: crate_id,
                         index: CRATE_DEF_INDEX,
                     };
-                    let parent_link = ModuleParentLink(parent, name);
                     let def = Def::Mod(def_id);
-                    let module = self.new_extern_crate_module(parent_link, def, item.id);
+                    let module = self.new_extern_crate_module(parent, name, def, item.id);
                     self.define(parent, name, TypeNS, (module, sp, vis));
 
                     self.populate_module_if_necessary(module);
@@ -206,9 +204,8 @@ fn build_reduced_graph_for_item(&mut self, item: &Item) {
             }
 
             ItemKind::Mod(..) => {
-                let parent_link = ModuleParentLink(parent, name);
                 let def = Def::Mod(self.definitions.local_def_id(item.id));
-                let module = self.new_module(parent_link, Some(def), Some(item.id));
+                let module = self.new_module(parent, ModuleKind::Def(def, name), Some(item.id));
                 module.no_implicit_prelude.set({
                     parent.no_implicit_prelude.get() ||
                         attr::contains_name(&item.attrs, "no_implicit_prelude")
@@ -244,9 +241,8 @@ fn build_reduced_graph_for_item(&mut self, item: &Item) {
             }
 
             ItemKind::Enum(ref enum_definition, _) => {
-                let parent_link = ModuleParentLink(parent, name);
-                let def = Def::Enum(self.definitions.local_def_id(item.id));
-                let module = self.new_module(parent_link, Some(def), parent.normal_ancestor_id);
+                let kind = ModuleKind::Def(Def::Enum(self.definitions.local_def_id(item.id)), name);
+                let module = self.new_module(parent, kind, parent.normal_ancestor_id);
                 self.define(parent, name, TypeNS, (module, sp, vis));
 
                 for variant in &(*enum_definition).variants {
@@ -297,10 +293,8 @@ fn build_reduced_graph_for_item(&mut self, item: &Item) {
                 let def_id = self.definitions.local_def_id(item.id);
 
                 // Add all the items within to a new module.
-                let parent_link = ModuleParentLink(parent, name);
-                let def = Def::Trait(def_id);
-                let module_parent =
-                    self.new_module(parent_link, Some(def), parent.normal_ancestor_id);
+                let kind = ModuleKind::Def(Def::Trait(def_id), name);
+                let module_parent = self.new_module(parent, kind, parent.normal_ancestor_id);
                 self.define(parent, name, TypeNS, (module_parent, sp, vis));
 
                 // Add the names of all the items to the trait info.
@@ -375,8 +369,8 @@ fn build_reduced_graph_for_block(&mut self, block: &Block) {
                     {}",
                    block_id);
 
-            let parent_link = BlockParentLink(parent, block_id);
-            let new_module = self.new_module(parent_link, None, parent.normal_ancestor_id);
+            let new_module =
+                self.new_module(parent, ModuleKind::Block(block_id), parent.normal_ancestor_id);
             self.module_map.insert(block_id, new_module);
             self.current_module = new_module; // Descend into the block.
         }
@@ -407,8 +401,7 @@ fn build_reduced_graph_for_external_crate_def(&mut self, parent: Module<'b>,
             Def::Mod(_) | Def::Enum(..) => {
                 debug!("(building reduced graph for external crate) building module {} {:?}",
                        name, vis);
-                let parent_link = ModuleParentLink(parent, name);
-                let module = self.new_module(parent_link, Some(def), None);
+                let module = self.new_module(parent, ModuleKind::Def(def, name), None);
                 let _ = self.try_define(parent, name, TypeNS, (module, DUMMY_SP, vis));
             }
             Def::Variant(variant_id) => {
@@ -451,8 +444,7 @@ fn build_reduced_graph_for_external_crate_def(&mut self, parent: Module<'b>,
                     self.trait_item_map.insert((trait_item_name, def_id), false);
                 }
 
-                let parent_link = ModuleParentLink(parent, name);
-                let module = self.new_module(parent_link, Some(def), None);
+                let module = self.new_module(parent, ModuleKind::Def(def, name), None);
                 let _ = self.try_define(parent, name, TypeNS, (module, DUMMY_SP, vis));
             }
             Def::TyAlias(..) | Def::AssociatedTy(..) => {
index 016b621eabd4c598c79421e17240667754a4a777..0a8514ffc73fbf202c093ca9c67eb3d86e8027d5 100644 (file)
@@ -41,7 +41,6 @@
 use self::RibKind::*;
 use self::UseLexicalScopeFlag::*;
 use self::ModulePrefixResult::*;
-use self::ParentLink::*;
 
 use rustc::hir::map::Definitions;
 use rustc::hir::{self, PrimTy, TyBool, TyChar, TyFloat, TyInt, TyUint, TyStr};
@@ -753,18 +752,15 @@ fn item(self) -> Option<&'a NameBinding<'a>> {
     }
 }
 
-/// The link from a module up to its nearest parent node.
-#[derive(Clone,Debug)]
-enum ParentLink<'a> {
-    NoParentLink,
-    ModuleParentLink(Module<'a>, Name),
-    BlockParentLink(Module<'a>, NodeId),
+enum ModuleKind {
+    Block(NodeId),
+    Def(Def, Name),
 }
 
 /// One node in the tree of modules.
 pub struct ModuleS<'a> {
-    parent_link: ParentLink<'a>,
-    def: Option<Def>,
+    parent: Option<Module<'a>>,
+    kind: ModuleKind,
 
     // The node id of the closest normal module (`mod`) ancestor (including this module).
     normal_ancestor_id: Option<NodeId>,
@@ -792,11 +788,11 @@ pub struct ModuleS<'a> {
 pub type Module<'a> = &'a ModuleS<'a>;
 
 impl<'a> ModuleS<'a> {
-    fn new(parent_link: ParentLink<'a>, def: Option<Def>, normal_ancestor_id: Option<NodeId>)
+    fn new(parent: Option<Module<'a>>, kind: ModuleKind, normal_ancestor_id: Option<NodeId>)
            -> Self {
         ModuleS {
-            parent_link: parent_link,
-            def: def,
+            parent: parent,
+            kind: kind,
             normal_ancestor_id: normal_ancestor_id,
             extern_crate_id: None,
             resolutions: RefCell::new(FnvHashMap()),
@@ -814,36 +810,36 @@ fn for_each_child<F: FnMut(Name, Namespace, &'a NameBinding<'a>)>(&self, mut f:
         }
     }
 
+    fn def(&self) -> Option<Def> {
+        match self.kind {
+            ModuleKind::Def(def, _) => Some(def),
+            _ => None,
+        }
+    }
+
     fn def_id(&self) -> Option<DefId> {
-        self.def.as_ref().map(Def::def_id)
+        self.def().as_ref().map(Def::def_id)
     }
 
     // `self` resolves to the first module ancestor that `is_normal`.
     fn is_normal(&self) -> bool {
-        match self.def {
-            Some(Def::Mod(_)) => true,
+        match self.kind {
+            ModuleKind::Def(Def::Mod(_), _) => true,
             _ => false,
         }
     }
 
     fn is_trait(&self) -> bool {
-        match self.def {
-            Some(Def::Trait(_)) => true,
+        match self.kind {
+            ModuleKind::Def(Def::Trait(_), _) => true,
             _ => false,
         }
     }
-
-    fn parent(&self) -> Option<&'a Self> {
-        match self.parent_link {
-            ModuleParentLink(parent, _) | BlockParentLink(parent, _) => Some(parent),
-            NoParentLink => None,
-        }
-    }
 }
 
 impl<'a> fmt::Debug for ModuleS<'a> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
-        write!(f, "{:?}", self.def)
+        write!(f, "{:?}", self.def())
     }
 }
 
@@ -903,7 +899,7 @@ fn module(&self) -> Result<Module<'a>, bool /* true if an error has already been
     fn def(&self) -> Def {
         match self.kind {
             NameBindingKind::Def(def) => def,
-            NameBindingKind::Module(module) => module.def.unwrap(),
+            NameBindingKind::Module(module) => module.def().unwrap(),
             NameBindingKind::Import { binding, .. } => binding.def(),
             NameBindingKind::Ambiguity { .. } => Def::Err,
         }
@@ -1111,7 +1107,7 @@ fn alloc_name_resolution(&'a self) -> &'a RefCell<NameResolution<'a>> {
 impl<'a> ty::NodeIdTree for Resolver<'a> {
     fn is_descendant_of(&self, mut node: NodeId, ancestor: NodeId) -> bool {
         while node != ancestor {
-            node = match self.module_map[&node].parent() {
+            node = match self.module_map[&node].parent {
                 Some(parent) => parent.normal_ancestor_id.unwrap(),
                 None => return false,
             }
@@ -1178,10 +1174,10 @@ pub fn new(session: &'a Session,
                macro_loader: &'a mut MacroLoader,
                arenas: &'a ResolverArenas<'a>)
                -> Resolver<'a> {
-        let root_def_id = DefId::local(CRATE_DEF_INDEX);
+        let graph_root_kind =
+            ModuleKind::Def(Def::Mod(DefId::local(CRATE_DEF_INDEX)), keywords::Invalid.name());
         let graph_root =
-            ModuleS::new(NoParentLink, Some(Def::Mod(root_def_id)), Some(CRATE_NODE_ID));
-        let graph_root = arenas.alloc_module(graph_root);
+            arenas.alloc_module(ModuleS::new(None, graph_root_kind, Some(CRATE_NODE_ID)));
         let mut module_map = NodeMap();
         module_map.insert(CRATE_NODE_ID, graph_root);
 
@@ -1263,18 +1259,15 @@ pub fn resolve_crate(&mut self, krate: &Crate) {
         self.report_errors();
     }
 
-    fn new_module(&self,
-                  parent_link: ParentLink<'a>,
-                  def: Option<Def>,
-                  normal_ancestor_id: Option<NodeId>)
+    fn new_module(&self, parent: Module<'a>, kind: ModuleKind, normal_ancestor_id: Option<NodeId>)
                   -> Module<'a> {
-        self.arenas.alloc_module(ModuleS::new(parent_link, def, normal_ancestor_id))
+        self.arenas.alloc_module(ModuleS::new(Some(parent), kind, normal_ancestor_id))
     }
 
-    fn new_extern_crate_module(&self, parent_link: ParentLink<'a>, def: Def, local_node_id: NodeId)
+    fn new_extern_crate_module(&self, parent: Module<'a>, name: Name, def: Def, node_id: NodeId)
                                -> Module<'a> {
-        let mut module = ModuleS::new(parent_link, Some(def), Some(local_node_id));
-        module.extern_crate_id = Some(local_node_id);
+        let mut module = ModuleS::new(Some(parent), ModuleKind::Def(def, name), Some(node_id));
+        module.extern_crate_id = Some(node_id);
         module.populated.set(false);
         self.arenas.modules.alloc(module)
     }
@@ -1336,11 +1329,10 @@ fn search_parent_externals<'a>(this: &mut Resolver<'a>, needle: Name, module: Mo
                                        -> Option<Module<'a>> {
             match this.resolve_name_in_module(module, needle, TypeNS, false, None) {
                 Success(binding) if binding.is_extern_crate() => Some(module),
-                _ => match module.parent_link {
-                    ModuleParentLink(ref parent, _) => {
-                        search_parent_externals(this, needle, parent)
-                    }
-                    _ => None,
+                _ => if let (&ModuleKind::Def(..), Some(parent)) = (&module.kind, module.parent) {
+                    search_parent_externals(this, needle, parent)
+                } else {
+                    None
                 },
             }
         }
@@ -1516,15 +1508,13 @@ fn resolve_ident_in_lexical_scope(&mut self,
                     return Some(LexicalScopeBinding::Item(binding));
                 }
 
-                // We can only see through anonymous modules
-                if module.def.is_some() {
-                    return match self.prelude {
-                        Some(prelude) if !module.no_implicit_prelude.get() => {
-                            self.resolve_name_in_module(prelude, name, ns, false, None).success()
-                                .map(LexicalScopeBinding::Item)
-                        }
-                        _ => None,
-                    };
+                if let ModuleKind::Block(..) = module.kind { // We can see through blocks
+                } else if !module.no_implicit_prelude.get() {
+                    return self.prelude.and_then(|prelude| {
+                        self.resolve_name_in_module(prelude, name, ns, false, None).success()
+                    }).map(LexicalScopeBinding::Item)
+                } else {
+                    return None;
                 }
             }
 
@@ -1561,7 +1551,7 @@ fn resolve_module_prefix(&mut self, module_path: &[Name], span: Option<Span>)
         while i < module_path.len() && "super" == module_path[i].as_str() {
             debug!("(resolving module prefix) resolving `super` at {}",
                    module_to_string(&containing_module));
-            if let Some(parent) = containing_module.parent() {
+            if let Some(parent) = containing_module.parent {
                 containing_module = self.module_map[&parent.normal_ancestor_id.unwrap()];
                 i += 1;
             } else {
@@ -2954,7 +2944,7 @@ fn resolve_expr(&mut self, expr: &Expr, parent: Option<&Expr>) {
                                                                    UseLexicalScope,
                                                                    Some(expr.span)) {
                                         Success(e) => {
-                                            if let Some(def_type) = e.def {
+                                            if let Some(def_type) = e.def() {
                                                 def = def_type;
                                             }
                                             context = UnresolvedNameContext::PathIsMod(parent);
@@ -3163,16 +3153,13 @@ fn add_trait_info(found_traits: &mut Vec<TraitCandidate>,
             };
             search_in_module(self, search_module);
 
-            match search_module.parent_link {
-                NoParentLink | ModuleParentLink(..) => {
-                    if !search_module.no_implicit_prelude.get() {
-                        self.prelude.map(|prelude| search_in_module(self, prelude));
-                    }
-                    break;
-                }
-                BlockParentLink(parent_module, _) => {
-                    search_module = parent_module;
+            if let ModuleKind::Block(..) = search_module.kind {
+                search_module = search_module.parent.unwrap();
+            } else {
+                if !search_module.no_implicit_prelude.get() {
+                    self.prelude.map(|prelude| search_in_module(self, prelude));
                 }
+                break;
             }
         }
 
@@ -3240,9 +3227,9 @@ fn lookup_candidates<FilterFn>(&mut self,
                 // collect submodules to explore
                 if let Ok(module) = name_binding.module() {
                     // form the path
-                    let path_segments = match module.parent_link {
-                        NoParentLink => path_segments.clone(),
-                        ModuleParentLink(_, name) => {
+                    let path_segments = match module.kind {
+                        _ if module.parent.is_none() => path_segments.clone(),
+                        ModuleKind::Def(_, name) => {
                             let mut paths = path_segments.clone();
                             let ident = ast::Ident::with_empty_ctxt(name);
                             let params = PathParameters::none();
@@ -3259,7 +3246,7 @@ fn lookup_candidates<FilterFn>(&mut self,
                     if !in_module_is_extern || name_binding.vis == ty::Visibility::Public {
                         // add the module to the lookup
                         let is_extern = in_module_is_extern || name_binding.is_extern_crate();
-                        if !worklist.iter().any(|&(m, ..)| m.def == module.def) {
+                        if !worklist.iter().any(|&(m, ..)| m.def() == module.def()) {
                             worklist.push((module, path_segments, is_extern));
                         }
                     }
@@ -3294,7 +3281,7 @@ fn resolve_visibility(&mut self, vis: &ast::Visibility) -> ty::Visibility {
         let mut path_resolution = err_path_resolution();
         let vis = match self.resolve_module_path(&segments, DontUseLexicalScope, Some(path.span)) {
             Success(module) => {
-                path_resolution = PathResolution::new(module.def.unwrap());
+                path_resolution = PathResolution::new(module.def().unwrap());
                 ty::Visibility::Restricted(module.normal_ancestor_id.unwrap())
             }
             Indeterminate => unreachable!(),
@@ -3360,10 +3347,10 @@ fn report_conflict(&self,
             return self.report_conflict(parent, name, ns, old_binding, binding);
         }
 
-        let container = match parent.def {
-            Some(Def::Mod(_)) => "module",
-            Some(Def::Trait(_)) => "trait",
-            None => "block",
+        let container = match parent.kind {
+            ModuleKind::Def(Def::Mod(_), _) => "module",
+            ModuleKind::Def(Def::Trait(_), _) => "trait",
+            ModuleKind::Block(..) => "block",
             _ => "enum",
         };
 
@@ -3510,17 +3497,15 @@ fn module_to_string(module: Module) -> String {
     let mut names = Vec::new();
 
     fn collect_mod(names: &mut Vec<ast::Name>, module: Module) {
-        match module.parent_link {
-            NoParentLink => {}
-            ModuleParentLink(ref module, name) => {
+        if let ModuleKind::Def(_, name) = module.kind {
+            if let Some(parent) = module.parent {
                 names.push(name);
-                collect_mod(names, module);
-            }
-            BlockParentLink(ref module, _) => {
-                // danger, shouldn't be ident?
-                names.push(token::intern("<opaque>"));
-                collect_mod(names, module);
+                collect_mod(names, parent);
             }
+        } else {
+            // danger, shouldn't be ident?
+            names.push(token::intern("<opaque>"));
+            collect_mod(names, module);
         }
     }
     collect_mod(&mut names, module);
index 29add1f9b9d4972b2329426593b0909c43d49002..ba45b773c09f36915174a4c5078e5da9bcbf0ef7 100644 (file)
@@ -733,7 +733,7 @@ fn resolve_glob_import(&mut self, directive: &'b ImportDirective<'b>) {
         let module = directive.imported_module.get().unwrap();
         self.populate_module_if_necessary(module);
 
-        if let Some(Def::Trait(_)) = module.def {
+        if let Some(Def::Trait(_)) = module.def() {
             self.session.span_err(directive.span, "items in traits are not importable.");
             return;
         } else if module.def_id() == directive.parent.def_id()  {