Add code documentation, improve code and improve error message
This commit is contained in:
parent
c06a076634
commit
1561efe41a
5 changed files with 28 additions and 14 deletions
|
|
@ -147,7 +147,7 @@ passes_doc_auto_cfg_expects_hide_or_show =
|
|||
`only "hide" or "show" are allowed in "#[doc(auto_cfg(...))]"`
|
||||
|
||||
passes_doc_auto_cfg_hide_show_expects_list =
|
||||
`#![doc(auto_cfg({$attr_name}(...)))]` only expects a list of items
|
||||
`#![doc(auto_cfg({$attr_name}(...)))]` expects a list of items
|
||||
|
||||
passes_doc_auto_cfg_hide_show_unexpected_item =
|
||||
`#![doc(auto_cfg({$attr_name}(...)))]` only accepts identifiers or key/values items
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ use std::collections::hash_map::Entry;
|
|||
use std::slice;
|
||||
|
||||
use rustc_abi::{Align, ExternAbi, Size};
|
||||
use rustc_ast::{AttrStyle, LitKind, MetaItemInner, MetaItemKind, ast};
|
||||
use rustc_ast::{AttrStyle, LitKind, MetaItem, MetaItemInner, MetaItemKind, ast};
|
||||
use rustc_attr_parsing::{AttributeParser, Late};
|
||||
use rustc_data_structures::fx::FxHashMap;
|
||||
use rustc_errors::{Applicability, DiagCtxtHandle, IntoDiagArg, MultiSpan, StashKey};
|
||||
|
|
@ -1161,10 +1161,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
|
|||
}
|
||||
|
||||
/// Check that the `#![doc(auto_cfg(..))]` attribute has expected input.
|
||||
fn check_doc_auto_cfg(&self, meta: &MetaItemInner, hir_id: HirId) {
|
||||
let MetaItemInner::MetaItem(meta) = meta else {
|
||||
unreachable!();
|
||||
};
|
||||
fn check_doc_auto_cfg(&self, meta: &MetaItem, hir_id: HirId) {
|
||||
match &meta.kind {
|
||||
MetaItemKind::Word => {}
|
||||
MetaItemKind::NameValue(lit) => {
|
||||
|
|
@ -1286,7 +1283,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
|
|||
}
|
||||
|
||||
Some(sym::auto_cfg) => {
|
||||
self.check_doc_auto_cfg(meta, hir_id);
|
||||
self.check_doc_auto_cfg(i_meta, hir_id);
|
||||
}
|
||||
|
||||
Some(sym::inline | sym::no_inline) => {
|
||||
|
|
|
|||
|
|
@ -922,11 +922,19 @@ pub(crate) fn hir_attr_lists<'a, I: IntoIterator<Item = &'a hir::Attribute>>(
|
|||
.flatten()
|
||||
}
|
||||
|
||||
/// This type keeps track of (doc) cfg information as we go down the item tree.
|
||||
#[derive(Clone, Debug)]
|
||||
pub(crate) struct CfgInfo {
|
||||
/// List of `doc(auto_cfg(hide(...)))` cfgs.
|
||||
hidden_cfg: FxHashSet<Cfg>,
|
||||
/// Current computed `cfg`. Each time we enter a new item, this field is updated as well while
|
||||
/// taking into account the `hidden_cfg` information.
|
||||
current_cfg: Cfg,
|
||||
/// Whether the `doc(auto_cfg())` feature is enabled or not at this point.
|
||||
auto_cfg_active: bool,
|
||||
/// If the parent item used `doc(cfg(...))`, then we don't want to overwrite `current_cfg`,
|
||||
/// instead we will concatenate with it. However, if it's not the case, we need to overwrite
|
||||
/// `current_cfg`.
|
||||
parent_is_doc_cfg: bool,
|
||||
}
|
||||
|
||||
|
|
@ -962,6 +970,11 @@ fn show_hide_show_conflict_error(
|
|||
diag.emit();
|
||||
}
|
||||
|
||||
/// This function checks if a same `cfg` is present in both `auto_cfg(hide(...))` and
|
||||
/// `auto_cfg(show(...))` on the same item. If so, it emits an error.
|
||||
///
|
||||
/// Because we go through a list of `cfg`s, we keep track of the `cfg`s we saw in `new_show_attrs`
|
||||
/// and in `new_hide_attrs` arguments.
|
||||
fn handle_auto_cfg_hide_show(
|
||||
tcx: TyCtxt<'_>,
|
||||
cfg_info: &mut CfgInfo,
|
||||
|
|
|
|||
|
|
@ -30,7 +30,8 @@ struct CfgPropagator<'a, 'tcx> {
|
|||
cfg_info: CfgInfo,
|
||||
}
|
||||
|
||||
fn should_retain(token: &TokenTree) -> bool {
|
||||
/// Returns true if the provided `token` is a `cfg` ident.
|
||||
fn is_cfg_token(token: &TokenTree) -> bool {
|
||||
// We only keep `doc(cfg)` items.
|
||||
matches!(
|
||||
token,
|
||||
|
|
@ -47,7 +48,9 @@ fn should_retain(token: &TokenTree) -> bool {
|
|||
)
|
||||
}
|
||||
|
||||
fn filter_tokens_from_list(args_tokens: &TokenStream) -> Vec<TokenTree> {
|
||||
/// We only want to keep `#[cfg()]` and `#[doc(cfg())]` attributes so we rebuild a vec of
|
||||
/// `TokenTree` with only the tokens we're interested into.
|
||||
fn filter_non_cfg_tokens_from_list(args_tokens: &TokenStream) -> Vec<TokenTree> {
|
||||
let mut tokens = Vec::with_capacity(args_tokens.len());
|
||||
let mut skip_next_delimited = false;
|
||||
for token in args_tokens.iter() {
|
||||
|
|
@ -58,7 +61,7 @@ fn filter_tokens_from_list(args_tokens: &TokenStream) -> Vec<TokenTree> {
|
|||
}
|
||||
skip_next_delimited = false;
|
||||
}
|
||||
token if should_retain(token) => {
|
||||
token if is_cfg_token(token) => {
|
||||
skip_next_delimited = false;
|
||||
tokens.push(token.clone());
|
||||
}
|
||||
|
|
@ -70,7 +73,8 @@ fn filter_tokens_from_list(args_tokens: &TokenStream) -> Vec<TokenTree> {
|
|||
tokens
|
||||
}
|
||||
|
||||
// We only care about `#[cfg()]` and `#[doc(cfg())]`, we discard everything else.
|
||||
/// This function goes through the attributes list (`new_attrs`) and extract the `cfg` tokens from
|
||||
/// it and put them into `attrs`.
|
||||
fn add_only_cfg_attributes(attrs: &mut Vec<Attribute>, new_attrs: &[Attribute]) {
|
||||
for attr in new_attrs {
|
||||
if attr.is_doc_comment() {
|
||||
|
|
@ -84,7 +88,7 @@ fn add_only_cfg_attributes(attrs: &mut Vec<Attribute>, new_attrs: &[Attribute])
|
|||
if ident == sym::doc
|
||||
&& let AttrArgs::Delimited(args) = &mut normal.args
|
||||
{
|
||||
let tokens = filter_tokens_from_list(&args.tokens);
|
||||
let tokens = filter_non_cfg_tokens_from_list(&args.tokens);
|
||||
args.tokens = TokenStream::new(tokens);
|
||||
attrs.push(attr);
|
||||
} else if ident == sym::cfg_trace {
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
error: `#![doc(auto_cfg(hide(...)))]` only expects a list of items
|
||||
error: `#![doc(auto_cfg(hide(...)))]` expects a list of items
|
||||
--> $DIR/doc_cfg_hide.rs:2:8
|
||||
|
|
||||
LL | #![doc(auto_cfg(hide = "test"))]
|
||||
|
|
@ -6,7 +6,7 @@ LL | #![doc(auto_cfg(hide = "test"))]
|
|||
|
|
||||
= note: `#[deny(invalid_doc_attributes)]` on by default
|
||||
|
||||
error: `#![doc(auto_cfg(hide(...)))]` only expects a list of items
|
||||
error: `#![doc(auto_cfg(hide(...)))]` expects a list of items
|
||||
--> $DIR/doc_cfg_hide.rs:3:8
|
||||
|
|
||||
LL | #![doc(auto_cfg(hide))]
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue