Skip to content

Commit

Permalink
Rollup merge of rust-lang#103190 - fmease:rustdoc-render-bounds-of-cr…
Browse files Browse the repository at this point in the history
…oss-crate-gat-params, r=GuillaumeGomez

rustdoc: render bounds of cross-crate GAT params

Follow-up to rust-lang#102439.
Render the trait bounds of type parameters of cross-crate (generic) associated types.

`@rustbot` label T-rustdoc A-cross-crate-reexports
r? `@GuillaumeGomez`
  • Loading branch information
matthiaskrgr authored Oct 20, 2022
2 parents dd348af + 2cc4a0a commit 38c5239
Show file tree
Hide file tree
Showing 7 changed files with 41 additions and 22 deletions.
44 changes: 30 additions & 14 deletions src/librustdoc/clean/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1201,21 +1201,19 @@ pub(crate) fn clean_middle_assoc_item<'tcx>(
}

if let ty::TraitContainer = assoc_item.container {
// FIXME(fmease): `tcx.explicit_item_bounds` does not contain the bounds of GATs,
// e.g. the bounds `Copy`, `Display` & (implicitly) `Sized` in
// `type Assoc<T: Copy> where T: Display`. This also means that we
// later incorrectly render `where T: ?Sized`.
//
// The result of `tcx.explicit_predicates_of` *does* contain them but
// it does not contain the other bounds / predicates we need.
// Either merge those two interned lists somehow or refactor
// `clean_ty_generics` to call `explicit_item_bounds` by itself.
let bounds = tcx.explicit_item_bounds(assoc_item.def_id);
let predicates = ty::GenericPredicates { parent: None, predicates: bounds };
let mut generics =
clean_ty_generics(cx, tcx.generics_of(assoc_item.def_id), predicates);
// Filter out the bounds that are (likely?) directly attached to the associated type,
// as opposed to being located in the where clause.
let predicates = tcx.explicit_predicates_of(assoc_item.def_id).predicates;
let predicates =
tcx.arena.alloc_from_iter(bounds.into_iter().chain(predicates).copied());
let mut generics = clean_ty_generics(
cx,
tcx.generics_of(assoc_item.def_id),
ty::GenericPredicates { parent: None, predicates },
);
// Move bounds that are (likely) directly attached to the associated type
// from the where clause to the associated type.
// There is no guarantee that this is what the user actually wrote but we have
// no way of knowing.
let mut bounds = generics
.where_predicates
.drain_filter(|pred| match *pred {
Expand Down Expand Up @@ -1273,6 +1271,24 @@ pub(crate) fn clean_middle_assoc_item<'tcx>(
}
None => bounds.push(GenericBound::maybe_sized(cx)),
}
// Move bounds that are (likely) directly attached to the parameters of the
// (generic) associated type from the where clause to the respective parameter.
// There is no guarantee that this is what the user actually wrote but we have
// no way of knowing.
let mut where_predicates = Vec::new();
for mut pred in generics.where_predicates {
if let WherePredicate::BoundPredicate { ty: Generic(arg), bounds, .. } = &mut pred
&& let Some(GenericParamDef {
kind: GenericParamDefKind::Type { bounds: param_bounds, .. },
..
}) = generics.params.iter_mut().find(|param| &param.name == arg)
{
param_bounds.extend(mem::take(bounds));
} else {
where_predicates.push(pred);
}
}
generics.where_predicates = where_predicates;

if tcx.impl_defaultness(assoc_item.def_id).has_value() {
AssocTypeItem(
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<h4 class="code-header">type <a href="#associatedtype.Out0" class="associatedtype">Out0</a>: <a class="trait" href="../assoc_item_trait_bounds/trait.Support.html" title="trait assoc_item_trait_bounds::Support">Support</a>&lt;Item = <a class="primitive" href="{{channel}}/std/primitive.unit.html">()</a>&gt;</h4>
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<h4 class="code-header">type <a href="#associatedtype.Out2" class="associatedtype">Out2</a>&lt;T&gt;: <a class="trait" href="../assoc_item_trait_bounds/trait.Support.html" title="trait assoc_item_trait_bounds::Support">Support</a>&lt;Item = T&gt;</h4>
Original file line number Diff line number Diff line change
@@ -1,13 +1,10 @@
// Regression test for issues #77763, #84579 and #102142.
#![crate_name = "main"]

// aux-build:assoc_item_trait_bounds_with_bindings.rs
// aux-build:assoc_item_trait_bounds.rs
// build-aux-docs
// ignore-cross-compile
extern crate assoc_item_trait_bounds_with_bindings as aux;

// FIXME(fmease): Don't render an incorrect `T: ?Sized` where-clause for parameters
// of GATs like `Main::Out{2,4}`. Add a snapshot test once it's fixed.
extern crate assoc_item_trait_bounds as aux;

// @has main/trait.Main.html
// @has - '//*[@id="associatedtype.Out0"]' 'type Out0: Support<Item = ()>'
Expand All @@ -24,11 +21,15 @@ extern crate assoc_item_trait_bounds_with_bindings as aux;
// @has - '//*[@id="associatedtype.Out11"]' "type Out11: for<'r, 's> Helper<A<'s> = &'s (), B<'r> = ()>"
// @has - '//*[@id="associatedtype.Out12"]' "type Out12: for<'w> Helper<B<'w> = Cow<'w, str>, A<'w> = bool>"
// @has - '//*[@id="associatedtype.Out13"]' "type Out13: for<'fst, 'snd> Aid<'snd, Result<'fst> = &'fst mut str>"
// @has - '//*[@id="associatedtype.Out14"]' "type Out14<P: Copy + Eq, Q: ?Sized>"
//
// Snapshots: Check that we do not render any where-clauses for those associated types since all of
// the trait bounds contained within were moved to the bounds of the respective item.
// Snapshots:
// Check that we don't render any where-clauses for the following associated types since
// all corresponding projection equality predicates should have already been re-sugared
// to associated type bindings:
//
// @snapshot out0 - '//*[@id="associatedtype.Out0"]/*[@class="code-header"]'
// @snapshot out2 - '//*[@id="associatedtype.Out2"]/*[@class="code-header"]'
// @snapshot out9 - '//*[@id="associatedtype.Out9"]/*[@class="code-header"]'
//
// @has - '//*[@id="tymethod.make"]' \
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ pub trait Main {
type Out11: for<'r, 's> Helper<A<'s> = &'s (), B<'r> = ()>;
type Out12: for<'w> Helper<B<'w> = std::borrow::Cow<'w, str>, A<'w> = bool>;
type Out13: for<'fst, 'snd> Aid<'snd, Result<'fst> = &'fst mut str>;
type Out14<P: Copy + Eq, Q: ?Sized>;

fn make<F>(_: F, _: impl FnMut(&str) -> bool)
where
Expand Down

0 comments on commit 38c5239

Please sign in to comment.