Skip to content

[clr-ios] Disable R2R IL-body stripping for more library tests that need IL at run time#130468

Merged
kotlarmilos merged 5 commits into
dotnet:mainfrom
kotlarmilos:dev/kotlarmilos/clr-ios-strip-il-bodies-more-tests
Jul 13, 2026
Merged

[clr-ios] Disable R2R IL-body stripping for more library tests that need IL at run time#130468
kotlarmilos merged 5 commits into
dotnet:mainfrom
kotlarmilos:dev/kotlarmilos/clr-ios-strip-il-bodies-more-tests

Conversation

@kotlarmilos

Copy link
Copy Markdown
Member

Description

Follow-up to #130360. The SDK strips IL bodies from the Apple mobile CoreCLR composite ReadyToRun image by default, replacing each body with an invalid stub, so any test that needs the real IL at run time fails. Three more projects hit this: System.Runtime.Extensions.Tests (AppDomainTests.ExecuteAssembly invokes a stripped entry point, InvalidProgramException), System.IO.Hashing.Tests (Crc64ParameterSet.ForwardCrc64.InitializeVectorized, a Vector128 intrinsic fallback), and System.Diagnostics.StackTrace.Tests (the runtime-async V2Methods.Quuux in ToString_Async). This sets PublishReadyToRunStripILBodies to false on those three test projects, which #130360 already forwards through the _ApplePropertyNames allowlist, leaving stripping on for every other Apple mobile CoreCLR test app.

…eed IL at run time

Follow-up to dotnet#130360. The SDK strips IL bodies from the Apple mobile
CoreCLR composite ReadyToRun image by default, replacing each body with
an invalid stub, so any test that needs the real IL at run time fails.
Three more projects hit this: System.Runtime.Extensions.Tests
(AppDomainTests.ExecuteAssembly invokes a stripped entry point,
InvalidProgramException), System.IO.Hashing.Tests
(Crc64ParameterSet.ForwardCrc64.InitializeVectorized, a Vector128
intrinsic fallback), and System.Diagnostics.StackTrace.Tests (the
runtime-async V2Methods.Quuux in ToString_Async). This sets
PublishReadyToRunStripILBodies to false on those three test projects,
which dotnet#130360 already forwards through the _ApplePropertyNames
allowlist, leaving stripping on for every other Apple mobile CoreCLR
test app.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 432f1ad3-ea7c-4c6e-8f53-c6ecb80338b6
@dotnet-policy-service

Copy link
Copy Markdown
Contributor

Tagging subscribers to this area: @dotnet/runtime-infrastructure
See info in area-owners.md if you want to be subscribed.

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

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 updates a small set of library test projects to opt out of IL-body stripping during Apple mobile CoreCLR composite ReadyToRun publishing, ensuring tests that depend on runtime IL inspection/execution aren’t broken by stripped method bodies.

Changes:

  • Set PublishReadyToRunStripILBodies to false for System.Runtime.Extensions.Tests.
  • Set PublishReadyToRunStripILBodies to false for System.IO.Hashing.Tests.
  • Set PublishReadyToRunStripILBodies to false for System.Diagnostics.StackTrace.Tests.
Show a summary per file
File Description
src/libraries/System.Runtime/tests/System.Runtime.Extensions.Tests/System.Runtime.Extensions.Tests.csproj Disables IL-body stripping for this test app to keep runtime IL available where needed.
src/libraries/System.IO.Hashing/tests/System.IO.Hashing.Tests.csproj Disables IL-body stripping for this test app to avoid failures when IL is required at runtime.
src/libraries/System.Diagnostics.StackTrace/tests/System.Diagnostics.StackTrace.Tests.csproj Disables IL-body stripping for this test app to preserve IL-dependent runtime behavior for specific tests.

Copilot's findings

  • Files reviewed: 3/3 changed files
  • Comments generated: 0

@kotlarmilos

Copy link
Copy Markdown
Member Author

/azp run runtime-extra-platforms

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

@jakobbotsch

Copy link
Copy Markdown
Member

and System.Diagnostics.StackTrace.Tests (the runtime-async V2Methods.Quuux in ToString_Async)

Why is this manual workaround needed for this case?

…ple mobile

The generated merged test runner entry point Program...RunTests(TestFilter)
has its IL stripped by crossgen2 --strip-il-bodies, which the interpreter on
Apple mobile CoreCLR needs at runtime, causing the iossimulator CoreCLR
runtime test leg to fail. Set PublishReadyToRunStripILBodies=false so the
property is forwarded through _ApplePropertyNames into the Helix Apple app
build, matching the approach used for the library test projects in this PR.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 24b062cc-cf90-4c79-868e-4c6d1fcc7c36
Copilot AI review requested due to automatic review settings July 10, 2026 11:03

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot's findings

  • Files reviewed: 4/4 changed files
  • Comments generated: 1

Comment thread src/tests/JIT/Regression/Regression_o_2.csproj
@kotlarmilos

Copy link
Copy Markdown
Member Author

and System.Diagnostics.StackTrace.Tests (the runtime-async V2Methods.Quuux in ToString_Async)

Why is this manual workaround needed for this case?

