public async Task LockManager_BasicTest() { LockManager <int, int> lockManager = new LockManager <int, int>(); await lockManager.AcquireLock(1, 1, LockMode.Update); await lockManager.AcquireLock(1, 2, LockMode.Update); await lockManager.AcquireLock(1, 3, LockMode.Update); Task[] tasks = new Task[] { lockManager.AcquireLock(2, 1, LockMode.Update), lockManager.AcquireLock(3, 2, LockMode.Update), lockManager.AcquireLock(4, 3, LockMode.Update), }; lockManager.ReleaseLocks(1); Task.WaitAll(tasks); lockManager.ReleaseLocks(2); lockManager.ReleaseLocks(3); await lockManager.AcquireLock(5, 1, LockMode.Default); await lockManager.AcquireLock(5, 2, LockMode.Default); await Assert.ThrowsExceptionAsync <TimeoutException>( async() => { await lockManager.AcquireLock(5, 3, LockMode.Default, timeout: TimeSpan.FromMilliseconds(10)); } ); }
public void No_deadlock_and_no_race_condition_on_resources_using_sessions() { var mgr = new LockManager(); var watch = new Stopwatch(); watch.Start(); int iterations = 10_000; Parallel.For(0, iterations, i => { Parallel.Invoke( () => { var session = Guid.NewGuid(); mgr.AcquireLock(session, false, "a", "b", "c"); ReadAbc(); mgr.CloseSession(session); }, () => { var session = Guid.NewGuid(); mgr.AcquireLock(session, false, "a"); ReadA(); mgr.CloseSession(session); }, () => { var session = Guid.NewGuid(); mgr.AcquireLock(session, true, "a", "b", "c"); WriteAbc(); mgr.CloseSession(session); }, () => { var session = Guid.NewGuid(); mgr.AcquireLock(session, true, "a"); WriteA(); mgr.CloseSession(session); }); }); watch.Stop(); Console.WriteLine($"{iterations} iterations took {watch.ElapsedMilliseconds} ms"); Console.WriteLine($"retries = {mgr.Retries}"); Console.WriteLine($"a = {_resourceA.Count} b = {_resourceB.Count} c = {_resourceC.Count}"); int locks = mgr.GetCurrentlyHoldLocks(); Assert.AreEqual(0, locks); }
public ChangeRequestTask GetChangeRequestTaskByIdForEdit(int id, string currentUser) { using (var transaction = _appDataContext.Database.BeginTransaction(System.Data.IsolationLevel.Serializable)) { try { LockManager lockManager = new LockManager(_appDataContext); lockManager.AcquireLock(id, "ChangeRequestTask", currentUser); ChangeRequestTask crt = _appDataContext.ChangeRequestTasks.Where(c => c.ID == id).SingleOrDefault(); if (crt != null) { transaction.Commit(); } else { throw new ConcurrencyException( "Entity not found. Entity man have been deleted by another user."); } return(crt); } catch (ConcurrencyException ex) { transaction.Rollback(); string newMessage = ex.Message.Replace("Entity", "Change Request Task " + id.ToString("D5")); throw new ConcurrencyException(newMessage); } catch (Exception) { transaction.Rollback(); throw; } } }
public void Consistent_read_sessions() { ILockManager lockManager = new LockManager(null); var session = Guid.NewGuid(); lockManager.AcquireLock(session, false, "x", "y", "z"); bool success = lockManager.CheckLock(session, false, "x"); Assert.IsTrue(success); // try with a new session (should not work) success = lockManager.CheckLock(Guid.NewGuid(), false, "x"); Assert.IsFalse(success); // read-only lock so it should not work success = lockManager.CheckLock(session, true, "x"); Assert.IsFalse(success); // different resource so it should not work success = lockManager.CheckLock(session, true, "nope"); Assert.IsFalse(success); // trying to close an inactive session throws an exception Assert.Throws <NotSupportedException>(() => lockManager.CloseSession(Guid.NewGuid())); }
public void Managing_pending_locks() { var log = A.Fake <IEventsLog>(); ILockManager lockManager = new LockManager(log); var sessionId = Guid.NewGuid(); lockManager.AcquireLock(sessionId, false, "x", "y", "z"); Assert.AreEqual(3, lockManager.GetCurrentlyHoldLocks()); Assert.IsTrue(lockManager.CheckLock(sessionId, false, "x", "y", "z")); // false because it is a read-only lock Assert.False(lockManager.CheckLock(sessionId, true, "x", "y", "z")); lockManager.CloseSession(sessionId); Assert.AreEqual(0, lockManager.GetCurrentlyHoldLocks()); // session no longer active Assert.IsFalse(lockManager.CheckLock(sessionId, false, "x", "y", "z")); lockManager.AcquireLock(sessionId, true, "tony", "tara"); Assert.AreEqual(2, lockManager.GetCurrentlyHoldLocks()); Thread.Sleep(500); Assert.AreEqual(2, lockManager.GetCurrentlyHoldLocks(100)); var locks = lockManager.ForceRemoveAllLocks(100); A.CallTo(() => log.LogEvent(EventType.LockRemoved, null, 0)).MustHaveHappened(); Assert.AreEqual(2, locks); Assert.AreEqual(0, lockManager.GetCurrentlyHoldLocks()); }
public void LockTest_PathPipLockNotMutallyExclusive() { Setup(); var lockManager = new LockManager(); var process = CreateProcess(new[] { CreateSourceFile() }, new[] { CreateOutputFileArtifact() }); // Test pip locks and path locks are NOT mutually exclusive TestMutuallyExclusive( () => lockManager.AcquirePathAccessLock(process), () => lockManager.AcquireLock(new PipId(30)), assertExclusive: false); }
public void LockTest_CommonPipLockMutallyExclusive() { Setup(); var lockManager = new LockManager(); // Single pip contention TestMutuallyExclusive(() => lockManager.AcquireLock(new PipId(20)), () => lockManager.AcquireLock(new PipId(20))); // Single pip contention with one pair pip lock TestMutuallyExclusive(() => lockManager.AcquireLocks(new PipId(20), new PipId(21)), () => lockManager.AcquireLock(new PipId(20))); // Pair pip contention reverse order TestMutuallyExclusive(() => lockManager.AcquireLocks(new PipId(20), new PipId(21)), () => lockManager.AcquireLocks(new PipId(21), new PipId(20))); }
public MsrLockResponse Lock(MsrLockRequest request) { ThrowIf.Null(request, "request"); NetTracer.Information(string.Format("The Msr lock request received: {0}", request.DeviceName)); IRamblerStripeReader device; MsrLockResponse result = new MsrLockResponse(); result.Token = LockManager.AcquireLock <IRamblerStripeReader>(Microsoft.Dynamics.Commerce.HardwareStation.HostHelpers.HostContext.GetCurrentUser(this.Request), request, out device); NetTracer.Information(string.Format("The Msr device is locked: {0}", result.Token)); return(result); }
public void LockTest_GlobalLock_PipLockMutallyExclusive() { Setup(); var lockManager = new LockManager(); // Global lock and pip lock are mutually exclusive TestMutuallyExclusive(() => lockManager.AcquireGlobalExclusiveLock(), () => lockManager.AcquireLock(new PipId(20))); }
public void Mixed_use_of_sessions_and_simple_accesses_simulating_both_transactional_and_non_transactional_clients() { var mgr = new LockManager(); var watch = new Stopwatch(); watch.Start(); int iterations = 100; Parallel.For(0, iterations, i => { Parallel.Invoke( () => { for (int i = 0; i < iterations; i++) { var session = Guid.NewGuid(); mgr.AcquireLock(session, false, "a", "b", "c"); ReadAbc(); mgr.CloseSession(session); } }, () => { for (int i = 0; i < iterations; i++) { var session = Guid.NewGuid(); mgr.AcquireLock(session, false, "a"); ReadA(); mgr.CloseSession(session); } }, () => { for (int i = 0; i < iterations; i++) { var session = Guid.NewGuid(); mgr.AcquireLock(session, true, "a", "b", "c"); WriteAbc(); mgr.CloseSession(session); } }, () => { for (int i = 0; i < iterations; i++) { var session = Guid.NewGuid(); mgr.AcquireLock(session, true, "a"); WriteA(); mgr.CloseSession(session); } }, () => { for (int i = 0; i < 100; i++) { mgr.DoWithReadLock(ReadAbc, "a", "b", "c"); } }, () => { for (int i = 0; i < 100; i++) { mgr.DoWithReadLock(ReadA, "a"); } }, () => { for (int i = 0; i < 100; i++) { mgr.DoWithWriteLock(WriteAbc, "a", "b", "c"); } }, () => { for (int i = 0; i < 100; i++) { mgr.DoWithWriteLock(WriteA, "a"); } }); }); watch.Stop(); Console.WriteLine($"{iterations} iterations took {watch.ElapsedMilliseconds} ms"); Console.WriteLine($"retries = {mgr.Retries}"); Console.WriteLine($"a = {_resourceA.Count} b = {_resourceB.Count} c = {_resourceC.Count}"); int locks = mgr.GetCurrentlyHoldLocks(); Assert.AreEqual(0, locks); }
/// <summary> /// Acquires an update lock /// </summary> /// <returns>False if lock is already set</returns> public bool AcquireUpdateLock() { return(lockManager.AcquireLock(LockManager.UpdateFlag)); }