Correctly handle paths from foreign items
This commit is contained in:
parent
36fa557a5e
commit
e161fa1a6b
3 changed files with 65 additions and 11 deletions
|
@ -1,7 +1,7 @@
|
||||||
use std::collections::hash_map::Entry;
|
use std::collections::hash_map::Entry;
|
||||||
use std::collections::BTreeMap;
|
use std::collections::BTreeMap;
|
||||||
|
|
||||||
use rustc_data_structures::fx::FxHashMap;
|
use rustc_data_structures::fx::{FxHashMap, FxIndexMap};
|
||||||
use rustc_middle::ty::TyCtxt;
|
use rustc_middle::ty::TyCtxt;
|
||||||
use rustc_span::symbol::Symbol;
|
use rustc_span::symbol::Symbol;
|
||||||
use serde::ser::{Serialize, SerializeSeq, SerializeStruct, Serializer};
|
use serde::ser::{Serialize, SerializeSeq, SerializeStruct, Serializer};
|
||||||
|
@ -246,6 +246,11 @@ pub(crate) fn build_index<'tcx>(
|
||||||
where
|
where
|
||||||
S: Serializer,
|
S: Serializer,
|
||||||
{
|
{
|
||||||
|
let mut extra_paths = FxHashMap::default();
|
||||||
|
// We need to keep the order of insertion, hence why we use an `IndexMap`. Then we will
|
||||||
|
// insert these "extra paths" (which are paths of items from external crates) into the
|
||||||
|
// `full_paths` list at the end.
|
||||||
|
let mut revert_extra_paths = FxIndexMap::default();
|
||||||
let mut mod_paths = FxHashMap::default();
|
let mut mod_paths = FxHashMap::default();
|
||||||
for (index, item) in self.items.iter().enumerate() {
|
for (index, item) in self.items.iter().enumerate() {
|
||||||
if item.path.is_empty() {
|
if item.path.is_empty() {
|
||||||
|
@ -253,17 +258,43 @@ pub(crate) fn build_index<'tcx>(
|
||||||
}
|
}
|
||||||
mod_paths.insert(&item.path, index);
|
mod_paths.insert(&item.path, index);
|
||||||
}
|
}
|
||||||
let paths = self
|
let mut paths = Vec::with_capacity(self.paths.len());
|
||||||
.paths
|
for (ty, path) in &self.paths {
|
||||||
.iter()
|
|
||||||
.map(|(ty, path)| {
|
|
||||||
if path.len() < 2 {
|
if path.len() < 2 {
|
||||||
return Paths { ty: *ty, name: path[0], path: None };
|
paths.push(Paths { ty: *ty, name: path[0], path: None });
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
let full_path = join_with_double_colon(&path[..path.len() - 1]);
|
||||||
|
if let Some(index) = mod_paths.get(&full_path) {
|
||||||
|
paths.push(Paths { ty: *ty, name: *path.last().unwrap(), path: Some(*index) });
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
// It means it comes from an external crate so the item and its path will be
|
||||||
|
// stored into another array.
|
||||||
|
//
|
||||||
|
// `index` is put after the last `mod_paths`
|
||||||
|
let index = extra_paths.len() + self.items.len();
|
||||||
|
if !revert_extra_paths.contains_key(&index) {
|
||||||
|
revert_extra_paths.insert(index, full_path.clone());
|
||||||
|
}
|
||||||
|
match extra_paths.entry(full_path) {
|
||||||
|
Entry::Occupied(entry) => {
|
||||||
|
paths.push(Paths {
|
||||||
|
ty: *ty,
|
||||||
|
name: *path.last().unwrap(),
|
||||||
|
path: Some(*entry.get()),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
Entry::Vacant(entry) => {
|
||||||
|
entry.insert(index);
|
||||||
|
paths.push(Paths {
|
||||||
|
ty: *ty,
|
||||||
|
name: *path.last().unwrap(),
|
||||||
|
path: Some(index),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
let index = mod_paths.get(&join_with_double_colon(&path[..path.len() - 1]));
|
|
||||||
Paths { ty: *ty, name: *path.last().unwrap(), path: index.copied() }
|
|
||||||
})
|
|
||||||
.collect::<Vec<_>>();
|
|
||||||
|
|
||||||
let mut names = Vec::with_capacity(self.items.len());
|
let mut names = Vec::with_capacity(self.items.len());
|
||||||
let mut types = String::with_capacity(self.items.len());
|
let mut types = String::with_capacity(self.items.len());
|
||||||
|
@ -322,6 +353,10 @@ pub(crate) fn build_index<'tcx>(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (index, path) in &revert_extra_paths {
|
||||||
|
full_paths.push((*index, path));
|
||||||
|
}
|
||||||
|
|
||||||
let has_aliases = !self.aliases.is_empty();
|
let has_aliases = !self.aliases.is_empty();
|
||||||
let mut crate_data =
|
let mut crate_data =
|
||||||
serializer.serialize_struct("CrateData", if has_aliases { 9 } else { 8 })?;
|
serializer.serialize_struct("CrateData", if has_aliases { 9 } else { 8 })?;
|
||||||
|
|
|
@ -22,4 +22,22 @@ const EXPECTED = [
|
||||||
{ 'path': 'full_path_function::b::Sac', 'name': 'bar2' },
|
{ 'path': 'full_path_function::b::Sac', 'name': 'bar2' },
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
'query': 'string::string -> u32',
|
||||||
|
'others': [
|
||||||
|
{ 'path': 'full_path_function::b::Sac', 'name': 'string' },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
'query': 'alloc::string::string -> u32',
|
||||||
|
'others': [
|
||||||
|
{ 'path': 'full_path_function::b::Sac', 'name': 'string' },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
'query': 'alloc::string -> u32',
|
||||||
|
'others': [
|
||||||
|
{ 'path': 'full_path_function::b::Sac', 'name': 'string' },
|
||||||
|
],
|
||||||
|
},
|
||||||
];
|
];
|
||||||
|
|
|
@ -12,5 +12,6 @@ pub mod b {
|
||||||
pub fn len(&self) -> usize { 0 }
|
pub fn len(&self) -> usize { 0 }
|
||||||
pub fn bar(&self, w: u32) -> usize { 0 }
|
pub fn bar(&self, w: u32) -> usize { 0 }
|
||||||
pub fn bar2(&self, w: u32) -> u32 { 0 }
|
pub fn bar2(&self, w: u32) -> u32 { 0 }
|
||||||
|
pub fn string(w: String) -> u32 { 0 }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue