-
Notifications
You must be signed in to change notification settings - Fork 5.2k
[RuntimeAsync] Follow up for unboxing and instantiating stubs. #118301
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
Conversation
Tagging subscribers to this area: @mangod9 |
@jakobbotsch Thanks!! |
I think this is ready for review. |
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.
Pull Request Overview
This PR adds support for async target methods in unboxing and instantiating stubs, ensuring that implicit continuation arguments are properly handled during argument propagation and that returned continuations are managed correctly for GC purposes.
Key changes include:
- Introduction of async IL stubs that handle continuation arguments explicitly
- Updates to portable shuffler to handle async continuation argument mapping
- Configuration changes to enable runtime async support by default
Reviewed Changes
Copilot reviewed 13 out of 13 changed files in this pull request and generated 3 comments.
Show a summary per file
File | Description |
---|---|
src/tests/async/inst-unbox-thunks/inst-unbox-thunks.csproj | Test project configuration for async unboxing/instantiating stub tests |
src/tests/async/inst-unbox-thunks/inst-unbox-thunks.cs | Comprehensive test cases covering async unboxing and instantiating stubs |
src/tests/async/Directory.Build.targets | Enables async testing by uncommenting DisableProjectBuild |
src/coreclr/vm/siginfo.cpp | Adds PermitUninstDefOrRef flag to type loading |
src/coreclr/vm/prestub.cpp | Major updates to support async in unboxing and instantiating stubs |
src/coreclr/vm/jitinterface.cpp | Adds async calling convention translation and removes unnecessary token reset |
src/coreclr/vm/ilstubcache.h | Extends IL stub cache to support async stubs |
src/coreclr/vm/ilstubcache.cpp | Implements async stub creation with proper async method data |
src/coreclr/vm/comdelegate.cpp | Adds async continuation argument handling to portable shuffle array |
src/coreclr/vm/callingconvention.h | Adds GetAsyncContinuatioLoc method for argument location |
src/coreclr/jit/importercalls.cpp | Updates async call handling for CALLI instructions |
src/coreclr/inc/corhdr.h | Defines new IMAGE_CEE_CS_CALLCONV_ASYNC calling convention |
src/coreclr/inc/clrconfigvalues.h | Enables RuntimeAsync support by default |
The network timeouts on Android are unlikely related to the changes |
Re: #117266
Adding support for async target methods in unboxing and instantiating stubs.
As far as stubs are concerned, async is a passive participant. The main reason for this change is to make sure that whenever arguments are propagated/shuffled by a stub and the target is using async calling convention, the implicit continuation arguments are not lost or corrupted.
Also need to ensure that returned continuation is handled correctly. Since it is a managed object, if stub is managed code, then it needs to be aware of continuation return, at very least for GC purposes.
That seems sufficient for the continuation to be handled correctly.
This is a bit more complicated. The IL stubs typically come into play when we cannot tailcall. Even if we immediately return from the stub, a non-async stub method would have two problems: a) ensure that implicit continuation return is not trashed in the epilog, b) ensure that continuation return is GC protected.
Thus we go with a different solution - we introduce
async IL stubs
. Since IL stubs are fully normal methods sent through the JIT, we can ask the JIT to treat them asAsyncMethodKind::AsyncExplicitImpl
.One subtle part is that in the async stubs' CALLI we pass the continuation argument explicitly, similar to what we do with generic contexts. The JIT expects this pattern when seeing async CALLI. Since only stubs use async CALLI, this convention is sufficient.
The reason we cannot rely on normal inserting of continuation arg by the JIT is that in stub calls the generic context is passed as an ordinary parameter and JIT would not know how to order continuation argument with respect to that.
(the knowledge that one of the parameter is a generic context stays on stub's side, means the continuation needs to be inserted on the stub's side as well).