提交 7b590893 编写于 作者: G Guillaume Gomez

Split clean::Constant enum into a struct and an enum

上级 ee509337
...@@ -500,7 +500,10 @@ fn build_module( ...@@ -500,7 +500,10 @@ fn build_module(
} }
fn build_const(cx: &mut DocContext<'_>, def_id: DefId) -> clean::Constant { fn build_const(cx: &mut DocContext<'_>, def_id: DefId) -> clean::Constant {
clean::Constant::Extern { type_: cx.tcx.type_of(def_id).clean(cx), def_id } clean::Constant {
type_: cx.tcx.type_of(def_id).clean(cx),
kind: clean::ConstantKind::Extern { def_id },
}
} }
fn build_static(cx: &mut DocContext<'_>, did: DefId, mutable: bool) -> clean::Static { fn build_static(cx: &mut DocContext<'_>, did: DefId, mutable: bool) -> clean::Static {
......
...@@ -393,12 +393,12 @@ fn clean(&self, _: &mut DocContext<'_>) -> Lifetime { ...@@ -393,12 +393,12 @@ fn clean(&self, _: &mut DocContext<'_>) -> Lifetime {
impl Clean<Constant> for hir::ConstArg { impl Clean<Constant> for hir::ConstArg {
fn clean(&self, cx: &mut DocContext<'_>) -> Constant { fn clean(&self, cx: &mut DocContext<'_>) -> Constant {
Constant::Anonymous { Constant {
type_: cx type_: cx
.tcx .tcx
.type_of(cx.tcx.hir().body_owner_def_id(self.value.body).to_def_id()) .type_of(cx.tcx.hir().body_owner_def_id(self.value.body).to_def_id())
.clean(cx), .clean(cx),
body: self.value.body, kind: ConstantKind::Anonymous { body: self.value.body },
} }
} }
} }
...@@ -1744,7 +1744,10 @@ fn clean(&self, cx: &mut DocContext<'_>) -> Type { ...@@ -1744,7 +1744,10 @@ fn clean(&self, cx: &mut DocContext<'_>) -> Type {
impl<'tcx> Clean<Constant> for ty::Const<'tcx> { impl<'tcx> Clean<Constant> for ty::Const<'tcx> {
fn clean(&self, cx: &mut DocContext<'_>) -> Constant { fn clean(&self, cx: &mut DocContext<'_>) -> Constant {
// FIXME: instead of storing the stringified expression, store `self` directly instead. // FIXME: instead of storing the stringified expression, store `self` directly instead.
Constant::TyConst { type_: self.ty.clean(cx), expr: self.to_string() } Constant {
type_: self.ty.clean(cx),
kind: ConstantKind::TyConst { expr: self.to_string() },
}
} }
} }
...@@ -1945,9 +1948,10 @@ fn clean(&self, cx: &mut DocContext<'_>) -> Vec<Item> { ...@@ -1945,9 +1948,10 @@ fn clean(&self, cx: &mut DocContext<'_>) -> Vec<Item> {
ItemKind::Static(ty, mutability, body_id) => { ItemKind::Static(ty, mutability, body_id) => {
StaticItem(Static { type_: ty.clean(cx), mutability, expr: Some(body_id) }) StaticItem(Static { type_: ty.clean(cx), mutability, expr: Some(body_id) })
} }
ItemKind::Const(ty, body_id) => { ItemKind::Const(ty, body_id) => ConstantItem(Constant {
ConstantItem(Constant::Local { type_: ty.clean(cx), body: body_id, def_id }) type_: ty.clean(cx),
} kind: ConstantKind::Local { body: body_id, def_id },
}),
ItemKind::OpaqueTy(ref ty) => OpaqueTyItem(OpaqueTy { ItemKind::OpaqueTy(ref ty) => OpaqueTyItem(OpaqueTy {
bounds: ty.bounds.clean(cx), bounds: ty.bounds.clean(cx),
generics: ty.generics.clean(cx), generics: ty.generics.clean(cx),
......
...@@ -1987,67 +1987,60 @@ fn def_id_full(&self, cache: &Cache) -> Option<DefId> { ...@@ -1987,67 +1987,60 @@ fn def_id_full(&self, cache: &Cache) -> Option<DefId> {
} }
#[derive(Clone, PartialEq, Eq, Hash, Debug)] #[derive(Clone, PartialEq, Eq, Hash, Debug)]
crate enum Constant { crate struct Constant {
crate type_: Type,
crate kind: ConstantKind,
}
#[derive(Clone, PartialEq, Eq, Hash, Debug)]
crate enum ConstantKind {
/// This is the wrapper around `ty::Const` for a non-local constant. Because it doesn't have a /// This is the wrapper around `ty::Const` for a non-local constant. Because it doesn't have a
/// `BodyId`, we need to handle it on its own. /// `BodyId`, we need to handle it on its own.
TyConst { type_: Type, expr: String }, ///
/// A constant (expression) that’s not an item or associated item. These are usually found /// Note that `ty::Const` includes generic parameters, and may not always be uniquely identified
/// by a DefId. So this field must be different from `Extern`.
TyConst { expr: String },
/// A constant (expression) that's not an item or associated item. These are usually found
/// nested inside types (e.g., array lengths) or expressions (e.g., repeat counts), and also /// nested inside types (e.g., array lengths) or expressions (e.g., repeat counts), and also
/// used to define explicit discriminant values for enum variants. /// used to define explicit discriminant values for enum variants.
Anonymous { type_: Type, body: BodyId }, Anonymous { body: BodyId },
/// A constant from a different crate. /// A constant from a different crate.
Extern { type_: Type, def_id: DefId }, Extern { def_id: DefId },
/// const FOO: u32 = ...; /// `const FOO: u32 = ...;`
Local { type_: Type, def_id: DefId, body: BodyId }, Local { def_id: DefId, body: BodyId },
} }
impl Constant { impl Constant {
crate fn expr(&self, tcx: TyCtxt<'_>) -> String { crate fn expr(&self, tcx: TyCtxt<'_>) -> String {
match self { match self.kind {
Self::TyConst { expr, .. } => expr.clone(), ConstantKind::TyConst { ref expr } => expr.clone(),
Self::Extern { def_id, .. } => print_inlined_const(tcx, *def_id), ConstantKind::Extern { def_id } => print_inlined_const(tcx, def_id),
Self::Local { body, .. } | Self::Anonymous { body, .. } => print_const_expr(tcx, *body), ConstantKind::Local { body, .. } | ConstantKind::Anonymous { body } => {
print_const_expr(tcx, body)
}
} }
} }
crate fn value(&self, tcx: TyCtxt<'_>) -> Option<String> { crate fn value(&self, tcx: TyCtxt<'_>) -> Option<String> {
match self { match self.kind {
Self::TyConst { .. } | Self::Anonymous { .. } => None, ConstantKind::TyConst { .. } | ConstantKind::Anonymous { .. } => None,
Self::Extern { def_id, .. } | Self::Local { def_id, .. } => { ConstantKind::Extern { def_id } | ConstantKind::Local { def_id, .. } => {
print_evaluated_const(tcx, *def_id) print_evaluated_const(tcx, def_id)
} }
} }
} }
crate fn is_literal(&self, tcx: TyCtxt<'_>) -> bool { crate fn is_literal(&self, tcx: TyCtxt<'_>) -> bool {
match self { match self.kind {
Self::TyConst { .. } => false, ConstantKind::TyConst { .. } => false,
Self::Extern { def_id, .. } => def_id.as_local().map_or(false, |def_id| { ConstantKind::Extern { def_id } => def_id.as_local().map_or(false, |def_id| {
is_literal_expr(tcx, tcx.hir().local_def_id_to_hir_id(def_id)) is_literal_expr(tcx, tcx.hir().local_def_id_to_hir_id(def_id))
}), }),
Self::Local { body, .. } | Self::Anonymous { body, .. } => { ConstantKind::Local { body, .. } | ConstantKind::Anonymous { body } => {
is_literal_expr(tcx, body.hir_id) is_literal_expr(tcx, body.hir_id)
} }
} }
} }
crate fn type_(&self) -> &Type {
match *self {
Self::TyConst { ref type_, .. }
| Self::Extern { ref type_, .. }
| Self::Local { ref type_, .. }
| Self::Anonymous { ref type_, .. } => type_,
}
}
crate fn to_type(self) -> Type {
match self {
Self::TyConst { type_, .. }
| Self::Extern { type_, .. }
| Self::Local { type_, .. }
| Self::Anonymous { type_, .. } => type_,
}
}
} }
#[derive(Clone, Debug)] #[derive(Clone, Debug)]
......
...@@ -982,7 +982,7 @@ fn item_constant(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, c: &clean:: ...@@ -982,7 +982,7 @@ fn item_constant(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, c: &clean::
"{vis}const {name}: {typ}", "{vis}const {name}: {typ}",
vis = it.visibility.print_with_space(cx.tcx(), it.def_id, cx.cache()), vis = it.visibility.print_with_space(cx.tcx(), it.def_id, cx.cache()),
name = it.name.as_ref().unwrap(), name = it.name.as_ref().unwrap(),
typ = c.type_().print(cx.cache(), cx.tcx()), typ = c.type_.print(cx.cache(), cx.tcx()),
); );
let value = c.value(cx.tcx()); let value = c.value(cx.tcx());
......
...@@ -142,7 +142,7 @@ fn from_tcx(constant: clean::Constant, tcx: TyCtxt<'_>) -> Self { ...@@ -142,7 +142,7 @@ fn from_tcx(constant: clean::Constant, tcx: TyCtxt<'_>) -> Self {
let expr = constant.expr(tcx); let expr = constant.expr(tcx);
let value = constant.value(tcx); let value = constant.value(tcx);
let is_literal = constant.is_literal(tcx); let is_literal = constant.is_literal(tcx);
Constant { type_: constant.to_type().into_tcx(tcx), expr, value, is_literal } Constant { type_: constant.type_.into_tcx(tcx), expr, value, is_literal }
} }
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册