The guard MayNeedILAtRuntime keeps IL only when ReturnsTaskOrValueTask() && !method.IsAsync. The guard is scoped to preserve IL of non-async Task returning methods. V2Methods.Quuux public static async Task Quuux() marked [RuntimeAsyncMethodGeneration(true)].

The alternative is to fix this by expanding the guard so IL is preserved for any Task or ValueTask returning method, that is dropping the, since both the non-async path and the async variant path read the same RVA IL.

@kotlarmilos

Copy link
Copy Markdown
Member Author

/azp run runtime-extra-platforms

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

@jakobbotsch

Copy link
Copy Markdown
Member

and System.Diagnostics.StackTrace.Tests (the runtime-async V2Methods.Quuux in ToString_Async)

Why is this manual workaround needed for this case?

The guard MayNeedILAtRuntime keeps IL only when ReturnsTaskOrValueTask() && !method.IsAsync. The guard is scoped to preserve IL of non-async Task returning methods. V2Methods.Quuux public static async Task Quuux() marked [RuntimeAsyncMethodGeneration(true)].

The alternative is to fix this by expanding the guard so IL is preserved for any Task or ValueTask returning method, that is dropping the, since both the non-async path and the async variant path read the same RVA IL.

The situation is:
For a method marked as async:

  • The IL is needed for the async variant
  • The IL is not needed for the Task-returning variant

For a method not marked as async:

  • The IL is needed for the async variant
  • The IL is needed for the Task-returning variant

The check checks for the second case and it expects the former case to be covered by the existing factory.OptimizationFlags.CompiledMethodDefs check. If that isn't the case, can we make it so it is?

CopiedMethodILNode stripped the RVA IL body of a runtime-async method
whenever the method's Task-returning entrypoint was compiled, because the
CompiledMethodDefs gate keys on the EcmaMethod while AsyncMethodVariant
records itself under its own key. The RVA body is consumed at run time only
by the async variant, so the body was stripped even when the variant was not
compiled into the image and had to be materialized from IL, faulting on the
invalid stub.

Keep the IL for an already-async method unless its async variant is present
in CompiledMethodDefs. This removes the need for the per-test
PublishReadyToRunStripILBodies override on System.Diagnostics.StackTrace.Tests.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 24b062cc-cf90-4c79-868e-4c6d1fcc7c36
Copilot AI review requested due to automatic review settings July 10, 2026 12:50

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot's findings

  • Files reviewed: 4/4 changed files
  • Comments generated: 3

Comment thread src/tests/JIT/Regression/Regression_o_2.csproj
@kotlarmilos

Copy link
Copy Markdown
Member Author

/azp run runtime-extra-platforms

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

… variant

Covers the newly-precise guard: a non-async Task-returning method whose async
variant is compiled (because a runtime-async method awaits it) now has its IL
stripped. The case fails under the previous logic, which kept the IL of all
non-async Task-returning methods unconditionally, and passes with the fix.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 24b062cc-cf90-4c79-868e-4c6d1fcc7c36
Copilot AI review requested due to automatic review settings July 10, 2026 16:11

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot's findings

  • Files reviewed: 6/6 changed files
  • Comments generated: 2

Comment thread src/tests/JIT/Regression/Regression_o_2.csproj
@kotlarmilos

Copy link
Copy Markdown
Member Author

/azp run runtime-extra-platforms

@azure-pipelines

Copy link
Copy Markdown
Azure Pipelines successfully started running 1 pipeline(s).

@kotlarmilos

Copy link
Copy Markdown
Member Author

Apple mobile tests no longer fail with InvalidProgramException from stripped IL bodies

@kotlarmilos

Copy link
Copy Markdown
Member Author

/ba-g timeouts and unrelated extra-platforms failures

@kotlarmilos kotlarmilos merged commit a90733c into dotnet:main Jul 13, 2026
166 of 184 checks passed
@BrzVlad

BrzVlad commented Jul 13, 2026

Copy link
Copy Markdown
Member

Are we too aggressive with disabling tests here ? Which one of these patterns can happen with user code ? IIRC ALC unload didn't actually free memory on mono, but otherwise they would be working. I know users having been asking for this support in the past. Also, why would we ever need the IL for Crc64ParameterSet.ForwardCrc64.InitializeVectorized ? I believe we should fix all these scenarios otherwise users will just get regression as we have this stripping enabled by default.

@kotlarmilos

Copy link
Copy Markdown
Member Author

Are we too aggressive with disabling tests here ? Which one of these patterns can happen with user code ? IIRC ALC unload didn't actually free memory on mono, but otherwise they would be working. I know users having been asking for this support in the past. Also, why would we ever need the IL for Crc64ParameterSet.ForwardCrc64.InitializeVectorized ? I believe we should fix all these scenarios otherwise users will just get regression as we have this stripping enabled by default.

Agreed. The project-level stripping property is broad workaround and should not be the final state. The runtime-async  System.Diagnostics.StackTrace.Tests  case is fixed in this PR. System.Runtime.Extensions.Tests exercises dynamic assembly loading where the load path cannot use the composite R2R code and the interpreter needs IL. The same applies to the AssemblyLoadContext.

Since stripping is enabled by default, I agree the remaining cases need fixes and the opt-outs should be removed as those fixes land.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

Status: Done

Development

Successfully merging this pull request may close these issues.

5 participants