rustdoc: Compute enum discriminant on demand

This commit is contained in:
Nixon Enraght-Moony 2022-09-04 12:53:25 +01:00
parent b76a012be1
commit efbd8f62ed
3 changed files with 28 additions and 24 deletions

View file

@ -1787,10 +1787,7 @@ pub(crate) fn clean_visibility(vis: ty::Visibility) -> Visibility {
pub(crate) fn clean_variant_def<'tcx>(variant: &ty::VariantDef, cx: &mut DocContext<'tcx>) -> Item {
let kind = match variant.ctor_kind {
CtorKind::Const => Variant::CLike(match variant.discr {
ty::VariantDiscr::Explicit(def_id) => Some(Discriminant {
expr: None,
value: print_evaluated_const(cx.tcx, def_id, false).unwrap(),
}),
ty::VariantDiscr::Explicit(def_id) => Some(Discriminant { expr: None, value: def_id }),
ty::VariantDiscr::Relative(_) => None,
}),
CtorKind::Fn => Variant::Tuple(
@ -1820,16 +1817,9 @@ fn clean_variant_data<'tcx>(
hir::VariantData::Tuple(..) => {
Variant::Tuple(variant.fields().iter().map(|x| clean_field(x, cx)).collect())
}
hir::VariantData::Unit(..) => Variant::CLike(disr_expr.map(|disr| {
Discriminant {
expr: Some(print_const_expr(cx.tcx, disr.body)),
value: print_evaluated_const(
cx.tcx,
cx.tcx.hir().local_def_id(disr.hir_id).to_def_id(),
false,
)
.unwrap(),
}
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(),
})),
}
}

View file

@ -2116,8 +2116,20 @@ impl Variant {
pub(crate) struct Discriminant {
// In the case of cross crate re-exports, we don't have the nessesary information
// to reconstruct the expression of the discriminant, only the value.
pub(crate) expr: Option<String>,
pub(crate) value: String,
pub(super) expr: Option<BodyId>,
pub(super) value: DefId,
}
impl Discriminant {
/// Will be `None` in the case of cross-crate reexports, and may be
/// simplified
pub(crate) fn expr(&self, tcx: TyCtxt<'_>) -> Option<String> {
self.expr.map(|body| print_const_expr(tcx, body))
}
/// Will always be a machine readable number, without underscores or suffixes.
pub(crate) fn value(&self, tcx: TyCtxt<'_>) -> String {
print_evaluated_const(tcx, self.value, false).unwrap()
}
}
/// Small wrapper around [`rustc_span::Span`] that adds helper methods

View file

@ -662,7 +662,7 @@ 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(convert_discriminant)),
CLike(disr) => Variant::Plain(disr.map(|disr| disr.into_tcx(tcx))),
Tuple(fields) => Variant::Tuple(
fields
.into_iter()
@ -678,13 +678,15 @@ impl FromWithTcx<clean::Variant> for Variant {
}
}
fn convert_discriminant(disr: clean::Discriminant) -> Discriminant {
Discriminant {
// expr is only none if going throught the inlineing path, which gets
// `rustc_middle` types, not `rustc_hir`, but because JSON never inlines
// the expr is always some.
expr: disr.expr.unwrap(),
value: disr.value,
impl FromWithTcx<clean::Discriminant> for Discriminant {
fn from_tcx(disr: clean::Discriminant, tcx: TyCtxt<'_>) -> Self {
Discriminant {
// expr is only none if going throught the inlineing path, which gets
// `rustc_middle` types, not `rustc_hir`, but because JSON never inlines
// the expr is always some.
expr: disr.expr(tcx).unwrap(),
value: disr.value(tcx),
}
}
}