Skip to content

Commit c3d0d5a

Browse files
QuietMisdreavusManishearth
authored andcommitted
resolve paths when cleaning docs
1 parent 76f8316 commit c3d0d5a

File tree

3 files changed

+45
-5
lines changed

3 files changed

+45
-5
lines changed

src/librustdoc/clean/mod.rs

Lines changed: 40 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,9 @@ use syntax::abi::Abi;
2323
use syntax::ast;
2424
use syntax::attr;
2525
use syntax::codemap::Spanned;
26+
use syntax::feature_gate::UnstableFeatures;
2627
use syntax::ptr::P;
27-
use syntax::symbol::keywords;
28+
use syntax::symbol::{keywords, Symbol};
2829
use syntax_pos::{self, DUMMY_SP, Pos, FileName};
2930

3031
use rustc::middle::const_val::ConstVal;
@@ -33,6 +34,7 @@ use rustc::middle::resolve_lifetime as rl;
3334
use rustc::middle::lang_items;
3435
use rustc::hir::def::{Def, CtorKind};
3536
use rustc::hir::def_id::{CrateNum, DefId, CRATE_DEF_INDEX, LOCAL_CRATE};
37+
use rustc::hir::lowering::Resolver;
3638
use rustc::ty::subst::Substs;
3739
use rustc::ty::{self, Ty, AdtKind};
3840
use rustc::middle::stability;
@@ -43,7 +45,7 @@ use rustc::hir;
4345

4446
use rustc_const_math::ConstInt;
4547
use std::default::Default;
46-
use std::{mem, slice, vec};
48+
use std::{mem, slice, vec, iter};
4749
use std::iter::FromIterator;
4850
use std::rc::Rc;
4951
use std::sync::Arc;
@@ -53,6 +55,7 @@ use core::DocContext;
5355
use doctree;
5456
use visit_ast;
5557
use html::item_type::ItemType;
58+
use html::markdown::markdown_links;
5659

5760
pub mod inline;
5861
pub mod cfg;
@@ -633,6 +636,7 @@ pub struct Attributes {
633636
pub other_attrs: Vec<ast::Attribute>,
634637
pub cfg: Option<Rc<Cfg>>,
635638
pub span: Option<syntax_pos::Span>,
639+
pub links: Vec<(String, DefId)>,
636640
}
637641

638642
impl Attributes {
@@ -762,11 +766,13 @@ impl Attributes {
762766
Some(attr.clone())
763767
})
764768
}).collect();
769+
765770
Attributes {
766771
doc_strings,
767772
other_attrs,
768773
cfg: if cfg == Cfg::True { None } else { Some(Rc::new(cfg)) },
769774
span: sp,
775+
links: vec![],
770776
}
771777
}
772778

@@ -795,7 +801,38 @@ impl AttributesExt for Attributes {
795801

796802
impl Clean<Attributes> for [ast::Attribute] {
797803
fn clean(&self, cx: &DocContext) -> Attributes {
798-
Attributes::from_ast(cx.sess().diagnostic(), self)
804+
let mut attrs = Attributes::from_ast(cx.sess().diagnostic(), self);
805+
806+
if UnstableFeatures::from_environment().is_nightly_build() {
807+
let dox = attrs.collapsed_doc_value().unwrap_or_else(String::new);
808+
for link in markdown_links(&dox, cx.render_type) {
809+
if !link.starts_with("::") {
810+
// FIXME (misdreavus): can only support absolute paths because of limitations
811+
// in Resolver. this may, with a lot of effort, figure out how to resolve paths
812+
// within scopes, but the one use of `resolve_hir_path` i found in the HIR
813+
// lowering code itself used an absolute path. we're brushing up against some
814+
// structural limitations in the compiler already, but this may be a design one
815+
// as well >_>
816+
continue;
817+
}
818+
819+
let mut path = hir::Path {
820+
span: DUMMY_SP,
821+
def: Def::Err,
822+
segments: iter::once(keywords::CrateRoot.name()).chain({
823+
link.split("::").skip(1).map(Symbol::intern)
824+
}).map(hir::PathSegment::from_name).collect(),
825+
};
826+
827+
cx.resolver.borrow_mut().resolve_hir_path(&mut path, false);
828+
829+
if path.def != Def::Err {
830+
attrs.links.push((link, path.def.def_id()));
831+
}
832+
}
833+
}
834+
835+
attrs
799836
}
800837
}
801838

src/librustdoc/core.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ pub type ExternalPaths = FxHashMap<DefId, (Vec<String>, clean::TypeKind)>;
4646

4747
pub struct DocContext<'a, 'tcx: 'a, 'rcx> {
4848
pub tcx: TyCtxt<'a, 'tcx, 'tcx>,
49-
pub resolver: resolve::Resolver<'rcx>,
49+
pub resolver: RefCell<resolve::Resolver<'rcx>>,
5050
pub populated_all_crate_impls: Cell<bool>,
5151
// Note that external items for which `doc(hidden)` applies to are shown as
5252
// non-reachable while local items aren't. This is because we're reusing
@@ -227,7 +227,7 @@ pub fn run_core(search_paths: SearchPaths,
227227

228228
let ctxt = DocContext {
229229
tcx,
230-
resolver,
230+
resolver: RefCell::new(resolver),
231231
populated_all_crate_impls: Cell::new(false),
232232
access_levels: RefCell::new(access_levels),
233233
external_traits: Default::default(),

src/librustdoc/html/markdown.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1169,6 +1169,8 @@ pub fn markdown_links(md: &str, render_type: RenderType) -> Vec<String> {
11691169
let s = unsafe { (*link).as_bytes() };
11701170
let s = str::from_utf8(&s).unwrap().to_owned();
11711171

1172+
debug!("found link: {}", s);
1173+
11721174
links.push(s);
11731175
}
11741176

@@ -1214,6 +1216,7 @@ pub fn markdown_links(md: &str, render_type: RenderType) -> Vec<String> {
12141216

12151217
for ev in iter {
12161218
if let Event::Start(Tag::Link(dest, _)) = ev {
1219+
debug!("found link: {}", dest);
12171220
links.push(dest.into_owned());
12181221
}
12191222
}

0 commit comments

Comments
 (0)