[corlib] Disable ThreadLocalTests.DisposeOnThreadExit on MonoTouch, it's randomly...
[mono.git] / mcs / class / corlib / Test / System.Threading / ThreadLocalTests.cs
index 5682c6cdae073fbd0e4f84ad8aa1118eac49bb0a..8c063dccdc879ca860f78b88fe19806d97ff35bf 100644 (file)
@@ -1,4 +1,3 @@
-#if NET_4_0
 // 
 // ThreadLazyTests.cs
 //  
@@ -30,6 +29,9 @@ using System.Threading;
 
 using NUnit;
 using NUnit.Framework;
+#if !MOBILE
+using NUnit.Framework.SyntaxHelpers;
+#endif
 
 namespace MonoTests.System.Threading
 {
@@ -69,7 +71,6 @@ namespace MonoTests.System.Threading
                        threadLocal = new ThreadLocal<int> (() => {
                                        Interlocked.Increment (ref callTime);
                                        throw new ApplicationException ("foo");
-                                       return 43;
                                });
 
                        Exception exception = null;
@@ -81,7 +82,7 @@ namespace MonoTests.System.Threading
                        }
 
                        Assert.IsNotNull (exception, "#1");
-                       Assert.IsInstanceOfType (typeof (ApplicationException), exception, "#2");
+                       Assert.That (exception, Is.TypeOf (typeof (ApplicationException)), "#2");
                        Assert.AreEqual (1, callTime, "#3");
 
                        exception = null;
@@ -93,17 +94,20 @@ namespace MonoTests.System.Threading
                        }
 
                        Assert.IsNotNull (exception, "#4");
-                       Assert.IsInstanceOfType (typeof (ApplicationException), exception, "#5");
-                       Assert.AreEqual (1, callTime, "#6");
+                       Assert.That (exception, Is.TypeOf (typeof (ApplicationException)), "#5");
+                       Assert.AreEqual (2, callTime, "#6");
                }
 
-               [Test, ExpectedException (typeof (InvalidOperationException))]
                [Category ("NotDotNet")] // nunit results in stack overflow
                public void MultipleReferenceToValueTest ()
                {
-                       threadLocal = new ThreadLocal<int> (() => threadLocal.Value + 1);
+                       try {
+                               threadLocal = new ThreadLocal<int> (() => threadLocal.Value + 1);
+                               var v = threadLocal.Value;
 
-                       var value = threadLocal.Value;
+                               Assert.Fail ("#1");
+                       } catch (InvalidOperationException e) {
+                       }
                }
 
                [Test]
@@ -161,7 +165,7 @@ namespace MonoTests.System.Threading
                        t.Join ();
                        Assert.AreEqual (false, thread_value_created, "#4");
                        Assert.IsNotNull (exception, "#5");
-                       Assert.IsInstanceOfType (typeof (ApplicationException), exception, "#6");
+                       Assert.That (exception, Is.TypeOf (typeof (ApplicationException)), "#6");
                }
 
                void AssertThreadLocal ()
@@ -172,6 +176,45 @@ namespace MonoTests.System.Threading
                        Assert.AreEqual (42, threadLocal.Value, "#4");
                        Assert.AreEqual (1, nTimes, "#5");
                }
+
+               class SetMreOnFinalize
+               {
+                       ManualResetEventSlim m_mres;
+
+                       public SetMreOnFinalize (ManualResetEventSlim mres)
+                       {
+                               m_mres = mres;
+                       }
+
+                       ~SetMreOnFinalize()
+                       {
+                               m_mres.Set();
+                       }
+               }
+
+               [Test]
+               [Category ("NotWorking")] // Finalizers aren't guaranteed
+#if MONOTOUCH
+               [Category ("NotWorking")] // https://bugzilla.xamarin.com/show_bug.cgi?id=34617
+#endif
+               public void DisposeOnThreadExit ()
+               {
+                       var threadLocal = new ThreadLocal<SetMreOnFinalize>();
+                       var mres = new ManualResetEventSlim(false);
+                       var thread = new Thread (() => { threadLocal.Value = new SetMreOnFinalize (mres); });
+
+                       thread.Start ();
+                       thread.Join ();
+
+                       SpinWait.SpinUntil (() => {
+                               GC.Collect();
+                               GC.WaitForPendingFinalizers();
+                               GC.Collect();
+                               return mres.IsSet;
+                       }, 500);
+
+                       if (!mres.IsSet)
+                               Assert.Fail ("Finalizer didn't run after thread termination");
+               }
        }
 }
-#endif