mirror of
https://github.com/rust-lang/rust
synced 2024-10-14 20:46:49 +00:00
Encode VariantIdx so we can decode variants in the right order
This commit is contained in:
parent
7d59fa3d23
commit
ff54c801f0
|
@ -856,7 +856,12 @@ fn get_explicit_item_bounds(
|
|||
ty::EarlyBinder(&*output)
|
||||
}
|
||||
|
||||
fn get_variant(self, kind: &DefKind, index: DefIndex, parent_did: DefId) -> ty::VariantDef {
|
||||
fn get_variant(
|
||||
self,
|
||||
kind: DefKind,
|
||||
index: DefIndex,
|
||||
parent_did: DefId,
|
||||
) -> (VariantIdx, ty::VariantDef) {
|
||||
let adt_kind = match kind {
|
||||
DefKind::Variant => ty::AdtKind::Enum,
|
||||
DefKind::Struct => ty::AdtKind::Struct,
|
||||
|
@ -870,22 +875,25 @@ fn get_variant(self, kind: &DefKind, index: DefIndex, parent_did: DefId) -> ty::
|
|||
if adt_kind == ty::AdtKind::Enum { Some(self.local_def_id(index)) } else { None };
|
||||
let ctor = data.ctor.map(|(kind, index)| (kind, self.local_def_id(index)));
|
||||
|
||||
ty::VariantDef::new(
|
||||
self.item_name(index),
|
||||
variant_did,
|
||||
ctor,
|
||||
data.discr,
|
||||
self.get_associated_item_or_field_def_ids(index)
|
||||
.map(|did| ty::FieldDef {
|
||||
did,
|
||||
name: self.item_name(did.index),
|
||||
vis: self.get_visibility(did.index),
|
||||
})
|
||||
.collect(),
|
||||
adt_kind,
|
||||
parent_did,
|
||||
false,
|
||||
data.is_non_exhaustive,
|
||||
(
|
||||
data.idx,
|
||||
ty::VariantDef::new(
|
||||
self.item_name(index),
|
||||
variant_did,
|
||||
ctor,
|
||||
data.discr,
|
||||
self.get_associated_item_or_field_def_ids(index)
|
||||
.map(|did| ty::FieldDef {
|
||||
did,
|
||||
name: self.item_name(did.index),
|
||||
vis: self.get_visibility(did.index),
|
||||
})
|
||||
.collect(),
|
||||
adt_kind,
|
||||
parent_did,
|
||||
false,
|
||||
data.is_non_exhaustive,
|
||||
),
|
||||
)
|
||||
}
|
||||
|
||||
|
@ -901,7 +909,7 @@ fn get_adt_def(self, item_id: DefIndex, tcx: TyCtxt<'tcx>) -> ty::AdtDef<'tcx> {
|
|||
};
|
||||
let repr = self.root.tables.repr_options.get(self, item_id).unwrap().decode(self);
|
||||
|
||||
let variants = if let ty::AdtKind::Enum = adt_kind {
|
||||
let mut variants: Vec<_> = if let ty::AdtKind::Enum = adt_kind {
|
||||
self.root
|
||||
.tables
|
||||
.module_children_non_reexports
|
||||
|
@ -912,15 +920,22 @@ fn get_adt_def(self, item_id: DefIndex, tcx: TyCtxt<'tcx>) -> ty::AdtDef<'tcx> {
|
|||
let kind = self.def_kind(index);
|
||||
match kind {
|
||||
DefKind::Ctor(..) => None,
|
||||
_ => Some(self.get_variant(&kind, index, did)),
|
||||
_ => Some(self.get_variant(kind, index, did)),
|
||||
}
|
||||
})
|
||||
.collect()
|
||||
} else {
|
||||
std::iter::once(self.get_variant(&kind, item_id, did)).collect()
|
||||
std::iter::once(self.get_variant(kind, item_id, did)).collect()
|
||||
};
|
||||
|
||||
tcx.mk_adt_def(did, adt_kind, variants, repr)
|
||||
variants.sort_by_key(|(idx, _)| *idx);
|
||||
|
||||
tcx.mk_adt_def(
|
||||
did,
|
||||
adt_kind,
|
||||
variants.into_iter().map(|(_, variant)| variant).collect(),
|
||||
repr,
|
||||
)
|
||||
}
|
||||
|
||||
fn get_visibility(self, id: DefIndex) -> Visibility<DefId> {
|
||||
|
|
|
@ -1375,9 +1375,10 @@ fn encode_info_for_adt(&mut self, local_def_id: LocalDefId) {
|
|||
// Therefore, the loop over variants will encode its fields as the adt's children.
|
||||
}
|
||||
|
||||
for variant in adt_def.variants().iter() {
|
||||
for (idx, variant) in adt_def.variants().iter_enumerated() {
|
||||
let data = VariantData {
|
||||
discr: variant.discr,
|
||||
idx,
|
||||
ctor: variant.ctor.map(|(kind, def_id)| (kind, def_id.index)),
|
||||
is_non_exhaustive: variant.is_field_list_non_exhaustive(),
|
||||
};
|
||||
|
|
|
@ -31,6 +31,7 @@
|
|||
use rustc_span::hygiene::{ExpnIndex, MacroKind};
|
||||
use rustc_span::symbol::{Ident, Symbol};
|
||||
use rustc_span::{self, ExpnData, ExpnHash, ExpnId, Span};
|
||||
use rustc_target::abi::VariantIdx;
|
||||
use rustc_target::spec::{PanicStrategy, TargetTriple};
|
||||
|
||||
use std::marker::PhantomData;
|
||||
|
@ -430,6 +431,7 @@ fn encode(&self, buf: &mut FileEncoder) -> LazyTables {
|
|||
|
||||
#[derive(TyEncodable, TyDecodable)]
|
||||
struct VariantData {
|
||||
idx: VariantIdx,
|
||||
discr: ty::VariantDiscr,
|
||||
/// If this is unit or tuple-variant/struct, then this is the index of the ctor id.
|
||||
ctor: Option<(CtorKind, DefIndex)>,
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
#[derive(Default)]
|
||||
pub enum Foo {
|
||||
A(u32),
|
||||
#[default]
|
||||
B,
|
||||
C(u32),
|
||||
}
|
11
tests/ui/enum-discriminant/discr-foreign.rs
Normal file
11
tests/ui/enum-discriminant/discr-foreign.rs
Normal file
|
@ -0,0 +1,11 @@
|
|||
// aux-build:discr-foreign-dep.rs
|
||||
// build-pass
|
||||
|
||||
extern crate discr_foreign_dep;
|
||||
|
||||
fn main() {
|
||||
match Default::default() {
|
||||
discr_foreign_dep::Foo::A(_) => {}
|
||||
_ => {}
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue