Skip to content

Commit daed864

Browse files
authored
Rollup merge of #93926 - PatchMixolydic:bugfix/must_use-on-exprs, r=cjgillot
Lint against more useless `#[must_use]` attributes This expands the existing `#[must_use]` check in `unused_attributes` to lint against pretty much everything `#[must_use]` doesn't support. Fixes #93906.
2 parents 2fb5a16 + 6dcf5d8 commit daed864

File tree

6 files changed

+527
-164
lines changed

6 files changed

+527
-164
lines changed

compiler/rustc_macros/src/session_diagnostic.rs

-1
Original file line numberDiff line numberDiff line change
@@ -587,7 +587,6 @@ impl<'a> SessionDiagnosticDeriveBuilder<'a> {
587587
// next call to `it.next()` retrieves the next character.
588588
while let Some(c) = it.next() {
589589
if c == '{' && *it.peek().unwrap_or(&'\0') != '{' {
590-
#[must_use]
591590
let mut eat_argument = || -> Option<String> {
592591
let mut result = String::new();
593592
// Format specifiers look like

compiler/rustc_passes/src/check_attr.rs

+34-1
Original file line numberDiff line numberDiff line change
@@ -1111,7 +1111,7 @@ impl CheckAttrVisitor<'_> {
11111111
}
11121112

11131113
/// Warns against some misuses of `#[must_use]`
1114-
fn check_must_use(&self, hir_id: HirId, attr: &Attribute, span: Span, _target: Target) -> bool {
1114+
fn check_must_use(&self, hir_id: HirId, attr: &Attribute, span: Span, target: Target) -> bool {
11151115
let node = self.tcx.hir().get(hir_id);
11161116
if let Some(fn_node) = node.fn_kind() {
11171117
if let rustc_hir::IsAsync::Async = fn_node.asyncness() {
@@ -1131,6 +1131,39 @@ impl CheckAttrVisitor<'_> {
11311131
}
11321132
}
11331133

1134+
if !matches!(
1135+
target,
1136+
Target::Fn
1137+
| Target::Enum
1138+
| Target::Struct
1139+
| Target::Union
1140+
| Target::Method(_)
1141+
| Target::ForeignFn
1142+
// `impl Trait` in return position can trip
1143+
// `unused_must_use` if `Trait` is marked as
1144+
// `#[must_use]`
1145+
| Target::Trait
1146+
) {
1147+
let article = match target {
1148+
Target::ExternCrate
1149+
| Target::OpaqueTy
1150+
| Target::Enum
1151+
| Target::Impl
1152+
| Target::Expression
1153+
| Target::Arm
1154+
| Target::AssocConst
1155+
| Target::AssocTy => "an",
1156+
_ => "a",
1157+
};
1158+
1159+
self.tcx.struct_span_lint_hir(UNUSED_ATTRIBUTES, hir_id, attr.span, |lint| {
1160+
lint.build(&format!(
1161+
"`#[must_use]` has no effect when applied to {article} {target}"
1162+
))
1163+
.emit();
1164+
});
1165+
}
1166+
11341167
// For now, its always valid
11351168
true
11361169
}

src/test/ui/feature-gates/issue-43106-gating-of-builtin-attrs.rs

+5-4
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,7 @@
7171
//~^^ WARN this was previously accepted by the compiler
7272
// see issue-43106-gating-of-rustc_deprecated.rs
7373
#![must_use]
74+
//~^ WARN `#[must_use]` has no effect
7475
// see issue-43106-gating-of-stable.rs
7576
// see issue-43106-gating-of-unstable.rs
7677
// see issue-43106-gating-of-deprecated.rs
@@ -597,17 +598,17 @@ mod deprecated {
597598
#[deprecated] impl super::StructForDeprecated { }
598599
}
599600

600-
#[must_use]
601+
#[must_use] //~ WARN `#[must_use]` has no effect
601602
mod must_use {
602-
mod inner { #![must_use] }
603+
mod inner { #![must_use] } //~ WARN `#[must_use]` has no effect
603604

604605
#[must_use] fn f() { }
605606

606607
#[must_use] struct S;
607608

608-
#[must_use] type T = S;
609+
#[must_use] type T = S; //~ WARN `#[must_use]` has no effect
609610

610-
#[must_use] impl S { }
611+
#[must_use] impl S { } //~ WARN `#[must_use]` has no effect
611612
}
612613

613614
#[windows_subsystem = "windows"]

0 commit comments

Comments
 (0)