예제 #1
0
        static string StartClients(string sctx, SynchronizedLogger logger, out DomainCommunicationProvider clientsNetworkProvider)
        {
            var configuration = Configuration.Create().WithMonitorsInProductionEnabled().WithVerbosityEnabled(2);
            var runtime       = PSharpRuntime.Create(configuration);
            var runtimeHost   = HostInfo.NewRuntimeHost(runtime);

            clientsNetworkProvider = new DomainCommunicationProvider(runtimeHost, "clients");
            runtimeHost.SetNetworkProvider(clientsNetworkProvider);
            runtimeHost.SetLogger(logger);

            var messages = new MessageCollection();

            messages.CollectionChanged += (sender, e) => logger.WriteLine(e.NewItems[0].ToString());
            var ctx = sctx.FromJson <DistributedStorageContext>();

            var synchronizable = Synchronizable.Empty();

            foreach (var storageNode in ctx.StorageNodes)
            {
                var waitIfHandledReplReq = logger.MachineActionHandledWait((machineId, _, actionName) => Equals(machineId, storageNode.Id) && actionName == "HandleReplReq");
                synchronizable = synchronizable.Then(waitIfHandledReplReq.Delay(10));
            }
            logger.ApplySynchronization(synchronizable);

            NewClients(runtimeHost, ctx, messages);
            logger.WaitForWriting(6000);
            return(ctx.ToJson());
        }
예제 #2
0
        public void Lock()
        {
            object instance = new object();

            var synchronizable = new Synchronizable <object>(instance);

            Assert.NotNull(synchronizable.Lock);
        }
예제 #3
0
        public void Lock()
        {
            object instance = new object();

            var synchronizable = new Synchronizable<object>(instance);

            Assert.NotNull(synchronizable.Lock);
        }
예제 #4
0
        public void Can_restrain_apps_to_wait_until_beginning_start_of_all_apps()
        {
            // Arrange
            var starts        = new ConcurrentBag <int>();
            var starts_Add    = new MarshalByRefAction <int>(i => starts.Add(i));
            var processes     = new ConcurrentBag <int>();
            var processes_Add = new MarshalByRefAction <int>(i => processes.Add(i));

            void Synchronize(Action <ISynchronizer> action)
            {
                var curMeth = MethodBase.GetCurrentMethod();
                var setter1 = Synchronizable.SystemWideEventSet(Key.Get(curMeth, "Foo"), obj => (int)obj == 1);
                var setter2 = Synchronizable.SystemWideEventSet(Key.Get(curMeth, "Bar"), obj => (int)obj == 2);

                using (var sync = setter1.And(setter2).GetSynchronizer())
                    action(sync);
            }

            // Act
            Synchronize(sync =>
            {
                var mre1  = new ST::ManualResetEvent(false);
                var task1 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((starts_Add_, processes_Add_, mre1_) =>
                                                                                 Synchronize(sync_ =>
                {
                    starts_Add_.Invoke(1);
                    sync_.Begin(1).Wait();
                    mre1_.WaitOne(10000);
                    processes_Add_.Invoke(1);
                    sync_.End(1).Wait();
                }), starts_Add, processes_Add, mre1));

                var mre2  = new ST::ManualResetEvent(false);
                var task2 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((starts_Add_, processes_Add_, mre2_) =>
                                                                                 Synchronize(sync_ =>
                {
                    starts_Add_.Invoke(2);
                    sync_.Begin(2).Wait();
                    mre2_.WaitOne(10000);
                    processes_Add_.Invoke(2);
                    sync_.End(2).Wait();
                }), starts_Add, processes_Add, mre2));

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.AreEquivalent(new[] { 1, 2 }, starts);
                CollectionAssert.IsEmpty(processes);
                mre1.Set();
                mre2.Set();
                Task.WaitAll(task1, task2);
            });
        }
