@@ -20,13 +20,13 @@ use rustc_hir::{
20
20
TraitItem , CRATE_HIR_ID , CRATE_OWNER_ID ,
21
21
} ;
22
22
use rustc_macros:: LintDiagnostic ;
23
- use rustc_middle:: bug;
24
23
use rustc_middle:: hir:: nested_filter;
25
24
use rustc_middle:: middle:: resolve_bound_vars:: ObjectLifetimeDefault ;
26
25
use rustc_middle:: query:: Providers ;
27
26
use rustc_middle:: traits:: ObligationCause ;
28
27
use rustc_middle:: ty:: error:: { ExpectedFound , TypeError } ;
29
28
use rustc_middle:: ty:: { self , TyCtxt } ;
29
+ use rustc_middle:: { bug, span_bug} ;
30
30
use rustc_session:: lint:: builtin:: {
31
31
CONFLICTING_REPR_HINTS , INVALID_DOC_ATTRIBUTES , INVALID_MACRO_EXPORT_ARGUMENTS ,
32
32
UNKNOWN_OR_MALFORMED_DIAGNOSTIC_ATTRIBUTES , UNUSED_ATTRIBUTES ,
@@ -238,7 +238,60 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
238
238
self . check_generic_attr ( hir_id, attr, target, Target :: Fn ) ;
239
239
self . check_proc_macro ( hir_id, target, ProcMacroKind :: Derive )
240
240
}
241
- _ => { }
241
+ [ sym:: coroutine] => {
242
+ self . check_coroutine ( attr, target) ;
243
+ }
244
+ [
245
+ // ok
246
+ sym:: allow
247
+ | sym:: expect
248
+ | sym:: warn
249
+ | sym:: deny
250
+ | sym:: forbid
251
+ | sym:: cfg
252
+ // need to be fixed
253
+ | sym:: cfi_encoding // FIXME(cfi_encoding)
254
+ | sym:: may_dangle // FIXME(dropck_eyepatch)
255
+ | sym:: pointee // FIXME(derive_smart_pointer)
256
+ | sym:: linkage // FIXME(linkage)
257
+ | sym:: no_sanitize // FIXME(no_sanitize)
258
+ | sym:: omit_gdb_pretty_printer_section // FIXME(omit_gdb_pretty_printer_section)
259
+ | sym:: used // handled elsewhere to restrict to static items
260
+ | sym:: repr // handled elsewhere to restrict to type decls items
261
+ | sym:: optimize // FIXME(optimize_attribute)
262
+ | sym:: instruction_set // broken on stable!!!
263
+ | sym:: windows_subsystem // broken on stable!!!
264
+ | sym:: patchable_function_entry // FIXME(patchable_function_entry)
265
+ | sym:: deprecated_safe // FIXME(deprecated_safe)
266
+ // internal
267
+ | sym:: prelude_import
268
+ | sym:: panic_handler
269
+ | sym:: allow_internal_unsafe
270
+ | sym:: fundamental
271
+ | sym:: lang
272
+ | sym:: needs_allocator
273
+ | sym:: default_lib_allocator
274
+ | sym:: start
275
+ | sym:: custom_mir,
276
+ ] => { }
277
+ [ name, ..] => {
278
+ match BUILTIN_ATTRIBUTE_MAP . get ( name) {
279
+ // checked below
280
+ Some ( BuiltinAttribute { type_ : AttributeType :: CrateLevel , .. } ) => { }
281
+ Some ( _) => {
282
+ // FIXME: differentiate between unstable and internal attributes just like we do with features instead
283
+ // of just accepting `rustc_` attributes by name. That should allow trimming the above list, too.
284
+ if !name. as_str ( ) . starts_with ( "rustc_" ) {
285
+ span_bug ! (
286
+ attr. span,
287
+ "builtin attribute {name:?} not handled by `CheckAttrVisitor`"
288
+ )
289
+ }
290
+ }
291
+ None => ( ) ,
292
+ }
293
+ }
294
+ [ ] => unreachable ! ( ) ,
242
295
}
243
296
244
297
let builtin = attr. ident ( ) . and_then ( |ident| BUILTIN_ATTRIBUTE_MAP . get ( & ident. name ) ) ;
@@ -2251,6 +2304,15 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
2251
2304
self . abort . set ( true ) ;
2252
2305
}
2253
2306
}
2307
+
2308
+ fn check_coroutine ( & self , attr : & Attribute , target : Target ) {
2309
+ match target {
2310
+ Target :: Closure => return ,
2311
+ _ => {
2312
+ self . dcx ( ) . emit_err ( errors:: CoroutineOnNonClosure { span : attr. span } ) ;
2313
+ }
2314
+ }
2315
+ }
2254
2316
}
2255
2317
2256
2318
impl < ' tcx > Visitor < ' tcx > for CheckAttrVisitor < ' tcx > {
0 commit comments