-
-
Notifications
You must be signed in to change notification settings - Fork 14.9k
Async drop box support #145316
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Async drop box support #145316
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -388,8 +388,10 @@ declare_features! ( | |
| (unstable, associated_const_equality, "1.58.0", Some(92827)), | ||
| /// Allows associated type defaults. | ||
| (unstable, associated_type_defaults, "1.2.0", Some(29661)), | ||
| /// Allows implementing `AsyncDrop`. | ||
| /// Enables async drop code generation | ||
| (incomplete, async_drop, "1.88.0", Some(126482)), | ||
| /// Allows implementing `AsyncDrop`. For usage in standard library. | ||
| (incomplete, async_drop_lib, "1.88.0", Some(126482)), | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. this feature is not checked anywhere in the compiler in the first commit. Move this change to the second commit |
||
| /// Allows async functions to be called from `dyn Trait`. | ||
| (incomplete, async_fn_in_dyn_trait, "1.85.0", Some(133119)), | ||
| /// Allows `#[track_caller]` on async functions. | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -13,6 +13,8 @@ use crate::ty::{self, Instance, TraitRef, Ty, TyCtxt}; | |
| pub enum VtblEntry<'tcx> { | ||
| /// destructor of this type (used in vtable header) | ||
| MetadataDropInPlace, | ||
| /// async destructor of this type, function returns Pin<Box<Future>>> (used in vtable header) | ||
| MetadataAsyncDropInPlace, | ||
| /// layout size of this type (used in vtable header) | ||
| MetadataSize, | ||
| /// layout align of this type (used in vtable header) | ||
|
|
@@ -31,6 +33,7 @@ impl<'tcx> fmt::Debug for VtblEntry<'tcx> { | |
| // so we implement this manually. | ||
| match self { | ||
| VtblEntry::MetadataDropInPlace => write!(f, "MetadataDropInPlace"), | ||
| VtblEntry::MetadataAsyncDropInPlace => write!(f, "MetadataAsyncDropInPlace"), | ||
| VtblEntry::MetadataSize => write!(f, "MetadataSize"), | ||
| VtblEntry::MetadataAlign => write!(f, "MetadataAlign"), | ||
| VtblEntry::Vacant => write!(f, "Vacant"), | ||
|
|
@@ -42,13 +45,18 @@ impl<'tcx> fmt::Debug for VtblEntry<'tcx> { | |
|
|
||
| // Needs to be associated with the `'tcx` lifetime | ||
| impl<'tcx> TyCtxt<'tcx> { | ||
| pub const COMMON_VTABLE_ENTRIES: &'tcx [VtblEntry<'tcx>] = | ||
| &[VtblEntry::MetadataDropInPlace, VtblEntry::MetadataSize, VtblEntry::MetadataAlign]; | ||
| pub const COMMON_VTABLE_ENTRIES: &'tcx [VtblEntry<'tcx>] = &[ | ||
| VtblEntry::MetadataDropInPlace, | ||
| VtblEntry::MetadataAsyncDropInPlace, | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. hmm... somewhat annoying that we would need to modify all vtables out there, even if a lot of code never uses async drop at all. Maybe there could be a solution akin to #156090 plus requiring
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The main issue I see is that this change happens on stable immediately, so all vtables get bigger with a field that is alway null |
||
| VtblEntry::MetadataSize, | ||
| VtblEntry::MetadataAlign, | ||
| ]; | ||
| } | ||
|
|
||
| pub const COMMON_VTABLE_ENTRIES_DROPINPLACE: usize = 0; | ||
| pub const COMMON_VTABLE_ENTRIES_SIZE: usize = 1; | ||
| pub const COMMON_VTABLE_ENTRIES_ALIGN: usize = 2; | ||
| pub const COMMON_VTABLE_ENTRIES_ASYNCDROPINPLACE: usize = 1; | ||
| pub const COMMON_VTABLE_ENTRIES_SIZE: usize = 2; | ||
| pub const COMMON_VTABLE_ENTRIES_ALIGN: usize = 3; | ||
|
|
||
| // Note that we don't have access to a self type here, this has to be purely based on the trait (and | ||
| // supertrait) definitions. That means we can't call into the same vtable_entries code since that | ||
|
|
@@ -129,6 +137,18 @@ pub(super) fn vtable_allocation_provider<'tcx>( | |
| Scalar::from_maybe_pointer(Pointer::null(), &tcx) | ||
| } | ||
| } | ||
| VtblEntry::MetadataAsyncDropInPlace => { | ||
| if tcx.features().async_drop() | ||
| && ty.needs_async_drop(tcx, ty::TypingEnv::fully_monomorphized()) | ||
| && let Some(instance) = ty::Instance::resolve_async_drop_in_place_dyn(tcx, ty) | ||
| { | ||
| let fn_alloc_id = tcx.reserve_and_set_fn_alloc(instance, CTFE_ALLOC_SALT); | ||
| let fn_ptr = Pointer::from(fn_alloc_id); | ||
| Scalar::from_pointer(fn_ptr, &tcx) | ||
| } else { | ||
| Scalar::from_maybe_pointer(Pointer::null(), &tcx) | ||
| } | ||
| } | ||
| VtblEntry::MetadataSize => Scalar::from_uint(size, ptr_size), | ||
| VtblEntry::MetadataAlign => Scalar::from_uint(align, ptr_size), | ||
| VtblEntry::Vacant => continue, | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why do we need backend-specific logic? I would expect all of this to happen in shims, as the backends all already know how to process shims
View changes since the review