Rollup merge of #106354 - aDotInTheVoid:rdj-always-discr, r=GuillaumeGomez

Rustdoc-Json: Report discriminant on all kinds of enum variant.

Closes https://github.com/rust-lang/rust/issues/106299

Probably easier to review one commit at a time.

r? `@GuillaumeGomez`
This commit is contained in:
Michael Goulet 2023-01-02 15:39:18 -08:00 committed by GitHub
commit 0d5c5fae61
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
22 changed files with 257 additions and 201 deletions

View File

@ -1949,20 +1949,28 @@ pub(crate) fn clean_field_with_def_id(
}
pub(crate) fn clean_variant_def<'tcx>(variant: &ty::VariantDef, cx: &mut DocContext<'tcx>) -> Item {
let discriminant = match variant.discr {
ty::VariantDiscr::Explicit(def_id) => Some(Discriminant { expr: None, value: def_id }),
ty::VariantDiscr::Relative(_) => None,
};
let kind = match variant.ctor_kind() {
Some(CtorKind::Const) => Variant::CLike(match variant.discr {
ty::VariantDiscr::Explicit(def_id) => Some(Discriminant { expr: None, value: def_id }),
ty::VariantDiscr::Relative(_) => None,
}),
Some(CtorKind::Fn) => Variant::Tuple(
Some(CtorKind::Const) => VariantKind::CLike,
Some(CtorKind::Fn) => VariantKind::Tuple(
variant.fields.iter().map(|field| clean_middle_field(field, cx)).collect(),
),
None => Variant::Struct(VariantStruct {
None => VariantKind::Struct(VariantStruct {
ctor_kind: None,
fields: variant.fields.iter().map(|field| clean_middle_field(field, cx)).collect(),
}),
};
Item::from_def_id_and_parts(variant.def_id, Some(variant.name), VariantItem(kind), cx)
Item::from_def_id_and_parts(
variant.def_id,
Some(variant.name),
VariantItem(Variant { kind, discriminant }),
cx,
)
}
fn clean_variant_data<'tcx>(
@ -1970,19 +1978,23 @@ fn clean_variant_data<'tcx>(
disr_expr: &Option<hir::AnonConst>,
cx: &mut DocContext<'tcx>,
) -> Variant {
match variant {
hir::VariantData::Struct(..) => Variant::Struct(VariantStruct {
let discriminant = disr_expr.map(|disr| Discriminant {
expr: Some(disr.body),
value: cx.tcx.hir().local_def_id(disr.hir_id).to_def_id(),
});
let kind = match variant {
hir::VariantData::Struct(..) => VariantKind::Struct(VariantStruct {
ctor_kind: None,
fields: variant.fields().iter().map(|x| clean_field(x, cx)).collect(),
}),
hir::VariantData::Tuple(..) => {
Variant::Tuple(variant.fields().iter().map(|x| clean_field(x, cx)).collect())
VariantKind::Tuple(variant.fields().iter().map(|x| clean_field(x, cx)).collect())
}
hir::VariantData::Unit(..) => Variant::CLike(disr_expr.map(|disr| Discriminant {
expr: Some(disr.body),
value: cx.tcx.hir().local_def_id(disr.hir_id).to_def_id(),
})),
}
hir::VariantData::Unit(..) => VariantKind::CLike,
};
Variant { discriminant, kind }
}
fn clean_path<'tcx>(path: &hir::Path<'tcx>, cx: &mut DocContext<'tcx>) -> Path {

View File

@ -807,8 +807,11 @@ impl ItemKind {
match self {
StructItem(s) => s.fields.iter(),
UnionItem(u) => u.fields.iter(),
VariantItem(Variant::Struct(v)) => v.fields.iter(),
VariantItem(Variant::Tuple(v)) => v.iter(),
VariantItem(v) => match &v.kind {
VariantKind::CLike => [].iter(),
VariantKind::Tuple(t) => t.iter(),
VariantKind::Struct(s) => s.fields.iter(),
},
EnumItem(e) => e.variants.iter(),
TraitItem(t) => t.items.iter(),
ImplItem(i) => i.items.iter(),
@ -824,7 +827,6 @@ impl ItemKind {
| TyMethodItem(_)
| MethodItem(_, _)
| StructFieldItem(_)
| VariantItem(_)
| ForeignFunctionItem(_)
| ForeignStaticItem(_)
| ForeignTypeItem
@ -2136,17 +2138,23 @@ impl Enum {
}
#[derive(Clone, Debug)]
pub(crate) enum Variant {
CLike(Option<Discriminant>),
pub(crate) struct Variant {
pub kind: VariantKind,
pub discriminant: Option<Discriminant>,
}
#[derive(Clone, Debug)]
pub(crate) enum VariantKind {
CLike,
Tuple(Vec<Item>),
Struct(VariantStruct),
}
impl Variant {
pub(crate) fn has_stripped_entries(&self) -> Option<bool> {
match *self {
Self::Struct(ref struct_) => Some(struct_.has_stripped_entries()),
Self::CLike(..) | Self::Tuple(_) => None,
match &self.kind {
VariantKind::Struct(struct_) => Some(struct_.has_stripped_entries()),
VariantKind::CLike | VariantKind::Tuple(_) => None,
}
}
}

View File

@ -37,17 +37,21 @@ pub(crate) trait DocFolder: Sized {
i.items = i.items.into_iter().filter_map(|x| self.fold_item(x)).collect();
ImplItem(i)
}
VariantItem(i) => match i {
Variant::Struct(mut j) => {
j.fields = j.fields.into_iter().filter_map(|x| self.fold_item(x)).collect();
VariantItem(Variant::Struct(j))
}
Variant::Tuple(fields) => {
let fields = fields.into_iter().filter_map(|x| self.fold_item(x)).collect();
VariantItem(Variant::Tuple(fields))
}
Variant::CLike(disr) => VariantItem(Variant::CLike(disr)),
},
VariantItem(Variant { kind, discriminant }) => {
let kind = match kind {
VariantKind::Struct(mut j) => {
j.fields = j.fields.into_iter().filter_map(|x| self.fold_item(x)).collect();
VariantKind::Struct(j)
}
VariantKind::Tuple(fields) => {
let fields = fields.into_iter().filter_map(|x| self.fold_item(x)).collect();
VariantKind::Tuple(fields)
}
VariantKind::CLike => VariantKind::CLike,
};
VariantItem(Variant { kind, discriminant })
}
ExternCrateItem { src: _ }
| ImportItem(_)
| FunctionItem(_)

View File

@ -1220,15 +1220,15 @@ fn item_enum(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, e: &clean::
w.write_str(" ");
let name = v.name.unwrap();
match *v.kind {
clean::VariantItem(ref var) => match var {
// FIXME(#101337): Show discriminant
clean::Variant::CLike(..) => write!(w, "{}", name),
clean::Variant::Tuple(ref s) => {
// FIXME(#101337): Show discriminant
clean::VariantItem(ref var) => match var.kind {
clean::VariantKind::CLike => write!(w, "{}", name),
clean::VariantKind::Tuple(ref s) => {
write!(w, "{}(", name);
print_tuple_struct_fields(w, cx, s);
w.write_str(")");
}
clean::Variant::Struct(ref s) => {
clean::VariantKind::Struct(ref s) => {
render_struct(
w,
v,
@ -1286,25 +1286,28 @@ fn item_enum(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, e: &clean::
" rightside",
);
write!(w, "<h3 class=\"code-header\">{name}", name = variant.name.unwrap());
if let clean::VariantItem(clean::Variant::Tuple(ref s)) = *variant.kind {
let clean::VariantItem(variant_data) = &*variant.kind else { unreachable!() };
if let clean::VariantKind::Tuple(ref s) = variant_data.kind {
w.write_str("(");
print_tuple_struct_fields(w, cx, s);
w.write_str(")");
}
w.write_str("</h3></section>");
use crate::clean::Variant;
let heading_and_fields = match &*variant.kind {
clean::VariantItem(Variant::Struct(s)) => Some(("Fields", &s.fields)),
// Documentation on tuple variant fields is rare, so to reduce noise we only emit
// the section if at least one field is documented.
clean::VariantItem(Variant::Tuple(fields))
if fields.iter().any(|f| f.doc_value().is_some()) =>
{
Some(("Tuple Fields", fields))
let heading_and_fields = match &variant_data.kind {
clean::VariantKind::Struct(s) => Some(("Fields", &s.fields)),
clean::VariantKind::Tuple(fields) => {
// Documentation on tuple variant fields is rare, so to reduce noise we only emit
// the section if at least one field is documented.
if fields.iter().any(|f| f.doc_value().is_some()) {
Some(("Tuple Fields", fields))
} else {
None
}
}
_ => None,
clean::VariantKind::CLike => None,
};
if let Some((heading, fields)) = heading_and_fields {

View File

@ -646,15 +646,20 @@ impl FromWithTcx<clean::Enum> for Enum {
impl FromWithTcx<clean::Variant> for Variant {
fn from_tcx(variant: clean::Variant, tcx: TyCtxt<'_>) -> Self {
use clean::Variant::*;
match variant {
CLike(disr) => Variant::Plain(disr.map(|disr| disr.into_tcx(tcx))),
Tuple(fields) => Variant::Tuple(ids_keeping_stripped(fields, tcx)),
Struct(s) => Variant::Struct {
use clean::VariantKind::*;
let discriminant = variant.discriminant.map(|d| d.into_tcx(tcx));
let kind = match variant.kind {
CLike => VariantKind::Plain,
Tuple(fields) => VariantKind::Tuple(ids_keeping_stripped(fields, tcx)),
Struct(s) => VariantKind::Struct {
fields_stripped: s.has_stripped_entries(),
fields: ids(s.fields, tcx),
},
}
};
Variant { kind, discriminant }
}
}

View File

@ -132,7 +132,10 @@ impl<'a, 'tcx> DocFolder for Stripper<'a, 'tcx> {
// implementations of traits are always public.
clean::ImplItem(ref imp) if imp.trait_.is_some() => true,
// Variant fields have inherited visibility
clean::VariantItem(clean::Variant::Struct(..) | clean::Variant::Tuple(..)) => true,
clean::VariantItem(clean::Variant {
kind: clean::VariantKind::Struct(..) | clean::VariantKind::Tuple(..),
..
}) => true,
_ => false,
};

View File

@ -17,10 +17,10 @@ pub(crate) trait DocVisitor: Sized {
EnumItem(i) => i.variants.iter().for_each(|x| self.visit_item(x)),
TraitItem(i) => i.items.iter().for_each(|x| self.visit_item(x)),
ImplItem(i) => i.items.iter().for_each(|x| self.visit_item(x)),
VariantItem(i) => match i {
Variant::Struct(j) => j.fields.iter().for_each(|x| self.visit_item(x)),
Variant::Tuple(fields) => fields.iter().for_each(|x| self.visit_item(x)),
Variant::CLike(_) => {}
VariantItem(i) => match &i.kind {
VariantKind::Struct(j) => j.fields.iter().for_each(|x| self.visit_item(x)),
VariantKind::Tuple(fields) => fields.iter().for_each(|x| self.visit_item(x)),
VariantKind::CLike => {}
},
ExternCrateItem { src: _ }
| ImportItem(_)

View File

@ -9,7 +9,7 @@ use std::path::PathBuf;
use serde::{Deserialize, Serialize};
/// rustdoc format-version.
pub const FORMAT_VERSION: u32 = 23;
pub const FORMAT_VERSION: u32 = 24;
/// A `Crate` is the root of the emitted JSON blob. It contains all type/documentation information
/// about the language items in the local crate, as well as info about external items to allow
@ -333,11 +333,18 @@ pub struct Enum {
pub impls: Vec<Id>,
}
#[derive(Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)]
pub struct Variant {
/// Whether the variant is plain, a tuple-like, or struct-like. Contains the fields.
pub kind: VariantKind,
/// The discriminant, if explicitly specified.
pub discriminant: Option<Discriminant>,
}
#[derive(Clone, Debug, PartialEq, Eq, Hash, Serialize, Deserialize)]
#[serde(rename_all = "snake_case")]
#[serde(tag = "variant_kind", content = "variant_inner")]
pub enum Variant {
/// A variant with no parentheses, and possible discriminant.
pub enum VariantKind {
/// A variant with no parentheses
///
/// ```rust
/// enum Demo {
@ -345,7 +352,7 @@ pub enum Variant {
/// PlainWithDiscriminant = 1,
/// }
/// ```
Plain(Option<Discriminant>),
Plain,
/// A variant with unnamed fields.
///
/// Unlike most of json, `#[doc(hidden)]` fields will be given as `None`

View File

@ -1,12 +1,12 @@
#[repr(i8)]
pub enum Ordering {
// @is "$.index[*][?(@.name=='Less')].inner.variant_inner.expr" '"-1"'
// @is "$.index[*][?(@.name=='Less')].inner.variant_inner.value" '"-1"'
// @is "$.index[*][?(@.name=='Less')].inner.discriminant.expr" '"-1"'
// @is "$.index[*][?(@.name=='Less')].inner.discriminant.value" '"-1"'
Less = -1,
// @is "$.index[*][?(@.name=='Equal')].inner.variant_inner.expr" '"0"'
// @is "$.index[*][?(@.name=='Equal')].inner.variant_inner.value" '"0"'
// @is "$.index[*][?(@.name=='Equal')].inner.discriminant.expr" '"0"'
// @is "$.index[*][?(@.name=='Equal')].inner.discriminant.value" '"0"'
Equal = 0,
// @is "$.index[*][?(@.name=='Greater')].inner.variant_inner.expr" '"1"'
// @is "$.index[*][?(@.name=='Greater')].inner.variant_inner.value" '"1"'
// @is "$.index[*][?(@.name=='Greater')].inner.discriminant.expr" '"1"'
// @is "$.index[*][?(@.name=='Greater')].inner.discriminant.value" '"1"'
Greater = 1,
}

View File

@ -1,30 +1,30 @@
pub enum Foo {
// @is "$.index[*][?(@.name=='Addition')].inner.variant_inner.value" '"0"'
// @is "$.index[*][?(@.name=='Addition')].inner.variant_inner.expr" '"{ _ }"'
// @is "$.index[*][?(@.name=='Addition')].inner.discriminant.value" '"0"'
// @is "$.index[*][?(@.name=='Addition')].inner.discriminant.expr" '"{ _ }"'
Addition = 0 + 0,
// @is "$.index[*][?(@.name=='Bin')].inner.variant_inner.value" '"1"'
// @is "$.index[*][?(@.name=='Bin')].inner.variant_inner.expr" '"0b1"'
// @is "$.index[*][?(@.name=='Bin')].inner.discriminant.value" '"1"'
// @is "$.index[*][?(@.name=='Bin')].inner.discriminant.expr" '"0b1"'
Bin = 0b1,
// @is "$.index[*][?(@.name=='Oct')].inner.variant_inner.value" '"2"'
// @is "$.index[*][?(@.name=='Oct')].inner.variant_inner.expr" '"0o2"'
// @is "$.index[*][?(@.name=='Oct')].inner.discriminant.value" '"2"'
// @is "$.index[*][?(@.name=='Oct')].inner.discriminant.expr" '"0o2"'
Oct = 0o2,
// @is "$.index[*][?(@.name=='PubConst')].inner.variant_inner.value" '"3"'
// @is "$.index[*][?(@.name=='PubConst')].inner.variant_inner.expr" '"THREE"'
// @is "$.index[*][?(@.name=='PubConst')].inner.discriminant.value" '"3"'
// @is "$.index[*][?(@.name=='PubConst')].inner.discriminant.expr" '"THREE"'
PubConst = THREE,
// @is "$.index[*][?(@.name=='Hex')].inner.variant_inner.value" '"4"'
// @is "$.index[*][?(@.name=='Hex')].inner.variant_inner.expr" '"0x4"'
// @is "$.index[*][?(@.name=='Hex')].inner.discriminant.value" '"4"'
// @is "$.index[*][?(@.name=='Hex')].inner.discriminant.expr" '"0x4"'
Hex = 0x4,
// @is "$.index[*][?(@.name=='Cast')].inner.variant_inner.value" '"5"'
// @is "$.index[*][?(@.name=='Cast')].inner.variant_inner.expr" '"{ _ }"'
// @is "$.index[*][?(@.name=='Cast')].inner.discriminant.value" '"5"'
// @is "$.index[*][?(@.name=='Cast')].inner.discriminant.expr" '"{ _ }"'
Cast = 5 as isize,
// @is "$.index[*][?(@.name=='PubCall')].inner.variant_inner.value" '"6"'
// @is "$.index[*][?(@.name=='PubCall')].inner.variant_inner.expr" '"{ _ }"'
// @is "$.index[*][?(@.name=='PubCall')].inner.discriminant.value" '"6"'
// @is "$.index[*][?(@.name=='PubCall')].inner.discriminant.expr" '"{ _ }"'
PubCall = six(),
// @is "$.index[*][?(@.name=='PrivCall')].inner.variant_inner.value" '"7"'
// @is "$.index[*][?(@.name=='PrivCall')].inner.variant_inner.expr" '"{ _ }"'
// @is "$.index[*][?(@.name=='PrivCall')].inner.discriminant.value" '"7"'
// @is "$.index[*][?(@.name=='PrivCall')].inner.discriminant.expr" '"{ _ }"'
PrivCall = seven(),
// @is "$.index[*][?(@.name=='PrivConst')].inner.variant_inner.value" '"8"'
// @is "$.index[*][?(@.name=='PrivConst')].inner.variant_inner.expr" '"EIGHT"'
// @is "$.index[*][?(@.name=='PrivConst')].inner.discriminant.value" '"8"'
// @is "$.index[*][?(@.name=='PrivConst')].inner.discriminant.expr" '"EIGHT"'
PrivConst = EIGHT,
}

View File

@ -4,40 +4,40 @@
#[repr(u64)]
pub enum U64 {
// @is "$.index[*][?(@.name=='U64Min')].inner.variant_inner.value" '"0"'
// @is "$.index[*][?(@.name=='U64Min')].inner.variant_inner.expr" '"u64::MIN"'
// @is "$.index[*][?(@.name=='U64Min')].inner.discriminant.value" '"0"'
// @is "$.index[*][?(@.name=='U64Min')].inner.discriminant.expr" '"u64::MIN"'
U64Min = u64::MIN,
// @is "$.index[*][?(@.name=='U64Max')].inner.variant_inner.value" '"18446744073709551615"'
// @is "$.index[*][?(@.name=='U64Max')].inner.variant_inner.expr" '"u64::MAX"'
// @is "$.index[*][?(@.name=='U64Max')].inner.discriminant.value" '"18446744073709551615"'
// @is "$.index[*][?(@.name=='U64Max')].inner.discriminant.expr" '"u64::MAX"'
U64Max = u64::MAX,
}
#[repr(i64)]
pub enum I64 {
// @is "$.index[*][?(@.name=='I64Min')].inner.variant_inner.value" '"-9223372036854775808"'
// @is "$.index[*][?(@.name=='I64Min')].inner.variant_inner.expr" '"i64::MIN"'
// @is "$.index[*][?(@.name=='I64Min')].inner.discriminant.value" '"-9223372036854775808"'
// @is "$.index[*][?(@.name=='I64Min')].inner.discriminant.expr" '"i64::MIN"'
I64Min = i64::MIN,
// @is "$.index[*][?(@.name=='I64Max')].inner.variant_inner.value" '"9223372036854775807"'
// @is "$.index[*][?(@.name=='I64Max')].inner.variant_inner.expr" '"i64::MAX"'
// @is "$.index[*][?(@.name=='I64Max')].inner.discriminant.value" '"9223372036854775807"'
// @is "$.index[*][?(@.name=='I64Max')].inner.discriminant.expr" '"i64::MAX"'
I64Max = i64::MAX,
}
#[repr(u128)]
pub enum U128 {
// @is "$.index[*][?(@.name=='U128Min')].inner.variant_inner.value" '"0"'
// @is "$.index[*][?(@.name=='U128Min')].inner.variant_inner.expr" '"u128::MIN"'
// @is "$.index[*][?(@.name=='U128Min')].inner.discriminant.value" '"0"'
// @is "$.index[*][?(@.name=='U128Min')].inner.discriminant.expr" '"u128::MIN"'
U128Min = u128::MIN,
// @is "$.index[*][?(@.name=='U128Max')].inner.variant_inner.value" '"340282366920938463463374607431768211455"'
// @is "$.index[*][?(@.name=='U128Max')].inner.variant_inner.expr" '"u128::MAX"'
// @is "$.index[*][?(@.name=='U128Max')].inner.discriminant.value" '"340282366920938463463374607431768211455"'
// @is "$.index[*][?(@.name=='U128Max')].inner.discriminant.expr" '"u128::MAX"'
U128Max = u128::MAX,
}
#[repr(i128)]
pub enum I128 {
// @is "$.index[*][?(@.name=='I128Min')].inner.variant_inner.value" '"-170141183460469231731687303715884105728"'
// @is "$.index[*][?(@.name=='I128Min')].inner.variant_inner.expr" '"i128::MIN"'
// @is "$.index[*][?(@.name=='I128Min')].inner.discriminant.value" '"-170141183460469231731687303715884105728"'
// @is "$.index[*][?(@.name=='I128Min')].inner.discriminant.expr" '"i128::MIN"'
I128Min = i128::MIN,
// @is "$.index[*][?(@.name=='I128Max')].inner.variant_inner.value" '"170141183460469231731687303715884105727"'
// @is "$.index[*][?(@.name=='I128Max')].inner.variant_inner.expr" '"i128::MAX"'
// @is "$.index[*][?(@.name=='I128Max')].inner.discriminant.value" '"170141183460469231731687303715884105727"'
// @is "$.index[*][?(@.name=='I128Max')].inner.discriminant.expr" '"i128::MAX"'
I128Max = i128::MAX,
}

View File

@ -1,15 +1,15 @@
#[repr(u32)]
pub enum Foo {
// @is "$.index[*][?(@.name=='Basic')].inner.variant_inner.value" '"0"'
// @is "$.index[*][?(@.name=='Basic')].inner.variant_inner.expr" '"0"'
// @is "$.index[*][?(@.name=='Basic')].inner.discriminant.value" '"0"'
// @is "$.index[*][?(@.name=='Basic')].inner.discriminant.expr" '"0"'
Basic = 0,
// @is "$.index[*][?(@.name=='Suffix')].inner.variant_inner.value" '"10"'
// @is "$.index[*][?(@.name=='Suffix')].inner.variant_inner.expr" '"10u32"'
// @is "$.index[*][?(@.name=='Suffix')].inner.discriminant.value" '"10"'
// @is "$.index[*][?(@.name=='Suffix')].inner.discriminant.expr" '"10u32"'
Suffix = 10u32,
// @is "$.index[*][?(@.name=='Underscore')].inner.variant_inner.value" '"100"'
// @is "$.index[*][?(@.name=='Underscore')].inner.variant_inner.expr" '"1_0_0"'
// @is "$.index[*][?(@.name=='Underscore')].inner.discriminant.value" '"100"'
// @is "$.index[*][?(@.name=='Underscore')].inner.discriminant.expr" '"1_0_0"'
Underscore = 1_0_0,
// @is "$.index[*][?(@.name=='SuffixUnderscore')].inner.variant_inner.value" '"1000"'
// @is "$.index[*][?(@.name=='SuffixUnderscore')].inner.variant_inner.expr" '"1_0_0_0u32"'
// @is "$.index[*][?(@.name=='SuffixUnderscore')].inner.discriminant.value" '"1000"'
// @is "$.index[*][?(@.name=='SuffixUnderscore')].inner.discriminant.expr" '"1_0_0_0u32"'
SuffixUnderscore = 1_0_0_0u32,
}

View File

@ -1,10 +1,10 @@
pub enum Foo {
// @is "$.index[*][?(@.name=='Has')].inner.variant_inner" '{"expr":"0", "value":"0"}'
// @is "$.index[*][?(@.name=='Has')].inner.discriminant" '{"expr":"0", "value":"0"}'
Has = 0,
// @is "$.index[*][?(@.name=='Doesnt')].inner.variant_inner" null
// @is "$.index[*][?(@.name=='Doesnt')].inner.discriminant" null
Doesnt,
// @is "$.index[*][?(@.name=='AlsoDoesnt')].inner.variant_inner" null
// @is "$.index[*][?(@.name=='AlsoDoesnt')].inner.discriminant" null
AlsoDoesnt,
// @is "$.index[*][?(@.name=='AlsoHas')].inner.variant_inner" '{"expr":"44", "value":"44"}'
// @is "$.index[*][?(@.name=='AlsoHas')].inner.discriminant" '{"expr":"44", "value":"44"}'
AlsoHas = 44,
}

View File

@ -0,0 +1,15 @@
// ignore-tidy-linelength
#[repr(i32)]
// @is "$.index[*][?(@.name=='Foo')].attrs" '["#[repr(i32)]"]'
pub enum Foo {
// @is "$.index[*][?(@.name=='Struct')].inner.discriminant" null
// @count "$.index[*][?(@.name=='Struct')].inner.kind.struct.fields[*]" 0
Struct {},
// @is "$.index[*][?(@.name=='StructWithDiscr')].inner.discriminant" '{"expr": "42", "value": "42"}'
// @count "$.index[*][?(@.name=='StructWithDiscr')].inner.kind.struct.fields[*]" 1
StructWithDiscr { x: i32 } = 42,
// @is "$.index[*][?(@.name=='StructWithHexDiscr')].inner.discriminant" '{"expr": "0x42", "value": "66"}'
// @count "$.index[*][?(@.name=='StructWithHexDiscr')].inner.kind.struct.fields[*]" 2
StructWithHexDiscr { x: i32, y: bool } = 0x42,
}

View File

@ -0,0 +1,15 @@
// ignore-tidy-linelength
#[repr(u32)]
// @is "$.index[*][?(@.name=='Foo')].attrs" '["#[repr(u32)]"]'
pub enum Foo {
// @is "$.index[*][?(@.name=='Tuple')].inner.discriminant" null
// @count "$.index[*][?(@.name=='Tuple')].inner.kind.tuple[*]" 0
Tuple(),
// @is "$.index[*][?(@.name=='TupleWithDiscr')].inner.discriminant" '{"expr": "1", "value": "1"}'
// @count "$.index[*][?(@.name=='TupleWithDiscr')].inner.kind.tuple[*]" 1
TupleWithDiscr(i32) = 1,
// @is "$.index[*][?(@.name=='TupleWithBinDiscr')].inner.discriminant" '{"expr": "0b10", "value": "2"}'
// @count "$.index[*][?(@.name=='TupleWithBinDiscr')].inner.kind.tuple[*]" 2
TupleWithBinDiscr(i32, i32) = 0b10,
}

View File

@ -5,8 +5,8 @@
// @has "$.index[*][?(@.name=='ParseError')]"
// @has "$.index[*][?(@.name=='UnexpectedEndTag')]"
// @is "$.index[*][?(@.name=='UnexpectedEndTag')].inner.variant_kind" '"tuple"'
// @is "$.index[*][?(@.name=='UnexpectedEndTag')].inner.variant_inner" [null]
// @is "$.index[*][?(@.name=='UnexpectedEndTag')].inner.kind.tuple" [null]
// @is "$.index[*][?(@.name=='UnexpectedEndTag')].inner.discriminant" null
pub enum ParseError {
UnexpectedEndTag(#[doc(hidden)] u32),

View File

@ -5,27 +5,22 @@
pub enum Foo {
// @set Unit = "$.index[*][?(@.name=='Unit')].id"
// @is "$.index[*][?(@.name=='Unit')].inner.variant_kind" '"plain"'
// @is "$.index[*][?(@.name=='Unit')].inner.variant_inner" null
// @is "$.index[*][?(@.name=='Unit')].inner.kind" '"plain"'
Unit,
// @set Named = "$.index[*][?(@.name=='Named')].id"
// @is "$.index[*][?(@.name=='Named')].inner.variant_kind" '"struct"'
// @is "$.index[*][?(@.name=='Named')].inner.variant_inner" '{"fields": [], "fields_stripped": false}'
// @is "$.index[*][?(@.name=='Named')].inner.kind.struct" '{"fields": [], "fields_stripped": false}'
Named {},
// @set Tuple = "$.index[*][?(@.name=='Tuple')].id"
// @is "$.index[*][?(@.name=='Tuple')].inner.variant_kind" '"tuple"'
// @is "$.index[*][?(@.name=='Tuple')].inner.variant_inner" []
// @is "$.index[*][?(@.name=='Tuple')].inner.kind.tuple" []
Tuple(),
// @set NamedField = "$.index[*][?(@.name=='NamedField')].id"
// @set x = "$.index[*][?(@.name=='x' && @.kind=='struct_field')].id"
// @is "$.index[*][?(@.name=='NamedField')].inner.variant_kind" '"struct"'
// @is "$.index[*][?(@.name=='NamedField')].inner.variant_inner.fields[*]" $x
// @is "$.index[*][?(@.name=='NamedField')].inner.variant_inner.fields_stripped" false
// @is "$.index[*][?(@.name=='NamedField')].inner.kind.struct.fields[*]" $x
// @is "$.index[*][?(@.name=='NamedField')].inner.kind.struct.fields_stripped" false
NamedField { x: i32 },
// @set TupleField = "$.index[*][?(@.name=='TupleField')].id"
// @is "$.index[*][?(@.name=='TupleField')].inner.variant_kind" '"tuple"'
// @set tup_field = "$.index[*][?(@.name=='0' && @.kind=='struct_field')].id"
// @is "$.index[*][?(@.name=='TupleField')].inner.variant_inner[*]" $tup_field
// @is "$.index[*][?(@.name=='TupleField')].inner.kind.tuple[*]" $tup_field
TupleField(i32),
}

View File

@ -9,9 +9,8 @@ pub enum Foo {
// @set y = "$.index[*][?(@.name=='y')].id"
y: i32,
},
// @is "$.index[*][?(@.name=='Variant')].inner.variant_kind" '"struct"'
// @is "$.index[*][?(@.name=='Variant')].inner.variant_inner.fields_stripped" true
// @is "$.index[*][?(@.name=='Variant')].inner.variant_inner.fields[0]" $b
// @is "$.index[*][?(@.name=='Variant')].inner.variant_inner.fields[1]" $y
// @count "$.index[*][?(@.name=='Variant')].inner.variant_inner.fields[*]" 2
// @is "$.index[*][?(@.name=='Variant')].inner.kind.struct.fields_stripped" true
// @is "$.index[*][?(@.name=='Variant')].inner.kind.struct.fields[0]" $b
// @is "$.index[*][?(@.name=='Variant')].inner.kind.struct.fields[1]" $y
// @count "$.index[*][?(@.name=='Variant')].inner.kind.struct.fields[*]" 2
}

View File

@ -14,61 +14,50 @@
// @set 3.3.1 = "$.index[*][?(@.docs=='3.3.1')].id"
pub enum EnumWithStrippedTupleVariants {
// @is "$.index[*][?(@.name=='None')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='None')].inner.variant_inner[*]" 0
// @count "$.index[*][?(@.name=='None')].inner.kind.tuple[*]" 0
None(),
// @is "$.index[*][?(@.name=='One')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='One')].inner.variant_inner[*]" 1
// @is "$.index[*][?(@.name=='One')].inner.variant_inner[0]" $1.1.0
// @count "$.index[*][?(@.name=='One')].inner.kind.tuple[*]" 1
// @is "$.index[*][?(@.name=='One')].inner.kind.tuple[0]" $1.1.0
One(/** 1.1.0*/ bool),
// @is "$.index[*][?(@.name=='OneHidden')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='OneHidden')].inner.variant_inner[*]" 1
// @is "$.index[*][?(@.name=='OneHidden')].inner.variant_inner[0]" null
// @count "$.index[*][?(@.name=='OneHidden')].inner.kind.tuple[*]" 1
// @is "$.index[*][?(@.name=='OneHidden')].inner.kind.tuple[0]" null
OneHidden(#[doc(hidden)] bool),
// @is "$.index[*][?(@.name=='Two')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='Two')].inner.variant_inner[*]" 2
// @is "$.index[*][?(@.name=='Two')].inner.variant_inner[0]" $2.1.0
// @is "$.index[*][?(@.name=='Two')].inner.variant_inner[1]" $2.1.1
// @count "$.index[*][?(@.name=='Two')].inner.kind.tuple[*]" 2
// @is "$.index[*][?(@.name=='Two')].inner.kind.tuple[0]" $2.1.0
// @is "$.index[*][?(@.name=='Two')].inner.kind.tuple[1]" $2.1.1
Two(/** 2.1.0*/ bool, /** 2.1.1*/ bool),
// @is "$.index[*][?(@.name=='TwoLeftHidden')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='TwoLeftHidden')].inner.variant_inner[*]" 2
// @is "$.index[*][?(@.name=='TwoLeftHidden')].inner.variant_inner[0]" null
// @is "$.index[*][?(@.name=='TwoLeftHidden')].inner.variant_inner[1]" $2.2.1
// @count "$.index[*][?(@.name=='TwoLeftHidden')].inner.kind.tuple[*]" 2
// @is "$.index[*][?(@.name=='TwoLeftHidden')].inner.kind.tuple[0]" null
// @is "$.index[*][?(@.name=='TwoLeftHidden')].inner.kind.tuple[1]" $2.2.1
TwoLeftHidden(#[doc(hidden)] bool, /** 2.2.1*/ bool),
// @is "$.index[*][?(@.name=='TwoRightHidden')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='TwoRightHidden')].inner.variant_inner[*]" 2
// @is "$.index[*][?(@.name=='TwoRightHidden')].inner.variant_inner[0]" $2.3.0
// @is "$.index[*][?(@.name=='TwoRightHidden')].inner.variant_inner[1]" null
// @count "$.index[*][?(@.name=='TwoRightHidden')].inner.kind.tuple[*]" 2
// @is "$.index[*][?(@.name=='TwoRightHidden')].inner.kind.tuple[0]" $2.3.0
// @is "$.index[*][?(@.name=='TwoRightHidden')].inner.kind.tuple[1]" null
TwoRightHidden(/** 2.3.0*/ bool, #[doc(hidden)] bool),
// @is "$.index[*][?(@.name=='TwoBothHidden')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='TwoBothHidden')].inner.variant_inner[*]" 2
// @is "$.index[*][?(@.name=='TwoBothHidden')].inner.variant_inner[0]" null
// @is "$.index[*][?(@.name=='TwoBothHidden')].inner.variant_inner[1]" null
// @count "$.index[*][?(@.name=='TwoBothHidden')].inner.kind.tuple[*]" 2
// @is "$.index[*][?(@.name=='TwoBothHidden')].inner.kind.tuple[0]" null
// @is "$.index[*][?(@.name=='TwoBothHidden')].inner.kind.tuple[1]" null
TwoBothHidden(#[doc(hidden)] bool, #[doc(hidden)] bool),
// @is "$.index[*][?(@.name=='Three1')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='Three1')].inner.variant_inner[*]" 3
// @is "$.index[*][?(@.name=='Three1')].inner.variant_inner[0]" null
// @is "$.index[*][?(@.name=='Three1')].inner.variant_inner[1]" $3.1.1
// @is "$.index[*][?(@.name=='Three1')].inner.variant_inner[2]" $3.1.2
// @count "$.index[*][?(@.name=='Three1')].inner.kind.tuple[*]" 3
// @is "$.index[*][?(@.name=='Three1')].inner.kind.tuple[0]" null
// @is "$.index[*][?(@.name=='Three1')].inner.kind.tuple[1]" $3.1.1
// @is "$.index[*][?(@.name=='Three1')].inner.kind.tuple[2]" $3.1.2
Three1(#[doc(hidden)] bool, /** 3.1.1*/ bool, /** 3.1.2*/ bool),
// @is "$.index[*][?(@.name=='Three2')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='Three2')].inner.variant_inner[*]" 3
// @is "$.index[*][?(@.name=='Three2')].inner.variant_inner[0]" $3.2.0
// @is "$.index[*][?(@.name=='Three2')].inner.variant_inner[1]" null
// @is "$.index[*][?(@.name=='Three2')].inner.variant_inner[2]" $3.2.2
// @count "$.index[*][?(@.name=='Three2')].inner.kind.tuple[*]" 3
// @is "$.index[*][?(@.name=='Three2')].inner.kind.tuple[0]" $3.2.0
// @is "$.index[*][?(@.name=='Three2')].inner.kind.tuple[1]" null
// @is "$.index[*][?(@.name=='Three2')].inner.kind.tuple[2]" $3.2.2
Three2(/** 3.2.0*/ bool, #[doc(hidden)] bool, /** 3.2.2*/ bool),
// @is "$.index[*][?(@.name=='Three3')].inner.variant_kind" '"tuple"'
// @count "$.index[*][?(@.name=='Three3')].inner.variant_inner[*]" 3
// @is "$.index[*][?(@.name=='Three3')].inner.variant_inner[0]" $3.3.0
// @is "$.index[*][?(@.name=='Three3')].inner.variant_inner[1]" $3.3.1
// @is "$.index[*][?(@.name=='Three3')].inner.variant_inner[2]" null
// @count "$.index[*][?(@.name=='Three3')].inner.kind.tuple[*]" 3
// @is "$.index[*][?(@.name=='Three3')].inner.kind.tuple[0]" $3.3.0
// @is "$.index[*][?(@.name=='Three3')].inner.kind.tuple[1]" $3.3.1
// @is "$.index[*][?(@.name=='Three3')].inner.kind.tuple[2]" null
Three3(/** 3.3.0*/ bool, /** 3.3.1*/ bool, #[doc(hidden)] bool),
}
// @is "$.index[*][?(@.docs=='1.1.0')].name" '"0"'
// @is "$.index[*][?(@.docs=='2.1.0')].name" '"0"'
// @is "$.index[*][?(@.docs=='2.1.1')].name" '"1"'

View File

@ -1,11 +1,10 @@
// @is "$.index[*][?(@.name=='EnumStruct')].visibility" \"public\"
// @is "$.index[*][?(@.name=='EnumStruct')].kind" \"enum\"
pub enum EnumStruct {
// @is "$.index[*][?(@.name=='VariantS')].inner.variant_kind" \"struct\"
// @is "$.index[*][?(@.name=='x')].kind" \"struct_field\"
// @set x = "$.index[*][?(@.name=='x')].id"
// @is "$.index[*][?(@.name=='y')].kind" \"struct_field\"
VariantS {
x: u32,
y: String,
},
// @set y = "$.index[*][?(@.name=='y')].id"
// @ismany "$.index[*][?(@.name=='VariantS')].inner.kind.struct.fields[*]" $x $y
VariantS { x: u32, y: String },
}

View File

@ -1,8 +1,10 @@
// @is "$.index[*][?(@.name=='EnumTupleStruct')].visibility" \"public\"
// @is "$.index[*][?(@.name=='EnumTupleStruct')].kind" \"enum\"
pub enum EnumTupleStruct {
// @is "$.index[*][?(@.name=='VariantA')].inner.variant_kind" \"tuple\"
// @is "$.index[*][?(@.name=='0')].kind" \"struct_field\"
// @set f0 = "$.index[*][?(@.name=='0')].id"
// @is "$.index[*][?(@.name=='1')].kind" \"struct_field\"
// @set f1 = "$.index[*][?(@.name=='1')].id"
// @ismany "$.index[*][?(@.name=='VariantA')].inner.kind.tuple[*]" $f0 $f1
VariantA(u32, String),
}

View File

@ -5,7 +5,7 @@ use rustdoc_json_types::{
Constant, Crate, DynTrait, Enum, FnDecl, Function, FunctionPointer, GenericArg, GenericArgs,
GenericBound, GenericParamDef, Generics, Id, Impl, Import, ItemEnum, Module, OpaqueTy, Path,
Primitive, ProcMacro, Static, Struct, StructKind, Term, Trait, TraitAlias, Type, TypeBinding,
TypeBindingKind, Typedef, Union, Variant, WherePredicate,
TypeBindingKind, Typedef, Union, Variant, VariantKind, WherePredicate,
};
use crate::{item_kind::Kind, Error, ErrorKind};
@ -140,24 +140,24 @@ impl<'a> Validator<'a> {
}
fn check_variant(&mut self, x: &'a Variant, id: &'a Id) {
match x {
Variant::Plain(discr) => {
if let Some(discr) = discr {
if let (Err(_), Err(_)) =
(discr.value.parse::<i128>(), discr.value.parse::<u128>())
{
self.fail(
id,
ErrorKind::Custom(format!(
"Failed to parse discriminant value `{}`",
discr.value
)),
);
}
}
let Variant { kind, discriminant } = x;
if let Some(discr) = discriminant {
if let (Err(_), Err(_)) = (discr.value.parse::<i128>(), discr.value.parse::<u128>()) {
self.fail(
id,
ErrorKind::Custom(format!(
"Failed to parse discriminant value `{}`",
discr.value
)),
);
}
Variant::Tuple(tys) => tys.iter().flatten().for_each(|t| self.add_field_id(t)),
Variant::Struct { fields, fields_stripped: _ } => {
}
match kind {
VariantKind::Plain => {}
VariantKind::Tuple(tys) => tys.iter().flatten().for_each(|t| self.add_field_id(t)),
VariantKind::Struct { fields, fields_stripped: _ } => {
fields.iter().for_each(|f| self.add_field_id(f))
}
}