Skip to content

Commit e173857

Browse files
Use ItemKind placeholders for alternative macro kinds
1 parent 07871bd commit e173857

File tree

14 files changed

+214
-152
lines changed

14 files changed

+214
-152
lines changed

src/librustdoc/clean/inline.rs

Lines changed: 74 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,27 @@ pub(crate) fn try_inline(
4646
attrs: Option<(&[hir::Attribute], Option<LocalDefId>)>,
4747
visited: &mut DefIdSet,
4848
) -> Option<Vec<clean::Item>> {
49+
fn try_inline_inner(
50+
cx: &mut DocContext<'_>,
51+
kind: clean::ItemKind,
52+
did: DefId,
53+
name: Symbol,
54+
import_def_id: Option<LocalDefId>,
55+
) -> clean::Item {
56+
cx.inlined.insert(did.into());
57+
let mut item = crate::clean::generate_item_with_correct_attrs(
58+
cx,
59+
kind,
60+
did,
61+
name,
62+
import_def_id.as_slice(),
63+
None,
64+
);
65+
// The visibility needs to reflect the one from the reexport and not from the "source" DefId.
66+
item.inner.inline_stmt_id = import_def_id;
67+
item
68+
}
69+
4970
let did = res.opt_def_id()?;
5071
if did.is_local() {
5172
return None;
@@ -138,7 +159,7 @@ pub(crate) fn try_inline(
138159
})
139160
}
140161
Res::Def(DefKind::Macro(kinds), did) => {
141-
let mac = build_macro(cx, did, name, kinds);
162+
let (mac, others) = build_macro(cx, did, name, kinds);
142163

143164
let type_kind = match kinds {
144165
MacroKinds::BANG => ItemType::Macro,
@@ -148,23 +169,21 @@ pub(crate) fn try_inline(
148169
_ => panic!("unsupported macro kind {kinds:?}"),
149170
};
150171
record_extern_fqn(cx, did, type_kind);
151-
mac
172+
let first = try_inline_inner(cx, mac, did, name, import_def_id);
173+
if let Some(others) = others {
174+
for mac_kind in others {
175+
let mut mac = first.clone();
176+
mac.inner.kind = mac_kind;
177+
ret.push(mac);
178+
}
179+
}
180+
ret.push(first);
181+
return Some(ret);
152182
}
153183
_ => return None,
154184
};
155185

156-
cx.inlined.insert(did.into());
157-
let mut item = crate::clean::generate_item_with_correct_attrs(
158-
cx,
159-
kind,
160-
did,
161-
name,
162-
import_def_id.as_slice(),
163-
None,
164-
);
165-
// The visibility needs to reflect the one from the reexport and not from the "source" DefId.
166-
item.inner.inline_stmt_id = import_def_id;
167-
ret.push(item);
186+
ret.push(try_inline_inner(cx, kind, did, name, import_def_id));
168187
Some(ret)
169188
}
170189

