diff options
| author | Matthias Krüger <476013+matthiaskrgr@users.noreply.github.com> | 2025-05-17 10:33:09 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2025-05-17 10:33:09 +0200 |
| commit | 04bc9d13caa5231facfb28ddf02ba6b148ee25fb (patch) | |
| tree | 0184594c8c608a4ab929662135bd00af37f879fa | |
| parent | 642cd65ab256fe70e4e185def0816ab39077f5c6 (diff) | |
| parent | 7b2dcf298909f1493a57387be564fc2f07a3c6ad (diff) | |
| download | rust-04bc9d13caa5231facfb28ddf02ba6b148ee25fb.tar.gz rust-04bc9d13caa5231facfb28ddf02ba6b148ee25fb.zip | |
Rollup merge of #141031 - azhogin:azhogin/async-drop-dependency-fix, r=oli-obk
Async drop fix for dropee from another crate (#140858) Fixes https://github.com/rust-lang/rust/issues/140858. For `AsyncDestructor` impl def id was wrongly kept as a LocalDefId, which causes crash when dropee is declared in another crate. Also, potential problem found: when user crate drops type with async drop in dependency crate, and user crate doesn't enable `feature(async_drop)`, then sync drop version will be used. Is it a problem? Do we need some notification about such situations?
| -rw-r--r-- | compiler/rustc_middle/src/ty/mod.rs | 2 | ||||
| -rw-r--r-- | compiler/rustc_middle/src/ty/util.rs | 2 | ||||
| -rw-r--r-- | tests/ui/async-await/async-drop/auxiliary/async-drop-dep.rs | 28 | ||||
| -rw-r--r-- | tests/ui/async-await/async-drop/dependency-dropped.rs | 34 | ||||
| -rw-r--r-- | tests/ui/async-await/async-drop/dependency-dropped.run.stdout | 1 |
5 files changed, 65 insertions, 2 deletions
diff --git a/compiler/rustc_middle/src/ty/mod.rs b/compiler/rustc_middle/src/ty/mod.rs index 83b318435f9..657bda23bc4 100644 --- a/compiler/rustc_middle/src/ty/mod.rs +++ b/compiler/rustc_middle/src/ty/mod.rs @@ -1185,7 +1185,7 @@ pub struct Destructor { #[derive(Copy, Clone, Debug, HashStable, Encodable, Decodable)] pub struct AsyncDestructor { /// The `DefId` of the `impl AsyncDrop` - pub impl_did: LocalDefId, + pub impl_did: DefId, } #[derive(Clone, Copy, PartialEq, Eq, HashStable, TyEncodable, TyDecodable)] diff --git a/compiler/rustc_middle/src/ty/util.rs b/compiler/rustc_middle/src/ty/util.rs index 6fe5927c29f..9676aa40448 100644 --- a/compiler/rustc_middle/src/ty/util.rs +++ b/compiler/rustc_middle/src/ty/util.rs @@ -465,7 +465,7 @@ impl<'tcx> TyCtxt<'tcx> { dtor_candidate = Some(impl_did); } - Some(ty::AsyncDestructor { impl_did: dtor_candidate? }) + Some(ty::AsyncDestructor { impl_did: dtor_candidate?.into() }) } /// Returns the set of types that are required to be alive in diff --git a/tests/ui/async-await/async-drop/auxiliary/async-drop-dep.rs b/tests/ui/async-await/async-drop/auxiliary/async-drop-dep.rs new file mode 100644 index 00000000000..1729599f7b3 --- /dev/null +++ b/tests/ui/async-await/async-drop/auxiliary/async-drop-dep.rs @@ -0,0 +1,28 @@ +//@ edition:2021 + +#![feature(async_drop)] +#![allow(incomplete_features)] + +pub struct HasDrop; +impl Drop for HasDrop{ + fn drop(&mut self) { + println!("Sync drop"); + } +} + +pub struct MongoDrop; +impl MongoDrop { + pub async fn new() -> Result<Self, HasDrop> { + Ok(Self) + } +} +impl Drop for MongoDrop{ + fn drop(&mut self) { + println!("Sync drop"); + } +} +impl std::future::AsyncDrop for MongoDrop { + async fn drop(self: std::pin::Pin<&mut Self>) { + println!("Async drop"); + } +} diff --git a/tests/ui/async-await/async-drop/dependency-dropped.rs b/tests/ui/async-await/async-drop/dependency-dropped.rs new file mode 100644 index 00000000000..f763bb32b17 --- /dev/null +++ b/tests/ui/async-await/async-drop/dependency-dropped.rs @@ -0,0 +1,34 @@ +//@ run-pass +//@ check-run-results +//@ aux-build:async-drop-dep.rs +//@ edition:2021 + +#![feature(async_drop)] +#![allow(incomplete_features)] + +extern crate async_drop_dep; + +use async_drop_dep::MongoDrop; +use std::pin::pin; +use std::task::{Context, Poll, Waker}; +use std::future::Future; + +async fn asyncdrop() { + let _ = MongoDrop::new().await; +} + +pub fn block_on<T>(fut: impl Future<Output = T>) -> T { + let mut fut = pin!(fut); + let ctx = &mut Context::from_waker(Waker::noop()); + + loop { + match fut.as_mut().poll(ctx) { + Poll::Pending => {} + Poll::Ready(t) => break t, + } + } +} + +fn main() { + let _ = block_on(asyncdrop()); +} diff --git a/tests/ui/async-await/async-drop/dependency-dropped.run.stdout b/tests/ui/async-await/async-drop/dependency-dropped.run.stdout new file mode 100644 index 00000000000..7aaf70c12d6 --- /dev/null +++ b/tests/ui/async-await/async-drop/dependency-dropped.run.stdout @@ -0,0 +1 @@ +Async drop |
