From fa63c8299c52865deca35d81431115392ff48f6b Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Sun, 27 Sep 2026 20:48:12 -0500 Subject: [PATCH 01/14] [Apple][CoreCLR] Don't pass the executable path as managed args[0] NSProcessInfo.arguments includes the executable path as element 0, and the CoreCLR Apple host passed the whole array to coreclr_execute_assembly, whose argv becomes Main's args. The merged runtime-test runner treats args[0] as the test to run, so every runtime test on iOS, tvOS and maccatalyst was reported as skipped. Fixes #134766 Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tasks/AppleAppBuilder/Templates/runtime-coreclr.m | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/tasks/AppleAppBuilder/Templates/runtime-coreclr.m b/src/tasks/AppleAppBuilder/Templates/runtime-coreclr.m index a651718b567b69..4c4c35b10a111f 100644 --- a/src/tasks/AppleAppBuilder/Templates/runtime-coreclr.m +++ b/src/tasks/AppleAppBuilder/Templates/runtime-coreclr.m @@ -216,7 +216,8 @@ bool get_native_code_data(const struct host_runtime_contract_native_code_context &coreclr_handle, &coreclr_domainId); assert (res == 0); - coreclr_execute_assembly (coreclr_handle, coreclr_domainId, argi, managed_argv, path, &res); + // managed_argv[0] is the executable path; managed Main expects only the arguments after it. + coreclr_execute_assembly (coreclr_handle, coreclr_domainId, argi - 1, managed_argv + 1, path, &res); // Print this so apps parsing logs can detect when we exited os_log_info (OS_LOG_DEFAULT, EXIT_CODE_TAG ": %d", res); From 207485e3243483ce3aae7a00fdf18aecec5f891c Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Sun, 27 Sep 2026 23:10:15 -0500 Subject: [PATCH 02/14] [Android][CoreCLR] Don't pass the bundle path as managed args[0] monodroid-coreclr.c prepended the bundle path to the arguments it passed to coreclr_execute_assembly, whose argv becomes Main's args. The merged runtime-test runner treats args[0] as the test to run, so every Android CoreCLR runtime test was reported as skipped. The Mono host keeps argv[0] because mono_jit_exec expects the program name there. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .../AndroidAppBuilder/Templates/monodroid-coreclr.c | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/src/tasks/AndroidAppBuilder/Templates/monodroid-coreclr.c b/src/tasks/AndroidAppBuilder/Templates/monodroid-coreclr.c index 19d11ad3fb62fb..50b57ea630e47a 100644 --- a/src/tasks/AndroidAppBuilder/Templates/monodroid-coreclr.c +++ b/src/tasks/AndroidAppBuilder/Templates/monodroid-coreclr.c @@ -277,27 +277,26 @@ Java_net_dot_MonoRunner_execEntryPoint (JNIEnv* env, jobject thiz, jstring j_ent } int args_len = (*env)->GetArrayLength (env, j_args); - int managed_argc = args_len + 1; - const char** managed_argv = (const char**)malloc (managed_argc * sizeof(char*)); + // Managed Main receives only the app arguments, not the bundle path. + const char** managed_argv = (const char**)malloc ((args_len > 0 ? args_len : 1) * sizeof(char*)); if (managed_argv == NULL) { LOG_ERROR("Failed to allocate memory for managed_argv"); return -1; } - managed_argv[0] = g_bundle_path; for (int i = 0; i < args_len; ++i) { jstring j_arg = (*env)->GetObjectArrayElement(env, j_args, i); - managed_argv[i + 1] = (char*)((*env)->GetStringUTFChars(env, j_arg, NULL)); + managed_argv[i] = (char*)((*env)->GetStringUTFChars(env, j_arg, NULL)); } - int rv = mono_droid_execute_assembly (g_executable_path, g_coreclr_handle, g_coreclr_domainId, managed_argc, managed_argv); + int rv = mono_droid_execute_assembly (g_executable_path, g_coreclr_handle, g_coreclr_domainId, args_len, managed_argv); for (int i = 0; i < args_len; ++i) { jstring j_arg = (*env)->GetObjectArrayElement(env, j_args, i); - (*env)->ReleaseStringUTFChars(env, j_arg, managed_argv[i + 1]); + (*env)->ReleaseStringUTFChars(env, j_arg, managed_argv[i]); } free(managed_argv); From 089d42fe820651ecb767ff1a20fe3bc1ba2a56d2 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Sun, 27 Sep 2026 23:19:32 -0500 Subject: [PATCH 03/14] Quarantine b425314 on Apple mobile CoreCLR (#134770) The test hangs on maccatalyst CoreCLR: a GC suspension never completes because the runtime can't suspend a tight R2R loop, which also blocks the test's own timeout timer. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .../JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b425314/b425314.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b425314/b425314.cs b/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b425314/b425314.cs index ea19f3e4652644..d73e36bf302e16 100644 --- a/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b425314/b425314.cs +++ b/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b425314/b425314.cs @@ -936,6 +936,7 @@ internal static void RecordFailure(Exception ex) [Fact] [ActiveIssue("https://github.com/dotnet/runtime/issues/41472", typeof(PlatformDetection), nameof(PlatformDetection.IsNotMultithreadingSupported))] + [ActiveIssue("https://github.com/dotnet/runtime/issues/134770", typeof(PlatformDetection), nameof(PlatformDetection.IsAppleMobile), nameof(PlatformDetection.IsCoreCLR))] [SkipOnCoreClr("This test takes too long and internally times out under GCStress/heap verify. It is not fundamentally incompatible if stress testing is fast enough.", RuntimeTestModes.AnyGCStress | RuntimeTestModes.HeapVerify)] public static int TestEntryPoint() { From 1cac9a9b291fa69f31bad8d37ab90dc17d5f0b1c Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 00:02:53 -0500 Subject: [PATCH 04/14] Quarantine b426654 on Apple mobile CoreCLR (#134770) Same GC suspension hang as b425314: a flip thread in a tight R2R loop can't be suspended. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .../JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b426654/b426654.il | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b426654/b426654.il b/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b426654/b426654.il index 39a46cf0f39d5c..866dd6d2e811c0 100644 --- a/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b426654/b426654.il +++ b/src/tests/JIT/Regression/CLR-x86-JIT/V2.0-Beta2/b426654/b426654.il @@ -217,6 +217,11 @@ string('This test is too slow under GCStress=3. See https://github.com/dotnet/runtime/issues/50615.') int32(0xC0) // AnyGCStress } + .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.ActiveIssueAttribute::.ctor(string, class [System.Runtime]System.Type, string[]) = { + string('https://github.com/dotnet/runtime/issues/134770') + type([TestLibrary]TestLibrary.PlatformDetection) + string[2] ('IsAppleMobile' 'IsCoreCLR') + } .entrypoint .maxstack 5 .locals init (class cs1 V_0, From 98c5fe9039f702bc426602df72f50877106f4c1a Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 00:58:25 -0500 Subject: [PATCH 05/14] Bundle FSharp.Core into mobile runtime-test apps F# tests load FSharp.Core from CORE_ROOT on other platforms, but Apple and Android merged runners bundle only their own publish output, so F# tests failed with FileNotFoundException. Resolve FSharp.Core from the test_dependencies_fs restore (the same source CORE_ROOT uses; CORE_ROOT itself is laid out after the managed test build) and add it to runners that reference an .fsproj. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tests/Common/mergedrunnermobile.targets | 14 ++++++++++++++ .../test_dependencies_fs/test_dependencies.fsproj | 7 +++++++ 2 files changed, 21 insertions(+) diff --git a/src/tests/Common/mergedrunnermobile.targets b/src/tests/Common/mergedrunnermobile.targets index 4ee3dcf2246b7b..b79853443f09e7 100644 --- a/src/tests/Common/mergedrunnermobile.targets +++ b/src/tests/Common/mergedrunnermobile.targets @@ -31,6 +31,20 @@ + + + + + + + + + + diff --git a/src/tests/Common/test_dependencies_fs/test_dependencies.fsproj b/src/tests/Common/test_dependencies_fs/test_dependencies.fsproj index d5db8298bb7d74..2bd9290e4031be 100644 --- a/src/tests/Common/test_dependencies_fs/test_dependencies.fsproj +++ b/src/tests/Common/test_dependencies_fs/test_dependencies.fsproj @@ -16,4 +16,11 @@ + + + + + + + From f582faff1d927c695aaca8a4f60cb8e8a99f2f64 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 00:58:25 -0500 Subject: [PATCH 06/14] Quarantine mutual_recursion on Apple mobile CoreCLR (#134775) With FSharp.Core bundled, the test now runs and hits a fatal stack overflow: tail calls between R2R and interpreted code grow the stack. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tests/JIT/Directed/tailcall/mutual_recursion.fs | 1 + 1 file changed, 1 insertion(+) diff --git a/src/tests/JIT/Directed/tailcall/mutual_recursion.fs b/src/tests/JIT/Directed/tailcall/mutual_recursion.fs index 413f79b8c1e2c8..172ceae56f0515 100644 --- a/src/tests/JIT/Directed/tailcall/mutual_recursion.fs +++ b/src/tests/JIT/Directed/tailcall/mutual_recursion.fs @@ -559,6 +559,7 @@ type Driver() = [] [] [, [| "IsWasmReadyToRun" |])>] +[, [| "IsAppleMobile"; "IsCoreCLR" |])>] [, [| "IsNotNativeAot" |])>] let main () = let driver = Driver() From b2864a681687cd8b1c76ed207415c3fb7a39825e Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 00:58:25 -0500 Subject: [PATCH 07/14] Skip Test_HndIndex_10 tests when CoreCLR runs without a JIT The tests expect the JIT to reject invalid IL. Without a JIT (Apple mobile), crossgen2 skips the method and the interpreter runs it without an exception. The existing InterpreterActive skip only covers DOTNET_Interpreter/InterpMode and wasm; gate on Utilities.IsCoreClrInterpreter, which also covers the no-JIT case. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tests/Common/CoreCLRTestLibrary/Utilities.cs | 2 ++ .../Dev11/Dev11_468598/Test_HndIndex_10_Plain.il | 9 ++++++--- .../Dev11/Dev11_468598/Test_HndIndex_10_Plain.ilproj | 3 +++ .../Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il | 9 ++++++--- .../Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj | 3 +++ 5 files changed, 20 insertions(+), 6 deletions(-) diff --git a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs index f257d4b1b9595e..f967db5ccdcb10 100644 --- a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs +++ b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs @@ -110,6 +110,8 @@ public static bool IsCoreClrInterpreter } } + public static bool IsNotCoreClrInterpreter => !IsCoreClrInterpreter; + public static bool HasAssemblyFiles => !string.IsNullOrEmpty(typeof(Utilities).Assembly.Location); public static bool IsSingleFile => !HasAssemblyFiles; diff --git a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.il b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.il index bd6a1cc61978b4..0bc024ac52e234 100644 --- a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.il +++ b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.il @@ -11,6 +11,8 @@ .ver 4:0:0:0 } .assembly extern Microsoft.DotNet.XUnitExtensions { .publickeytoken = (31 BF 38 56 AD 36 4E 35 ) } +.assembly extern System.Runtime { .publickeytoken = (B0 3F 5F 7F 11 D5 0A 3A ) } +.assembly extern TestLibrary { .ver 0:0:0:0 } .assembly Test_HndIndex_10_Plain { @@ -32,9 +34,10 @@ .class nested public auto ansi Test_Test_HndIndex_10_Plain extends [mscorlib] System.Object { .method public hidebysig static int32 Main() cil managed { - .custom instance void [xunit.core]Xunit.FactAttribute::.ctor() = ( - 01 00 00 00 - ) + .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.ConditionalFactAttribute::.ctor(class [System.Runtime]System.Type, string[]) = { + type([TestLibrary]TestLibrary.Utilities) + string[1] ('IsNotCoreClrInterpreter') + } .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.ActiveIssueAttribute::.ctor(string, valuetype [Microsoft.DotNet.XUnitExtensions]Xunit.TestRuntimes) = { string('Needs triage') int32(0x2) // Mono diff --git a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.ilproj b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.ilproj index ffd7fd6ac2020e..1c41ae33c626f3 100644 --- a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.ilproj +++ b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Plain.ilproj @@ -6,4 +6,7 @@ + + + diff --git a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il index 7b7b0dd56035f2..a64d2c9c6ff6de 100644 --- a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il +++ b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il @@ -23,6 +23,8 @@ } .assembly extern xunit.core {} .assembly extern Microsoft.DotNet.XUnitExtensions { .publickeytoken = (31 BF 38 56 AD 36 4E 35 ) } +.assembly extern System.Runtime { .publickeytoken = (B0 3F 5F 7F 11 D5 0A 3A ) } +.assembly extern TestLibrary { .ver 0:0:0:0 } // MVID: {68AEE7ED-2AC8-4330-9EC7-4EBFD6BD74E0} .imagebase 0x00400000 @@ -41,9 +43,10 @@ .method public hidebysig static int32 Main() cil managed { - .custom instance void [xunit.core]Xunit.FactAttribute::.ctor() = ( - 01 00 00 00 - ) + .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.ConditionalFactAttribute::.ctor(class [System.Runtime]System.Type, string[]) = { + type([TestLibrary]TestLibrary.Utilities) + string[1] ('IsNotCoreClrInterpreter') + } .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.SkipOnCoreClrAttribute::.ctor(string, valuetype [Microsoft.DotNet.XUnitExtensions]Xunit.RuntimeTestModes) = { string('Test checks for an issue that cannot occur with the interpreter') int32(0x400) // InterpreterActive diff --git a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj index 8843e470e7d79c..2bbe74e34287e7 100644 --- a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj +++ b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj @@ -7,4 +7,7 @@ + + + From 5db12a3d50866203f4d9ab445a944aff3276e385 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 02:06:00 -0500 Subject: [PATCH 08/14] Skip Runtime_90219 on Android The test loads its own assembly from Assembly.Location, which is empty for assemblies bundled in an Android app. It is already skipped on the other bundled platforms (Browser, Wasi, iOS, tvOS, MacCatalyst) for the same reason. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tests/JIT/Regression_o_3/Runtime_90219.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/tests/JIT/Regression_o_3/Runtime_90219.cs b/src/tests/JIT/Regression_o_3/Runtime_90219.cs index 84ab3a70db0e8e..dcd72d726d8753 100644 --- a/src/tests/JIT/Regression_o_3/Runtime_90219.cs +++ b/src/tests/JIT/Regression_o_3/Runtime_90219.cs @@ -40,7 +40,7 @@ public class Runtime_90219 [Fact] [ActiveIssue("https://github.com/dotnet/runtimelab/issues/155: Assembly.Load", typeof(TestLibrary.Utilities), nameof(TestLibrary.Utilities.IsNativeAot))] [ActiveIssue("https://github.com/dotnet/runtime/issues/90374", TestRuntimes.Mono)] - [SkipOnPlatform(TestPlatforms.Browser | TestPlatforms.Wasi | TestPlatforms.iOS | TestPlatforms.tvOS | TestPlatforms.MacCatalyst, "Loads assembly from file.")] + [SkipOnPlatform(TestPlatforms.Browser | TestPlatforms.Wasi | TestPlatforms.iOS | TestPlatforms.tvOS | TestPlatforms.MacCatalyst | TestPlatforms.Android, "Loads assembly from file.")] public static int TestEntryPoint() { CollectibleALC alc = new CollectibleALC(); From c4e410a1e5dd537bdb69062f71a5649f55e4bba1 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 10:30:32 -0500 Subject: [PATCH 09/14] Make InterpreterActive mean code runs in the interpreter InterpreterActive was true for every wasm run, including ReadyToRun, and never true on Apple mobile, which has no JIT. Define it as DOTNET_Interpreter/InterpMode, or no JIT without ReadyToRun, and set TEST_READY_TO_RUN_MODE=1 in Apple mobile runtime-test apps when they are ReadyToRun-compiled so the runtime can tell. Tests this now runs on wasm ReadyToRun: GetGeneration fails there (#134803, quarantined), and ManagedPointers.Validate_GeneratedILStubs_NullByRef hits the interpreter even with ReadyToRun, so it now requires a JIT via Utilities.IsNotCoreClrInterpreter. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .../CoreCLRTestLibrary/CoreClrConfigurationDetection.cs | 7 ++++--- src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs | 2 +- src/tests/Common/mergedrunnermobile.targets | 5 +++++ src/tests/GC/API/GC/GetGeneration.cs | 1 + .../baseservices/invalid_operations/ManagedPointers.cs | 3 ++- 5 files changed, 13 insertions(+), 5 deletions(-) diff --git a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs index e49c9d4dc758ca..4d9bfb18673355 100644 --- a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs +++ b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs @@ -5,6 +5,7 @@ using System; using System.Globalization; using System.Reflection; +using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Security; using System.Text; @@ -27,13 +28,13 @@ public static bool IsCoreClrInterpreter { get { - // WASM-TODO: update when codegen is in place - if (PlatformDetection.IsWasm) - return true; if (!string.IsNullOrWhiteSpace(GetEnvironmentVariableValue("Interpreter", ""))) return true; if (int.TryParse(GetEnvironmentVariableValue("InterpMode", "0"), out int mode) && (mode > 0)) return true; + // Without a JIT (WebAssembly, Apple mobile), code that isn't ReadyToRun-compiled runs in the interpreter. + if (RuntimeFeature.IsDynamicCodeSupported && !RuntimeFeature.IsDynamicCodeCompiled && !PlatformDetection.IsReadyToRunCompiled) + return true; return false; } } diff --git a/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs b/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs index d2c3edc20e17e6..8b6421676e57fd 100644 --- a/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs +++ b/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs @@ -44,6 +44,6 @@ public enum RuntimeTestModes HeapVerify = 1 << 9, // DOTNET_HeapVerify (or COMPlus_HeapVerify) is set. - InterpreterActive = 1 << 10, // DOTNET_Interpreter != "" or DOTNET_InterpMode != 0 + InterpreterActive = 1 << 10, // DOTNET_Interpreter != "", DOTNET_InterpMode != 0, or no JIT and not ReadyToRun-compiled (TEST_READY_TO_RUN_MODE != 1) } } diff --git a/src/tests/Common/mergedrunnermobile.targets b/src/tests/Common/mergedrunnermobile.targets index b79853443f09e7..d9b4c2911e2163 100644 --- a/src/tests/Common/mergedrunnermobile.targets +++ b/src/tests/Common/mergedrunnermobile.targets @@ -31,6 +31,11 @@ + + + + + Date: Mon, 28 Sep 2026 11:32:16 -0500 Subject: [PATCH 10/14] Gate Runtime_90219 on assembly files instead of a platform list The test loads its own assembly from Assembly.Location, so require Utilities.HasAssemblyFiles rather than listing every configuration that bundles assemblies. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tests/JIT/Regression_o_3/Runtime_90219.cs | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/tests/JIT/Regression_o_3/Runtime_90219.cs b/src/tests/JIT/Regression_o_3/Runtime_90219.cs index dcd72d726d8753..33bde17ad44925 100644 --- a/src/tests/JIT/Regression_o_3/Runtime_90219.cs +++ b/src/tests/JIT/Regression_o_3/Runtime_90219.cs @@ -37,10 +37,9 @@ public class Runtime_90219 public static byte Result; [ActiveIssue("https://github.com/dotnet/runtimelab/issues/155: Assembly.Load", typeof(Utilities), nameof(Utilities.IsNativeAot))] - [Fact] + [ConditionalFact(typeof(Utilities), nameof(Utilities.HasAssemblyFiles))] [ActiveIssue("https://github.com/dotnet/runtimelab/issues/155: Assembly.Load", typeof(TestLibrary.Utilities), nameof(TestLibrary.Utilities.IsNativeAot))] [ActiveIssue("https://github.com/dotnet/runtime/issues/90374", TestRuntimes.Mono)] - [SkipOnPlatform(TestPlatforms.Browser | TestPlatforms.Wasi | TestPlatforms.iOS | TestPlatforms.tvOS | TestPlatforms.MacCatalyst | TestPlatforms.Android, "Loads assembly from file.")] public static int TestEntryPoint() { CollectibleALC alc = new CollectibleALC(); From c2108510db8edbeb68ce48169fa893e255a9d6a5 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 11:32:16 -0500 Subject: [PATCH 11/14] Rename CoreClrConfigurationDetection.IsCoreClrInterpreter to IsInterpreterMode Its meaning (an interpreter test mode) now differs from Utilities.IsCoreClrInterpreter and the library-test PlatformDetection.IsCoreClrInterpreter (no JIT, so some code may be interpreted). Give it a distinct name and document both. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .../Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs | 3 ++- src/tests/Common/CoreCLRTestLibrary/Utilities.cs | 3 ++- .../Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs | 2 +- 3 files changed, 5 insertions(+), 3 deletions(-) diff --git a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs index 4d9bfb18673355..53da71f06d6dde 100644 --- a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs +++ b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs @@ -24,7 +24,8 @@ public static class CoreClrConfigurationDetection public static bool IsTieredCompilation => string.Equals(GetEnvironmentVariableValue("TieredCompilation", "1"), "1", StringComparison.InvariantCulture); public static bool IsHeapVerify => string.Equals(GetEnvironmentVariableValue("HeapVerify"), "1", StringComparison.InvariantCulture); - public static bool IsCoreClrInterpreter + // An interpreter test mode (RuntimeTestModes.InterpreterActive): the interpreter is configured, or there is no JIT and the test is not ReadyToRun-compiled. + public static bool IsInterpreterMode { get { diff --git a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs index f967db5ccdcb10..9fd0aaf29b1ea8 100644 --- a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs +++ b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs @@ -100,13 +100,14 @@ public static bool IsWindowsIoTCore public static bool IsNativeAot => IsNotMonoRuntime && !IsReflectionEmitSupported; public static bool IsNotNativeAot => !IsNativeAot; + // No JIT, or the interpreter is configured: some code may be interpreted even when ReadyToRun-compiled. public static bool IsCoreClrInterpreter { get { if (RuntimeFeature.IsDynamicCodeSupported && !RuntimeFeature.IsDynamicCodeCompiled) return true; - return CoreClrConfigurationDetection.IsCoreClrInterpreter; + return CoreClrConfigurationDetection.IsInterpreterMode; } } diff --git a/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs b/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs index d9234a414a37f7..3c09ac0d9b2de6 100644 --- a/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs +++ b/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs @@ -1017,7 +1017,7 @@ private static ImmutableArray DecorateWithSkipOnCoreClrConfiguration( } if (skippedTestModes.HasFlag(Xunit.RuntimeTestModes.InterpreterActive)) { - conditions.Add($"!{ConditionClass}.IsCoreClrInterpreter"); + conditions.Add($"!{ConditionClass}.IsInterpreterMode"); } if (skippedTestModes.HasFlag(Xunit.RuntimeTestModes.AnyGCStress)) From b645870bd306d424f7de104a870d07f66bdc6402 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 12:22:05 -0500 Subject: [PATCH 12/14] Remove the misleading Utilities.IsCoreClrInterpreter comment The property's meaning is unchanged; only its call to the renamed CoreClrConfigurationDetection.IsInterpreterMode differs from main. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- src/tests/Common/CoreCLRTestLibrary/Utilities.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs index 9fd0aaf29b1ea8..37945fbc35bb1d 100644 --- a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs +++ b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs @@ -100,7 +100,6 @@ public static bool IsWindowsIoTCore public static bool IsNativeAot => IsNotMonoRuntime && !IsReflectionEmitSupported; public static bool IsNotNativeAot => !IsNativeAot; - // No JIT, or the interpreter is configured: some code may be interpreted even when ReadyToRun-compiled. public static bool IsCoreClrInterpreter { get From d7cab8451312108d9d438e4bd80a5b296ed72ac9 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 13:11:15 -0500 Subject: [PATCH 13/14] Set TEST_READY_TO_RUN_MODE for all Apple mobile CoreCLR ReadyToRun test apps Mirror tests.browser.targets so both library and runtime-test Apple apps report PlatformDetection.IsReadyToRunCompiled. AssemblyTests.GetEntryAssembly now reached its desktop single-file R2R branch on Apple, so exclude Apple mobile from it; it keeps expecting AppleTestRunner. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- eng/testing/tests.ioslike.targets | 4 ++++ .../tests/System.Reflection.Tests/AssemblyTests.cs | 2 +- .../CoreClrConfigurationDetection.cs | 10 ++++------ src/tests/Common/CoreCLRTestLibrary/Utilities.cs | 4 +--- .../Common/XUnitWrapperGenerator/RuntimeTestModes.cs | 2 +- .../XUnitWrapperGenerator/XUnitWrapperGenerator.cs | 2 +- src/tests/Common/mergedrunnermobile.targets | 5 ----- src/tests/GC/API/GC/GetGeneration.cs | 1 - .../Dev11/Dev11_468598/Test_HndIndex_10_Plain.il | 9 +++------ .../Dev11/Dev11_468598/Test_HndIndex_10_Plain.ilproj | 3 --- .../Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il | 9 +++------ .../Dev11_468598/Test_HndIndex_10_Reordered.ilproj | 3 --- .../baseservices/invalid_operations/ManagedPointers.cs | 3 +-- 13 files changed, 19 insertions(+), 38 deletions(-) diff --git a/eng/testing/tests.ioslike.targets b/eng/testing/tests.ioslike.targets index 35a39ab6a120e5..858bd37011cdd0 100644 --- a/eng/testing/tests.ioslike.targets +++ b/eng/testing/tests.ioslike.targets @@ -24,6 +24,10 @@ + + + + helix helix diff --git a/src/libraries/System.Runtime/tests/System.Reflection.Tests/AssemblyTests.cs b/src/libraries/System.Runtime/tests/System.Reflection.Tests/AssemblyTests.cs index ff9a5d3a1613a9..fdaffdf8383d3d 100644 --- a/src/libraries/System.Runtime/tests/System.Reflection.Tests/AssemblyTests.cs +++ b/src/libraries/System.Runtime/tests/System.Reflection.Tests/AssemblyTests.cs @@ -158,7 +158,7 @@ public void GetEntryAssembly() { correct = assembly.IndexOf("WasmTestRunner", StringComparison.OrdinalIgnoreCase) != -1; } - else if (PlatformDetection.IsNativeAot || PlatformDetection.IsReadyToRunCompiled) + else if (PlatformDetection.IsNativeAot || (PlatformDetection.IsReadyToRunCompiled && !PlatformDetection.IsAppleMobile)) { // The single file test runner is not 'xunit.console'. correct = assembly.IndexOf("System.Reflection.Tests", StringComparison.OrdinalIgnoreCase) != -1; diff --git a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs index 53da71f06d6dde..e49c9d4dc758ca 100644 --- a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs +++ b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs @@ -5,7 +5,6 @@ using System; using System.Globalization; using System.Reflection; -using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Security; using System.Text; @@ -24,18 +23,17 @@ public static class CoreClrConfigurationDetection public static bool IsTieredCompilation => string.Equals(GetEnvironmentVariableValue("TieredCompilation", "1"), "1", StringComparison.InvariantCulture); public static bool IsHeapVerify => string.Equals(GetEnvironmentVariableValue("HeapVerify"), "1", StringComparison.InvariantCulture); - // An interpreter test mode (RuntimeTestModes.InterpreterActive): the interpreter is configured, or there is no JIT and the test is not ReadyToRun-compiled. - public static bool IsInterpreterMode + public static bool IsCoreClrInterpreter { get { + // WASM-TODO: update when codegen is in place + if (PlatformDetection.IsWasm) + return true; if (!string.IsNullOrWhiteSpace(GetEnvironmentVariableValue("Interpreter", ""))) return true; if (int.TryParse(GetEnvironmentVariableValue("InterpMode", "0"), out int mode) && (mode > 0)) return true; - // Without a JIT (WebAssembly, Apple mobile), code that isn't ReadyToRun-compiled runs in the interpreter. - if (RuntimeFeature.IsDynamicCodeSupported && !RuntimeFeature.IsDynamicCodeCompiled && !PlatformDetection.IsReadyToRunCompiled) - return true; return false; } } diff --git a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs index 37945fbc35bb1d..f257d4b1b9595e 100644 --- a/src/tests/Common/CoreCLRTestLibrary/Utilities.cs +++ b/src/tests/Common/CoreCLRTestLibrary/Utilities.cs @@ -106,12 +106,10 @@ public static bool IsCoreClrInterpreter { if (RuntimeFeature.IsDynamicCodeSupported && !RuntimeFeature.IsDynamicCodeCompiled) return true; - return CoreClrConfigurationDetection.IsInterpreterMode; + return CoreClrConfigurationDetection.IsCoreClrInterpreter; } } - public static bool IsNotCoreClrInterpreter => !IsCoreClrInterpreter; - public static bool HasAssemblyFiles => !string.IsNullOrEmpty(typeof(Utilities).Assembly.Location); public static bool IsSingleFile => !HasAssemblyFiles; diff --git a/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs b/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs index 8b6421676e57fd..d2c3edc20e17e6 100644 --- a/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs +++ b/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs @@ -44,6 +44,6 @@ public enum RuntimeTestModes HeapVerify = 1 << 9, // DOTNET_HeapVerify (or COMPlus_HeapVerify) is set. - InterpreterActive = 1 << 10, // DOTNET_Interpreter != "", DOTNET_InterpMode != 0, or no JIT and not ReadyToRun-compiled (TEST_READY_TO_RUN_MODE != 1) + InterpreterActive = 1 << 10, // DOTNET_Interpreter != "" or DOTNET_InterpMode != 0 } } diff --git a/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs b/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs index 3c09ac0d9b2de6..d9234a414a37f7 100644 --- a/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs +++ b/src/tests/Common/XUnitWrapperGenerator/XUnitWrapperGenerator.cs @@ -1017,7 +1017,7 @@ private static ImmutableArray DecorateWithSkipOnCoreClrConfiguration( } if (skippedTestModes.HasFlag(Xunit.RuntimeTestModes.InterpreterActive)) { - conditions.Add($"!{ConditionClass}.IsInterpreterMode"); + conditions.Add($"!{ConditionClass}.IsCoreClrInterpreter"); } if (skippedTestModes.HasFlag(Xunit.RuntimeTestModes.AnyGCStress)) diff --git a/src/tests/Common/mergedrunnermobile.targets b/src/tests/Common/mergedrunnermobile.targets index d9b4c2911e2163..b79853443f09e7 100644 --- a/src/tests/Common/mergedrunnermobile.targets +++ b/src/tests/Common/mergedrunnermobile.targets @@ -31,11 +31,6 @@ - - - - - - - - diff --git a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il index a64d2c9c6ff6de..7b7b0dd56035f2 100644 --- a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il +++ b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.il @@ -23,8 +23,6 @@ } .assembly extern xunit.core {} .assembly extern Microsoft.DotNet.XUnitExtensions { .publickeytoken = (31 BF 38 56 AD 36 4E 35 ) } -.assembly extern System.Runtime { .publickeytoken = (B0 3F 5F 7F 11 D5 0A 3A ) } -.assembly extern TestLibrary { .ver 0:0:0:0 } // MVID: {68AEE7ED-2AC8-4330-9EC7-4EBFD6BD74E0} .imagebase 0x00400000 @@ -43,10 +41,9 @@ .method public hidebysig static int32 Main() cil managed { - .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.ConditionalFactAttribute::.ctor(class [System.Runtime]System.Type, string[]) = { - type([TestLibrary]TestLibrary.Utilities) - string[1] ('IsNotCoreClrInterpreter') - } + .custom instance void [xunit.core]Xunit.FactAttribute::.ctor() = ( + 01 00 00 00 + ) .custom instance void [Microsoft.DotNet.XUnitExtensions]Xunit.SkipOnCoreClrAttribute::.ctor(string, valuetype [Microsoft.DotNet.XUnitExtensions]Xunit.RuntimeTestModes) = { string('Test checks for an issue that cannot occur with the interpreter') int32(0x400) // InterpreterActive diff --git a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj index 2bbe74e34287e7..8843e470e7d79c 100644 --- a/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj +++ b/src/tests/JIT/Regression/Dev11/Dev11_468598/Test_HndIndex_10_Reordered.ilproj @@ -7,7 +7,4 @@ - - - diff --git a/src/tests/baseservices/invalid_operations/ManagedPointers.cs b/src/tests/baseservices/invalid_operations/ManagedPointers.cs index deb8c21c7876be..c6c20f344793f0 100644 --- a/src/tests/baseservices/invalid_operations/ManagedPointers.cs +++ b/src/tests/baseservices/invalid_operations/ManagedPointers.cs @@ -35,8 +35,7 @@ public static void Validate_BoxingHelpers_NullByRef() [ActiveIssue("Function mismatch", TestPlatforms.iOS | TestPlatforms.tvOS | TestPlatforms.MacCatalyst)] [ActiveIssue("Function mismatch", typeof(PlatformDetection), nameof(PlatformDetection.IsBrowser), nameof(PlatformDetection.IsMonoRuntime))] [ActiveIssue("Doesn't compile with LLVM AOT.", typeof(PlatformDetection), nameof(PlatformDetection.IsMonoAnyAOT))] - // Without a JIT the marshalled calli still reaches the interpreter in ReadyToRun mode (InvalidProgramException on wasm R2R). - [ConditionalFact(typeof(Utilities), nameof(Utilities.IsNotCoreClrInterpreter))] + [Fact] [Xunit.SkipOnCoreClrAttribute("Depends on marshalled calli", RuntimeTestModes.InterpreterActive)] public static void Validate_GeneratedILStubs_NullByRef() { From db3c2ff5104af0bf622b34bb492dfbcadbcd27c9 Mon Sep 17 00:00:00 2001 From: Larry Ewing Date: Mon, 28 Sep 2026 13:11:15 -0500 Subject: [PATCH 14/14] Keep the meaning of IsCoreClrInterpreter and fix GetGeneration's skip instead Revert the InterpreterActive redefinition and the IsInterpreterMode rename. CoreClrConfigurationDetection.IsCoreClrInterpreter keeps meaning 'some code may be interpreted'; its WebAssembly special case becomes a general no-JIT check, which also covers Apple mobile. HndIndex and ManagedPointers go back to their existing InterpreterActive skips. GetGeneration only needs its own code to be compiled, so it gets a local condition (not interpreted, or ReadyToRun) and a permanent WebAssembly skip because stack roots there are reported as pinned (#134803). It keeps running on Apple mobile ReadyToRun. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .../CoreCLRTestLibrary/CoreClrConfigurationDetection.cs | 5 +++-- src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs | 2 +- src/tests/GC/API/GC/GetGeneration.cs | 7 +++++-- 3 files changed, 9 insertions(+), 5 deletions(-) diff --git a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs index e49c9d4dc758ca..81bf98ee8ca577 100644 --- a/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs +++ b/src/tests/Common/CoreCLRTestLibrary/CoreClrConfigurationDetection.cs @@ -5,6 +5,7 @@ using System; using System.Globalization; using System.Reflection; +using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Security; using System.Text; @@ -27,8 +28,8 @@ public static bool IsCoreClrInterpreter { get { - // WASM-TODO: update when codegen is in place - if (PlatformDetection.IsWasm) + // Without a JIT (e.g. WebAssembly, Apple mobile), code that isn't precompiled runs in the interpreter. + if (RuntimeFeature.IsDynamicCodeSupported && !RuntimeFeature.IsDynamicCodeCompiled) return true; if (!string.IsNullOrWhiteSpace(GetEnvironmentVariableValue("Interpreter", ""))) return true; diff --git a/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs b/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs index d2c3edc20e17e6..ba82ef093d113d 100644 --- a/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs +++ b/src/tests/Common/XUnitWrapperGenerator/RuntimeTestModes.cs @@ -44,6 +44,6 @@ public enum RuntimeTestModes HeapVerify = 1 << 9, // DOTNET_HeapVerify (or COMPlus_HeapVerify) is set. - InterpreterActive = 1 << 10, // DOTNET_Interpreter != "" or DOTNET_InterpMode != 0 + InterpreterActive = 1 << 10, // DOTNET_Interpreter != "", DOTNET_InterpMode != 0, or no JIT (some code may be interpreted) } } diff --git a/src/tests/GC/API/GC/GetGeneration.cs b/src/tests/GC/API/GC/GetGeneration.cs index cd2ebd6d5b0357..245d8b36b2b488 100644 --- a/src/tests/GC/API/GC/GetGeneration.cs +++ b/src/tests/GC/API/GC/GetGeneration.cs @@ -119,10 +119,13 @@ public bool RunTests() + // Interpreted frames report their locals as pinned, causing generation demotion that this test does not expect. + public static bool IsTestCodeCompiled => !Utilities.IsCoreClrInterpreter || PlatformDetection.IsReadyToRunCompiled; + [ActiveIssue("needs triage", TestRuntimes.Mono)] [SkipOnCoreClr("This test is not compatible with GC stress.", RuntimeTestModes.AnyGCStress)] - [SkipOnCoreClr("Interpreter reports locals as pinned, causing generation demotion that this test does not expect.", RuntimeTestModes.InterpreterActive)] - [Fact] + [SkipOnPlatform(TestPlatforms.Browser | TestPlatforms.Wasi, "WebAssembly reports stack roots as pinned, causing generation demotion that this test does not expect. See https://github.com/dotnet/runtime/issues/134803.")] + [ConditionalFact(typeof(GetGenerationTest), nameof(IsTestCodeCompiled))] public static int TestEntryPoint() { GetGenerationTest t = new GetGenerationTest();