예제 #5
0
        public void Can_delay_apps_by_the_passed_time_span()
        {
            // Arrange
            var task1BeginTime        = default(DateTimeOffset);
            var task1BeginTime_Assign = new MarshalByRefAction <DateTimeOffset>(dt => task1BeginTime = dt);
            var task2BegunTime        = default(DateTimeOffset);
            var task2BegunTime_Assign = new MarshalByRefAction <DateTimeOffset>(dt => task2BegunTime = dt);

            void Synchronize(Action <ISynchronizer> action)
            {
                var curMeth = MethodBase.GetCurrentMethod();
                var setter1 = Synchronizable.SystemWideEventSet(Key.Get(curMeth, "Foo"), obj => (int)obj == 1);
                var setter2 = Synchronizable.SystemWideEventSet(Key.Get(curMeth, "Bar"), obj => (int)obj == 2);

                using (var sync = setter1.And(setter2.Delay(TimeSpan.FromMilliseconds(1000))).GetSynchronizer())
                    action(sync);
            }

            // Act
            Synchronize(sync =>
            {
                var mre1  = new ST::ManualResetEvent(false);
                var task1 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((task1BeginTime_Assign_, mre1_) =>
                                                                                 Synchronize(sync_ =>
                {
                    task1BeginTime_Assign_.Invoke(DateTimeOffset.Now);
                    sync_.Begin(1).Wait();
                    mre1_.Set();
                    sync_.End(1).Wait();
                }), task1BeginTime_Assign, mre1));

                var mre2  = new ST::ManualResetEvent(false);
                var task2 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((task2BegunTime_Assign_, mre2_) =>
                                                                                 Synchronize(sync_ =>
                {
                    sync_.Begin(2).Wait();
                    task2BegunTime_Assign_.Invoke(DateTimeOffset.Now);
                    mre2_.Set();
                    sync_.End(2).Wait();
                }), task2BegunTime_Assign, mre2));

                sync.NotifyAll(false).Wait();


                // Assert
                ST::WaitHandle.WaitAll(new[] { mre1, mre2 });
                Assert.GreaterOrEqual(task2BegunTime - task1BeginTime, TimeSpan.FromMilliseconds(1000));
                Task.WaitAll(task1, task2);
            });
        }
예제 #6
0
        public void Can_restrain_tasks_to_wait_until_beginning_start_of_all_tasks()
        {
            // Arrange
            var starts    = new ConcurrentBag <int>();
            var processes = new ConcurrentBag <int>();
            var setter1   = Synchronizable.EventSet(obj => (int)obj == 1);
            var setter2   = Synchronizable.EventSet(obj => (int)obj == 2);


            var sync = default(ISynchronizer);

            try
            {
                // Act
                sync = setter1.And(setter2).GetSynchronizer();

                var mre1  = new ST::ManualResetEventSlim(false);
                var task1 = Task.Run(() =>
                {
                    starts.Add(1);
                    sync.Begin(1).Wait();
                    mre1.Wait(10000);
                    processes.Add(1);
                    sync.End(1).Wait();
                });

                var mre2  = new ST::ManualResetEventSlim(false);
                var task2 = Task.Run(() =>
                {
                    starts.Add(2);
                    sync.Begin(2).Wait();
                    mre2.Wait(10000);
                    processes.Add(2);
                    sync.End(2).Wait();
                });

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.AreEquivalent(new[] { 1, 2 }, starts);
                CollectionAssert.IsEmpty(processes);
                mre1.Set();
                mre2.Set();
                Task.WaitAll(task1, task2);
            }
            finally
            {
                sync?.Dispose();
            }
        }
예제 #7
0
        public void Can_restrain_tasks_to_wait_until_ending_process_in_order_of_all_tasks()
        {
            // Arrange
            var processes = new ConcurrentBag <int>();
            var waiter1   = Synchronizable.EventWait(obj => (int)obj == 1);
            var waiter2   = Synchronizable.EventWait(obj => (int)obj == 2);
            var waiter3   = Synchronizable.EventWait(obj => (int)obj == 3);


            var sync = default(ISynchronizer);

            try
            {
                // Act
                sync = waiter1.Then(waiter2).Then(waiter3).GetSynchronizer();
                var task1 = Task.Run(() =>
                {
                    sync.Begin(1).Wait();
                    processes.Add(1);
                    sync.End(1).Wait();
                });

                var task2 = Task.Run(() =>
                {
                    sync.Begin(2).Wait();
                    processes.Add(2);
                    sync.End(2).Wait();
                });

                var task3 = Task.Run(() =>
                {
                    sync.Begin(3).Wait();
                    processes.Add(3);
                    sync.End(3).Wait();
                });

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.AreEqual(new[] { 1, 2, 3 }, processes);
                Task.WaitAll(task1, task2, task3);
            }
            finally
            {
                sync?.Dispose();
            }
        }
