1
Fork 0

Fix rustdoc for GATs with with anonymous bound regions

This commit is contained in:
Michael Goulet 2022-03-06 15:56:29 -08:00
parent c38b8a8c62
commit 890a44f66b
3 changed files with 40 additions and 35 deletions

View file

@ -402,16 +402,7 @@ fn projection_to_path_segment(ty: ty::ProjectionTy<'_>, cx: &mut DocContext<'_>)
PathSegment { PathSegment {
name: item.name, name: item.name,
args: GenericArgs::AngleBracketed { args: GenericArgs::AngleBracketed {
args: ty.substs[generics.parent_count..] args: substs_to_args(cx, &ty.substs[generics.parent_count..], false),
.iter()
.map(|ty| match ty.unpack() {
ty::subst::GenericArgKind::Lifetime(lt) => {
GenericArg::Lifetime(lt.clean(cx).unwrap())
}
ty::subst::GenericArgKind::Type(ty) => GenericArg::Type(ty.clean(cx)),
ty::subst::GenericArgKind::Const(c) => GenericArg::Const(Box::new(c.clean(cx))),
})
.collect(),
bindings: Default::default(), bindings: Default::default(),
}, },
} }
@ -1379,11 +1370,7 @@ fn maybe_expand_private_type_alias(cx: &mut DocContext<'_>, path: &hir::Path<'_>
}); });
if let Some(lt) = lifetime.cloned() { if let Some(lt) = lifetime.cloned() {
let lt_def_id = cx.tcx.hir().local_def_id(param.hir_id); let lt_def_id = cx.tcx.hir().local_def_id(param.hir_id);
let cleaned = if !lt.is_elided() { let cleaned = if !lt.is_elided() { lt.clean(cx) } else { Lifetime::elided() };
lt.clean(cx)
} else {
self::types::Lifetime::elided()
};
substs.insert(lt_def_id.to_def_id(), SubstParam::Lifetime(cleaned)); substs.insert(lt_def_id.to_def_id(), SubstParam::Lifetime(cleaned));
} }
indices.lifetimes += 1; indices.lifetimes += 1;

View file

@ -77,16 +77,12 @@ crate fn krate(cx: &mut DocContext<'_>) -> Crate {
Crate { module, primitives, external_traits: cx.external_traits.clone() } Crate { module, primitives, external_traits: cx.external_traits.clone() }
} }
fn external_generic_args( crate fn substs_to_args(
cx: &mut DocContext<'_>, cx: &mut DocContext<'_>,
did: DefId, substs: &[ty::subst::GenericArg<'_>],
has_self: bool, mut skip_first: bool,
bindings: Vec<TypeBinding>, ) -> Vec<GenericArg> {
substs: SubstsRef<'_>, substs
) -> GenericArgs {
let mut skip_self = has_self;
let mut ty_kind = None;
let args: Vec<_> = substs
.iter() .iter()
.filter_map(|kind| match kind.unpack() { .filter_map(|kind| match kind.unpack() {
GenericArgKind::Lifetime(lt) => match *lt { GenericArgKind::Lifetime(lt) => match *lt {
@ -95,23 +91,32 @@ fn external_generic_args(
} }
_ => lt.clean(cx).map(GenericArg::Lifetime), _ => lt.clean(cx).map(GenericArg::Lifetime),
}, },
GenericArgKind::Type(_) if skip_self => { GenericArgKind::Type(_) if skip_first => {
skip_self = false; skip_first = false;
None None
} }
GenericArgKind::Type(ty) => { GenericArgKind::Type(ty) => Some(GenericArg::Type(ty.clean(cx))),
ty_kind = Some(ty.kind());
Some(GenericArg::Type(ty.clean(cx)))
}
GenericArgKind::Const(ct) => Some(GenericArg::Const(Box::new(ct.clean(cx)))), GenericArgKind::Const(ct) => Some(GenericArg::Const(Box::new(ct.clean(cx)))),
}) })
.collect(); .collect()
}
fn external_generic_args(
cx: &mut DocContext<'_>,
did: DefId,
has_self: bool,
bindings: Vec<TypeBinding>,
substs: SubstsRef<'_>,
) -> GenericArgs {
let args = substs_to_args(cx, &substs, has_self);
if cx.tcx.fn_trait_kind_from_lang_item(did).is_some() { if cx.tcx.fn_trait_kind_from_lang_item(did).is_some() {
let inputs = match ty_kind.unwrap() { let inputs =
ty::Tuple(tys) => tys.iter().map(|t| t.clean(cx)).collect(), // The trait's first substitution is the one after self, if there is one.
_ => return GenericArgs::AngleBracketed { args, bindings: bindings.into() }, match substs.iter().nth(if has_self { 1 } else { 0 }).unwrap().expect_ty().kind() {
}; ty::Tuple(tys) => tys.iter().map(|t| t.clean(cx)).collect(),
_ => return GenericArgs::AngleBracketed { args, bindings: bindings.into() },
};
let output = None; let output = None;
// FIXME(#20299) return type comes from a projection now // FIXME(#20299) return type comes from a projection now
// match types[1].kind { // match types[1].kind {

View file

@ -0,0 +1,13 @@
#![crate_name = "foo"]
#![feature(generic_associated_types)]
pub trait Trait {
type Gat<'a>;
}
// Make sure that the elided lifetime shows up
// @has foo/type.T.html
// @has - "pub type T = "
// @has - "&lt;'_&gt;"
pub type T = fn(&<() as Trait>::Gat<'_>);