@@ -752,31 +771,51 @@ fn build_macro(
752771
def_id: DefId,
753772
name: Symbol,
754773
macro_kinds: MacroKinds,
755-
) -> clean::ItemKind {
774+
) -> (clean::ItemKind, Option<Vec<clean::ItemKind>>) {
756775
match CStore::from_tcx(cx.tcx).load_macro_untracked(def_id, cx.tcx) {
757776
LoadedMacro::MacroDef { def, .. } => match macro_kinds {
758-
MacroKinds::BANG => clean::MacroItem(
759-
clean::Macro {
760-
source: utils::display_macro_source(cx, name, &def),
761-
macro_rules: def.macro_rules,
762-
},
777+
MacroKinds::BANG => (
778+
clean::MacroItem(
779+
clean::Macro {
780+
source: utils::display_macro_source(cx, name, &def),
781+
macro_rules: def.macro_rules,
782+
},
783+
None,
784+
),
785+
None,
786+
),
787+
MacroKinds::DERIVE => (
788+
clean::ProcMacroItem(clean::ProcMacro {
789+
kind: MacroKind::Derive,
790+
helpers: Vec::new(),
791+
}),
763792
None,
764793
),
765-
MacroKinds::DERIVE => clean::ProcMacroItem(clean::ProcMacro {
766-
kind: MacroKind::Derive,
767-
helpers: Vec::new(),
768-
}),
769-
MacroKinds::ATTR => clean::ProcMacroItem(clean::ProcMacro {
770-
kind: MacroKind::Attr,
771-
helpers: Vec::new(),
772-
}),
773-
_ if macro_kinds == (MacroKinds::BANG | MacroKinds::ATTR) => clean::MacroItem(
774-
clean::Macro {
775-
source: utils::display_macro_source(cx, name, &def),
776-
macro_rules: def.macro_rules,
777-
},
778-
Some(macro_kinds),
794+
MacroKinds::ATTR => (
795+
clean::ProcMacroItem(clean::ProcMacro {
796+
kind: MacroKind::Attr,
797+
helpers: Vec::new(),
798+
}),
799+
None,
779800
),
801+
_ if macro_kinds.contains(MacroKinds::BANG) => {
802+
let kind = clean::MacroItem(
803+
clean::Macro {
804+
source: utils::display_macro_source(cx, name, &def),
805+
macro_rules: def.macro_rules,
806+
},
807+
Some(macro_kinds),
808+
);
809+
let mut ret = vec![];
810+
for kind in macro_kinds.iter().filter(|kind| *kind != MacroKinds::BANG) {
811+
match kind {
812+
MacroKinds::ATTR => ret.push(clean::AttrMacroItem),
813+
MacroKinds::DERIVE => ret.push(clean::DeriveMacroItem),
814+
_ => panic!("unsupported macro kind {kind:?}"),
815+
}
816+
}
817+
(kind, Some(ret))
818+
}
780819
_ => panic!("unsupported macro kind {macro_kinds:?}"),
781820
},
782821
LoadedMacro::ProcMacro(ext) => {
@@ -787,7 +826,7 @@ fn build_macro(
787826
MacroKinds::DERIVE => MacroKind::Derive,
788827
_ => unreachable!(),
789828
};
790-
clean::ProcMacroItem(clean::ProcMacro { kind, helpers: ext.helper_attrs })
829+
(clean::ProcMacroItem(clean::ProcMacro { kind, helpers: ext.helper_attrs }), None)
791830
}
792831
}
793832
}

src/librustdoc/clean/mod.rs

Lines changed: 37 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2855,13 +2855,43 @@ fn clean_maybe_renamed_item<'tcx>(
28552855
),
28562856
MacroKinds::ATTR => clean_proc_macro(item, &mut name, MacroKind::Attr, cx),
28572857
MacroKinds::DERIVE => clean_proc_macro(item, &mut name, MacroKind::Derive, cx),
2858-
_ => MacroItem(
2859-
Macro {
2860-
source: display_macro_source(cx, name, macro_def),
2861-
macro_rules: macro_def.macro_rules,
2862-
},
2863-
Some(kinds),
2864-
),
2858+
_ if kinds.contains(MacroKinds::BANG) => {
2859+
let kind = MacroItem(
2860+
Macro {
2861+
source: display_macro_source(cx, name, macro_def),
2862+
macro_rules: macro_def.macro_rules,
2863+
},
2864+
Some(kinds),
2865+
);
2866+
let mac = generate_item_with_correct_attrs(
2867+
cx,
2868+
kind,
2869+
item.owner_id.def_id.to_def_id(),
2870+
name,
2871+
import_ids,
2872+
renamed,
2873+
);
2874+
2875+
let mut ret = Vec::with_capacity(3);
2876+
for kind in kinds.iter().filter(|kind| *kind != MacroKinds::BANG) {
2877+
match kind {
2878+
MacroKinds::ATTR => {
2879+
let mut attr = mac.clone();
2880+
attr.inner.kind = AttrMacroItem;
2881+
ret.push(attr);
2882+
}
2883+
MacroKinds::DERIVE => {
2884+
let mut derive = mac.clone();
2885+
derive.inner.kind = DeriveMacroItem;
2886+
ret.push(derive);
2887+
}
2888+
_ => panic!("unsupported macro kind {kind:?}"),
2889+
}
2890+
}
2891+
ret.push(mac);
2892+
return ret;
2893+
}
2894+
_ => panic!("unsupported macro kind {kinds:?}"),
28652895
},
28662896
// proc macros can have a name set by attributes
28672897
ItemKind::Fn { ref sig, generics, body: body_id, .. } => {

src/librustdoc/clean/types.rs

Lines changed: 16 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -637,29 +637,23 @@ impl Item {
637637
find_attr!(&self.attrs.other_attrs, AttributeKind::NonExhaustive(..))
638638
}
639639

640-
pub(crate) fn bang_macro_types(&self) -> Option<Vec<ItemType>> {
641-
match self.kind {
642-
ItemKind::MacroItem(_, None) => Some(vec![ItemType::Macro]),
643-
ItemKind::MacroItem(_, Some(kinds)) => Some(
644-
kinds
645-
.iter()
646-
.map(|kind| match kind {
647-
MacroKinds::BANG => ItemType::Macro,
648-
MacroKinds::ATTR => ItemType::ProcAttribute,
649-
MacroKinds::DERIVE => ItemType::ProcDerive,
650-
_ => panic!("unexpected macro kind {kind:?}"),
651-
})
652-
.collect::<Vec<_>>(),
653-
),
654-
_ => None,
655-
}
656-
}
657-
658640
/// Returns a documentation-level item type from the item.
659641
pub(crate) fn type_(&self) -> ItemType {
660642
ItemType::from(self)
661643
}
662644

645+
/// Generates the HTML file name based on the item kind.
646+
pub(crate) fn html_filename(&self) -> String {
647+
let type_ = if self.is_macro_placeholder() { ItemType::Macro } else { self.type_() };
648+
format!("{type_}.{}.html", self.name.unwrap())
649+
}
650+
651+
/// If the current item is a "fake" macro (ie, `AttrMacroItem | ItemKind::DeriveMacroItem` which
652+
/// don't hold any data), it returns `true`.
653+
pub(crate) fn is_macro_placeholder(&self) -> bool {
654+
matches!(self.kind, ItemKind::AttrMacroItem | ItemKind::DeriveMacroItem)
655+
}
656+
663657
pub(crate) fn is_default(&self) -> bool {
664658
match self.kind {
665659
ItemKind::MethodItem(_, Some(defaultness)) => {
@@ -943,6 +937,8 @@ pub(crate) enum ItemKind {
943937
/// `type`s from an extern block
944938
ForeignTypeItem,
945939
MacroItem(Macro, Option<MacroKinds>),
940+
AttrMacroItem,
941+
DeriveMacroItem,
946942
ProcMacroItem(ProcMacro),
947943
PrimitiveItem(PrimitiveType),
948944
/// A required associated constant in a trait declaration.
@@ -993,6 +989,8 @@ impl ItemKind {
993989
| ForeignStaticItem(_, _)
994990
| ForeignTypeItem
995991
| MacroItem(..)
992+
| AttrMacroItem
993+
| DeriveMacroItem
996994
| ProcMacroItem(_)
997995
| PrimitiveItem(_)
998996
| RequiredAssocConstItem(..)

src/librustdoc/fold.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,8 @@ pub(crate) trait DocFolder: Sized {
8989
| ForeignStaticItem(..)
9090
| ForeignTypeItem
9191
| MacroItem(..)
92+
| AttrMacroItem
93+
| DeriveMacroItem
9294
| ProcMacroItem(_)
9395
| PrimitiveItem(_)
9496
| RequiredAssocConstItem(..)

src/librustdoc/formats/cache.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -373,6 +373,8 @@ impl DocFolder for CacheBuilder<'_, '_> {
373373
| clean::RequiredAssocTypeItem(..)
374374
| clean::AssocTypeItem(..)
375375
| clean::StrippedItem(..)
376+
| clean::AttrMacroItem
377+
| clean::DeriveMacroItem
376378
| clean::KeywordItem => {
377379
// FIXME: Do these need handling?
378380
// The person writing this comment doesn't know.

src/librustdoc/formats/item_type.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,10 @@ impl<'a> From<&'a clean::Item> for ItemType {
9595
clean::ForeignFunctionItem(..) => ItemType::Function, // no ForeignFunction
9696
clean::ForeignStaticItem(..) => ItemType::Static, // no ForeignStatic
9797
clean::MacroItem(..) => ItemType::Macro,
98+
// Is this a good idea?
99+
clean::AttrMacroItem => ItemType::ProcAttribute,
100+
// Is this a good idea?
101+
clean::DeriveMacroItem => ItemType::ProcDerive,
98102
clean::PrimitiveItem(..) => ItemType::Primitive,
99103
clean::RequiredAssocConstItem(..)
100104
| clean::ProvidedAssocConstItem(..)

0 commit comments

Comments
 (0)