@@ -15,11 +15,18 @@ use its = syntax::parse::token::ident_to_str;
1515
1616use syntax;
1717use syntax:: ast;
18+ use syntax:: ast_map;
1819use syntax:: ast_util;
1920use syntax:: attr;
2021use syntax:: attr:: AttributeMethods ;
2122
23+ use rustc:: metadata:: cstore;
24+ use rustc:: metadata:: csearch;
25+ use rustc:: metadata:: decoder;
26+
2227use std;
28+ use std:: hashmap:: HashMap ;
29+
2330use doctree;
2431use visit_ast;
2532use std:: local_data;
@@ -61,19 +68,44 @@ impl<T: Clean<U>, U> Clean<~[U]> for syntax::opt_vec::OptVec<T> {
6168pub struct Crate {
6269 name : ~str ,
6370 module : Option < Item > ,
71+ externs : HashMap < ast:: CrateNum , ExternalCrate > ,
6472}
6573
6674impl Clean < Crate > for visit_ast:: RustdocVisitor {
6775 fn clean ( & self ) -> Crate {
6876 use syntax:: attr:: { find_linkage_metas, last_meta_item_value_str_by_name} ;
69- let maybe_meta = last_meta_item_value_str_by_name ( find_linkage_metas ( self . attrs ) , "name" ) ;
77+ let maybe_meta = last_meta_item_value_str_by_name (
78+ find_linkage_metas ( self . attrs ) , "name" ) ;
79+ let cx = local_data:: get ( super :: ctxtkey, |x| * x. unwrap ( ) ) ;
80+
81+ let mut externs = HashMap :: new ( ) ;
82+ do cstore:: iter_crate_data ( cx. sess . cstore ) |n, meta| {
83+ externs. insert ( n, meta. clean ( ) ) ;
84+ }
7085
7186 Crate {
7287 name : match maybe_meta {
7388 Some ( x) => x. to_owned ( ) ,
74- None => fail2 ! ( "rustdoc_ng requires a \\ #[link(name=\" foo\" )] crate attribute" ) ,
89+ None => fail2 ! ( "rustdoc requires a \\ #[link(name=\" foo\" )] \
90+ crate attribute") ,
7591 } ,
7692 module : Some ( self . module . clean ( ) ) ,
93+ externs : externs,
94+ }
95+ }
96+ }
97+
98+ #[ deriving( Clone , Encodable , Decodable ) ]
99+ pub struct ExternalCrate {
100+ name : ~str ,
101+ attrs : ~[ Attribute ] ,
102+ }
103+
104+ impl Clean < ExternalCrate > for cstore:: crate_metadata {
105+ fn clean ( & self ) -> ExternalCrate {
106+ ExternalCrate {
107+ name : self . name . to_owned ( ) ,
108+ attrs : decoder:: get_crate_attributes ( self . data ) . clean ( )
77109 }
78110 }
79111}
@@ -542,7 +574,15 @@ pub enum Type {
542574 ResolvedPath {
543575 path : Path ,
544576 typarams : Option < ~[ TyParamBound ] > ,
545- did : ast:: DefId
577+ id : ast:: NodeId ,
578+ } ,
579+ /// Same as above, but only external variants
580+ ExternalPath {
581+ path : Path ,
582+ typarams : Option < ~[ TyParamBound ] > ,
583+ fqn : ~[ ~str ] ,
584+ kind : TypeKind ,
585+ crate : ast : : CrateNum ,
546586 } ,
547587 // I have no idea how to usefully use this.
548588 TyParamBinder ( ast:: NodeId ) ,
@@ -572,6 +612,14 @@ pub enum Type {
572612 // region, raw, other boxes, mutable
573613}
574614
615+ #[ deriving( Clone , Encodable , Decodable ) ]
616+ pub enum TypeKind {
617+ TypeStruct ,
618+ TypeEnum ,
619+ TypeTrait ,
620+ TypeFunction ,
621+ }
622+
575623impl Clean < Type > for ast:: Ty {
576624 fn clean ( & self ) -> Type {
577625 use syntax:: ast:: * ;
@@ -1099,26 +1147,12 @@ fn name_from_pat(p: &ast::Pat) -> ~str {
10991147 }
11001148}
11011149
1102- fn remove_comment_tags ( s : & str ) -> ~str {
1103- if s. starts_with ( "/" ) {
1104- match s. slice ( 0 , 3 ) {
1105- & "///" => return s. slice ( 3 , s. len ( ) ) . trim ( ) . to_owned ( ) ,
1106- & "/**" | & "/*!" => return s. slice ( 3 , s. len ( ) - 2 ) . trim ( ) . to_owned ( ) ,
1107- _ => return s. trim ( ) . to_owned ( )
1108- }
1109- } else {
1110- return s. to_owned ( ) ;
1111- }
1112- }
1113-
11141150/// Given a Type, resolve it using the def_map
11151151fn resolve_type ( path : Path , tpbs : Option < ~[ TyParamBound ] > ,
11161152 id : ast:: NodeId ) -> Type {
1117- use syntax:: ast:: * ;
1118-
1119- let dm = local_data:: get ( super :: ctxtkey, |x| * x. unwrap ( ) ) . tycx . def_map ;
1153+ let cx = local_data:: get ( super :: ctxtkey, |x| * x. unwrap ( ) ) ;
11201154 debug2 ! ( "searching for {:?} in defmap" , id) ;
1121- let d = match dm . find ( & id) {
1155+ let d = match cx . tycx . def_map . find ( & id) {
11221156 Some ( k) => k,
11231157 None => {
11241158 let ctxt = local_data:: get ( super :: ctxtkey, |x| * x. unwrap ( ) ) ;
@@ -1128,28 +1162,41 @@ fn resolve_type(path: Path, tpbs: Option<~[TyParamBound]>,
11281162 }
11291163 } ;
11301164
1131- let def_id = match * d {
1132- DefFn ( i, _) => i ,
1133- DefSelf ( i) | DefSelfTy ( i) => return Self ( i) ,
1134- DefTy ( i) => i ,
1135- DefTrait ( i) => {
1165+ let ( def_id, kind ) = match * d {
1166+ ast :: DefFn ( i, _) => ( i , TypeFunction ) ,
1167+ ast :: DefSelf ( i) | ast :: DefSelfTy ( i) => return Self ( i) ,
1168+ ast :: DefTy ( i) => ( i , TypeEnum ) ,
1169+ ast :: DefTrait ( i) => {
11361170 debug2 ! ( "saw DefTrait in def_to_id" ) ;
1137- i
1171+ ( i , TypeTrait )
11381172 } ,
1139- DefPrimTy ( p) => match p {
1140- ty_str => return String ,
1141- ty_bool => return Bool ,
1173+ ast :: DefPrimTy ( p) => match p {
1174+ ast :: ty_str => return String ,
1175+ ast :: ty_bool => return Bool ,
11421176 _ => return Primitive ( p)
11431177 } ,
1144- DefTyParam ( i, _) => return Generic ( i. node ) ,
1145- DefStruct ( i) => i ,
1146- DefTyParamBinder ( i) => {
1178+ ast :: DefTyParam ( i, _) => return Generic ( i. node ) ,
1179+ ast :: DefStruct ( i) => ( i , TypeStruct ) ,
1180+ ast :: DefTyParamBinder ( i) => {
11471181 debug2 ! ( "found a typaram_binder, what is it? {}" , i) ;
11481182 return TyParamBinder ( i) ;
11491183 } ,
11501184 x => fail2 ! ( "resolved type maps to a weird def {:?}" , x) ,
11511185 } ;
1152- ResolvedPath { path : path, typarams : tpbs, did : def_id }
1186+ if ast_util:: is_local ( def_id) {
1187+ ResolvedPath { path : path, typarams : tpbs, id : def_id. node }
1188+ } else {
1189+ let fqn = csearch:: get_item_path ( cx. tycx , def_id) ;
1190+ let fqn = fqn. move_iter ( ) . map ( |i| {
1191+ match i {
1192+ ast_map:: path_mod( id) |
1193+ ast_map:: path_name( id) |
1194+ ast_map:: path_pretty_name( id, _) => id. clean ( )
1195+ }
1196+ } ) . to_owned_vec ( ) ;
1197+ ExternalPath { path : path, typarams : tpbs, fqn : fqn, kind : kind,
1198+ crate : def_id. crate }
1199+ }
11531200}
11541201
11551202fn resolve_use_source ( path : Path , id : ast:: NodeId ) -> ImportSource {
0 commit comments