@@ -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 ,
@@ -239,7 +239,59 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
239
239
self . check_generic_attr ( hir_id, attr, target, Target :: Fn ) ;
240
240
self . check_proc_macro ( hir_id, target, ProcMacroKind :: Derive )
241
241
}
242
- _ => { }
242
+ [ sym:: coroutine] => {
243
+ self . check_coroutine ( attr, target) ;
244
+ }
245
+ [
246
+ // ok
247
+ sym:: allow
248
+ | sym:: expect
249
+ | sym:: warn
250
+ | sym:: deny
251
+ | sym:: forbid
252
+ | sym:: cfg
253
+ // need to be fixed
254
+ | sym:: cfi_encoding // FIXME(cfi_encoding)
255
+ | sym:: may_dangle // FIXME(dropck_eyepatch)
256
+ | sym:: pointee // FIXME(derive_smart_pointer)
257
+ | sym:: linkage // FIXME(linkage)
258
+ | sym:: no_sanitize // FIXME(no_sanitize)
259
+ | sym:: omit_gdb_pretty_printer_section // FIXME(omit_gdb_pretty_printer_section)
260
+ | sym:: used // handled elsewhere to restrict to static items
261
+ | sym:: repr // handled elsewhere to restrict to type decls items
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 ! ( ) ,
243
295
}
244
296
245
297
let builtin = attr. ident ( ) . and_then ( |ident| BUILTIN_ATTRIBUTE_MAP . get ( & ident. name ) ) ;
@@ -376,6 +428,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
376
428
377
429
/// Checks that `#[optimize(..)]` is applied to a function/closure/method,
378
430
/// or to an impl block or module.
431
+ // FIXME(#128488): this should probably be elevated to an error?
379
432
fn check_optimize ( & self , hir_id : HirId , attr : & Attribute , target : Target ) {
380
433
match target {
381
434
Target :: Fn
@@ -2279,6 +2332,15 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
2279
2332
self . abort . set ( true ) ;
2280
2333
}
2281
2334
}
2335
+
2336
+ fn check_coroutine ( & self , attr : & Attribute , target : Target ) {
2337
+ match target {
2338
+ Target :: Closure => return ,
2339
+ _ => {
2340
+ self . dcx ( ) . emit_err ( errors:: CoroutineOnNonClosure { span : attr. span } ) ;
2341
+ }
2342
+ }
2343
+ }
2282
2344
}
2283
2345
2284
2346
impl < ' tcx > Visitor < ' tcx > for CheckAttrVisitor < ' tcx > {
0 commit comments