resolve: Mark items under ambigous imports as exported

This commit is contained in:
Vadim Petrochenkov 2026-01-08 23:48:46 +03:00
parent a8e91473c5
commit 44e89f8262
5 changed files with 18 additions and 45 deletions

View file

@ -96,13 +96,10 @@ impl<'a, 'ra, 'tcx> EffectiveVisibilitiesVisitor<'a, 'ra, 'tcx> {
// is the maximum value among visibilities of declarations corresponding to that def id.
for (decl, eff_vis) in visitor.import_effective_visibilities.iter() {
let DeclKind::Import { import, .. } = decl.kind else { unreachable!() };
if !decl.is_ambiguity_recursive() {
if let Some(node_id) = import.id() {
r.effective_visibilities.update_eff_vis(r.local_def_id(node_id), eff_vis, r.tcx)
}
} else if decl.ambiguity.get().is_some()
&& eff_vis.is_public_at_level(Level::Reexported)
{
if let Some(node_id) = import.id() {
r.effective_visibilities.update_eff_vis(r.local_def_id(node_id), eff_vis, r.tcx)
}
if decl.ambiguity.get().is_some() && eff_vis.is_public_at_level(Level::Reexported) {
exported_ambiguities.insert(*decl);
}
}
@ -123,31 +120,13 @@ impl<'a, 'ra, 'tcx> EffectiveVisibilitiesVisitor<'a, 'ra, 'tcx> {
// Set the given effective visibility level to `Level::Direct` and
// sets the rest of the `use` chain to `Level::Reexported` until
// we hit the actual exported item.
//
// If the binding is ambiguous, put the root ambiguity binding and all reexports
// leading to it into the table. They are used by the `ambiguous_glob_reexports`
// lint. For all bindings added to the table this way `is_ambiguity` returns true.
let is_ambiguity =
|decl: Decl<'ra>, warn: bool| decl.ambiguity.get().is_some() && !warn;
let mut parent_id = ParentId::Def(module_id);
let mut warn_ambiguity = decl.warn_ambiguity.get();
while let DeclKind::Import { source_decl, .. } = decl.kind {
self.update_import(decl, parent_id);
if is_ambiguity(decl, warn_ambiguity) {
// Stop at the root ambiguity, further bindings in the chain should not
// be reexported because the root ambiguity blocks any access to them.
// (Those further bindings are most likely not ambiguities themselves.)
break;
}
parent_id = ParentId::Import(decl);
decl = source_decl;
warn_ambiguity |= source_decl.warn_ambiguity.get();
}
if !is_ambiguity(decl, warn_ambiguity)
&& let Some(def_id) = decl.res().opt_def_id().and_then(|id| id.as_local())
{
if let Some(def_id) = decl.res().opt_def_id().and_then(|id| id.as_local()) {
self.update_def(def_id, decl.vis().expect_local(), parent_id);
}
}

View file

@ -1,9 +1,9 @@
//@ has 'glob_shadowing/index.html'
//@ count - '//dt' 6
//@ !has - '//dd' 'sub1::describe'
//@ count - '//dt' 7
//@ !has - '//dd' 'sub1::describe1'
//@ has - '//dd' 'sub2::describe'
//@ !has - '//dd' 'sub1::describe2'
//@ has - '//dd' 'sub1::describe2'
//@ !has - '//dd' 'sub1::prelude'
//@ has - '//dd' 'mod::prelude'
@ -18,7 +18,7 @@
mod sub1 {
// this should be shadowed by sub2::describe
/// sub1::describe
/// sub1::describe1
pub fn describe() -> &'static str {
"sub1::describe"
}
@ -33,7 +33,9 @@ mod sub1 {
pub struct Foo;
// this should be shadowed,
// because both sub1::describe2 and sub3::describe2 are from glob reexport
// because both sub1::describe2 and sub3::describe2 are from glob reexport,
// but it is still usable from other crates under the `ambiguous_glob_imports` lint,
// so it is reachable and documented
/// sub1::describe2
pub fn describe2() -> &'static str {
"sub1::describe2"

View file

@ -1,7 +1,9 @@
// Regression test for https://github.com/rust-lang/rust/issues/100973
// Update: the rules has changed after #147984, one of the colliding items is now available
// from other crates under a deprecation lint.
//@ set m1 = "$.index[?(@.name == 'm1' && @.inner.module)].id"
//@ is "$.index[?(@.name == 'm1')].inner.module.items" []
//@ is "$.index[?(@.name == 'm1')].inner.module.items" [0]
//@ is "$.index[?(@.name == 'm1')].inner.module.is_stripped" true
mod m1 {
pub fn f() {}

View file

@ -1,4 +1,4 @@
//@ build-fail
//@ build-pass
//@ aux-crate: ambiguous_reachable_extern=ambiguous-reachable-extern.rs
#![allow(ambiguous_glob_imports)]
@ -6,5 +6,3 @@
fn main() {
ambiguous_reachable_extern::generic::<u8>();
}
//~? ERROR missing optimized MIR

View file

@ -1,13 +1,3 @@
error: missing optimized MIR for `ambiguous_reachable_extern::m1::generic::<u8>` in the crate `ambiguous_reachable_extern`
|
note: missing optimized MIR for this item (was the crate `ambiguous_reachable_extern` compiled with `--emit=metadata`?)
--> $DIR/auxiliary/ambiguous-reachable-extern.rs:2:5
|
LL | pub fn generic<T>() {
| ^^^^^^^^^^^^^^^^^^^
error: aborting due to 1 previous error
Future incompatibility report: Future breakage diagnostic:
warning: `generic` is ambiguous
--> $DIR/ambiguous-reachable.rs:7:33
@ -23,6 +13,8 @@ note: `generic` could refer to the function defined here
|
LL | pub use m1::*;
| ^^
= help: consider updating this dependency to resolve this error
= help: if updating the dependency does not resolve the problem report the problem to the author of the relevant crate
note: `generic` could also refer to the function defined here
--> $DIR/auxiliary/ambiguous-reachable-extern.rs:14:9
|