Skip to content

Commit f18c6f3

Browse files
Port #[path] to the new attribute parsing infrastructure
Signed-off-by: Jonathan Brouwer <[email protected]>
1 parent 0112fc1 commit f18c6f3

File tree

12 files changed

+136
-64
lines changed

12 files changed

+136
-64
lines changed

compiler/rustc_attr_data_structures/src/attributes.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -284,6 +284,9 @@ pub enum AttributeKind {
284284
/// Represents `#[optimize(size|speed)]`
285285
Optimize(OptimizeAttr, Span),
286286

287+
/// Represents `#[path]`
288+
Path(Symbol, Span),
289+
287290
/// Represents `#[rustc_pub_transparent]` (used by the `repr_transparent_external_private_fields` lint).
288291
PubTransparent(Span),
289292

compiler/rustc_attr_data_structures/src/encode_cross_crate.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ impl AttributeKind {
3737
Naked(..) => No,
3838
NoMangle(..) => No,
3939
Optimize(..) => No,
40+
Path(..) => No,
4041
PubTransparent(..) => Yes,
4142
RustcLayoutScalarValidRangeEnd(..) => Yes,
4243
RustcLayoutScalarValidRangeStart(..) => Yes,

compiler/rustc_attr_parsing/src/attributes/mod.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ pub(crate) mod link_attrs;
3535
pub(crate) mod lint_helpers;
3636
pub(crate) mod loop_match;
3737
pub(crate) mod must_use;
38+
pub(crate) mod path;
3839
pub(crate) mod repr;
3940
pub(crate) mod rustc_internal;
4041
pub(crate) mod semantics;
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
use rustc_attr_data_structures::AttributeKind;
2+
use rustc_feature::{AttributeTemplate, template};
3+
use rustc_span::{Symbol, sym};
4+
5+
use crate::attributes::{AttributeOrder, OnDuplicate, SingleAttributeParser};
6+
use crate::context::{AcceptContext, Stage};
7+
use crate::parser::ArgParser;
8+
9+
pub(crate) struct PathParser;
10+
11+
impl<S: Stage> SingleAttributeParser<S> for PathParser {
12+
const PATH: &[Symbol] = &[sym::path];
13+
const ATTRIBUTE_ORDER: AttributeOrder = AttributeOrder::KeepLast;
14+
const ON_DUPLICATE: OnDuplicate<S> = OnDuplicate::WarnButFutureError;
15+
const TEMPLATE: AttributeTemplate = template!(NameValueStr: "file");
16+
17+
fn convert(cx: &mut AcceptContext<'_, '_, S>, args: &ArgParser<'_>) -> Option<AttributeKind> {
18+
let Some(nv) = args.name_value() else {
19+
cx.expected_name_value(cx.attr_span, None);
20+
return None;
21+
};
22+
let Some(path) = nv.value_as_str() else {
23+
cx.expected_string_literal(nv.value_span, Some(nv.value_as_lit()));
24+
return None;
25+
};
26+
27+
Some(AttributeKind::Path(path, cx.attr_span))
28+
}
29+
}

compiler/rustc_attr_parsing/src/context.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ use crate::attributes::link_attrs::{LinkNameParser, LinkSectionParser};
2626
use crate::attributes::lint_helpers::{AsPtrParser, PubTransparentParser};
2727
use crate::attributes::loop_match::{ConstContinueParser, LoopMatchParser};
2828
use crate::attributes::must_use::MustUseParser;
29+
use crate::attributes::path::PathParser as PathAttributeParser;
2930
use crate::attributes::repr::{AlignParser, ReprParser};
3031
use crate::attributes::rustc_internal::{
3132
RustcLayoutScalarValidRangeEnd, RustcLayoutScalarValidRangeStart,
@@ -133,6 +134,7 @@ attribute_parsers!(
133134
Single<MustUseParser>,
134135
Single<NoMangleParser>,
135136
Single<OptimizeParser>,
137+
Single<PathAttributeParser>,
136138
Single<PubTransparentParser>,
137139
Single<RustcForceInlineParser>,
138140
Single<RustcLayoutScalarValidRangeEnd>,

compiler/rustc_parse/src/validate_attr.rs

Lines changed: 23 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -271,28 +271,29 @@ pub fn check_builtin_meta_item(
271271
if matches!(
272272
name,
273273
sym::inline
274-
| sym::may_dangle
275-
| sym::rustc_as_ptr
276-
| sym::rustc_pub_transparent
277-
| sym::rustc_const_stable_indirect
278-
| sym::rustc_force_inline
279-
| sym::rustc_confusables
280-
| sym::rustc_skip_during_method_dispatch
281-
| sym::repr
282-
| sym::align
283-
| sym::deprecated
284-
| sym::optimize
285-
| sym::cold
286-
| sym::naked
287-
| sym::no_mangle
288-
| sym::must_use
289-
| sym::track_caller
290-
| sym::link_name
291-
| sym::export_name
292-
| sym::rustc_macro_transparency
293-
| sym::link_section
294-
| sym::rustc_layout_scalar_valid_range_start
295-
| sym::rustc_layout_scalar_valid_range_end
274+
| sym::may_dangle
275+
| sym::rustc_as_ptr
276+
| sym::rustc_pub_transparent
277+
| sym::rustc_const_stable_indirect
278+
| sym::rustc_force_inline
279+
| sym::rustc_confusables
280+
| sym::rustc_skip_during_method_dispatch
281+
| sym::repr
282+
| sym::align
283+
| sym::deprecated
284+
| sym::optimize
285+
| sym::cold
286+
| sym::naked
287+
| sym::no_mangle
288+
| sym::must_use
289+
| sym::track_caller
290+
| sym::link_name
291+
| sym::export_name
292+
| sym::rustc_macro_transparency
293+
| sym::link_section
294+
| sym::rustc_layout_scalar_valid_range_start
295+
| sym::rustc_layout_scalar_valid_range_end
296+
| sym::path
296297
) {
297298
return;
298299
}

compiler/rustc_passes/src/check_attr.rs

Lines changed: 31 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -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
};

tests/ui/feature-gates/issue-43106-gating-of-builtin-attrs-error.stderr

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -121,21 +121,6 @@ LL - #![rustc_main]
121121
LL + #[rustc_main]
122122
|
123123

124-
error: `path` attribute cannot be used at crate level
125-
--> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:21:1
126-
|
127-
LL | #![path = "3800"]
128-
| ^^^^^^^^^^^^^^^^^
129-
...
130-
LL | mod inline {
131-
| ------ the inner attribute doesn't annotate this module
132-
|
133-
help: perhaps you meant to use an outer attribute
134-
|
135-
LL - #![path = "3800"]
136-
LL + #[path = "3800"]
137-
|
138-
139124
error: `automatically_derived` attribute cannot be used at crate level
140125
--> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:23:1
141126
|
@@ -166,6 +151,21 @@ LL - #![repr()]
166151
LL + #[repr()]
167152
|
168153

154+
error: `path` attribute cannot be used at crate level
155+
--> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:21:1
156+
|
157+
LL | #![path = "3800"]
158+
| ^^^^^^^^^^^^^^^^^
159+
...
160+
LL | mod inline {
161+
| ------ the inner attribute doesn't annotate this module
162+
|
163+
help: perhaps you meant to use an outer attribute
164+
|
165+
LL - #![path = "3800"]
166+
LL + #[path = "3800"]
167+
|
168+
169169
error[E0518]: attribute should be applied to function or closure
170170
--> $DIR/issue-43106-gating-of-builtin-attrs-error.rs:42:17
171171
|

tests/ui/lint/unused/unused-attr-duplicate.stderr

Lines changed: 13 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -27,19 +27,6 @@ note: attribute also specified here
2727
LL | #[macro_use]
2828
| ^^^^^^^^^^^^
2929

30-
error: unused attribute
31-
--> $DIR/unused-attr-duplicate.rs:47:1
32-
|
33-
LL | #[path = "bar.rs"]
34-
| ^^^^^^^^^^^^^^^^^^ help: remove this attribute
35-
|
36-
note: attribute also specified here
37-
--> $DIR/unused-attr-duplicate.rs:46:1
38-
|
39-
LL | #[path = "auxiliary/lint_unused_extern_crate.rs"]
40-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
41-
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
42-
4330
error: unused attribute
4431
--> $DIR/unused-attr-duplicate.rs:53:1
4532
|
@@ -189,6 +176,19 @@ note: attribute also specified here
189176
LL | #[macro_export]
190177
| ^^^^^^^^^^^^^^^
191178

179+
error: unused attribute
180+
--> $DIR/unused-attr-duplicate.rs:47:1
181+
|
182+
LL | #[path = "bar.rs"]
183+
| ^^^^^^^^^^^^^^^^^^ help: remove this attribute
184+
|
185+
note: attribute also specified here
186+
--> $DIR/unused-attr-duplicate.rs:46:1
187+
|
188+
LL | #[path = "auxiliary/lint_unused_extern_crate.rs"]
189+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
190+
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
191+
192192
error: unused attribute
193193
--> $DIR/unused-attr-duplicate.rs:60:1
194194
|

tests/ui/lint/unused/unused-attr-macro-rules.stderr

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,17 +10,17 @@ note: the lint level is defined here
1010
LL | #![deny(unused_attributes)]
1111
| ^^^^^^^^^^^^^^^^^
1212

13-
error: `#[path]` only has an effect on modules
14-
--> $DIR/unused-attr-macro-rules.rs:8:1
15-
|
16-
LL | #[path="foo"]
17-
| ^^^^^^^^^^^^^
18-
1913
error: crate-level attribute should be an inner attribute: add an exclamation mark: `#![foo]`
2014
--> $DIR/unused-attr-macro-rules.rs:9:1
2115
|
2216
LL | #[recursion_limit="1"]
2317
| ^^^^^^^^^^^^^^^^^^^^^^
2418

19+
error: `#[path]` only has an effect on modules
20+
--> $DIR/unused-attr-macro-rules.rs:8:1
21+
|
22+
LL | #[path="foo"]
23+
| ^^^^^^^^^^^^^
24+
2525
error: aborting due to 3 previous errors
2626

tests/ui/resolve/path-attr-in-const-block.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,5 +5,6 @@ fn main() {
55
const {
66
#![path = foo!()]
77
//~^ ERROR: cannot find macro `foo` in this scope
8+
//~| ERROR malformed `path` attribute input
89
}
910
}

tests/ui/resolve/path-attr-in-const-block.stderr

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,5 +4,15 @@ error: cannot find macro `foo` in this scope
44
LL | #![path = foo!()]
55
| ^^^
66

7-
error: aborting due to 1 previous error
7+
error[E0539]: malformed `path` attribute input
8+
--> $DIR/path-attr-in-const-block.rs:6:9
9+
|
10+
LL | #![path = foo!()]
11+
| ^^^^^^^^^^------^
12+
| | |
13+
| | expected a string literal here
14+
| help: must be of the form: `#[path = "file"]`
15+
16+
error: aborting due to 2 previous errors
817

18+
For more information about this error, try `rustc --explain E0539`.

0 commit comments

Comments
 (0)