示例#1
0
        public void TestInterruptOnDispose()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int exitCount = 0;
                var task      = Task.Run(() =>
                {
                    try
                    {
                        lock (syncObj)
                        {
                            testInst.Wait(_ => false, (object)null);
                        }
                    }
                    catch (OperationInterruptedException) { }
                    Interlocked.Increment(ref exitCount);
                });


                TimingAssert.AreEqual(10000, 1, () => testInst.WaiterCount);

                testInst.Dispose();
                TimingAssert.AreEqual(10000, 1, () => Volatile.Read(ref exitCount));

                task.Wait();
            }
        }
示例#2
0
        public void TestAllThreadWakeUpOnSignalAll()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int         exitCount = 0;
                int         state     = 0;
                List <Task> tasks     = new List <Task>();
                for (int i = 0; i < 6; i++)
                {
                    var task = Task.Run(() =>
                    {
                        lock (syncObj)
                        {
                            testInst.Wait(_ => { return(Volatile.Read(ref state) > 0); }, (object)null);
                            Interlocked.Increment(ref exitCount);
                        }
                    });
                    tasks.Add(task);
                }


                TimingAssert.AreEqual(10000, 6, () => testInst.WaiterCount);
                Interlocked.Increment(ref state);

                lock (syncObj)
                {
                    testInst.PulseAll();
                }
                TimingAssert.AreEqual(10000, 0, () => testInst.WaiterCount);
                TimingAssert.AreEqual(10000, 6, () => Volatile.Read(ref exitCount));
            }
        }
示例#3
0
        public void TestLongPredicateEstimatesOnceWithSmallTimeout()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result     = 0;
                int estimCount = 0;
                var task       = Task.Run(() =>
                {
                    lock (syncObj)
                    {
                        if (testInst.Wait(_ => { Interlocked.Increment(ref estimCount); Thread.Sleep(500); return(false); }, (object)null, 200))
                        {
                            Interlocked.Exchange(ref result, 1);
                        }
                        else
                        {
                            Interlocked.Exchange(ref result, 2);
                        }
                    }
                });

                lock (syncObj)
                {
                    testInst.Pulse();
                }
                TimingAssert.AreEqual(10000, 2, () => Volatile.Read(ref result));
                Assert.AreEqual(1, Volatile.Read(ref estimCount));
            }
        }
示例#4
0
        public void TestPredicateCalledOnTimeout()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result = 0;
                int state  = 0;
                int called = 0;
                var task   = Task.Run(() =>
                {
                    lock (syncObj)
                    {
                        if (testInst.Wait((s) => { Interlocked.Increment(ref called); return(Volatile.Read(ref state) > 0); }, new object(), 100))
                        {
                            Interlocked.Exchange(ref result, 1);
                        }
                        else
                        {
                            Interlocked.Exchange(ref result, 2);
                        }
                    }
                });

                TimingAssert.AreEqual(10000, 1, () => testInst.WaiterCount);
                TimingAssert.AreEqual(10000, 2, () => Volatile.Read(ref result));
                TimingAssert.AreEqual(10000, 2, () => Volatile.Read(ref called));
            }
        }
示例#5
0
        public void TestTimeoutWorks()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result = 0;
                var task   = Task.Run(() =>
                {
                    lock (syncObj)
                    {
                        if (testInst.Wait(_ => false, (object)null, 500))
                        {
                            Interlocked.Exchange(ref result, 1);
                        }
                        else
                        {
                            Interlocked.Exchange(ref result, 2);
                        }
                    }
                });

                lock (syncObj)
                {
                    testInst.Pulse();
                }
                TimingAssert.AreEqual(10000, 2, () => Volatile.Read(ref result));
            }
        }
示例#6
0
        public void TestNotificationReceived()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result = 0;
                var task   = Task.Run(() =>
                {
                    lock (syncObj)
                    {
                        if (testInst.Wait(60000))
                        {
                            Interlocked.Exchange(ref result, 1);
                        }
                        else
                        {
                            Interlocked.Exchange(ref result, 2);
                        }
                    }
                });

                TimingAssert.AreEqual(10000, 1, () => testInst.WaiterCount);
                Assert.AreEqual(0, Volatile.Read(ref result));

                lock (syncObj)
                {
                    testInst.Pulse();
                }
                TimingAssert.AreEqual(10000, 1, () => Volatile.Read(ref result));
            }
        }
示例#7
0
        public void TestPulseThrowsIfExternalLockNotAcquired()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                testInst.Pulse();
            }
        }
示例#8
0
        public void TestWaitWithPredicateThrowsIfExternalLockNotAcquired()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                testInst.Wait(_ => true, (object)null, 10);
            }
        }
示例#9
0
        public void TestPredicateCalledInsideLock()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result         = 0;
                int estimCount     = 0;
                int inMonitorCount = 0;
                int stopEstim      = 0;
                var task           = Task.Run(() =>
                {
                    lock (syncObj)
                    {
                        if (testInst.Wait(_ =>
                        {
                            if (Monitor.IsEntered(syncObj))
                            {
                                Interlocked.Increment(ref inMonitorCount);
                            }
                            Interlocked.Increment(ref estimCount);
                            return(Volatile.Read(ref stopEstim) != 0);
                        }, (object)null, 60000))
                        {
                            Interlocked.Exchange(ref result, 1);
                        }
                        else
                        {
                            Interlocked.Exchange(ref result, 2);
                        }
                    }
                });

                TimingAssert.AreEqual(10000, 1, () => testInst.WaiterCount);
                for (int i = 0; i < 20; i++)
                {
                    lock (syncObj)
                    {
                        testInst.Pulse();
                    }
                    Thread.Sleep(10);
                }
                Interlocked.Increment(ref stopEstim);
                lock (syncObj)
                {
                    testInst.Pulse();
                }

                TimingAssert.AreEqual(10000, 1, () => Volatile.Read(ref result));
                Assert.IsTrue(Volatile.Read(ref estimCount) > 1);
                Assert.AreEqual(Volatile.Read(ref inMonitorCount), Volatile.Read(ref estimCount));
            }
        }
示例#10
0
        public void TestStatePassedCorrectly()
        {
            object syncObj = new object();

            lock (syncObj)
            {
                using (var testInst = new ConditionVariableOld(syncObj))
                {
                    object state  = new object();
                    bool   result = testInst.Wait((s) => { Assert.AreEqual(state, s); return(true); }, state, 100000);
                    Assert.IsTrue(result);
                }
            }
        }
示例#11
0
        public void TestWaitWithPredicateThrowsIfExternalLockTakenRecursively()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                lock (syncObj)
                {
                    lock (syncObj)
                    {
                        testInst.Wait(_ => false, (object)null, 10);
                    }
                }
            }
        }
示例#12
0
        public void TestWaitThrowsIfExternalLockTakenRecursively()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                lock (syncObj)
                {
                    lock (syncObj)
                    {
                        testInst.Wait(10);
                    }
                }
            }
        }
示例#13
0
        public void TestAlwaysPositivePredicate()
        {
            object syncObj = new object();

            lock (syncObj)
            {
                using (var testInst = new ConditionVariableOld(syncObj))
                {
                    int  called = 0;
                    bool result = testInst.Wait((s) => { called++; return(true); }, new object(), 100000);
                    Assert.IsTrue(result);
                    Assert.AreEqual(1, called);
                }
            }
        }
示例#14
0
        public void TestCancellationWorks()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result = 0;
                CancellationTokenSource tokenSrc = new CancellationTokenSource();
                var task = Task.Run(() =>
                {
                    try
                    {
                        lock (syncObj)
                        {
                            if (testInst.Wait(_ => false, (object)null, 60000, tokenSrc.Token))
                            {
                                Interlocked.Exchange(ref result, 1);
                            }
                            else
                            {
                                Interlocked.Exchange(ref result, 2);
                            }
                        }
                    }
                    catch (OperationCanceledException)
                    {
                        Interlocked.Exchange(ref result, 3);
                    }
                });

                lock (syncObj)
                {
                    testInst.Pulse();
                }

                Thread.Sleep(100);
                Assert.AreEqual(0, Volatile.Read(ref result));

                tokenSrc.Cancel();
                TimingAssert.AreEqual(10000, 3, () => Volatile.Read(ref result));
            }
        }
示例#15
0
        public void TestNotificationWithPredicate()
        {
            object syncObj = new object();

            using (var testInst = new ConditionVariableOld(syncObj))
            {
                int result = 0;
                int state  = 0;
                var task   = Task.Run(() =>
                {
                    lock (syncObj)
                    {
                        if (testInst.Wait((s) => Volatile.Read(ref state) > 0, new object(), 60000))
                        {
                            Interlocked.Exchange(ref result, 1);
                        }
                        else
                        {
                            Interlocked.Exchange(ref result, 2);
                        }
                    }
                });

                Thread.Sleep(100);
                Assert.AreEqual(0, Volatile.Read(ref result));

                lock (syncObj)
                {
                    testInst.Pulse();
                }
                Thread.Sleep(100);
                Assert.AreEqual(0, Volatile.Read(ref result));

                Interlocked.Increment(ref state);
                lock (syncObj)
                {
                    testInst.Pulse();
                }
                TimingAssert.AreEqual(10000, 1, () => Volatile.Read(ref result));
            }
        }
示例#16
0
        public void TestExceptionPassedFromPredicate()
        {
            object syncObj = new object();

            lock (syncObj)
            {
                using (var testInst = new ConditionVariableOld(syncObj))
                {
                    try
                    {
                        object state  = new object();
                        bool   result = testInst.Wait((s) => { throw new ApplicationException("test"); }, state, 100000);
                        Assert.IsTrue(result);
                    }
                    catch (Exception)
                    {
                        Assert.AreEqual(0, testInst.WaiterCount);
                        throw;
                    }
                }
            }
        }
示例#17
0
 public ThreadSafeQueue()
 {
     VarFull  = new ConditionVariableOld(SharedSyncObj);
     VarEmpty = new ConditionVariableOld(SharedSyncObj);
 }