Rollup merge of #59936 - petrochenkov:confict, r=davidtwco

Fix cross-crate visibility of fictive variant constructors

After merging https://github.com/rust-lang/rust/pull/59376 I realized that the code in the decoder wasn't entirely correct - we "decoded" fictive variant constructors with their variant's visibility, which could be public, rather than demoted to `pub(crate)`.

Fictive constructors are not directly usable in expression/patterns, but the effect still can be observed with imports.

r? @davidtwco
This commit is contained in:
Mazdak Farrokhzad 2019-04-14 17:49:26 +02:00 committed by GitHub
commit 9506f62a7a
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 24 additions and 1 deletions

View file

@ -831,7 +831,18 @@ impl<'a, 'tcx> CrateMetadata {
let ctor_def_id = self.get_ctor_def_id(child_index).unwrap_or(def_id);
let ctor_kind = self.get_ctor_kind(child_index);
let ctor_def = Def::Ctor(ctor_def_id, CtorOf::Variant, ctor_kind);
let vis = self.get_visibility(ctor_def_id.index);
let mut vis = self.get_visibility(ctor_def_id.index);
if ctor_def_id == def_id && vis == ty::Visibility::Public {
// For non-exhaustive variants lower the constructor visibility to
// within the crate. We only need this for fictive constructors,
// for other constructors correct visibilities
// were already encoded in metadata.
let attrs = self.get_item_attrs(def_id.index, sess);
if attr::contains_name(&attrs, "non_exhaustive") {
let crate_def_id = DefId { index: CRATE_DEF_INDEX, ..def_id };
vis = ty::Visibility::Restricted(crate_def_id);
}
}
callback(def::Export { def: ctor_def, ident, vis, span });
}
_ => {}

View file

@ -0,0 +1,12 @@
// compile-pass
// aux-build:variants.rs
extern crate variants;
const S: u8 = 0;
// OK, `Struct` in value namespace is crate-private, so it's filtered away
// and there's no conflict with the previously defined `const S`.
use variants::NonExhaustiveVariants::Struct as S;
fn main() {}