Auto merge of #148059 - Zalathar:rollup-zkk5prm, r=Zalathar
Rollup of 5 pull requests Successful merges: - rust-lang/rust#148016 (Revert constification of `Borrow` and `Deref for Cow` due to inference failure) - rust-lang/rust#148021 ([rustdoc] Simplify module rendering and HTML tags handling) - rust-lang/rust#148039 (Add myself to the review rotation) - rust-lang/rust#148042 (test(frontmatter): Cover spaces between infostring parts) - rust-lang/rust#148054 (Streamline iterator chaining when computing successors.) r? `@ghost` `@rustbot` modify labels: rollup
This commit is contained in:
commit
75948c8bb3
7 changed files with 206 additions and 165 deletions
|
|
@ -501,6 +501,8 @@ pub use helper::*;
|
|||
|
||||
mod helper {
|
||||
use super::*;
|
||||
// Note: the methods below use a `slice.chain(Option).chain(Option)` pattern so that all paths
|
||||
// produce an iterator with the same concrete type.
|
||||
pub type Successors<'a> = impl DoubleEndedIterator<Item = BasicBlock> + 'a;
|
||||
|
||||
impl SwitchTargets {
|
||||
|
|
@ -510,7 +512,7 @@ mod helper {
|
|||
#[define_opaque(Successors)]
|
||||
pub fn successors_for_value(&self, value: u128) -> Successors<'_> {
|
||||
let target = self.target_for_value(value);
|
||||
(&[]).into_iter().copied().chain(Some(target).into_iter().chain(None))
|
||||
(&[]).into_iter().copied().chain(Some(target)).chain(None)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -522,10 +524,7 @@ mod helper {
|
|||
match *self {
|
||||
// 3-successors for async drop: target, unwind, dropline (parent coroutine drop)
|
||||
Drop { target: ref t, unwind: UnwindAction::Cleanup(u), drop: Some(d), .. } => {
|
||||
slice::from_ref(t)
|
||||
.into_iter()
|
||||
.copied()
|
||||
.chain(Some(u).into_iter().chain(Some(d)))
|
||||
slice::from_ref(t).into_iter().copied().chain(Some(u)).chain(Some(d))
|
||||
}
|
||||
// 2-successors
|
||||
Call { target: Some(ref t), unwind: UnwindAction::Cleanup(u), .. }
|
||||
|
|
@ -534,7 +533,7 @@ mod helper {
|
|||
| Drop { target: ref t, unwind: _, drop: Some(u), .. }
|
||||
| Assert { target: ref t, unwind: UnwindAction::Cleanup(u), .. }
|
||||
| FalseUnwind { real_target: ref t, unwind: UnwindAction::Cleanup(u) } => {
|
||||
slice::from_ref(t).into_iter().copied().chain(Some(u).into_iter().chain(None))
|
||||
slice::from_ref(t).into_iter().copied().chain(Some(u)).chain(None)
|
||||
}
|
||||
// single successor
|
||||
Goto { target: ref t }
|
||||
|
|
@ -544,7 +543,7 @@ mod helper {
|
|||
| Drop { target: ref t, unwind: _, .. }
|
||||
| Assert { target: ref t, unwind: _, .. }
|
||||
| FalseUnwind { real_target: ref t, unwind: _ } => {
|
||||
slice::from_ref(t).into_iter().copied().chain(None.into_iter().chain(None))
|
||||
slice::from_ref(t).into_iter().copied().chain(None).chain(None)
|
||||
}
|
||||
// No successors
|
||||
UnwindResume
|
||||
|
|
@ -554,23 +553,24 @@ mod helper {
|
|||
| Unreachable
|
||||
| TailCall { .. }
|
||||
| Call { target: None, unwind: _, .. } => {
|
||||
(&[]).into_iter().copied().chain(None.into_iter().chain(None))
|
||||
(&[]).into_iter().copied().chain(None).chain(None)
|
||||
}
|
||||
// Multiple successors
|
||||
InlineAsm { ref targets, unwind: UnwindAction::Cleanup(u), .. } => {
|
||||
targets.iter().copied().chain(Some(u).into_iter().chain(None))
|
||||
targets.iter().copied().chain(Some(u)).chain(None)
|
||||
}
|
||||
InlineAsm { ref targets, unwind: _, .. } => {
|
||||
targets.iter().copied().chain(None.into_iter().chain(None))
|
||||
targets.iter().copied().chain(None).chain(None)
|
||||
}
|
||||
SwitchInt { ref targets, .. } => {
|
||||
targets.targets.iter().copied().chain(None.into_iter().chain(None))
|
||||
targets.targets.iter().copied().chain(None).chain(None)
|
||||
}
|
||||
// FalseEdge
|
||||
FalseEdge { ref real_target, imaginary_target } => slice::from_ref(real_target)
|
||||
.into_iter()
|
||||
.copied()
|
||||
.chain(Some(imaginary_target).into_iter().chain(None)),
|
||||
.chain(Some(imaginary_target))
|
||||
.chain(None),
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -16,12 +16,13 @@ use crate::fmt;
|
|||
#[cfg(not(no_global_oom_handling))]
|
||||
use crate::string::String;
|
||||
|
||||
// FIXME(inference): const bounds removed due to inference regressions found by crater;
|
||||
// see https://github.com/rust-lang/rust/issues/147964
|
||||
// #[rustc_const_unstable(feature = "const_convert", issue = "143773")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[rustc_const_unstable(feature = "const_convert", issue = "143773")]
|
||||
impl<'a, B: ?Sized> const Borrow<B> for Cow<'a, B>
|
||||
where
|
||||
B: ToOwned,
|
||||
B::Owned: [const] Borrow<B>,
|
||||
impl<'a, B: ?Sized + ToOwned> Borrow<B> for Cow<'a, B>
|
||||
// where
|
||||
// B::Owned: [const] Borrow<B>,
|
||||
{
|
||||
fn borrow(&self) -> &B {
|
||||
&**self
|
||||
|
|
@ -327,11 +328,13 @@ impl<B: ?Sized + ToOwned> Cow<'_, B> {
|
|||
}
|
||||
}
|
||||
|
||||
// FIXME(inference): const bounds removed due to inference regressions found by crater;
|
||||
// see https://github.com/rust-lang/rust/issues/147964
|
||||
// #[rustc_const_unstable(feature = "const_convert", issue = "143773")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[rustc_const_unstable(feature = "const_convert", issue = "143773")]
|
||||
impl<B: ?Sized + ToOwned> const Deref for Cow<'_, B>
|
||||
where
|
||||
B::Owned: [const] Borrow<B>,
|
||||
impl<B: ?Sized + ToOwned> Deref for Cow<'_, B>
|
||||
// where
|
||||
// B::Owned: [const] Borrow<B>,
|
||||
{
|
||||
type Target = B;
|
||||
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ use std::iter;
|
|||
use askama::Template;
|
||||
use rustc_abi::VariantIdx;
|
||||
use rustc_ast::join_path_syms;
|
||||
use rustc_data_structures::fx::{FxHashMap, FxIndexSet};
|
||||
use rustc_data_structures::fx::{FxHashMap, FxIndexMap, FxIndexSet};
|
||||
use rustc_hir as hir;
|
||||
use rustc_hir::def::CtorKind;
|
||||
use rustc_hir::def_id::DefId;
|
||||
|
|
@ -307,8 +307,12 @@ fn item_module(cx: &Context<'_>, item: &clean::Item, items: &[clean::Item]) -> i
|
|||
fmt::from_fn(|w| {
|
||||
write!(w, "{}", document(cx, item, None, HeadingOffset::H2))?;
|
||||
|
||||
let mut not_stripped_items =
|
||||
items.iter().filter(|i| !i.is_stripped()).enumerate().collect::<Vec<_>>();
|
||||
let mut not_stripped_items: FxIndexMap<ItemType, Vec<(usize, &clean::Item)>> =
|
||||
FxIndexMap::default();
|
||||
|
||||
for (index, item) in items.iter().filter(|i| !i.is_stripped()).enumerate() {
|
||||
not_stripped_items.entry(item.type_()).or_default().push((index, item));
|
||||
}
|
||||
|
||||
// the order of item types in the listing
|
||||
fn reorder(ty: ItemType) -> u8 {
|
||||
|
|
@ -331,11 +335,6 @@ fn item_module(cx: &Context<'_>, item: &clean::Item, items: &[clean::Item]) -> i
|
|||
}
|
||||
|
||||
fn cmp(i1: &clean::Item, i2: &clean::Item, tcx: TyCtxt<'_>) -> Ordering {
|
||||
let rty1 = reorder(i1.type_());
|
||||
let rty2 = reorder(i2.type_());
|
||||
if rty1 != rty2 {
|
||||
return rty1.cmp(&rty2);
|
||||
}
|
||||
let is_stable1 =
|
||||
i1.stability(tcx).as_ref().map(|s| s.level.is_stable()).unwrap_or(true);
|
||||
let is_stable2 =
|
||||
|
|
@ -357,7 +356,9 @@ fn item_module(cx: &Context<'_>, item: &clean::Item, items: &[clean::Item]) -> i
|
|||
|
||||
match cx.shared.module_sorting {
|
||||
ModuleSorting::Alphabetical => {
|
||||
not_stripped_items.sort_by(|(_, i1), (_, i2)| cmp(i1, i2, tcx));
|
||||
for items in not_stripped_items.values_mut() {
|
||||
items.sort_by(|(_, i1), (_, i2)| cmp(i1, i2, tcx));
|
||||
}
|
||||
}
|
||||
ModuleSorting::DeclarationOrder => {}
|
||||
}
|
||||
|
|
@ -380,155 +381,152 @@ fn item_module(cx: &Context<'_>, item: &clean::Item, items: &[clean::Item]) -> i
|
|||
// can be identical even if the elements are different (mostly in imports).
|
||||
// So in case this is an import, we keep everything by adding a "unique id"
|
||||
// (which is the position in the vector).
|
||||
not_stripped_items.dedup_by_key(|(idx, i)| {
|
||||
(
|
||||
i.item_id,
|
||||
if i.name.is_some() { Some(full_path(cx, i)) } else { None },
|
||||
i.type_(),
|
||||
if i.is_import() { *idx } else { 0 },
|
||||
)
|
||||
});
|
||||
for items in not_stripped_items.values_mut() {
|
||||
items.dedup_by_key(|(idx, i)| {
|
||||
(
|
||||
i.item_id,
|
||||
if i.name.is_some() { Some(full_path(cx, i)) } else { None },
|
||||
i.type_(),
|
||||
if i.is_import() { *idx } else { 0 },
|
||||
)
|
||||
});
|
||||
}
|
||||
|
||||
debug!("{not_stripped_items:?}");
|
||||
let mut last_section = None;
|
||||
|
||||
for (_, myitem) in ¬_stripped_items {
|
||||
let my_section = item_ty_to_section(myitem.type_());
|
||||
if Some(my_section) != last_section {
|
||||
if last_section.is_some() {
|
||||
w.write_str(ITEM_TABLE_CLOSE)?;
|
||||
}
|
||||
last_section = Some(my_section);
|
||||
let section_id = my_section.id();
|
||||
let tag =
|
||||
if section_id == "reexports" { REEXPORTS_TABLE_OPEN } else { ITEM_TABLE_OPEN };
|
||||
write!(
|
||||
w,
|
||||
"{}",
|
||||
write_section_heading(my_section.name(), &cx.derive_id(section_id), None, tag)
|
||||
)?;
|
||||
}
|
||||
let mut types = not_stripped_items.keys().copied().collect::<Vec<_>>();
|
||||
types.sort_unstable_by(|a, b| reorder(*a).cmp(&reorder(*b)));
|
||||
|
||||
match myitem.kind {
|
||||
clean::ExternCrateItem { ref src } => {
|
||||
use crate::html::format::print_anchor;
|
||||
for type_ in types {
|
||||
let my_section = item_ty_to_section(type_);
|
||||
let tag = if my_section == super::ItemSection::Reexports {
|
||||
REEXPORTS_TABLE_OPEN
|
||||
} else {
|
||||
ITEM_TABLE_OPEN
|
||||
};
|
||||
write!(
|
||||
w,
|
||||
"{}",
|
||||
write_section_heading(my_section.name(), &cx.derive_id(my_section.id()), None, tag)
|
||||
)?;
|
||||
|
||||
match *src {
|
||||
Some(src) => {
|
||||
write!(
|
||||
w,
|
||||
"<dt><code>{}extern crate {} as {};",
|
||||
visibility_print_with_space(myitem, cx),
|
||||
print_anchor(myitem.item_id.expect_def_id(), src, cx),
|
||||
EscapeBodyTextWithWbr(myitem.name.unwrap().as_str())
|
||||
)?;
|
||||
}
|
||||
None => {
|
||||
write!(
|
||||
w,
|
||||
"<dt><code>{}extern crate {};",
|
||||
visibility_print_with_space(myitem, cx),
|
||||
print_anchor(
|
||||
myitem.item_id.expect_def_id(),
|
||||
myitem.name.unwrap(),
|
||||
cx
|
||||
)
|
||||
)?;
|
||||
}
|
||||
}
|
||||
w.write_str("</code></dt>")?;
|
||||
}
|
||||
for (_, myitem) in ¬_stripped_items[&type_] {
|
||||
match myitem.kind {
|
||||
clean::ExternCrateItem { ref src } => {
|
||||
use crate::html::format::print_anchor;
|
||||
|
||||
clean::ImportItem(ref import) => {
|
||||
let stab_tags = import.source.did.map_or_else(String::new, |import_def_id| {
|
||||
print_extra_info_tags(tcx, myitem, item, Some(import_def_id)).to_string()
|
||||
});
|
||||
|
||||
let id = match import.kind {
|
||||
clean::ImportKind::Simple(s) => {
|
||||
format!(" id=\"{}\"", cx.derive_id(format!("reexport.{s}")))
|
||||
}
|
||||
clean::ImportKind::Glob => String::new(),
|
||||
};
|
||||
write!(
|
||||
w,
|
||||
"<dt{id}>\
|
||||
<code>"
|
||||
)?;
|
||||
render_attributes_in_code(w, myitem, "", cx);
|
||||
write!(
|
||||
w,
|
||||
"{vis}{imp}</code>{stab_tags}\
|
||||
</dt>",
|
||||
vis = visibility_print_with_space(myitem, cx),
|
||||
imp = import.print(cx)
|
||||
)?;
|
||||
}
|
||||
|
||||
_ => {
|
||||
if myitem.name.is_none() {
|
||||
continue;
|
||||
}
|
||||
|
||||
let unsafety_flag = match myitem.kind {
|
||||
clean::FunctionItem(_) | clean::ForeignFunctionItem(..)
|
||||
if myitem.fn_header(tcx).unwrap().safety
|
||||
== hir::HeaderSafety::Normal(hir::Safety::Unsafe) =>
|
||||
{
|
||||
"<sup title=\"unsafe function\">⚠</sup>"
|
||||
}
|
||||
clean::ForeignStaticItem(_, hir::Safety::Unsafe) => {
|
||||
"<sup title=\"unsafe static\">⚠</sup>"
|
||||
}
|
||||
_ => "",
|
||||
};
|
||||
|
||||
let visibility_and_hidden = match myitem.visibility(tcx) {
|
||||
Some(ty::Visibility::Restricted(_)) => {
|
||||
if myitem.is_doc_hidden() {
|
||||
// Don't separate with a space when there are two of them
|
||||
"<span title=\"Restricted Visibility\"> 🔒</span><span title=\"Hidden item\">👻</span> "
|
||||
} else {
|
||||
"<span title=\"Restricted Visibility\"> 🔒</span> "
|
||||
match *src {
|
||||
Some(src) => {
|
||||
write!(
|
||||
w,
|
||||
"<dt><code>{}extern crate {} as {};",
|
||||
visibility_print_with_space(myitem, cx),
|
||||
print_anchor(myitem.item_id.expect_def_id(), src, cx),
|
||||
EscapeBodyTextWithWbr(myitem.name.unwrap().as_str())
|
||||
)?;
|
||||
}
|
||||
None => {
|
||||
write!(
|
||||
w,
|
||||
"<dt><code>{}extern crate {};",
|
||||
visibility_print_with_space(myitem, cx),
|
||||
print_anchor(
|
||||
myitem.item_id.expect_def_id(),
|
||||
myitem.name.unwrap(),
|
||||
cx
|
||||
)
|
||||
)?;
|
||||
}
|
||||
}
|
||||
_ if myitem.is_doc_hidden() => {
|
||||
"<span title=\"Hidden item\"> 👻</span> "
|
||||
}
|
||||
clean::ImportItem(ref import) => {
|
||||
let stab_tags =
|
||||
import.source.did.map_or_else(String::new, |import_def_id| {
|
||||
print_extra_info_tags(tcx, myitem, item, Some(import_def_id))
|
||||
.to_string()
|
||||
});
|
||||
let id = match import.kind {
|
||||
clean::ImportKind::Simple(s) => {
|
||||
format!(" id=\"{}\"", cx.derive_id(format!("reexport.{s}")))
|
||||
}
|
||||
clean::ImportKind::Glob => String::new(),
|
||||
};
|
||||
write!(
|
||||
w,
|
||||
"<dt{id}>\
|
||||
<code>"
|
||||
)?;
|
||||
render_attributes_in_code(w, myitem, "", cx);
|
||||
write!(
|
||||
w,
|
||||
"{vis}{imp}</code>{stab_tags}\
|
||||
</dt>",
|
||||
vis = visibility_print_with_space(myitem, cx),
|
||||
imp = import.print(cx)
|
||||
)?;
|
||||
}
|
||||
_ => {
|
||||
if myitem.name.is_none() {
|
||||
continue;
|
||||
}
|
||||
_ => "",
|
||||
};
|
||||
|
||||
let docs =
|
||||
MarkdownSummaryLine(&myitem.doc_value(), &myitem.links(cx)).into_string();
|
||||
let (docs_before, docs_after) =
|
||||
if docs.is_empty() { ("", "") } else { ("<dd>", "</dd>") };
|
||||
write!(
|
||||
w,
|
||||
"<dt>\
|
||||
<a class=\"{class}\" href=\"{href}\" title=\"{title1} {title2}\">\
|
||||
{name}\
|
||||
</a>\
|
||||
{visibility_and_hidden}\
|
||||
{unsafety_flag}\
|
||||
{stab_tags}\
|
||||
</dt>\
|
||||
{docs_before}{docs}{docs_after}",
|
||||
name = EscapeBodyTextWithWbr(myitem.name.unwrap().as_str()),
|
||||
visibility_and_hidden = visibility_and_hidden,
|
||||
stab_tags = print_extra_info_tags(tcx, myitem, item, None),
|
||||
class = myitem.type_(),
|
||||
unsafety_flag = unsafety_flag,
|
||||
href = print_item_path(myitem.type_(), myitem.name.unwrap().as_str()),
|
||||
title1 = myitem.type_(),
|
||||
title2 = full_path(cx, myitem),
|
||||
)?;
|
||||
let unsafety_flag = match myitem.kind {
|
||||
clean::FunctionItem(_) | clean::ForeignFunctionItem(..)
|
||||
if myitem.fn_header(tcx).unwrap().safety
|
||||
== hir::HeaderSafety::Normal(hir::Safety::Unsafe) =>
|
||||
{
|
||||
"<sup title=\"unsafe function\">⚠</sup>"
|
||||
}
|
||||
clean::ForeignStaticItem(_, hir::Safety::Unsafe) => {
|
||||
"<sup title=\"unsafe static\">⚠</sup>"
|
||||
}
|
||||
_ => "",
|
||||
};
|
||||
let visibility_and_hidden = match myitem.visibility(tcx) {
|
||||
Some(ty::Visibility::Restricted(_)) => {
|
||||
if myitem.is_doc_hidden() {
|
||||
// Don't separate with a space when there are two of them
|
||||
"<span title=\"Restricted Visibility\"> 🔒</span><span title=\"Hidden item\">👻</span> "
|
||||
} else {
|
||||
"<span title=\"Restricted Visibility\"> 🔒</span> "
|
||||
}
|
||||
}
|
||||
_ if myitem.is_doc_hidden() => {
|
||||
"<span title=\"Hidden item\"> 👻</span> "
|
||||
}
|
||||
_ => "",
|
||||
};
|
||||
|
||||
let docs = MarkdownSummaryLine(&myitem.doc_value(), &myitem.links(cx))
|
||||
.into_string();
|
||||
let (docs_before, docs_after) =
|
||||
if docs.is_empty() { ("", "") } else { ("<dd>", "</dd>") };
|
||||
write!(
|
||||
w,
|
||||
"<dt>\
|
||||
<a class=\"{class}\" href=\"{href}\" title=\"{title1} {title2}\">\
|
||||
{name}\
|
||||
</a>\
|
||||
{visibility_and_hidden}\
|
||||
{unsafety_flag}\
|
||||
{stab_tags}\
|
||||
</dt>\
|
||||
{docs_before}{docs}{docs_after}",
|
||||
name = EscapeBodyTextWithWbr(myitem.name.unwrap().as_str()),
|
||||
visibility_and_hidden = visibility_and_hidden,
|
||||
stab_tags = print_extra_info_tags(tcx, myitem, item, None),
|
||||
class = type_,
|
||||
unsafety_flag = unsafety_flag,
|
||||
href = print_item_path(type_, myitem.name.unwrap().as_str()),
|
||||
title1 = myitem.type_(),
|
||||
title2 = full_path(cx, myitem),
|
||||
)?;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if last_section.is_some() {
|
||||
w.write_str(ITEM_TABLE_CLOSE)?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
})
|
||||
}
|
||||
|
|
|
|||
9
tests/ui/frontmatter/space-in-infostring.rs
Normal file
9
tests/ui/frontmatter/space-in-infostring.rs
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
--- cargo clippy
|
||||
//~^ ERROR: invalid infostring for frontmatter
|
||||
---
|
||||
|
||||
// infostrings cannot have spaces
|
||||
|
||||
#![feature(frontmatter)]
|
||||
|
||||
fn main() {}
|
||||
10
tests/ui/frontmatter/space-in-infostring.stderr
Normal file
10
tests/ui/frontmatter/space-in-infostring.stderr
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
error: invalid infostring for frontmatter
|
||||
--> $DIR/space-in-infostring.rs:1:4
|
||||
|
|
||||
LL | --- cargo clippy
|
||||
| ^^^^^^^^^^^^^
|
||||
|
|
||||
= note: frontmatter infostrings must be a single identifier immediately following the opening
|
||||
|
||||
error: aborting due to 1 previous error
|
||||
|
||||
20
tests/ui/traits/generic-cow-inference-regression.rs
Normal file
20
tests/ui/traits/generic-cow-inference-regression.rs
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
//@ run-pass
|
||||
|
||||
// regression test for #147964:
|
||||
// constification of these traits resulted in inference errors due to additional where clauses
|
||||
|
||||
use std::borrow::{Cow, Borrow};
|
||||
|
||||
pub fn generic_deref<'a, T: ToOwned<Owned = U>, U>(cow: Cow<'a, T>) {
|
||||
let _: &T = &cow;
|
||||
}
|
||||
|
||||
pub fn generic_borrow<'a, T: ToOwned<Owned = U>, U>(cow: Cow<'a, T>) {
|
||||
let _: &T = cow.borrow();
|
||||
}
|
||||
|
||||
pub fn generic_as_ref<'a, T: ToOwned<Owned = U>, U>(cow: Cow<'a, T>) {
|
||||
let _: &T = cow.as_ref();
|
||||
}
|
||||
|
||||
fn main() {}
|
||||
|
|
@ -1370,6 +1370,7 @@ compiler = [
|
|||
"@jackh726",
|
||||
"@jieyouxu",
|
||||
"@jdonszelmann",
|
||||
"@JonathanBrouwer",
|
||||
"@lcnr",
|
||||
"@madsmtm",
|
||||
"@Nadrieril",
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue