@@ -185,6 +185,9 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
185185 Attribute :: Parsed ( AttributeKind :: Naked ( attr_span) ) => {
186186 self . check_naked ( hir_id, * attr_span, span, target)
187187 }
188+ Attribute :: Parsed ( AttributeKind :: Path ( _, attr_span) ) => {
189+ self . check_generic_attr ( hir_id, sym:: path, * attr_span, target, Target :: Mod )
190+ }
188191 Attribute :: Parsed ( AttributeKind :: TrackCaller ( attr_span) ) => {
189192 self . check_track_caller ( hir_id, * attr_span, attrs, span, target)
190193 }
@@ -294,16 +297,15 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
294297 [ sym:: macro_use, ..] | [ sym:: macro_escape, ..] => {
295298 self . check_macro_use ( hir_id, attr, target)
296299 }
297- [ sym:: path, ..] => self . check_generic_attr ( hir_id, attr, target, Target :: Mod ) ,
298300 [ sym:: macro_export, ..] => self . check_macro_export ( hir_id, attr, target) ,
299301 [ sym:: ignore, ..] | [ sym:: should_panic, ..] => {
300- self . check_generic_attr ( hir_id, attr, target, Target :: Fn )
302+ self . check_generic_attr_unparsed ( hir_id, attr, target, Target :: Fn )
301303 }
302304 [ sym:: automatically_derived, ..] => {
303- self . check_generic_attr ( hir_id, attr, target, Target :: Impl )
305+ self . check_generic_attr_unparsed ( hir_id, attr, target, Target :: Impl )
304306 }
305307 [ sym:: no_implicit_prelude, ..] => {
306- self . check_generic_attr ( hir_id, attr, target, Target :: Mod )
308+ self . check_generic_attr_unparsed ( hir_id, attr, target, Target :: Mod )
307309 }
308310 [ sym:: proc_macro, ..] => {
309311 self . check_proc_macro ( hir_id, target, ProcMacroKind :: FunctionLike )
@@ -312,7 +314,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
312314 self . check_proc_macro ( hir_id, target, ProcMacroKind :: Attribute ) ;
313315 }
314316 [ sym:: proc_macro_derive, ..] => {
315- self . check_generic_attr ( hir_id, attr, target, Target :: Fn ) ;
317+ self . check_generic_attr_unparsed ( hir_id, attr, target, Target :: Fn ) ;
316318 self . check_proc_macro ( hir_id, target, ProcMacroKind :: Derive )
317319 }
318320 [ sym:: autodiff_forward, ..] | [ sym:: autodiff_reverse, ..] => {
@@ -621,7 +623,7 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
621623 }
622624 }
623625
624- fn check_generic_attr (
626+ fn check_generic_attr_unparsed (
625627 & self ,
626628 hir_id : HirId ,
627629 attr : & Attribute ,
@@ -644,6 +646,27 @@ impl<'tcx> CheckAttrVisitor<'tcx> {
644646 }
645647 }
646648
649+ fn check_generic_attr (
650+ & self ,
651+ hir_id : HirId ,
652+ attr_name : Symbol ,
653+ attr_span : Span ,
654+ target : Target ,
655+ allowed_target : Target ,
656+ ) {
657+ if target != allowed_target {
658+ self . tcx . emit_node_span_lint (
659+ UNUSED_ATTRIBUTES ,
660+ hir_id,
661+ attr_span,
662+ errors:: OnlyHasEffectOn {
663+ attr_name : attr_name. to_string ( ) ,
664+ target_name : allowed_target. name ( ) . replace ( ' ' , "_" ) ,
665+ } ,
666+ ) ;
667+ }
668+ }
669+
647670 /// Checks if `#[naked]` is applied to a function definition.
648671 fn check_naked ( & self , hir_id : HirId , attr_span : Span , span : Span , target : Target ) {
649672 match target {
@@ -2804,7 +2827,6 @@ fn check_invalid_crate_level_attr(tcx: TyCtxt<'_>, attrs: &[Attribute]) {
28042827 // resolution for the attribute macro error.
28052828 const ATTRS_TO_CHECK : & [ Symbol ] = & [
28062829 sym:: macro_export,
2807- sym:: path,
28082830 sym:: automatically_derived,
28092831 sym:: rustc_main,
28102832 sym:: derive,
@@ -2822,6 +2844,8 @@ fn check_invalid_crate_level_attr(tcx: TyCtxt<'_>, attrs: &[Attribute]) {
28222844 ( attr. span ( ) , * a)
28232845 } else if let Attribute :: Parsed ( AttributeKind :: Repr ( r) ) = attr {
28242846 ( r. first ( ) . unwrap ( ) . 1 , sym:: repr)
2847+ } else if let Attribute :: Parsed ( AttributeKind :: Path ( .., span) ) = attr {
2848+ ( * span, sym:: path)
28252849 } else {
28262850 continue ;
28272851 } ;
0 commit comments