Skip to content

Commit 301e456

Browse files
committed
Unrolled build for #162346 in rollup 162612
Rollup merge of #162346 - notriddle:rustdoc-merge-type, r=lolbinarycat,GuillaumeGomez rustdoc: add missing CCI union logic This fixes a bug that was found where `PathBuf` didn't show up in the standard library search results, because the crate that defined it (libstd) was merged into a crate that already had a path entry in its search index (libproc_macro). Fixes #162334
2 parents 67eda61 + 0a9186a commit 301e456

10 files changed

Lines changed: 242 additions & 87 deletions

File tree

src/librustdoc/html/render/search_index.rs

Lines changed: 87 additions & 79 deletions
Original file line numberDiff line numberDiff line change
@@ -315,6 +315,29 @@ impl SerializedSearchIndex {
315315
let other_entryid_offset = self.names.len();
316316
let mut map_other_pathid_to_self_pathid = Vec::new();
317317
let mut skips = FxHashSet::default();
318+
319+
fn remap_entry_data(
320+
other_entry_data: &EntryData,
321+
map_other_pathid_to_self_pathid: &[usize],
322+
) -> EntryData {
323+
EntryData {
324+
parent: other_entry_data
325+
.parent
326+
.map(|parent| map_other_pathid_to_self_pathid[parent])
327+
.clone(),
328+
module_path: other_entry_data
329+
.module_path
330+
.map(|path| map_other_pathid_to_self_pathid[path])
331+
.clone(),
332+
exact_module_path: other_entry_data
333+
.exact_module_path
334+
.map(|exact_path| map_other_pathid_to_self_pathid[exact_path])
335+
.clone(),
336+
krate: map_other_pathid_to_self_pathid[other_entry_data.krate],
337+
..other_entry_data.clone()
338+
}
339+
}
340+
318341
for (other_pathid, other_path_data) in other.path_data.iter().enumerate() {
319342
if let Some(other_path_data) = other_path_data {
320343
let name = Symbol::intern(&other.names[other_pathid]);
@@ -439,87 +462,72 @@ impl SerializedSearchIndex {
439462
}
440463
}
441464
for other_entryid in 0..other.names.len() {
442-
if skips.contains(&other_entryid) {
443-
// we push tombstone entries to keep the IDs lined up
444-
self.push(String::new(), None, None, String::new(), None, None, None);
445-
} else {
446-
self.push(
447-
other.names[other_entryid].clone(),
448-
other.path_data[other_entryid].clone(),
449-
other.entry_data[other_entryid].as_ref().map(|other_entry_data| EntryData {
450-
parent: other_entry_data
451-
.parent
452-
.map(|parent| map_other_pathid_to_self_pathid[parent])
453-
.clone(),
454-
module_path: other_entry_data
455-
.module_path
456-
.map(|path| map_other_pathid_to_self_pathid[path])
457-
.clone(),
458-
exact_module_path: other_entry_data
459-
.exact_module_path
460-
.map(|exact_path| map_other_pathid_to_self_pathid[exact_path])
461-
.clone(),
462-
krate: map_other_pathid_to_self_pathid[other_entry_data.krate],
463-
..other_entry_data.clone()
464-
}),
465-
other.descs[other_entryid].clone(),
466-
other.function_data[other_entryid].clone().map(|mut func| {
467-
fn map_fn_sig_item(
468-
map_other_pathid_to_self_pathid: &Vec<usize>,
469-
ty: &mut RenderType,
470-
) {
471-
match ty.id {
472-
None => {}
473-
Some(RenderTypeId::Index(generic)) if generic < 0 => {}
474-
Some(RenderTypeId::Index(id)) => {
475-
let id = usize::try_from(id).unwrap();
476-
let id = map_other_pathid_to_self_pathid[id];
477-
assert!(id != !0);
478-
ty.id = Some(RenderTypeId::Index(isize::try_from(id).unwrap()));
479-
}
480-
_ => unreachable!(),
465+
self.push(
466+
other.names[other_entryid].clone(),
467+
if skips.contains(&other_entryid) {
468+
None
469+
} else {
470+
other.path_data[other_entryid].clone()
471+
},
472+
other.entry_data[other_entryid].as_ref().map(|other_entry_data| {
473+
remap_entry_data(other_entry_data, &map_other_pathid_to_self_pathid)
474+
}),
475+
other.descs[other_entryid].clone(),
476+
other.function_data[other_entryid].clone().map(|mut func| {
477+
fn map_fn_sig_item(
478+
map_other_pathid_to_self_pathid: &Vec<usize>,
479+
ty: &mut RenderType,
480+
) {
481+
match ty.id {
482+
None => {}
483+
Some(RenderTypeId::Index(generic)) if generic < 0 => {}
484+
Some(RenderTypeId::Index(id)) => {
485+
let id = usize::try_from(id).unwrap();
486+
let id = map_other_pathid_to_self_pathid[id];
487+
assert!(id != !0);
488+
ty.id = Some(RenderTypeId::Index(isize::try_from(id).unwrap()));
481489
}
482-
if let Some(generics) = &mut ty.generics {
483-
for generic in generics {
484-
map_fn_sig_item(map_other_pathid_to_self_pathid, generic);
485-
}
490+
_ => unreachable!(),
491+
}
492+
if let Some(generics) = &mut ty.generics {
493+
for generic in generics {
494+
map_fn_sig_item(map_other_pathid_to_self_pathid, generic);
486495
}
487-
if let Some(bindings) = &mut ty.bindings {
488-
for (param, constraints) in bindings {
489-
*param = match *param {
490-
param @ RenderTypeId::Index(generic) if generic < 0 => {
491-
param
492-
}
493-
RenderTypeId::Index(id) => {
494-
let id = usize::try_from(id).unwrap();
495-
let id = map_other_pathid_to_self_pathid[id];
496-
assert!(id != !0);
497-
RenderTypeId::Index(isize::try_from(id).unwrap())
498-
}
499-
_ => unreachable!(),
500-
};
501-
for constraint in constraints {
502-
map_fn_sig_item(
503-
map_other_pathid_to_self_pathid,
504-
constraint,
505-
);
496+
}
497+
if let Some(bindings) = &mut ty.bindings {
498+
for (param, constraints) in bindings {
499+
*param = match *param {
500+
param @ RenderTypeId::Index(generic) if generic < 0 => param,
501+
RenderTypeId::Index(id) => {
502+
let id = usize::try_from(id).unwrap();
503+
let id = map_other_pathid_to_self_pathid[id];
504+
assert!(id != !0);
505+
RenderTypeId::Index(isize::try_from(id).unwrap())
506506
}
507+
_ => unreachable!(),
508+
};
509+
for constraint in constraints {
510+
map_fn_sig_item(map_other_pathid_to_self_pathid, constraint);
507511
}
508512
}
509513
}
510-
for input in &mut func.inputs {
511-
map_fn_sig_item(&map_other_pathid_to_self_pathid, input);
512-
}
513-
for output in &mut func.output {
514-
map_fn_sig_item(&map_other_pathid_to_self_pathid, output);
515-
}
516-
for clause in &mut func.where_clause {
517-
for entry in clause {
518-
map_fn_sig_item(&map_other_pathid_to_self_pathid, entry);
519-
}
514+
}
515+
for input in &mut func.inputs {
516+
map_fn_sig_item(&map_other_pathid_to_self_pathid, input);
517+
}
518+
for output in &mut func.output {
519+
map_fn_sig_item(&map_other_pathid_to_self_pathid, output);
520+
}
521+
for clause in &mut func.where_clause {
522+
for entry in clause {
523+
map_fn_sig_item(&map_other_pathid_to_self_pathid, entry);
520524
}
521-
func
522-
}),
525+
}
526+
func
527+
}),
528+
if skips.contains(&other_entryid) {
529+
None
530+
} else {
523531
other.type_data[other_entryid].as_ref().map(|type_data| TypeData {
524532
inverted_function_inputs_index: type_data
525533
.inverted_function_inputs_index
@@ -556,11 +564,11 @@ impl SerializedSearchIndex {
556564
})
557565
.collect(),
558566
search_unbox: type_data.search_unbox,
559-
}),
560-
other.alias_pointers[other_entryid]
561-
.map(|alias_pointer| alias_pointer + other_entryid_offset),
562-
);
563-
}
567+
})
568+
},
569+
other.alias_pointers[other_entryid]
570+
.map(|alias_pointer| alias_pointer + other_entryid_offset),
571+
);
564572
}
565573
if other.generic_inverted_index.len() > self.generic_inverted_index.len() {
566574
self.generic_inverted_index.resize(other.generic_inverted_index.len(), Vec::new());

src/librustdoc/html/render/write_shared.rs

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -375,15 +375,20 @@ impl CrateInfo {
375375
.fold(Ok(Vec::new()), |acc, parts_path| {
376376
let mut acc = acc?;
377377
let dir = &parts_path.0;
378-
acc.append(&mut try_err!(std::fs::read_dir(dir), dir.as_path())
378+
let mut files: Vec<Result<PathBuf, std::io::Error>> = try_err!(std::fs::read_dir(dir), dir.as_path())
379+
.map(|file| Ok(file?.path()))
380+
.collect();
381+
files.sort_by_key(|p| p.as_ref().map_or(PathBuf::new(), |p| p.clone()));
382+
acc.append(&mut files
383+
.into_iter()
379384
.filter_map(|file| {
380-
let to_crate_info = |file: Result<std::fs::DirEntry, std::io::Error>| -> Result<Option<CrateInfo>, Error> {
385+
let to_crate_info = |file: Result<PathBuf, std::io::Error>| -> Result<Option<CrateInfo>, Error> {
381386
let file = try_err!(file, dir.as_path());
382-
if file.path().extension() != Some(OsStr::new("json")) {
387+
if file.extension() != Some(OsStr::new("json")) {
383388
return Ok(None);
384389
}
385-
let parts = try_err!(fs::read(file.path()), file.path());
386-
let parts: CrateInfo = try_err!(serde_json::from_slice(&parts), file.path());
390+
let parts = try_err!(fs::read(&file), &file);
391+
let parts: CrateInfo = try_err!(serde_json::from_slice(&parts), &file);
387392
Ok(Some(parts))
388393
};
389394
to_crate_info(file).transpose()

src/tools/compiletest/src/directives.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -215,6 +215,8 @@ pub(crate) struct TestProps {
215215
pub(crate) disable_gdb_pretty_printers: bool,
216216
/// Compare the output by lines, rather than as a single string.
217217
pub(crate) compare_output_by_lines: bool,
218+
/// Use CCI (`--read-doc-meta` and `--write-doc-meta`) merge mode.
219+
pub(crate) use_rustdoc_cci_doc_meta_merge: bool,
218220
}
219221

220222
mod directives {
@@ -262,6 +264,7 @@ mod directives {
262264
pub(crate) const MINICORE_COMPILE_FLAGS: &str = "minicore-compile-flags";
263265
pub(crate) const DISABLE_GDB_PRETTY_PRINTERS: &str = "disable-gdb-pretty-printers";
264266
pub(crate) const COMPARE_OUTPUT_BY_LINES: &str = "compare-output-by-lines";
267+
pub(crate) const USE_RUSTDOC_CCI_DOC_META_MERGE: &str = "use-rustdoc-cci-doc-meta-merge";
265268
}
266269

267270
impl TestProps {
@@ -319,6 +322,7 @@ impl TestProps {
319322
dont_require_annotations: Default::default(),
320323
disable_gdb_pretty_printers: false,
321324
compare_output_by_lines: false,
325+
use_rustdoc_cci_doc_meta_merge: false,
322326
}
323327
}
324328

src/tools/compiletest/src/directives/directive_names.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -310,6 +310,7 @@ pub(crate) const KNOWN_DIRECTIVE_NAMES: &[&str] = &[
310310
"unset-rustc-env",
311311
// Used by the tidy check `unknown_revision`.
312312
"unused-revision-names",
313+
"use-rustdoc-cci-doc-meta-merge",
313314
// tidy-alphabetical-end
314315
];
315316

src/tools/compiletest/src/directives/handlers.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -364,6 +364,13 @@ fn make_directive_handlers_map() -> HashMap<&'static str, Handler> {
364364
&mut props.compare_output_by_lines,
365365
);
366366
}),
367+
handler(USE_RUSTDOC_CCI_DOC_META_MERGE, |config, ln, props| {
368+
config.set_name_directive(
369+
ln,
370+
USE_RUSTDOC_CCI_DOC_META_MERGE,
371+
&mut props.use_rustdoc_cci_doc_meta_merge,
372+
);
373+
}),
367374
];
368375

369376
handlers

src/tools/compiletest/src/runtest.rs

Lines changed: 34 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1047,14 +1047,21 @@ impl<'test> TestCx<'test> {
10471047
.args(&self.props.doc_flags);
10481048

10491049
match kind {
1050-
DocKind::Html => {}
1050+
DocKind::Html => {
1051+
if self.props.use_rustdoc_cci_doc_meta_merge {
1052+
rustdoc.arg("--write-doc-meta-dir").arg(out_dir.as_ref().join("doc.meta"));
1053+
}
1054+
}
10511055
DocKind::Json => {
10521056
rustdoc.arg("--output-format").arg("json");
10531057
}
10541058
}
10551059

10561060
// Both JSON output and `--disable-minification` are unstable rustdoc options.
1057-
if matches!(kind, DocKind::Json) || self.config.disable_minification {
1061+
if matches!(kind, DocKind::Json)
1062+
|| self.config.disable_minification
1063+
|| self.props.use_rustdoc_cci_doc_meta_merge
1064+
{
10581065
rustdoc.arg("-Zunstable-options");
10591066
}
10601067
if self.config.disable_minification {
@@ -1065,7 +1072,31 @@ impl<'test> TestCx<'test> {
10651072
rustdoc.arg(format!("-Clinker={}", linker));
10661073
}
10671074

1068-
self.compose_and_run_compiler(rustdoc, None)
1075+
let docres = self.compose_and_run_compiler(rustdoc, None);
1076+
if !docres.status.success() {
1077+
return docres;
1078+
}
1079+
if kind == DocKind::Html && self.props.use_rustdoc_cci_doc_meta_merge {
1080+
let mut rustdoc_merge = Command::new(rustdoc_path);
1081+
let current_dir = self.output_base_dir();
1082+
rustdoc_merge.current_dir(current_dir);
1083+
rustdoc_merge
1084+
.arg("-o")
1085+
.arg(out_dir.as_ref())
1086+
.args(&self.props.compile_flags)
1087+
.args(&self.props.doc_flags)
1088+
.arg("--read-doc-meta-dir")
1089+
.arg(out_dir.as_ref().join("doc.meta"))
1090+
.arg("-Zunstable-options");
1091+
if self.config.disable_minification {
1092+
rustdoc_merge.arg("--disable-minification");
1093+
}
1094+
let docmerge = self.compose_and_run_compiler(rustdoc_merge, None);
1095+
if !docmerge.status.success() {
1096+
return docmerge;
1097+
}
1098+
}
1099+
docres
10691100
}
10701101

10711102
fn exec_compiled_test(&self) -> ProcRes {

tests/rustdoc-js-std/pathbuf.js

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// The PathBuf type is defined in std,
2+
// but used in proc_macro. This means both crates'
3+
// search indexes contain TypeData for it,
4+
// but only std defines EntryData.
5+
// This test case ensures we can merge them.
6+
//
7+
// https://github.com/rust-lang/rust/issues/162334
8+
9+
10+
const EXPECTED = [
11+
{
12+
query: 'PathBuf',
13+
others: [
14+
{ 'path': 'std::path', 'name': 'PathBuf' },
15+
],
16+
},
17+
];
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
//@ use-rustdoc-cci-doc-meta-merge
2+
3+
/// <https://github.com/rust-lang/rust/issues/162334>
4+
pub struct FooBar;
5+
6+
/// Test case for overlapping struct and function name
7+
#[allow(nonstandard_style)]
8+
pub struct overlapping_name {
9+
_inner: (),
10+
}
11+
12+
/// Test case for overlapping function and struct name
13+
pub fn overlapping_name() -> FooBar {
14+
FooBar
15+
}

0 commit comments

Comments
 (0)