@@ -228,19 +228,10 @@ impl Clean<ExternalCrate> for CrateNum {
228
228
}
229
229
}
230
230
231
- /*
232
- impl Clean<ItemEnum> for hir::ItemKind<'_> {
233
- fn clean(&self, _cx: &DocContext<'_>) -> ItemEnum {
234
- match self {
235
- ExternalCrate(name) =>
236
- }
237
- }
238
- }
239
- */
240
-
241
- enum CleanedModule {
242
- Module ( ItemKind ) ,
243
- Inlined ( Vec < Item > ) ,
231
+ enum MaybeInlined {
232
+ NotInlined ( ItemKind ) ,
233
+ InlinedWithoutOriginal ( Vec < Item > ) ,
234
+ InlinedWithOriginal ( Vec < Item > , ItemKind ) ,
244
235
}
245
236
246
237
impl Clean < Vec < Item > > for hir:: Item < ' _ > {
@@ -249,23 +240,14 @@ impl Clean<Vec<Item>> for hir::Item<'_> {
249
240
250
241
let def_id = cx. tcx . hir ( ) . local_def_id ( self . hir_id ) . to_def_id ( ) ;
251
242
let name = cx. tcx . item_name ( def_id) . clean ( cx) ;
252
- let kind = match self . kind {
243
+ let maybe_inlined = match self . kind {
253
244
// TODO: should store Symbol, not String
254
- ItemKind :: ExternCrate ( renamed) => match clean_extern_crate ( self , renamed, cx) {
255
- CleanedModule :: Module ( inner) => inner,
256
- CleanedModule :: Inlined ( items) => return items,
257
- } ,
258
- ItemKind :: Use ( path, kind) => unimplemented ! ( ) ,
259
- /*
260
- ImportItem(Import {
261
- kind: kind.clean(cx),
262
- source: path.clean(cx),
263
- }),
264
- */
245
+ ItemKind :: ExternCrate ( renamed) => clean_extern_crate ( self , renamed, cx) ,
246
+ ItemKind :: Use ( path, kind) => clean_import ( self , path, kind, cx) ,
265
247
_ => unimplemented ! ( ) ,
266
248
} ;
267
249
268
- vec ! [ Item {
250
+ let build_item = |kind| Item {
269
251
def_id,
270
252
kind,
271
253
name : Some ( name) ,
@@ -274,7 +256,17 @@ impl Clean<Vec<Item>> for hir::Item<'_> {
274
256
visibility : self . vis . clean ( cx) , // TODO: use tcx.visibility once #78077 lands
275
257
stability : cx. tcx . lookup_stability ( def_id) . copied ( ) ,
276
258
deprecation : cx. tcx . lookup_deprecation ( def_id) . clean ( cx) ,
277
- } ]
259
+ } ;
260
+
261
+ match maybe_inlined {
262
+ MaybeInlined :: NotInlined ( inner) => vec ! [ build_item( inner) ] ,
263
+ MaybeInlined :: InlinedWithoutOriginal ( items) => items,
264
+ MaybeInlined :: InlinedWithOriginal ( mut items, inner) => {
265
+ let current = build_item ( inner) ;
266
+ items. push ( current) ;
267
+ items
268
+ }
269
+ }
278
270
}
279
271
}
280
272
@@ -2241,7 +2233,7 @@ fn clean_extern_crate(
2241
2233
item : & hir:: Item < ' _ > ,
2242
2234
renamed : Option < Symbol > ,
2243
2235
cx : & DocContext < ' _ > ,
2244
- ) -> CleanedModule {
2236
+ ) -> MaybeInlined {
2245
2237
let please_inline = item. vis . node . is_pub ( )
2246
2238
&& item. attrs . iter ( ) . any ( |a| {
2247
2239
a. has_name ( sym:: doc)
@@ -2266,102 +2258,91 @@ fn clean_extern_crate(
2266
2258
Some ( item. attrs ) ,
2267
2259
& mut visited,
2268
2260
) {
2269
- return CleanedModule :: Inlined ( items) ;
2261
+ return MaybeInlined :: InlinedWithoutOriginal ( items) ;
2270
2262
}
2271
2263
}
2272
2264
2273
- CleanedModule :: Module ( ExternCrateItem ( name. clean ( cx) , renamed. clean ( cx) ) )
2265
+ MaybeInlined :: NotInlined ( ExternCrateItem ( name. clean ( cx) , renamed. clean ( cx) ) )
2274
2266
}
2275
2267
2276
- impl Clean < Vec < Item > > for doctree:: Import < ' _ > {
2277
- fn clean ( & self , cx : & DocContext < ' _ > ) -> Vec < Item > {
2278
- // We need this comparison because some imports (for std types for example)
2279
- // are "inserted" as well but directly by the compiler and they should not be
2280
- // taken into account.
2281
- if self . span . ctxt ( ) . outer_expn_data ( ) . kind == ExpnKind :: AstPass ( AstPass :: StdImports ) {
2282
- return Vec :: new ( ) ;
2283
- }
2284
-
2285
- // We consider inlining the documentation of `pub use` statements, but we
2286
- // forcefully don't inline if this is not public or if the
2287
- // #[doc(no_inline)] attribute is present.
2288
- // Don't inline doc(hidden) imports so they can be stripped at a later stage.
2289
- let mut denied = !self . vis . node . is_pub ( )
2290
- || self . attrs . iter ( ) . any ( |a| {
2291
- a. has_name ( sym:: doc)
2292
- && match a. meta_item_list ( ) {
2293
- Some ( l) => {
2294
- attr:: list_contains_name ( & l, sym:: no_inline)
2295
- || attr:: list_contains_name ( & l, sym:: hidden)
2296
- }
2297
- None => false ,
2268
+ fn clean_import (
2269
+ item : & hir:: Item < ' _ > ,
2270
+ path : & hir:: Path < ' _ > ,
2271
+ kind : hir:: UseKind ,
2272
+ cx : & DocContext < ' _ > ,
2273
+ ) -> MaybeInlined {
2274
+ // We need this comparison because some imports (for std types for example)
2275
+ // are "inserted" as well but directly by the compiler and they should not be
2276
+ // taken into account.
2277
+ if item. span . ctxt ( ) . outer_expn_data ( ) . kind == ExpnKind :: AstPass ( AstPass :: StdImports )
2278
+ // Ignore ListStem; rustdoc doesn't care about it
2279
+ || kind == hir:: UseKind :: ListStem
2280
+ {
2281
+ return MaybeInlined :: InlinedWithoutOriginal ( Vec :: new ( ) ) ;
2282
+ }
2283
+
2284
+ // We consider inlining the documentation of `pub use` statements, but we
2285
+ // forcefully don't inline if this is not public or if the
2286
+ // #[doc(no_inline)] attribute is present.
2287
+ // Don't inline doc(hidden) imports so they can be stripped at a later stage.
2288
+ let mut denied = !item. vis . node . is_pub ( )
2289
+ || item. attrs . iter ( ) . any ( |a| {
2290
+ a. has_name ( sym:: doc)
2291
+ && match a. meta_item_list ( ) {
2292
+ Some ( l) => {
2293
+ attr:: list_contains_name ( & l, sym:: no_inline)
2294
+ || attr:: list_contains_name ( & l, sym:: hidden)
2298
2295
}
2299
- } ) ;
2300
- // Also check whether imports were asked to be inlined, in case we're trying to re-export a
2301
- // crate in Rust 2018+
2302
- let please_inline = self . attrs . lists ( sym:: doc) . has_word ( sym:: inline) ;
2303
- let path = self . path . clean ( cx) ;
2304
- let inner = if self . glob {
2305
- if !denied {
2306
- let mut visited = FxHashSet :: default ( ) ;
2307
- if let Some ( items) = inline:: try_inline_glob ( cx, path. res , & mut visited) {
2308
- return items;
2296
+ None => false ,
2309
2297
}
2298
+ } ) ;
2299
+ // Also check whether imports were asked to be inlined, in case we're trying to re-export a
2300
+ // crate in Rust 2018+
2301
+ let please_inline = item. attrs . lists ( sym:: doc) . has_word ( sym:: inline) ;
2302
+ let path = path. clean ( cx) ;
2303
+ let kind = if kind == hir:: UseKind :: Glob {
2304
+ if !denied {
2305
+ let mut visited = FxHashSet :: default ( ) ;
2306
+ if let Some ( items) = inline:: try_inline_glob ( cx, path. res , & mut visited) {
2307
+ return MaybeInlined :: InlinedWithoutOriginal ( items) ;
2310
2308
}
2311
- Import :: new_glob ( resolve_use_source ( cx, path) , true )
2312
- } else {
2313
- let name = self . name ;
2314
- if !please_inline {
2315
- if let Res :: Def ( DefKind :: Mod , did) = path. res {
2316
- if !did. is_local ( ) && did. index == CRATE_DEF_INDEX {
2317
- // if we're `pub use`ing an extern crate root, don't inline it unless we
2318
- // were specifically asked for it
2319
- denied = true ;
2320
- }
2309
+ }
2310
+ Import :: new_glob ( resolve_use_source ( cx, path) , true )
2311
+ } else {
2312
+ let def_id = cx. tcx . hir ( ) . local_def_id ( item. hir_id ) . to_def_id ( ) ;
2313
+ let name = cx. tcx . item_name ( def_id) ;
2314
+ if !please_inline {
2315
+ if let Res :: Def ( DefKind :: Mod , did) = path. res {
2316
+ if !did. is_local ( ) && did. index == CRATE_DEF_INDEX {
2317
+ // if we're `pub use`ing an extern crate root, don't inline it unless we
2318
+ // were specifically asked for it
2319
+ denied = true ;
2321
2320
}
2322
2321
}
2323
- if !denied {
2324
- let mut visited = FxHashSet :: default ( ) ;
2325
-
2326
- if let Some ( mut items) = inline:: try_inline (
2327
- cx,
2328
- cx. tcx . parent_module ( self . id ) . to_def_id ( ) ,
2329
- path. res ,
2330
- name,
2331
- Some ( self . attrs ) ,
2332
- & mut visited,
2333
- ) {
2334
- items. push ( Item {
2335
- name : None ,
2336
- attrs : self . attrs . clean ( cx) ,
2337
- source : self . span . clean ( cx) ,
2338
- def_id : cx. tcx . hir ( ) . local_def_id ( self . id ) . to_def_id ( ) ,
2339
- visibility : self . vis . clean ( cx) ,
2340
- stability : None ,
2341
- deprecation : None ,
2342
- kind : ImportItem ( Import :: new_simple (
2343
- self . name . clean ( cx) ,
2344
- resolve_use_source ( cx, path) ,
2345
- false ,
2346
- ) ) ,
2347
- } ) ;
2348
- return items;
2349
- }
2322
+ }
2323
+ if !denied {
2324
+ let mut visited = FxHashSet :: default ( ) ;
2325
+
2326
+ if let Some ( items) = inline:: try_inline (
2327
+ cx,
2328
+ cx. tcx . parent_module ( item. hir_id ) . to_def_id ( ) ,
2329
+ path. res ,
2330
+ name,
2331
+ Some ( item. attrs ) ,
2332
+ & mut visited,
2333
+ ) {
2334
+ let kind = ImportItem ( Import :: new_simple (
2335
+ name. clean ( cx) ,
2336
+ resolve_use_source ( cx, path) ,
2337
+ false ,
2338
+ ) ) ;
2339
+ return MaybeInlined :: InlinedWithOriginal ( items, kind) ;
2350
2340
}
2351
- Import :: new_simple ( name. clean ( cx) , resolve_use_source ( cx, path) , true )
2352
- } ;
2341
+ }
2342
+ Import :: new_simple ( name. clean ( cx) , resolve_use_source ( cx, path) , true )
2343
+ } ;
2353
2344
2354
- vec ! [ Item {
2355
- name: None ,
2356
- attrs: self . attrs. clean( cx) ,
2357
- source: self . span. clean( cx) ,
2358
- def_id: DefId :: local( CRATE_DEF_INDEX ) ,
2359
- visibility: self . vis. clean( cx) ,
2360
- stability: None ,
2361
- deprecation: None ,
2362
- kind: ImportItem ( inner) ,
2363
- } ]
2364
- }
2345
+ MaybeInlined :: NotInlined ( ImportItem ( kind) )
2365
2346
}
2366
2347
2367
2348
impl Clean < Item > for doctree:: ForeignItem < ' _ > {
0 commit comments