예제 #8
0
        public void Can_delay_tasks_by_the_passed_time_span()
        {
            // Arrange
            var task1BeginTime = default(DateTimeOffset);
            var task2BegunTime = default(DateTimeOffset);
            var setter1        = Synchronizable.EventSet(obj => (int)obj == 1);
            var setter2        = Synchronizable.EventSet(obj => (int)obj == 2);


            var sync = default(ISynchronizer);

            try
            {
                // Act
                sync = setter1.And(setter2.Delay(TimeSpan.FromMilliseconds(1000))).GetSynchronizer();

                var mre1  = new ST::ManualResetEventSlim(false);
                var task1 = Task.Run(() =>
                {
                    task1BeginTime = DateTimeOffset.Now;
                    sync.Begin(1).Wait();
                    mre1.Set();
                    sync.End(1).Wait();
                });

                var mre2  = new ST::ManualResetEventSlim(false);
                var task2 = Task.Run(() =>
                {
                    sync.Begin(2).Wait();
                    task2BegunTime = DateTimeOffset.Now;
                    mre2.Set();
                    sync.End(2).Wait();
                });

                sync.NotifyAll(false).Wait();


                // Assert
                mre1.Wait();
                mre2.Wait();
                Assert.GreaterOrEqual(task2BegunTime - task1BeginTime, TimeSpan.FromMilliseconds(1000));
                Task.WaitAll(task1, task2);
            }
            finally
            {
                sync?.Dispose();
            }
        }
예제 #9
0
        public void Can_pause_apps_by_the_passed_time_span()
        {
            // Arrange
            var task1EndTime          = default(DateTimeOffset);
            var task1EndTime_Assign   = new MarshalByRefAction <DateTimeOffset>(dt => task1EndTime = dt);
            var task2BegunTime        = default(DateTimeOffset);
            var task2BegunTime_Assign = new MarshalByRefAction <DateTimeOffset>(dt => task2BegunTime = dt);

            void Synchronize(Action <ISynchronizer> action)
            {
                var curMeth = MethodBase.GetCurrentMethod();
                var waiter1 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Foo"), obj => (int)obj == 1);
                var waiter2 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Bar"), obj => (int)obj == 2);

                using (var sync = waiter1.Then(waiter2.Pause(TimeSpan.FromMilliseconds(1000))).GetSynchronizer())
                    action(sync);
            }

            // Act
            Synchronize(sync =>
            {
                var task1 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((task1EndTime_Assign_) =>
                                                                                 Synchronize(sync_ =>
                {
                    sync_.Begin(1).Wait();
                    task1EndTime_Assign_.Invoke(DateTimeOffset.Now);
                    sync_.End(1).Wait();
                }), task1EndTime_Assign));

                var task2 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((task2BegunTime_Assign_) =>
                                                                                 Synchronize(sync_ =>
                {
                    sync_.Begin(2).Wait();
                    task2BegunTime_Assign_.Invoke(DateTimeOffset.Now);
                    sync_.End(2).Wait();
                }), task2BegunTime_Assign));

                sync.NotifyAll(false).Wait();


                // Assert
                Assert.GreaterOrEqual(task2BegunTime - task1EndTime, TimeSpan.FromMilliseconds(1000));
                Task.WaitAll(task1, task2);
            });
        }
예제 #10
0
        public void Can_pause_tasks_by_the_passed_time_span()
        {
            // Arrange
            var task1EndTime   = default(DateTimeOffset);
            var task2BegunTime = default(DateTimeOffset);
            var waiter1        = Synchronizable.EventWait(obj => (int)obj == 1);
            var waiter2        = Synchronizable.EventWait(obj => (int)obj == 2);


            var sync = default(ISynchronizer);

            try
            {
                // Act
                sync = waiter1.Then(waiter2.Pause(TimeSpan.FromMilliseconds(1000))).GetSynchronizer();
                var task1 = Task.Run(() =>
                {
                    sync.Begin(1).Wait();
                    task1EndTime = DateTimeOffset.Now;
                    sync.End(1).Wait();
                });

                var task2 = Task.Run(() =>
                {
                    sync.Begin(2).Wait();
                    task2BegunTime = DateTimeOffset.Now;
                    sync.End(2).Wait();
                });

                sync.NotifyAll(false).Wait();


                // Assert
                Assert.GreaterOrEqual(task2BegunTime - task1EndTime, TimeSpan.FromMilliseconds(1000));
                Task.WaitAll(task1, task2);
            }
            finally
            {
                sync?.Dispose();
            }
        }
예제 #11
0
 public SynchronizedDictionary(IDictionary <TKey, TValue> target)
     : base(target)
 {
     this.target = new Synchronizable <IDictionary <TKey, TValue> >(target);
 }
