Skip to content

Commit d68b0ec

Browse files
committed
Auto merge of #50030 - flip1995:rfc2103, r=petrochenkov
Implement tool_attributes feature (RFC 2103) cc #44690 This is currently just a rebased and compiling (hopefully) version of #47773. Let's see if travis likes this. I will add the implementation for `tool_lints` this week.
2 parents 698b956 + 84f4508 commit d68b0ec

File tree

35 files changed

+391
-302
lines changed

35 files changed

+391
-302
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
# `tool_attributes`
2+
3+
The tracking issue for this feature is: [#44690]
4+
5+
[#44690]: https://github.com/rust-lang/rust/issues/44690
6+
7+
------------------------
8+
9+
Tool attributes let you use scoped attributes to control the behavior
10+
of certain tools.
11+
12+
Currently tool names which can be appear in scoped attributes are restricted to
13+
`clippy` and `rustfmt`.
14+
15+
## An example
16+
17+
```rust
18+
#![feature(tool_attributes)]
19+
20+
#[rustfmt::skip]
21+
fn foo() { println!("hello, world"); }
22+
23+
fn main() {
24+
foo();
25+
}
26+
```

src/librustc/hir/check_attr.rs

+2-5
Original file line numberDiff line numberDiff line change
@@ -153,10 +153,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
153153
// ```
154154
let hints: Vec<_> = item.attrs
155155
.iter()
156-
.filter(|attr| match attr.name() {
157-
Some(name) => name == "repr",
158-
None => false,
159-
})
156+
.filter(|attr| attr.name() == "repr")
160157
.filter_map(|attr| attr.meta_item_list())
161158
.flat_map(|hints| hints)
162159
.collect();
@@ -311,7 +308,7 @@ impl<'a, 'tcx> CheckAttrVisitor<'a, 'tcx> {
311308

312309
fn check_used(&self, item: &hir::Item, target: Target) {
313310
for attr in &item.attrs {
314-
if attr.name().map(|name| name == "used").unwrap_or(false) && target != Target::Static {
311+
if attr.name() == "used" && target != Target::Static {
315312
self.tcx.sess
316313
.span_err(attr.span, "attribute must be applied to a `static` variable");
317314
}

src/librustc/ich/impls_syntax.rs

+14-7
Original file line numberDiff line numberDiff line change
@@ -199,8 +199,7 @@ impl<'a> HashStable<StableHashingContext<'a>> for [ast::Attribute] {
199199
let filtered: AccumulateVec<[&ast::Attribute; 8]> = self
200200
.iter()
201201
.filter(|attr| {
202-
!attr.is_sugared_doc &&
203-
attr.name().map(|name| !hcx.is_ignored_attr(name)).unwrap_or(true)
202+
!attr.is_sugared_doc && !hcx.is_ignored_attr(attr.name())
204203
})
205204
.collect();
206205

@@ -211,12 +210,23 @@ impl<'a> HashStable<StableHashingContext<'a>> for [ast::Attribute] {
211210
}
212211
}
213212

213+
impl<'a> HashStable<StableHashingContext<'a>> for ast::Path {
214+
fn hash_stable<W: StableHasherResult>(&self,
215+
hcx: &mut StableHashingContext<'a>,
216+
hasher: &mut StableHasher<W>) {
217+
self.segments.len().hash_stable(hcx, hasher);
218+
for segment in &self.segments {
219+
segment.ident.name.hash_stable(hcx, hasher);
220+
}
221+
}
222+
}
223+
214224
impl<'a> HashStable<StableHashingContext<'a>> for ast::Attribute {
215225
fn hash_stable<W: StableHasherResult>(&self,
216226
hcx: &mut StableHashingContext<'a>,
217227
hasher: &mut StableHasher<W>) {
218228
// Make sure that these have been filtered out.
219-
debug_assert!(self.name().map(|name| !hcx.is_ignored_attr(name)).unwrap_or(true));
229+
debug_assert!(!hcx.is_ignored_attr(self.name()));
220230
debug_assert!(!self.is_sugared_doc);
221231

222232
let ast::Attribute {
@@ -229,10 +239,7 @@ impl<'a> HashStable<StableHashingContext<'a>> for ast::Attribute {
229239
} = *self;
230240

231241
style.hash_stable(hcx, hasher);
232-
path.segments.len().hash_stable(hcx, hasher);
233-
for segment in &path.segments {
234-
segment.ident.name.hash_stable(hcx, hasher);
235-
}
242+
path.hash_stable(hcx, hasher);
236243
for tt in tokens.trees() {
237244
tt.hash_stable(hcx, hasher);
238245
}

src/librustc/lint/levels.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,7 @@ impl<'a> LintLevelsBuilder<'a> {
198198
"malformed lint attribute");
199199
};
200200
for attr in attrs {
201-
let level = match attr.name().and_then(|name| Level::from_str(&name.as_str())) {
201+
let level = match Level::from_str(&attr.name().as_str()) {
202202
None => continue,
203203
Some(lvl) => lvl,
204204
};
@@ -221,7 +221,7 @@ impl<'a> LintLevelsBuilder<'a> {
221221
continue
222222
}
223223
};
224-
let name = word.ident.name;
224+
let name = word.name();
225225
match store.check_lint_name(&name.as_str()) {
226226
CheckLintNameResult::Ok(ids) => {
227227
let src = LintSource::Node(name, li.span);
@@ -260,7 +260,7 @@ impl<'a> LintLevelsBuilder<'a> {
260260
Some(li.span.into()),
261261
&msg);
262262
if name.as_str().chars().any(|c| c.is_uppercase()) {
263-
let name_lower = name.as_str().to_lowercase();
263+
let name_lower = name.as_str().to_lowercase().to_string();
264264
if let CheckLintNameResult::NoLint =
265265
store.check_lint_name(&name_lower) {
266266
db.emit();

src/librustc/middle/stability.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -205,7 +205,7 @@ impl<'a, 'tcx: 'a> Annotator<'a, 'tcx> {
205205
} else {
206206
// Emit errors for non-staged-api crates.
207207
for attr in attrs {
208-
let tag = unwrap_or!(attr.name(), continue);
208+
let tag = attr.name();
209209
if tag == "unstable" || tag == "stable" || tag == "rustc_deprecated" {
210210
attr::mark_used(attr);
211211
self.tcx.sess.span_err(attr.span(), "stability attributes may not be used \

src/librustc/session/config.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1683,7 +1683,7 @@ pub fn parse_cfgspecs(cfgspecs: Vec<String>) -> ast::CrateConfig {
16831683
early_error(ErrorOutputType::default(), &msg)
16841684
}
16851685

1686-
(meta_item.ident.name, meta_item.value_str())
1686+
(meta_item.name(), meta_item.value_str())
16871687
})
16881688
.collect::<ast::CrateConfig>()
16891689
}

src/librustc/traits/on_unimplemented.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -190,7 +190,7 @@ impl<'a, 'gcx, 'tcx> OnUnimplementedDirective {
190190
for command in self.subcommands.iter().chain(Some(self)).rev() {
191191
if let Some(ref condition) = command.condition {
192192
if !attr::eval_condition(condition, &tcx.sess.parse_sess, &mut |c| {
193-
options.contains(&(c.ident.name.as_str().to_string(),
193+
options.contains(&(c.name().as_str().to_string(),
194194
match c.value_str().map(|s| s.as_str().to_string()) {
195195
Some(s) => Some(s),
196196
None => None

src/librustc_driver/lib.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1060,7 +1060,7 @@ impl RustcDefaultCalls {
10601060
let mut cfgs = Vec::new();
10611061
for &(name, ref value) in sess.parse_sess.config.iter() {
10621062
let gated_cfg = GatedCfg::gate(&ast::MetaItem {
1063-
ident: ast::Ident::with_empty_ctxt(name),
1063+
ident: ast::Path::from_ident(name.to_ident()),
10641064
node: ast::MetaItemKind::Word,
10651065
span: DUMMY_SP,
10661066
});

src/librustc_incremental/assert_dep_graph.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ impl<'a, 'tcx> IfThisChanged<'a, 'tcx> {
110110
for list_item in attr.meta_item_list().unwrap_or_default() {
111111
match list_item.word() {
112112
Some(word) if value.is_none() =>
113-
value = Some(word.ident.name),
113+
value = Some(word.name()),
114114
_ =>
115115
// FIXME better-encapsulate meta_item (don't directly access `node`)
116116
span_bug!(list_item.span(), "unexpected meta-item {:?}", list_item.node),

src/librustc_lint/builtin.rs

+1-2
Original file line numberDiff line numberDiff line change
@@ -675,9 +675,8 @@ impl LintPass for DeprecatedAttr {
675675

676676
impl EarlyLintPass for DeprecatedAttr {
677677
fn check_attribute(&mut self, cx: &EarlyContext, attr: &ast::Attribute) {
678-
let name = unwrap_or!(attr.name(), return);
679678
for &&(n, _, ref g) in &self.depr_attrs {
680-
if name == n {
679+
if attr.name() == n {
681680
if let &AttributeGate::Gated(Stability::Deprecated(link),
682681
ref name,
683682
ref reason,

src/librustc_lint/lib.rs

-1
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,6 @@
3030
#![feature(quote)]
3131
#![feature(rustc_diagnostic_macros)]
3232

33-
#[macro_use]
3433
extern crate syntax;
3534
#[macro_use]
3635
extern crate rustc;

src/librustc_lint/unused.rs

+1-2
Original file line numberDiff line numberDiff line change
@@ -192,8 +192,6 @@ impl LintPass for UnusedAttributes {
192192
impl<'a, 'tcx> LateLintPass<'a, 'tcx> for UnusedAttributes {
193193
fn check_attribute(&mut self, cx: &LateContext, attr: &ast::Attribute) {
194194
debug!("checking attribute: {:?}", attr);
195-
let name = unwrap_or!(attr.name(), return);
196-
197195
// Note that check_name() marks the attribute as used if it matches.
198196
for &(ref name, ty, _) in BUILTIN_ATTRIBUTES {
199197
match ty {
@@ -213,6 +211,7 @@ impl<'a, 'tcx> LateLintPass<'a, 'tcx> for UnusedAttributes {
213211
}
214212
}
215213

214+
let name = attr.name();
216215
if !attr::is_used(attr) {
217216
debug!("Emitting warning for: {:?}", attr);
218217
cx.span_lint(UNUSED_ATTRIBUTES, attr.span, "unused attribute");

src/librustc_resolve/build_reduced_graph.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -706,7 +706,7 @@ impl<'a> Resolver<'a> {
706706
match attr.meta_item_list() {
707707
Some(names) => for attr in names {
708708
if let Some(word) = attr.word() {
709-
imports.imports.push((word.ident.name, attr.span()));
709+
imports.imports.push((word.name(), attr.span()));
710710
} else {
711711
span_err!(self.session, attr.span(), E0466, "bad macro import");
712712
}

src/librustc_resolve/macros.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,7 @@ impl<'a> base::Resolver for Resolver<'a> {
209209
fn find_legacy_attr_invoc(&mut self, attrs: &mut Vec<ast::Attribute>, allow_derive: bool)
210210
-> Option<ast::Attribute> {
211211
for i in 0..attrs.len() {
212-
let name = unwrap_or!(attrs[i].name(), continue);
212+
let name = attrs[i].name();
213213

214214
if self.session.plugin_attributes.borrow().iter()
215215
.any(|&(ref attr_nm, _)| name == &**attr_nm) {
@@ -231,7 +231,7 @@ impl<'a> base::Resolver for Resolver<'a> {
231231

232232
// Check for legacy derives
233233
for i in 0..attrs.len() {
234-
let name = unwrap_or!(attrs[i].name(), continue);
234+
let name = attrs[i].name();
235235

236236
if name == "derive" {
237237
let result = attrs[i].parse_list(&self.session.parse_sess, |parser| {

0 commit comments

Comments
 (0)