GlobImport {
is_prelude: bool,
max_vis: Cell<ty::Visibility>, // The visibility of the greatest reexport.
+ // n.b. `max_vis` is only used in `finalize_import` to check for reexport errors.
},
}
if is_disallowed_private_import(binding) {
return Failed(None);
}
- self.record_use(name, ns, binding);
+ if self.record_use(name, ns, binding, span) {
+ return Success(self.dummy_binding);
+ }
if !self.is_accessible(binding.vis) {
self.privacy_errors.push(PrivacyError(span, name, binding));
}
where T: ToNameBinding<'a>
{
let binding = self.arenas.alloc_name_binding(binding.to_name_binding());
- self.update_resolution(module, name, ns, |_, resolution| {
+ self.update_resolution(module, name, ns, |this, resolution| {
if let Some(old_binding) = resolution.binding {
if binding.is_glob_import() {
- resolution.duplicate_globs.push(binding);
+ if !this.new_import_semantics || !old_binding.is_glob_import() {
+ resolution.duplicate_globs.push(binding);
+ } else if binding.def() != old_binding.def() {
+ resolution.binding = Some(this.arenas.alloc_name_binding(NameBinding {
+ kind: NameBindingKind::Ambiguity {
+ b1: old_binding,
+ b2: binding,
+ },
+ vis: if old_binding.vis.is_at_least(binding.vis, this) {
+ old_binding.vis
+ } else {
+ binding.vis
+ },
+ span: old_binding.span,
+ }));
+ } else if !old_binding.vis.is_at_least(binding.vis, this) {
+ // We are glob-importing the same item but with greater visibility.
+ resolution.binding = Some(binding);
+ }
} else if old_binding.is_glob_import() {
resolution.duplicate_globs.push(old_binding);
resolution.binding = Some(binding);
// during which the resolution might end up getting re-defined via a glob cycle.
let (binding, t) = {
let mut resolution = &mut *self.resolution(module, name, ns).borrow_mut();
- let was_known = resolution.binding().is_some();
+ let old_binding = resolution.binding();
let t = f(self, resolution);
- if was_known { return t; }
match resolution.binding() {
- Some(binding) => (binding, t),
+ _ if !self.new_import_semantics && old_binding.is_some() => return t,
None => return t,
+ Some(binding) => match old_binding {
+ Some(old_binding) if old_binding as *const _ == binding as *const _ => return t,
+ _ => (binding, t),
+ }
}
};
// Define `binding` in `module`s glob importers.
- if binding.vis == ty::Visibility::Public {
- for directive in module.glob_importers.borrow_mut().iter() {
+ for directive in module.glob_importers.borrow_mut().iter() {
+ if match self.new_import_semantics {
+ true => self.is_accessible_from(binding.vis, directive.parent),
+ false => binding.vis == ty::Visibility::Public,
+ } {
let imported_binding = self.import(binding, directive);
let _ = self.try_define(directive.parent, name, ns, imported_binding);
}
errors = true;
let (span, help) = match err {
Some((span, msg)) => (span, msg),
- None => (import.span, String::new()),
+ None => continue,
};
// If the error is a single failed import then create a "fake" import
for &(ns, result) in &[(ValueNS, value_result), (TypeNS, type_result)] {
if let Ok(binding) = result {
- self.record_use(name, ns, binding);
+ if self.record_use(name, ns, binding, directive.span) {
+ self.resolution(module, name, ns).borrow_mut().binding =
+ Some(self.dummy_binding);
+ }
}
}
resolution.borrow().binding().map(|binding| (*name, binding))
}).collect::<Vec<_>>();
for ((name, ns), binding) in bindings {
- if binding.pseudo_vis() == ty::Visibility::Public {
+ if binding.pseudo_vis() == ty::Visibility::Public ||
+ self.new_import_semantics && self.is_accessible(binding.vis) {
let imported_binding = self.import(binding, directive);
let _ = self.try_define(directive.parent, name, ns, imported_binding);
}
}
}
- self.report_conflict(module, name, ns, duplicate_glob, binding);
- }
- } else if binding.is_glob_import() {
- for duplicate_glob in resolution.duplicate_globs.iter() {
self.report_conflict(module, name, ns, duplicate_glob, binding);
}
}
if binding.vis == ty::Visibility::Public &&
(binding.is_import() || binding.is_extern_crate()) {
- reexports.push(Export { name: name, def_id: binding.def().def_id() });
+ let def = binding.def();
+ if def != Def::Err {
+ reexports.push(Export { name: name, def_id: def.def_id() });
+ }
}
if let NameBindingKind::Import { binding: orig_binding, directive, .. } = binding.kind {