예제 #12
0
        public void Can_restrain_apps_to_wait_until_ending_process_in_order_of_all_apps()
        {
            // Arrange
            var processes     = new ConcurrentBag <int>();
            var processes_Add = new MarshalByRefAction <int>(i => processes.Add(i));

            void Synchronize(Action <ISynchronizer> action)
            {
                var begun = new HandledCallback((id, obj, opts) =>
                {
                    var threadId = ST::Thread.CurrentThread.ManagedThreadId;
                    Debug.WriteLine($"Begun Id: { id }, Obj: { obj }, Thread: { threadId }");
                });
                var ended = new HandledCallback((id, obj, opts) =>
                {
                    var threadId = ST::Thread.CurrentThread.ManagedThreadId;
                    Debug.WriteLine($"Ended Id: { id }, Obj: { obj }, Thread: { threadId }");
                });
                var curMeth = MethodBase.GetCurrentMethod();
                var waiter1 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Foo"), obj => (int)obj == 1, begun, ended);
                var waiter2 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Bar"), obj => (int)obj == 2, begun, ended);
                var waiter3 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Baz"), obj => (int)obj == 3, begun, ended);

                using (var sync = waiter1.Then(waiter2).Then(waiter3).GetSynchronizer())
                    action(sync);
            }

            // Act
            Synchronize(sync =>
            {
                var task1 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain(processes_Add_ =>
                                                                                 Synchronize(sync_ =>
                {
                    sync_.Begin(1).Wait();
                    processes_Add_.Invoke(1);
                    sync_.End(1).Wait();
                }), processes_Add));

                var task2 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain(processes_Add_ =>
                                                                                 Synchronize(sync_ =>
                {
                    sync_.Begin(2).Wait();
                    processes_Add_.Invoke(2);
                    sync_.End(2).Wait();
                }), processes_Add));

                var task3 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain(processes_Add_ =>
                                                                                 Synchronize(sync_ =>
                {
                    sync_.Begin(3).Wait();
                    processes_Add_.Invoke(3);
                    sync_.End(3).Wait();
                }), processes_Add));

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.AreEqual(new[] { 1, 2, 3 }, processes);
                Task.WaitAll(task1, task2, task3);
            });
        }
예제 #13
0
        public void Should_ignore_empty_when_restraining_apps()
        {
            // Arrange
            var starts        = new ConcurrentBag <int>();
            var starts_Add    = new MarshalByRefAction <int>(i => starts.Add(i));
            var processes     = new ConcurrentBag <int>();
            var processes_Add = new MarshalByRefAction <int>(i => processes.Add(i));

            void Synchronize(Action <ISynchronizer> action)
            {
                var curMeth = MethodBase.GetCurrentMethod();
                var empty   = Synchronizable.Empty();
                var setter1 = Synchronizable.SystemWideEventSet(Key.Get(curMeth, "Foo"), obj => (int)obj == 1);
                var setter2 = Synchronizable.SystemWideEventSet(Key.Get(curMeth, "Bar"), obj => (int)obj == 2);
                var waiter3 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Baz"), obj => (int)obj == 3);
                var waiter4 = Synchronizable.SystemWideEventWait(Key.Get(curMeth, "Qux"), obj => (int)obj == 4);

                using (var sync = setter1.Or(setter2).Or(empty).And(empty.Then(waiter3).Then(empty).Then(waiter4).Then(empty)).And(empty).GetSynchronizer())
                    action(sync);
            }

            // Act
            Synchronize(sync =>
            {
                var mre1  = new ST::ManualResetEvent(false);
                var task1 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((starts_Add_, processes_Add_, mre1_) =>
                                                                                 Synchronize(sync_ =>
                {
                    mre1_.WaitOne(10000);
                    starts_Add_.Invoke(1);
                    sync_.Begin(1).Wait();
                    processes_Add_.Invoke(1);
                    sync_.End(1).Wait();
                }), starts_Add, processes_Add, mre1));

                var task2 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((starts_Add_, processes_Add_) =>
                                                                                 Synchronize(sync_ =>
                {
                    starts_Add_.Invoke(2);
                    sync_.Begin(2).Wait();
                    processes_Add_.Invoke(2);
                    sync_.End(2).Wait();
                }), starts_Add, processes_Add));

                var task3 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((starts_Add_, processes_Add_) =>
                                                                                 Synchronize(sync_ =>
                {
                    starts_Add_.Invoke(3);
                    sync_.Begin(3).Wait();
                    processes_Add_.Invoke(3);
                    sync_.End(3).Wait();
                }), starts_Add, processes_Add));

                var task4 = Task.Run(() =>
                                     AppDomain.CurrentDomain.RunAtIsolatedDomain((starts_Add_, processes_Add_) =>
                                                                                 Synchronize(sync_ =>
                {
                    starts_Add_.Invoke(4);
                    sync_.Begin(4).Wait();
                    processes_Add_.Invoke(4);
                    sync_.End(4).Wait();
                }), starts_Add, processes_Add));

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.DoesNotContain(starts, 1);
                CollectionAssert.AreEqual(new[] { 3, 4 }, processes.Intersect(new[] { 3, 4 }));
                mre1.Set();
                Task.WaitAll(task1, task2, task3, task4);
            });
        }
