Rollup merge of #118504 - compiler-errors:must-use, r=WaffleLapkin

Enforce `must_use` on associated types and RPITITs that have a must-use trait in bounds

Warn when an RPITIT or (un-normalized) associated type with a `#[must_use]` trait in its bounds is unused.

This is pending T-lang approval, since it changes the semantics of the `#[must_use]` attribute slightly, but I think it strictly catches more strange errors.

I could also limit this to just RPITITs, but that seems less useful.

Fixes #118444
This commit is contained in:
Matthias Krüger 2023-12-06 21:52:32 +01:00 committed by GitHub
commit 1b391d4ae4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 54 additions and 1 deletions

View File

@ -291,7 +291,7 @@ impl<'tcx> LateLintPass<'tcx> for UnusedResults {
.map(|inner| MustUsePath::Pinned(Box::new(inner)))
}
ty::Adt(def, _) => is_def_must_use(cx, def.did(), span),
ty::Alias(ty::Opaque, ty::AliasTy { def_id: def, .. }) => {
ty::Alias(ty::Opaque | ty::Projection, ty::AliasTy { def_id: def, .. }) => {
elaborate(
cx.tcx,
cx.tcx.explicit_item_bounds(def).instantiate_identity_iter_copied(),

View File

@ -0,0 +1,15 @@
error: unused implementer of `Future` that must be used
--> $DIR/assoc-types.rs:19:5
|
LL | T::foo();
| ^^^^^^^^
|
= note: futures do nothing unless you `.await` or poll them
note: the lint level is defined here
--> $DIR/assoc-types.rs:4:9
|
LL | #![deny(unused_must_use)]
| ^^^^^^^^^^^^^^^
error: aborting due to 1 previous error

View File

@ -0,0 +1,15 @@
error: unused implementer of `Future` that must be used
--> $DIR/assoc-types.rs:19:5
|
LL | T::foo();
| ^^^^^^^^
|
= note: futures do nothing unless you `.await` or poll them
note: the lint level is defined here
--> $DIR/assoc-types.rs:4:9
|
LL | #![deny(unused_must_use)]
| ^^^^^^^^^^^^^^^
error: aborting due to 1 previous error

View File

@ -0,0 +1,23 @@
// edition: 2021
// revisions: rpitit assoc_ty
#![deny(unused_must_use)]
use std::future::Future;
pub trait Tr {
type Fut: Future<Output = ()>;
#[cfg(rpitit)]
fn foo() -> impl Future<Output = ()>;
#[cfg(assoc_ty)]
fn foo() -> Self::Fut;
}
pub async fn bar<T: Tr>() {
T::foo();
//~^ ERROR unused implementer of `Future` that must be used
}
fn main() {}