1
+ //! Utility functions for attributes, including Clippy's built-in ones
2
+
1
3
use crate :: source:: SpanRangeExt ;
2
4
use crate :: { sym, tokenize_with_text} ;
3
5
use rustc_ast:: attr;
@@ -12,7 +14,8 @@ use rustc_session::Session;
12
14
use rustc_span:: { Span , Symbol } ;
13
15
use std:: str:: FromStr ;
14
16
15
- pub fn get_attr < ' a , A : AttributeExt + ' a > (
17
+ /// Given `attrs`, extract all the instances of a built-in Clippy attribute called `name`
18
+ pub fn get_builtin_attr < ' a , A : AttributeExt + ' a > (
16
19
sess : & ' a Session ,
17
20
attrs : & ' a [ A ] ,
18
21
name : Symbol ,
@@ -59,9 +62,11 @@ pub fn get_attr<'a, A: AttributeExt + 'a>(
59
62
} )
60
63
}
61
64
62
- pub fn get_unique_attr < ' a , A : AttributeExt > ( sess : & ' a Session , attrs : & ' a [ A ] , name : Symbol ) -> Option < & ' a A > {
65
+ /// If `attrs` contain exactly one instance of a built-in Clippy attribute called `name`,
66
+ /// returns that attribute, and `None` otherwise
67
+ pub fn get_unique_builtin_attr < ' a , A : AttributeExt > ( sess : & ' a Session , attrs : & ' a [ A ] , name : Symbol ) -> Option < & ' a A > {
63
68
let mut unique_attr: Option < & A > = None ;
64
- for attr in get_attr ( sess, attrs, name) {
69
+ for attr in get_builtin_attr ( sess, attrs, name) {
65
70
if let Some ( duplicate) = unique_attr {
66
71
sess. dcx ( )
67
72
. struct_span_err ( attr. span ( ) , format ! ( "`{name}` is defined multiple times" ) )
@@ -74,13 +79,13 @@ pub fn get_unique_attr<'a, A: AttributeExt>(sess: &'a Session, attrs: &'a [A], n
74
79
unique_attr
75
80
}
76
81
77
- /// Returns true if the attributes contain any of `proc_macro`,
78
- /// `proc_macro_derive` or ` proc_macro_attribute`, false otherwise
82
+ /// Checks whether `attrs` contain any of `proc_macro`, `proc_macro_derive` or
83
+ /// `proc_macro_attribute`
79
84
pub fn is_proc_macro ( attrs : & [ impl AttributeExt ] ) -> bool {
80
85
attrs. iter ( ) . any ( AttributeExt :: is_proc_macro_attr)
81
86
}
82
87
83
- /// Returns true if the attributes contain `#[doc(hidden)]`
88
+ /// Checks whether `attrs` contain `#[doc(hidden)]`
84
89
pub fn is_doc_hidden ( attrs : & [ impl AttributeExt ] ) -> bool {
85
90
attrs
86
91
. iter ( )
@@ -89,6 +94,7 @@ pub fn is_doc_hidden(attrs: &[impl AttributeExt]) -> bool {
89
94
. any ( |l| attr:: list_contains_name ( & l, sym:: hidden) )
90
95
}
91
96
97
+ /// Checks whether the given ADT, or any of its fields/variants, are marked as `#[non_exhaustive]`
92
98
pub fn has_non_exhaustive_attr ( tcx : TyCtxt < ' _ > , adt : AdtDef < ' _ > ) -> bool {
93
99
adt. is_variant_list_non_exhaustive ( )
94
100
|| find_attr ! ( tcx. get_all_attrs( adt. did( ) ) , AttributeKind :: NonExhaustive ( ..) )
@@ -101,7 +107,7 @@ pub fn has_non_exhaustive_attr(tcx: TyCtxt<'_>, adt: AdtDef<'_>) -> bool {
101
107
. any ( |field_def| find_attr ! ( tcx. get_all_attrs( field_def. did) , AttributeKind :: NonExhaustive ( ..) ) )
102
108
}
103
109
104
- /// Checks if the given span contains a `#[cfg(..)]` attribute
110
+ /// Checks whether the given span contains a `#[cfg(..)]` attribute
105
111
pub fn span_contains_cfg ( cx : & LateContext < ' _ > , s : Span ) -> bool {
106
112
s. check_source_text ( cx, |src| {
107
113
let mut iter = tokenize_with_text ( src) ;
@@ -123,6 +129,8 @@ pub fn span_contains_cfg(cx: &LateContext<'_>, s: Span) -> bool {
123
129
false
124
130
} )
125
131
}
132
+
133
+ /// Currently used to keep track of the current value of `#[clippy::cognitive_complexity(N)]`
126
134
pub struct LimitStack {
127
135
default : u64 ,
128
136
stack : Vec < u64 > ,
@@ -134,6 +142,7 @@ impl Drop for LimitStack {
134
142
}
135
143
}
136
144
145
+ #[ expect( missing_docs, reason = "they're all trivial..." ) ]
137
146
impl LimitStack {
138
147
#[ must_use]
139
148
/// Initialize the stack starting with a default value, which usually comes from configuration
@@ -157,7 +166,7 @@ impl LimitStack {
157
166
}
158
167
159
168
fn parse_attrs < F : FnMut ( u64 ) > ( sess : & Session , attrs : & [ impl AttributeExt ] , name : Symbol , mut f : F ) {
160
- for attr in get_attr ( sess, attrs, name) {
169
+ for attr in get_builtin_attr ( sess, attrs, name) {
161
170
let Some ( value) = attr. value_str ( ) else {
162
171
sess. dcx ( ) . span_err ( attr. span ( ) , "bad clippy attribute" ) ;
163
172
continue ;
0 commit comments