Pass Context as a &mut to allow to remove RefCell fields
This commit is contained in:
parent
1ab98933fa
commit
6ab8edb931
5 changed files with 128 additions and 111 deletions
|
@ -55,9 +55,9 @@ pub(crate) struct Context<'tcx> {
|
|||
pub(super) render_redirect_pages: bool,
|
||||
/// Tracks section IDs for `Deref` targets so they match in both the main
|
||||
/// body and the sidebar.
|
||||
pub(super) deref_id_map: RefCell<FxHashMap<DefId, String>>,
|
||||
pub(super) deref_id_map: FxHashMap<DefId, String>,
|
||||
/// The map used to ensure all generated 'id=' attributes are unique.
|
||||
pub(super) id_map: RefCell<IdMap>,
|
||||
pub(super) id_map: IdMap,
|
||||
/// Shared mutable state.
|
||||
///
|
||||
/// Issue for improving the situation: [#82381][]
|
||||
|
@ -72,7 +72,7 @@ pub(crate) struct Context<'tcx> {
|
|||
|
||||
// `Context` is cloned a lot, so we don't want the size to grow unexpectedly.
|
||||
#[cfg(all(target_arch = "x86_64", target_pointer_width = "64"))]
|
||||
rustc_data_structures::static_assert_size!(Context<'_>, 144);
|
||||
rustc_data_structures::static_assert_size!(Context<'_>, 128);
|
||||
|
||||
/// Shared mutable state used in [`Context`] and elsewhere.
|
||||
pub(crate) struct SharedContext<'tcx> {
|
||||
|
@ -155,9 +155,8 @@ impl<'tcx> Context<'tcx> {
|
|||
self.shared.tcx.sess
|
||||
}
|
||||
|
||||
pub(super) fn derive_id(&self, id: String) -> String {
|
||||
let mut map = self.id_map.borrow_mut();
|
||||
map.derive(id)
|
||||
pub(super) fn derive_id(&mut self, id: String) -> String {
|
||||
self.id_map.derive(id)
|
||||
}
|
||||
|
||||
/// String representation of how to get back to the root path of the 'doc/'
|
||||
|
@ -166,7 +165,7 @@ impl<'tcx> Context<'tcx> {
|
|||
"../".repeat(self.current.len())
|
||||
}
|
||||
|
||||
fn render_item(&self, it: &clean::Item, is_module: bool) -> String {
|
||||
fn render_item(&mut self, it: &clean::Item, is_module: bool) -> String {
|
||||
let mut title = String::new();
|
||||
if !is_module {
|
||||
title.push_str(it.name.unwrap().as_str());
|
||||
|
@ -203,23 +202,26 @@ impl<'tcx> Context<'tcx> {
|
|||
};
|
||||
|
||||
if !self.render_redirect_pages {
|
||||
let clone_shared = Rc::clone(&self.shared);
|
||||
let page = layout::Page {
|
||||
css_class: tyname_s,
|
||||
root_path: &self.root_path(),
|
||||
static_root_path: self.shared.static_root_path.as_deref(),
|
||||
static_root_path: clone_shared.static_root_path.as_deref(),
|
||||
title: &title,
|
||||
description: &desc,
|
||||
keywords: &keywords,
|
||||
resource_suffix: &self.shared.resource_suffix,
|
||||
resource_suffix: &clone_shared.resource_suffix,
|
||||
extra_scripts: &[],
|
||||
static_extra_scripts: &[],
|
||||
};
|
||||
let mut page_buffer = Buffer::html();
|
||||
print_item(self, it, &mut page_buffer, &page);
|
||||
layout::render(
|
||||
&self.shared.layout,
|
||||
&clone_shared.layout,
|
||||
&page,
|
||||
|buf: &mut _| print_sidebar(self, it, buf),
|
||||
|buf: &mut _| print_item(self, it, buf, &page),
|
||||
&self.shared.style_files,
|
||||
move |buf: &mut Buffer| buf.push_buffer(page_buffer),
|
||||
&clone_shared.style_files,
|
||||
)
|
||||
} else {
|
||||
if let Some(&(ref names, ty)) = self.cache().paths.get(&it.item_id.expect_def_id()) {
|
||||
|
@ -512,8 +514,8 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
current: Vec::new(),
|
||||
dst,
|
||||
render_redirect_pages: false,
|
||||
id_map: RefCell::new(id_map),
|
||||
deref_id_map: RefCell::new(FxHashMap::default()),
|
||||
id_map,
|
||||
deref_id_map: FxHashMap::default(),
|
||||
shared: Rc::new(scx),
|
||||
include_sources,
|
||||
};
|
||||
|
@ -528,7 +530,7 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
|
||||
// Write shared runs within a flock; disable thread dispatching of IO temporarily.
|
||||
Rc::get_mut(&mut cx.shared).unwrap().fs.set_sync_only(true);
|
||||
write_shared(&cx, &krate, index, &md_opts)?;
|
||||
write_shared(&mut cx, &krate, index, &md_opts)?;
|
||||
Rc::get_mut(&mut cx.shared).unwrap().fs.set_sync_only(false);
|
||||
}
|
||||
|
||||
|
@ -540,8 +542,8 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
current: self.current.clone(),
|
||||
dst: self.dst.clone(),
|
||||
render_redirect_pages: self.render_redirect_pages,
|
||||
deref_id_map: RefCell::new(FxHashMap::default()),
|
||||
id_map: RefCell::new(IdMap::new()),
|
||||
deref_id_map: FxHashMap::default(),
|
||||
id_map: IdMap::new(),
|
||||
shared: Rc::clone(&self.shared),
|
||||
include_sources: self.include_sources,
|
||||
}
|
||||
|
@ -557,31 +559,32 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
if !root_path.ends_with('/') {
|
||||
root_path.push('/');
|
||||
}
|
||||
let shared = Rc::clone(&self.shared);
|
||||
let mut page = layout::Page {
|
||||
title: "List of all items in this crate",
|
||||
css_class: "mod",
|
||||
root_path: "../",
|
||||
static_root_path: self.shared.static_root_path.as_deref(),
|
||||
static_root_path: shared.static_root_path.as_deref(),
|
||||
description: "List of all items in this crate",
|
||||
keywords: BASIC_KEYWORDS,
|
||||
resource_suffix: &self.shared.resource_suffix,
|
||||
resource_suffix: &shared.resource_suffix,
|
||||
extra_scripts: &[],
|
||||
static_extra_scripts: &[],
|
||||
};
|
||||
let sidebar = if self.shared.cache.crate_version.is_some() {
|
||||
let sidebar = if shared.cache.crate_version.is_some() {
|
||||
format!("<h2 class=\"location\">Crate {}</h2>", crate_name)
|
||||
} else {
|
||||
String::new()
|
||||
};
|
||||
let all = self.shared.all.replace(AllTypes::new());
|
||||
let all = shared.all.replace(AllTypes::new());
|
||||
let v = layout::render(
|
||||
&self.shared.layout,
|
||||
&shared.layout,
|
||||
&page,
|
||||
sidebar,
|
||||
|buf: &mut Buffer| all.print(buf),
|
||||
&self.shared.style_files,
|
||||
&shared.style_files,
|
||||
);
|
||||
self.shared.fs.write(final_file, v)?;
|
||||
shared.fs.write(final_file, v)?;
|
||||
|
||||
// Generating settings page.
|
||||
page.title = "Rustdoc settings";
|
||||
|
@ -590,7 +593,7 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
|
||||
let sidebar = "<h2 class=\"location\">Settings</h2><div class=\"sidebar-elems\"></div>";
|
||||
let v = layout::render(
|
||||
&self.shared.layout,
|
||||
&shared.layout,
|
||||
&page,
|
||||
sidebar,
|
||||
|buf: &mut Buffer| {
|
||||
|
@ -613,33 +616,36 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
suffix = page.resource_suffix,
|
||||
)
|
||||
},
|
||||
&self.shared.style_files,
|
||||
&shared.style_files,
|
||||
);
|
||||
self.shared.fs.write(settings_file, v)?;
|
||||
shared.fs.write(settings_file, v)?;
|
||||
|
||||
if self.shared.layout.scrape_examples_extension {
|
||||
if shared.layout.scrape_examples_extension {
|
||||
page.title = "About scraped examples";
|
||||
page.description = "How the scraped examples feature works in Rustdoc";
|
||||
let v = layout::render(
|
||||
&self.shared.layout,
|
||||
&shared.layout,
|
||||
&page,
|
||||
"",
|
||||
scrape_examples_help(&*self.shared),
|
||||
&self.shared.style_files,
|
||||
scrape_examples_help(&*shared),
|
||||
&shared.style_files,
|
||||
);
|
||||
self.shared.fs.write(scrape_examples_help_file, v)?;
|
||||
shared.fs.write(scrape_examples_help_file, v)?;
|
||||
}
|
||||
|
||||
if let Some(ref redirections) = self.shared.redirections {
|
||||
if let Some(ref redirections) = shared.redirections {
|
||||
if !redirections.borrow().is_empty() {
|
||||
let redirect_map_path =
|
||||
self.dst.join(crate_name.as_str()).join("redirect-map.json");
|
||||
let paths = serde_json::to_string(&*redirections.borrow()).unwrap();
|
||||
self.shared.ensure_dir(&self.dst.join(crate_name.as_str()))?;
|
||||
self.shared.fs.write(redirect_map_path, paths)?;
|
||||
shared.ensure_dir(&self.dst.join(crate_name.as_str()))?;
|
||||
shared.fs.write(redirect_map_path, paths)?;
|
||||
}
|
||||
}
|
||||
|
||||
// No need for it anymore.
|
||||
drop(shared);
|
||||
|
||||
// Flush pending errors.
|
||||
Rc::get_mut(&mut self.shared).unwrap().fs.close();
|
||||
let nb_errors =
|
||||
|
@ -662,7 +668,6 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
if !self.render_redirect_pages {
|
||||
self.render_redirect_pages = item.is_stripped();
|
||||
}
|
||||
let scx = &self.shared;
|
||||
let item_name = item.name.unwrap();
|
||||
self.dst.push(&*item_name.as_str());
|
||||
self.current.push(item_name);
|
||||
|
@ -674,7 +679,7 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
if !buf.is_empty() {
|
||||
self.shared.ensure_dir(&self.dst)?;
|
||||
let joint_dst = self.dst.join("index.html");
|
||||
scx.fs.write(joint_dst, buf)?;
|
||||
self.shared.fs.write(joint_dst, buf)?;
|
||||
}
|
||||
|
||||
// Render sidebar-items.js used throughout this module.
|
||||
|
@ -684,7 +689,7 @@ impl<'tcx> FormatRenderer<'tcx> for Context<'tcx> {
|
|||
let items = self.build_sidebar_items(module);
|
||||
let js_dst = self.dst.join(&format!("sidebar-items{}.js", self.shared.resource_suffix));
|
||||
let v = format!("initSidebarItems({});", serde_json::to_string(&items).unwrap());
|
||||
scx.fs.write(js_dst, v)?;
|
||||
self.shared.fs.write(js_dst, v)?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -42,6 +42,7 @@ use std::fmt;
|
|||
use std::fs;
|
||||
use std::iter::Peekable;
|
||||
use std::path::PathBuf;
|
||||
use std::rc::Rc;
|
||||
use std::str;
|
||||
use std::string::ToString;
|
||||
|
||||
|
@ -364,7 +365,7 @@ fn scrape_examples_help(shared: &SharedContext<'_>) -> String {
|
|||
|
||||
fn document(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
item: &clean::Item,
|
||||
parent: Option<&clean::Item>,
|
||||
heading_offset: HeadingOffset,
|
||||
|
@ -383,19 +384,18 @@ fn document(
|
|||
/// Render md_text as markdown.
|
||||
fn render_markdown(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
md_text: &str,
|
||||
links: Vec<RenderedLink>,
|
||||
heading_offset: HeadingOffset,
|
||||
) {
|
||||
let mut ids = cx.id_map.borrow_mut();
|
||||
write!(
|
||||
w,
|
||||
"<div class=\"docblock\">{}</div>",
|
||||
Markdown {
|
||||
content: md_text,
|
||||
links: &links,
|
||||
ids: &mut ids,
|
||||
ids: &mut cx.id_map,
|
||||
error_codes: cx.shared.codes,
|
||||
edition: cx.shared.edition(),
|
||||
playground: &cx.shared.playground,
|
||||
|
@ -410,7 +410,7 @@ fn render_markdown(
|
|||
fn document_short(
|
||||
w: &mut Buffer,
|
||||
item: &clean::Item,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
link: AssocItemLink<'_>,
|
||||
parent: &clean::Item,
|
||||
show_def_docs: bool,
|
||||
|
@ -439,7 +439,7 @@ fn document_short(
|
|||
fn document_full_collapsible(
|
||||
w: &mut Buffer,
|
||||
item: &clean::Item,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
heading_offset: HeadingOffset,
|
||||
) {
|
||||
document_full_inner(w, item, cx, true, heading_offset);
|
||||
|
@ -448,7 +448,7 @@ fn document_full_collapsible(
|
|||
fn document_full(
|
||||
w: &mut Buffer,
|
||||
item: &clean::Item,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
heading_offset: HeadingOffset,
|
||||
) {
|
||||
document_full_inner(w, item, cx, false, heading_offset);
|
||||
|
@ -457,7 +457,7 @@ fn document_full(
|
|||
fn document_full_inner(
|
||||
w: &mut Buffer,
|
||||
item: &clean::Item,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
is_collapsible: bool,
|
||||
heading_offset: HeadingOffset,
|
||||
) {
|
||||
|
@ -493,7 +493,7 @@ fn document_full_inner(
|
|||
/// * Required features (through the `doc_cfg` feature)
|
||||
fn document_item_info(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
item: &clean::Item,
|
||||
parent: Option<&clean::Item>,
|
||||
) {
|
||||
|
@ -522,7 +522,7 @@ fn portability(item: &clean::Item, parent: Option<&clean::Item>) -> Option<Strin
|
|||
/// the item's documentation.
|
||||
fn short_item_info(
|
||||
item: &clean::Item,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
parent: Option<&clean::Item>,
|
||||
) -> Vec<String> {
|
||||
let mut extra_info = vec![];
|
||||
|
@ -550,10 +550,9 @@ fn short_item_info(
|
|||
|
||||
if let Some(note) = note {
|
||||
let note = note.as_str();
|
||||
let mut ids = cx.id_map.borrow_mut();
|
||||
let html = MarkdownHtml(
|
||||
note,
|
||||
&mut ids,
|
||||
&mut cx.id_map,
|
||||
error_codes,
|
||||
cx.shared.edition(),
|
||||
&cx.shared.playground,
|
||||
|
@ -601,7 +600,7 @@ fn short_item_info(
|
|||
// Render the list of items inside one of the sections "Trait Implementations",
|
||||
// "Auto Trait Implementations," "Blanket Trait Implementations" (on struct/enum pages).
|
||||
fn render_impls(
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
w: &mut Buffer,
|
||||
impls: &[&&Impl],
|
||||
containing_item: &clean::Item,
|
||||
|
@ -994,7 +993,7 @@ impl<'a> AssocItemLink<'a> {
|
|||
|
||||
fn render_assoc_items(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
containing_item: &clean::Item,
|
||||
it: DefId,
|
||||
what: AssocItemRender<'_>,
|
||||
|
@ -1006,14 +1005,15 @@ fn render_assoc_items(
|
|||
|
||||
fn render_assoc_items_inner(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
containing_item: &clean::Item,
|
||||
it: DefId,
|
||||
what: AssocItemRender<'_>,
|
||||
derefs: &mut FxHashSet<DefId>,
|
||||
) {
|
||||
info!("Documenting associated items of {:?}", containing_item.name);
|
||||
let cache = cx.cache();
|
||||
let shared = Rc::clone(&cx.shared);
|
||||
let cache = &shared.cache;
|
||||
let Some(v) = cache.impls.get(&it) else { return };
|
||||
let (non_trait, traits): (Vec<_>, _) = v.iter().partition(|i| i.inner_impl().trait_.is_none());
|
||||
if !non_trait.is_empty() {
|
||||
|
@ -1032,7 +1032,7 @@ fn render_assoc_items_inner(
|
|||
let id =
|
||||
cx.derive_id(small_url_encode(format!("deref-methods-{:#}", type_.print(cx))));
|
||||
if let Some(def_id) = type_.def_id(cx.cache()) {
|
||||
cx.deref_id_map.borrow_mut().insert(def_id, id.clone());
|
||||
cx.deref_id_map.insert(def_id, id.clone());
|
||||
}
|
||||
write!(
|
||||
tmp_buf,
|
||||
|
@ -1138,7 +1138,7 @@ fn render_assoc_items_inner(
|
|||
|
||||
fn render_deref_methods(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
impl_: &Impl,
|
||||
container_item: &clean::Item,
|
||||
deref_mut: bool,
|
||||
|
@ -1285,7 +1285,7 @@ struct ImplRenderingParameters {
|
|||
|
||||
fn render_impl(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
i: &Impl,
|
||||
parent: &clean::Item,
|
||||
link: AssocItemLink<'_>,
|
||||
|
@ -1294,7 +1294,8 @@ fn render_impl(
|
|||
aliases: &[String],
|
||||
rendering_params: ImplRenderingParameters,
|
||||
) {
|
||||
let cache = cx.cache();
|
||||
let shared = Rc::clone(&cx.shared);
|
||||
let cache = &shared.cache;
|
||||
let traits = &cache.traits;
|
||||
let trait_ = i.trait_did().map(|did| &traits[&did]);
|
||||
let mut close_tags = String::new();
|
||||
|
@ -1307,7 +1308,7 @@ fn render_impl(
|
|||
fn doc_impl_item(
|
||||
boring: &mut Buffer,
|
||||
interesting: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
item: &clean::Item,
|
||||
parent: &clean::Item,
|
||||
containing_item: &clean::Item,
|
||||
|
@ -1520,7 +1521,7 @@ fn render_impl(
|
|||
fn render_default_items(
|
||||
boring: &mut Buffer,
|
||||
interesting: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
t: &clean::Trait,
|
||||
i: &clean::Impl,
|
||||
parent: &clean::Item,
|
||||
|
@ -1599,14 +1600,13 @@ fn render_impl(
|
|||
}
|
||||
|
||||
if let Some(ref dox) = i.impl_item.collapsed_doc_value() {
|
||||
let mut ids = cx.id_map.borrow_mut();
|
||||
write!(
|
||||
w,
|
||||
"<div class=\"docblock\">{}</div>",
|
||||
Markdown {
|
||||
content: &*dox,
|
||||
links: &i.impl_item.links(cx),
|
||||
ids: &mut ids,
|
||||
ids: &mut cx.id_map,
|
||||
error_codes: cx.shared.codes,
|
||||
edition: cx.shared.edition(),
|
||||
playground: &cx.shared.playground,
|
||||
|
@ -1664,7 +1664,7 @@ fn render_rightside(
|
|||
|
||||
pub(crate) fn render_impl_summary(
|
||||
w: &mut Buffer,
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
i: &Impl,
|
||||
parent: &clean::Item,
|
||||
containing_item: &clean::Item,
|
||||
|
@ -2092,10 +2092,8 @@ fn sidebar_deref_methods(
|
|||
})
|
||||
.collect::<Vec<_>>();
|
||||
if !ret.is_empty() {
|
||||
let map;
|
||||
let id = if let Some(target_def_id) = real_target.def_id(c) {
|
||||
map = cx.deref_id_map.borrow();
|
||||
map.get(&target_def_id).expect("Deref section without derived id")
|
||||
cx.deref_id_map.get(&target_def_id).expect("Deref section without derived id")
|
||||
} else {
|
||||
"deref-methods"
|
||||
};
|
||||
|
@ -2641,14 +2639,14 @@ const MAX_FULL_EXAMPLES: usize = 5;
|
|||
const NUM_VISIBLE_LINES: usize = 10;
|
||||
|
||||
/// Generates the HTML for example call locations generated via the --scrape-examples flag.
|
||||
fn render_call_locations(w: &mut Buffer, cx: &Context<'_>, item: &clean::Item) {
|
||||
fn render_call_locations(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item) {
|
||||
let tcx = cx.tcx();
|
||||
let def_id = item.item_id.expect_def_id();
|
||||
let key = tcx.def_path_hash(def_id);
|
||||
let Some(call_locations) = cx.shared.call_locations.get(&key) else { return };
|
||||
|
||||
// Generate a unique ID so users can link to this section for a given method
|
||||
let id = cx.id_map.borrow_mut().derive("scraped-examples");
|
||||
let id = cx.id_map.derive("scraped-examples");
|
||||
write!(
|
||||
w,
|
||||
"<div class=\"docblock scraped-example-list\">\
|
||||
|
|
|
@ -2,6 +2,7 @@ use clean::AttributesExt;
|
|||
|
||||
use std::cmp::Ordering;
|
||||
use std::fmt;
|
||||
use std::rc::Rc;
|
||||
|
||||
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
|
||||
use rustc_hir as hir;
|
||||
|
@ -60,7 +61,12 @@ struct ItemVars<'a> {
|
|||
src_href: Option<&'a str>,
|
||||
}
|
||||
|
||||
pub(super) fn print_item(cx: &Context<'_>, item: &clean::Item, buf: &mut Buffer, page: &Page<'_>) {
|
||||
pub(super) fn print_item(
|
||||
cx: &mut Context<'_>,
|
||||
item: &clean::Item,
|
||||
buf: &mut Buffer,
|
||||
page: &Page<'_>,
|
||||
) {
|
||||
debug_assert!(!item.is_stripped());
|
||||
let typ = match *item.kind {
|
||||
clean::ModuleItem(_) => {
|
||||
|
@ -187,7 +193,7 @@ fn toggle_close(w: &mut Buffer) {
|
|||
w.write_str("</details>");
|
||||
}
|
||||
|
||||
fn item_module(w: &mut Buffer, cx: &Context<'_>, item: &clean::Item, items: &[clean::Item]) {
|
||||
fn item_module(w: &mut Buffer, cx: &mut Context<'_>, item: &clean::Item, items: &[clean::Item]) {
|
||||
document(w, cx, item, None, HeadingOffset::H2);
|
||||
|
||||
let mut indices = (0..items.len()).filter(|i| !items[*i].is_stripped()).collect::<Vec<usize>>();
|
||||
|
@ -344,6 +350,12 @@ fn item_module(w: &mut Buffer, cx: &Context<'_>, item: &clean::Item, items: &[cl
|
|||
let add = if stab.is_some() { " " } else { "" };
|
||||
|
||||
w.write_str(ITEM_TABLE_ROW_OPEN);
|
||||
let id = match import.kind {
|
||||
clean::ImportKind::Simple(s) => {
|
||||
format!(" id=\"{}\"", cx.derive_id(format!("reexport.{}", s)))
|
||||
}
|
||||
clean::ImportKind::Glob => String::new(),
|
||||
};
|
||||
write!(
|
||||
w,
|
||||
"<div class=\"item-left {stab}{add}import-item\"{id}>\
|
||||
|
@ -351,15 +363,9 @@ fn item_module(w: &mut Buffer, cx: &Context<'_>, item: &clean::Item, items: &[cl
|
|||
</div>\
|
||||
<div class=\"item-right docblock-short\">{stab_tags}</div>",
|
||||
stab = stab.unwrap_or_default(),
|
||||
add = add,
|
||||
vis = myitem.visibility.print_with_space(myitem.item_id, cx),
|
||||
imp = import.print(cx),
|
||||
stab_tags = stab_tags.unwrap_or_default(),
|
||||
id = match import.kind {
|
||||
clean::ImportKind::Simple(s) =>
|
||||
format!(" id=\"{}\"", cx.derive_id(format!("reexport.{}", s))),
|
||||
clean::ImportKind::Glob => String::new(),
|
||||
},
|
||||
);
|
||||
w.write_str(ITEM_TABLE_ROW_CLOSE);
|
||||
}
|
||||
|
@ -464,7 +470,7 @@ fn extra_info_tags(item: &clean::Item, parent: &clean::Item, tcx: TyCtxt<'_>) ->
|
|||
tags
|
||||
}
|
||||
|
||||
fn item_function(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, f: &clean::Function) {
|
||||
fn item_function(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, f: &clean::Function) {
|
||||
let header = it.fn_header(cx.tcx()).expect("printing a function which isn't a function");
|
||||
let constness = print_constness_with_space(&header.constness, it.const_stability(cx.tcx()));
|
||||
let unsafety = header.unsafety.print_with_space();
|
||||
|
@ -507,7 +513,7 @@ fn item_function(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, f: &clean::
|
|||
document(w, cx, it, None, HeadingOffset::H2)
|
||||
}
|
||||
|
||||
fn item_trait(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Trait) {
|
||||
fn item_trait(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &clean::Trait) {
|
||||
let bounds = bounds(&t.bounds, false, cx);
|
||||
let required_types = t.items.iter().filter(|m| m.is_ty_associated_type()).collect::<Vec<_>>();
|
||||
let provided_types = t.items.iter().filter(|m| m.is_associated_type()).collect::<Vec<_>>();
|
||||
|
@ -674,7 +680,7 @@ fn item_trait(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Tra
|
|||
)
|
||||
}
|
||||
|
||||
fn trait_item(w: &mut Buffer, cx: &Context<'_>, m: &clean::Item, t: &clean::Item) {
|
||||
fn trait_item(w: &mut Buffer, cx: &mut Context<'_>, m: &clean::Item, t: &clean::Item) {
|
||||
let name = m.name.unwrap();
|
||||
info!("Documenting {} on {:?}", name, t.name);
|
||||
let item_type = m.type_();
|
||||
|
@ -791,14 +797,15 @@ fn item_trait(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Tra
|
|||
// If there are methods directly on this trait object, render them here.
|
||||
render_assoc_items(w, cx, it, it.item_id.expect_def_id(), AssocItemRender::All);
|
||||
|
||||
let cache = cx.cache();
|
||||
let cloned_shared = Rc::clone(&cx.shared);
|
||||
let cache = &cloned_shared.cache;
|
||||
let mut extern_crates = FxHashSet::default();
|
||||
if let Some(implementors) = cache.implementors.get(&it.item_id.expect_def_id()) {
|
||||
// The DefId is for the first Type found with that name. The bool is
|
||||
// if any Types with the same name but different DefId have been found.
|
||||
let mut implementor_dups: FxHashMap<Symbol, (DefId, bool)> = FxHashMap::default();
|
||||
for implementor in implementors {
|
||||
if let Some(did) = implementor.inner_impl().for_.without_borrowed_ref().def_id(cx.cache()) &&
|
||||
if let Some(did) = implementor.inner_impl().for_.without_borrowed_ref().def_id(cache) &&
|
||||
!did.is_local() {
|
||||
extern_crates.insert(did.krate);
|
||||
}
|
||||
|
@ -996,7 +1003,7 @@ fn item_trait(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Tra
|
|||
);
|
||||
}
|
||||
|
||||
fn item_trait_alias(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::TraitAlias) {
|
||||
fn item_trait_alias(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &clean::TraitAlias) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "trait-alias", |w| {
|
||||
render_attributes_in_pre(w, it, "");
|
||||
|
@ -1020,7 +1027,7 @@ fn item_trait_alias(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clea
|
|||
render_assoc_items(w, cx, it, it.item_id.expect_def_id(), AssocItemRender::All)
|
||||
}
|
||||
|
||||
fn item_opaque_ty(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::OpaqueTy) {
|
||||
fn item_opaque_ty(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &clean::OpaqueTy) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "opaque", |w| {
|
||||
render_attributes_in_pre(w, it, "");
|
||||
|
@ -1044,7 +1051,7 @@ fn item_opaque_ty(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean:
|
|||
render_assoc_items(w, cx, it, it.item_id.expect_def_id(), AssocItemRender::All)
|
||||
}
|
||||
|
||||
fn item_typedef(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Typedef) {
|
||||
fn item_typedef(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &clean::Typedef) {
|
||||
fn write_content(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Typedef) {
|
||||
wrap_item(w, "typedef", |w| {
|
||||
render_attributes_in_pre(w, it, "");
|
||||
|
@ -1073,7 +1080,7 @@ fn item_typedef(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::T
|
|||
document_type_layout(w, cx, def_id);
|
||||
}
|
||||
|
||||
fn item_union(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, s: &clean::Union) {
|
||||
fn item_union(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, s: &clean::Union) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "union", |w| {
|
||||
render_attributes_in_pre(w, it, "");
|
||||
|
@ -1135,7 +1142,7 @@ fn print_tuple_struct_fields(w: &mut Buffer, cx: &Context<'_>, s: &[clean::Item]
|
|||
}
|
||||
}
|
||||
|
||||
fn item_enum(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, e: &clean::Enum) {
|
||||
fn item_enum(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, e: &clean::Enum) {
|
||||
let count_variants = e.variants().count();
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "enum", |w| {
|
||||
|
@ -1283,7 +1290,7 @@ fn item_enum(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, e: &clean::Enum
|
|||
document_type_layout(w, cx, def_id);
|
||||
}
|
||||
|
||||
fn item_macro(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Macro) {
|
||||
fn item_macro(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, t: &clean::Macro) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
highlight::render_with_highlighting(
|
||||
&t.source,
|
||||
|
@ -1300,7 +1307,7 @@ fn item_macro(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, t: &clean::Mac
|
|||
document(w, cx, it, None, HeadingOffset::H2)
|
||||
}
|
||||
|
||||
fn item_proc_macro(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, m: &clean::ProcMacro) {
|
||||
fn item_proc_macro(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, m: &clean::ProcMacro) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
let name = it.name.expect("proc-macros always have names");
|
||||
match m.kind {
|
||||
|
@ -1332,12 +1339,12 @@ fn item_proc_macro(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, m: &clean
|
|||
document(w, cx, it, None, HeadingOffset::H2)
|
||||
}
|
||||
|
||||
fn item_primitive(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item) {
|
||||
fn item_primitive(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item) {
|
||||
document(w, cx, it, None, HeadingOffset::H2);
|
||||
render_assoc_items(w, cx, it, it.item_id.expect_def_id(), AssocItemRender::All)
|
||||
}
|
||||
|
||||
fn item_constant(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, c: &clean::Constant) {
|
||||
fn item_constant(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, c: &clean::Constant) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "const", |w| {
|
||||
render_attributes_in_code(w, it);
|
||||
|
@ -1377,7 +1384,7 @@ fn item_constant(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, c: &clean::
|
|||
document(w, cx, it, None, HeadingOffset::H2)
|
||||
}
|
||||
|
||||
fn item_struct(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, s: &clean::Struct) {
|
||||
fn item_struct(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, s: &clean::Struct) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "struct", |w| {
|
||||
render_attributes_in_code(w, it);
|
||||
|
@ -1430,7 +1437,7 @@ fn item_struct(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, s: &clean::St
|
|||
document_type_layout(w, cx, def_id);
|
||||
}
|
||||
|
||||
fn item_static(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, s: &clean::Static) {
|
||||
fn item_static(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item, s: &clean::Static) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "static", |w| {
|
||||
render_attributes_in_code(w, it);
|
||||
|
@ -1447,7 +1454,7 @@ fn item_static(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item, s: &clean::St
|
|||
document(w, cx, it, None, HeadingOffset::H2)
|
||||
}
|
||||
|
||||
fn item_foreign_type(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item) {
|
||||
fn item_foreign_type(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item) {
|
||||
wrap_into_docblock(w, |w| {
|
||||
wrap_item(w, "foreigntype", |w| {
|
||||
w.write_str("extern {\n");
|
||||
|
@ -1466,7 +1473,7 @@ fn item_foreign_type(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item) {
|
|||
render_assoc_items(w, cx, it, it.item_id.expect_def_id(), AssocItemRender::All)
|
||||
}
|
||||
|
||||
fn item_keyword(w: &mut Buffer, cx: &Context<'_>, it: &clean::Item) {
|
||||
fn item_keyword(w: &mut Buffer, cx: &mut Context<'_>, it: &clean::Item) {
|
||||
document(w, cx, it, None, HeadingOffset::H2)
|
||||
}
|
||||
|
||||
|
@ -1579,7 +1586,7 @@ fn compare_impl<'a, 'b>(lhs: &'a &&Impl, rhs: &'b &&Impl, cx: &Context<'_>) -> O
|
|||
}
|
||||
|
||||
fn render_implementor(
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
implementor: &Impl,
|
||||
trait_: &clean::Item,
|
||||
w: &mut Buffer,
|
||||
|
|
|
@ -5,6 +5,7 @@ use std::io::prelude::*;
|
|||
use std::io::{self, BufReader};
|
||||
use std::lazy::SyncLazy as Lazy;
|
||||
use std::path::{Component, Path, PathBuf};
|
||||
use std::rc::Rc;
|
||||
|
||||
use itertools::Itertools;
|
||||
use rustc_data_structures::flock;
|
||||
|
@ -135,7 +136,7 @@ impl Context<'_> {
|
|||
}
|
||||
|
||||
pub(super) fn write_shared(
|
||||
cx: &Context<'_>,
|
||||
cx: &mut Context<'_>,
|
||||
krate: &Crate,
|
||||
search_index: String,
|
||||
options: &RenderOptions,
|
||||
|
@ -462,15 +463,16 @@ if (typeof exports !== 'undefined') {exports.searchIndex = searchIndex};
|
|||
crate::markdown::render(&index_page, md_opts, cx.shared.edition())
|
||||
.map_err(|e| Error::new(e, &index_page))?;
|
||||
} else {
|
||||
let shared = Rc::clone(&cx.shared);
|
||||
let dst = cx.dst.join("index.html");
|
||||
let page = layout::Page {
|
||||
title: "Index of crates",
|
||||
css_class: "mod",
|
||||
root_path: "./",
|
||||
static_root_path: cx.shared.static_root_path.as_deref(),
|
||||
static_root_path: shared.static_root_path.as_deref(),
|
||||
description: "List of crates",
|
||||
keywords: BASIC_KEYWORDS,
|
||||
resource_suffix: &cx.shared.resource_suffix,
|
||||
resource_suffix: &shared.resource_suffix,
|
||||
extra_scripts: &[],
|
||||
static_extra_scripts: &[],
|
||||
};
|
||||
|
@ -490,8 +492,8 @@ if (typeof exports !== 'undefined') {exports.searchIndex = searchIndex};
|
|||
})
|
||||
.collect::<String>()
|
||||
);
|
||||
let v = layout::render(&cx.shared.layout, &page, "", content, &cx.shared.style_files);
|
||||
cx.shared.fs.write(dst, v)?;
|
||||
let v = layout::render(&shared.layout, &page, "", content, &shared.style_files);
|
||||
shared.fs.write(dst, v)?;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -6,15 +6,18 @@ use crate::html::highlight;
|
|||
use crate::html::layout;
|
||||
use crate::html::render::{Context, BASIC_KEYWORDS};
|
||||
use crate::visit::DocVisitor;
|
||||
|
||||
use rustc_data_structures::fx::{FxHashMap, FxHashSet};
|
||||
use rustc_hir::def_id::LOCAL_CRATE;
|
||||
use rustc_middle::ty::TyCtxt;
|
||||
use rustc_session::Session;
|
||||
use rustc_span::edition::Edition;
|
||||
use rustc_span::source_map::FileName;
|
||||
|
||||
use std::ffi::OsStr;
|
||||
use std::fs;
|
||||
use std::path::{Component, Path, PathBuf};
|
||||
use std::rc::Rc;
|
||||
|
||||
pub(crate) fn render(cx: &mut Context<'_>, krate: &clean::Crate) -> Result<(), Error> {
|
||||
info!("emitting source files");
|
||||
|
@ -174,15 +177,16 @@ impl SourceCollector<'_, '_> {
|
|||
// Remove the utf-8 BOM if any
|
||||
let contents = contents.strip_prefix('\u{feff}').unwrap_or(&contents);
|
||||
|
||||
let shared = Rc::clone(&self.cx.shared);
|
||||
// Create the intermediate directories
|
||||
let mut cur = self.dst.clone();
|
||||
let mut root_path = String::from("../../");
|
||||
clean_path(&self.cx.shared.src_root, &p, false, |component| {
|
||||
clean_path(&shared.src_root, &p, false, |component| {
|
||||
cur.push(component);
|
||||
root_path.push_str("../");
|
||||
});
|
||||
|
||||
self.cx.shared.ensure_dir(&cur)?;
|
||||
shared.ensure_dir(&cur)?;
|
||||
|
||||
let src_fname = p.file_name().expect("source has no filename").to_os_string();
|
||||
let mut fname = src_fname.clone();
|
||||
|
@ -195,32 +199,33 @@ impl SourceCollector<'_, '_> {
|
|||
title: &title,
|
||||
css_class: "source",
|
||||
root_path: &root_path,
|
||||
static_root_path: self.cx.shared.static_root_path.as_deref(),
|
||||
static_root_path: shared.static_root_path.as_deref(),
|
||||
description: &desc,
|
||||
keywords: BASIC_KEYWORDS,
|
||||
resource_suffix: &self.cx.shared.resource_suffix,
|
||||
extra_scripts: &[&format!("source-files{}", self.cx.shared.resource_suffix)],
|
||||
static_extra_scripts: &[&format!("source-script{}", self.cx.shared.resource_suffix)],
|
||||
resource_suffix: &shared.resource_suffix,
|
||||
extra_scripts: &[&format!("source-files{}", shared.resource_suffix)],
|
||||
static_extra_scripts: &[&format!("source-script{}", shared.resource_suffix)],
|
||||
};
|
||||
let v = layout::render(
|
||||
&self.cx.shared.layout,
|
||||
&shared.layout,
|
||||
&page,
|
||||
"",
|
||||
|buf: &mut _| {
|
||||
let cx = &mut self.cx;
|
||||
print_src(
|
||||
buf,
|
||||
contents,
|
||||
self.cx.shared.edition(),
|
||||
cx.shared.edition(),
|
||||
file_span,
|
||||
self.cx,
|
||||
cx,
|
||||
&root_path,
|
||||
None,
|
||||
SourceContext::Standalone,
|
||||
)
|
||||
},
|
||||
&self.cx.shared.style_files,
|
||||
&shared.style_files,
|
||||
);
|
||||
self.cx.shared.fs.write(cur, v)?;
|
||||
shared.fs.write(cur, v)?;
|
||||
self.emitted_local_sources.insert(p);
|
||||
Ok(())
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue