From af315f44c40dfb8767d64920bae2cdb8da7cc3f8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Aleksey=20Kliger=20=28=CE=BBgeek=29?= Date: Fri, 9 Oct 2020 10:34:28 -0400 Subject: [2020-02][corlib] ThreadAbortException protection for ArraySortHelper (#20468) * [test] Abort a thread doing a long-running Array.Sort The custom comparer is wrapped in a try/finally. Verify that it doesn't turn thread abort exceptions into some other exception. Regression test for https://github.com/mono/mono/issues/15418 * Bump corert To pick up fix for mono/mono#15418 * disable new test on platforms without Thread.Abort --- external/corert | 2 +- mcs/class/corlib/Test/System/ArrayTest.cs | 62 +++++++++++++++++++++++++++++++ 2 files changed, 63 insertions(+), 1 deletion(-) diff --git a/external/corert b/external/corert index ffcd7990d87..11136ad5576 160000 --- a/external/corert +++ b/external/corert @@ -1 +1 @@ -Subproject commit ffcd7990d87e560c63413293c8efe1d1fc4e3584 +Subproject commit 11136ad55767485063226be08cfbd32ed574ca43 diff --git a/mcs/class/corlib/Test/System/ArrayTest.cs b/mcs/class/corlib/Test/System/ArrayTest.cs index 819cb871749..3c168093cc1 100644 --- a/mcs/class/corlib/Test/System/ArrayTest.cs +++ b/mcs/class/corlib/Test/System/ArrayTest.cs @@ -12,6 +12,7 @@ using System; using System.Collections; using System.Globalization; using System.Reflection; +using System.Threading; using System.Collections.Generic; namespace MonoTests.System @@ -3745,5 +3746,66 @@ public class ArrayTest Assert.Throws (() => { var _ = x.GetValue (0); }, "#2"); Assert.Throws (() => { x.SetValue (0, 0); }, "#3"); } + + +#if MONO_FEATURE_THREAD_ABORT + public struct J + { + public int i; + + public J(int i_) { i = i_; } + } + + struct JComp : IComparer + { + public int Compare(J x, J y) + { + int val = 0; + Thread.Sleep (Timeout.Infinite); + return val; + } + } + + class ArraySortAbortData { + internal ManualResetEventSlim mre; + internal bool threw; + + internal ArraySortAbortData () { + mre = new ManualResetEventSlim (); + threw = false; + } + } + + [Test] + public void ArraySortAbort () + { + var d = new ArraySortAbortData(); + var t = new Thread(RunArraySort); + t.Start(d); + d.mre.Wait(); + Thread.Sleep(400); + t.Abort(); + t.Join(); + Assert.IsFalse (d.threw); + } + + public static void RunArraySort(object data) + { + var d = data as ArraySortAbortData; + int n = 10; + var a = new J[n]; + for (int i = 0; i < n; ++i) + { + a[i] = new J(n - i); + } + d.mre.Set(); + try { + Array.Sort(a, 0, n, new JComp()); + } catch (InvalidOperationException) { + // t.Abort in ArraySortAbort should _not_ end up here + d.threw = true; + } + } +#endif } } -- cgit v1.2.3