예제 #14
0
        public void Should_ignore_empty_when_restraining_tasks()
        {
            // Arrange
            var starts    = new ConcurrentBag <int>();
            var processes = new ConcurrentBag <int>();
            var empty     = Synchronizable.Empty();
            var setter1   = Synchronizable.EventSet(obj => (int)obj == 1);
            var setter2   = Synchronizable.EventSet(obj => (int)obj == 2);
            var waiter3   = Synchronizable.EventWait(obj => (int)obj == 3);
            var waiter4   = Synchronizable.EventWait(obj => (int)obj == 4);


            var sync = default(ISynchronizer);

            try
            {
                // Act
                sync = setter1.Or(setter2).Or(empty).And(empty.Then(waiter3).Then(empty).Then(waiter4).Then(empty)).And(empty).GetSynchronizer();

                var mre1  = new ST::ManualResetEventSlim(false);
                var task1 = Task.Run(() =>
                {
                    mre1.Wait(10000);
                    starts.Add(1);
                    sync.Begin(1).Wait();
                    processes.Add(1);
                    sync.End(1).Wait();
                });

                var task2 = Task.Run(() =>
                {
                    starts.Add(2);
                    sync.Begin(2).Wait();
                    processes.Add(2);
                    sync.End(2).Wait();
                });

                var task3 = Task.Run(() =>
                {
                    starts.Add(3);
                    sync.Begin(3).Wait();
                    processes.Add(3);
                    sync.End(3).Wait();
                });

                var task4 = Task.Run(() =>
                {
                    starts.Add(4);
                    sync.Begin(4).Wait();
                    processes.Add(4);
                    sync.End(4).Wait();
                });

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.DoesNotContain(starts, 1);
                CollectionAssert.AreEqual(new[] { 3, 4 }, processes.Intersect(new[] { 3, 4 }));
                mre1.Set();
                Task.WaitAll(task1, task2, task3, task4);
            }
            finally
            {
                sync?.Dispose();
            }
        }
예제 #15
0
        public void Can_restrain_tasks_to_wait_until_beginning_start_of_task1_or_task2_and_until_ending_process_of_task3_and_task4_in_order()
        {
            // Arrange
            var starts    = new ConcurrentBag <int>();
            var processes = new ConcurrentBag <int>();
            var setter1   = Synchronizable.EventSet(obj => (int)obj == 1);
            var setter2   = Synchronizable.EventSet(obj => (int)obj == 2);
            var waiter3   = Synchronizable.EventWait(obj => (int)obj == 3);
            var waiter4   = Synchronizable.EventWait(obj => (int)obj == 4);


            var sync = default(ISynchronizer);

            try
            {
                // Act
                sync = setter1.Or(setter2).And(waiter3.Then(waiter4)).GetSynchronizer();

                var mre1  = new ST::ManualResetEventSlim(false);
                var task1 = Task.Run(() =>
                {
                    mre1.Wait(10000);
                    starts.Add(1);
                    sync.Begin(1).Wait();
                    processes.Add(1);
                    sync.End(1).Wait();
                });

                var task2 = Task.Run(() =>
                {
                    starts.Add(2);
                    sync.Begin(2).Wait();
                    processes.Add(2);
                    sync.End(2).Wait();
                });

                var task3 = Task.Run(() =>
                {
                    starts.Add(3);
                    sync.Begin(3).Wait();
                    processes.Add(3);
                    sync.End(3).Wait();
                });

                var task4 = Task.Run(() =>
                {
                    starts.Add(4);
                    sync.Begin(4).Wait();
                    processes.Add(4);
                    sync.End(4).Wait();
                });

                sync.NotifyAll(false).Wait();


                // Assert
                CollectionAssert.DoesNotContain(starts, 1);
                CollectionAssert.AreEqual(new[] { 3, 4 }, processes.Intersect(new[] { 3, 4 }));
                mre1.Set();
                Task.WaitAll(task1, task2, task3, task4);
            }
            finally
            {
                sync?.Dispose();
            }
        }