Refactor away ParentLink
.
This commit is contained in:
parent
1cf592fa40
commit
9a0e88a339
@ -14,10 +14,9 @@
|
||||
//! 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 @@ impl<'b> Resolver<'b> {
|
||||
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 @@ impl<'b> Resolver<'b> {
|
||||
}
|
||||
|
||||
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 @@ impl<'b> Resolver<'b> {
|
||||
}
|
||||
|
||||
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 @@ impl<'b> Resolver<'b> {
|
||||
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 @@ impl<'b> Resolver<'b> {
|
||||
{}",
|
||||
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 @@ impl<'b> Resolver<'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 @@ impl<'b> Resolver<'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(..) => {
|
||||
|
@ -41,7 +41,6 @@ use self::TypeParameters::*;
|
||||
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 @@ impl<'a> LexicalScopeBinding<'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 @@ impl<'a> ModuleS<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
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 @@ impl<'a> NameBinding<'a> {
|
||||
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 @@ impl<'a> ResolverArenas<'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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
-> 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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
};
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
// 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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
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 @@ impl<'a> Resolver<'a> {
|
||||
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);
|
||||
|
@ -733,7 +733,7 @@ impl<'a, 'b:'a> ImportResolver<'a, '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() {
|
||||
|
Loading…
Reference in New Issue
Block a user