Skip to content

Commit d25d663

Browse files
Use the new attribute parser throughout the codebase
1 parent db50852 commit d25d663

File tree

4 files changed

+45
-29
lines changed

4 files changed

+45
-29
lines changed

compiler/rustc_attr_parsing/src/context.rs

Lines changed: 25 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
use std::borrow::Cow;
12
use std::cell::RefCell;
23
use std::collections::BTreeMap;
34
use std::ops::{Deref, DerefMut};
@@ -766,6 +767,7 @@ impl<'sess> AttributeParser<'sess, Early> {
766767
sess,
767768
attrs,
768769
Some(sym),
770+
Target::Crate, // Does not matter, we're not going to emit errors anyways
769771
target_span,
770772
target_node_id,
771773
features,
@@ -779,6 +781,7 @@ impl<'sess> AttributeParser<'sess, Early> {
779781
sess: &'sess Session,
780782
attrs: &[ast::Attribute],
781783
parse_only: Option<Symbol>,
784+
target: Target,
782785
target_span: Span,
783786
target_node_id: NodeId,
784787
features: Option<&'sess Features>,
@@ -790,11 +793,12 @@ impl<'sess> AttributeParser<'sess, Early> {
790793
attrs,
791794
target_span,
792795
target_node_id,
793-
Target::Crate, // Does not matter, we're not going to emit errors anyways
796+
target,
794797
OmitDoc::Skip,
795798
std::convert::identity,
796799
|_lint| {
797-
panic!("can't emit lints here for now (nothing uses this atm)");
800+
// FIXME: Can't emit lints here for now
801+
// This branch can be hit when an attribute produces a warning during early parsing (such as attributes on macro calls)
798802
},
799803
)
800804
}
@@ -806,9 +810,9 @@ impl<'sess> AttributeParser<'sess, Early> {
806810
target_node_id: NodeId,
807811
features: Option<&'sess Features>,
808812
emit_errors: ShouldEmit,
809-
parse_fn: fn(cx: &mut AcceptContext<'_, '_, Early>, item: &ArgParser<'_>) -> T,
813+
parse_fn: fn(cx: &mut AcceptContext<'_, '_, Early>, item: &ArgParser<'_>) -> Option<T>,
810814
template: &AttributeTemplate,
811-
) -> T {
815+
) -> Option<T> {
812816
let mut parser = Self {
813817
features,
814818
tools: Vec::new(),
@@ -819,7 +823,9 @@ impl<'sess> AttributeParser<'sess, Early> {
819823
let ast::AttrKind::Normal(normal_attr) = &attr.kind else {
820824
panic!("parse_single called on a doc attr")
821825
};
822-
let meta_parser = MetaItemParser::from_attr(normal_attr, parser.dcx());
826+
let parts =
827+
normal_attr.item.path.segments.iter().map(|seg| seg.ident.name).collect::<Vec<_>>();
828+
let meta_parser = MetaItemParser::from_attr(normal_attr, &parts, &sess.psess, emit_errors)?;
823829
let path = meta_parser.path();
824830
let args = meta_parser.args();
825831
let mut cx: AcceptContext<'_, 'sess, Early> = AcceptContext {
@@ -926,14 +932,23 @@ impl<'sess, S: Stage> AttributeParser<'sess, S> {
926932
// }))
927933
// }
928934
ast::AttrKind::Normal(n) => {
929-
attr_paths.push(PathParser::Ast(&n.item.path));
935+
attr_paths.push(PathParser(Cow::Borrowed(&n.item.path)));
930936

931-
let parser = MetaItemParser::from_attr(n, self.dcx());
932-
let path = parser.path();
933-
let args = parser.args();
934-
let parts = path.segments().map(|i| i.name).collect::<Vec<_>>();
937+
let parts =
938+
n.item.path.segments.iter().map(|seg| seg.ident.name).collect::<Vec<_>>();
935939

936940
if let Some(accepts) = S::parsers().accepters.get(parts.as_slice()) {
941+
let Some(parser) = MetaItemParser::from_attr(
942+
n,
943+
&parts,
944+
&self.sess.psess,
945+
self.stage.should_emit(),
946+
) else {
947+
continue;
948+
};
949+
let path = parser.path();
950+
let args = parser.args();
951+
937952
for accept in accepts {
938953
let mut cx: AcceptContext<'_, 'sess, S> = AcceptContext {
939954
shared: SharedContext {

compiler/rustc_attr_parsing/src/validate_attr.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,10 @@ pub fn check_attr(psess: &ParseSess, attr: &Attribute, id: NodeId) {
3333
// Check input tokens for built-in and key-value attributes.
3434
match builtin_attr_info {
3535
// `rustc_dummy` doesn't have any restrictions specific to built-in attributes.
36-
Some(BuiltinAttribute { name, template, .. }) if *name != sym::rustc_dummy => {
36+
Some(BuiltinAttribute { name, template, .. }) => {
37+
if AttributeParser::<Late>::is_parsed_attribute(slice::from_ref(&name)) {
38+
return;
39+
}
3740
match parse_meta(psess, attr) {
3841
// Don't check safety again, we just did that
3942
Ok(meta) => {
@@ -259,9 +262,6 @@ pub fn check_builtin_meta_item(
259262
) {
260263
if !is_attr_template_compatible(&template, &meta.kind) {
261264
// attrs with new parsers are locally validated so excluded here
262-
if AttributeParser::<Late>::is_parsed_attribute(slice::from_ref(&name)) {
263-
return;
264-
}
265265
emit_malformed_attribute(psess, style, meta.span, name, template);
266266
}
267267

compiler/rustc_expand/src/config.rs

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -415,16 +415,6 @@ impl<'a> StripUnconfigured<'a> {
415415
node: NodeId,
416416
emit_errors: ShouldEmit,
417417
) -> EvalConfigResult {
418-
// We need to run this to do basic validation of the attribute, such as that lits are valid, etc
419-
// FIXME(jdonszelmann) this should not be necessary in the future
420-
match validate_attr::parse_meta(&self.sess.psess, attr) {
421-
Ok(_) => {}
422-
Err(err) => {
423-
err.emit();
424-
return EvalConfigResult::True;
425-
}
426-
}
427-
428418
// Unsafety check needs to be done explicitly here because this attribute will be removed before the normal check
429419
deny_builtin_meta_unsafety(
430420
self.sess.dcx(),

compiler/rustc_expand/src/expand.rs

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,22 @@
11
use std::path::PathBuf;
22
use std::rc::Rc;
33
use std::sync::Arc;
4-
use std::{iter, mem};
4+
use std::{iter, mem, slice};
55

66
use rustc_ast::mut_visit::*;
77
use rustc_ast::tokenstream::TokenStream;
88
use rustc_ast::visit::{self, AssocCtxt, Visitor, VisitorResult, try_visit, walk_list};
99
use rustc_ast::{
10-
self as ast, AssocItemKind, AstNodeWrapper, AttrArgs, AttrStyle, AttrVec, DUMMY_NODE_ID,
11-
ExprKind, ForeignItemKind, HasAttrs, HasNodeId, Inline, ItemKind, MacStmtStyle, MetaItemInner,
12-
MetaItemKind, ModKind, NodeId, PatKind, StmtKind, TyKind, token,
10+
self as ast, AssocItemKind, AstNodeWrapper, AttrArgs, AttrStyle, AttrVec, CRATE_NODE_ID,
11+
DUMMY_NODE_ID, ExprKind, ForeignItemKind, HasAttrs, HasNodeId, Inline, ItemKind, MacStmtStyle,
12+
MetaItemInner, MetaItemKind, ModKind, NodeId, PatKind, StmtKind, TyKind, token,
1313
};
1414
use rustc_ast_pretty::pprust;
15-
use rustc_attr_parsing::{EvalConfigResult, ShouldEmit, validate_attr};
15+
use rustc_attr_parsing::{AttributeParser, EvalConfigResult, ShouldEmit, validate_attr};
1616
use rustc_data_structures::flat_map_in_place::FlatMapInPlace;
1717
use rustc_errors::PResult;
1818
use rustc_feature::Features;
19+
use rustc_hir::Target;
1920
use rustc_hir::def::MacroKinds;
2021
use rustc_parse::parser::{
2122
AttemptLocalParseRecovery, CommaRecoveryMode, ForceCollect, Parser, RecoverColon, RecoverComma,
@@ -2156,6 +2157,16 @@ impl<'a, 'b> InvocationCollector<'a, 'b> {
21562157
attr,
21572158
self.cx.current_expansion.lint_node_id,
21582159
);
2160+
AttributeParser::parse_limited_all(
2161+
self.cx.sess,
2162+
slice::from_ref(attr),
2163+
None,
2164+
Target::MacroCall,
2165+
call.span(),
2166+
CRATE_NODE_ID,
2167+
Some(self.cx.ecfg.features),
2168+
ShouldEmit::ErrorsAndLints,
2169+
);
21592170

21602171
let current_span = if let Some(sp) = span { sp.to(attr.span) } else { attr.span };
21612172
span = Some(current_span);

0 commit comments

Comments
 (0)