void WithAtomicLong_Entry() { for (var i = 0; i < NumIterations; ++i) { _atomicLong.Decrement(); _atomicLong.Increment(); BenchmarkUtils.SimulateContention(ContentionLevel); _atomicLong.Increment(); var curVal = _atomicLong.Value; curVal = _atomicLong.Exchange(curVal * 2L).CurrentValue; BenchmarkUtils.SimulateContention(ContentionLevel); curVal = _atomicLong.TryExchange(curVal / 2L, curVal).CurrentValue; var prevVal = _atomicLong.TryBoundedExchange(curVal + 10L, curVal - 3L, curVal + 3L).PreviousValue; if (prevVal == curVal) { _atomicLong.Subtract(10L); } BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithAtomicRef_WriterEntry() { for (var i = 0; i < NumIterations; ++i) { _atomicUser.Exchange(cur => new User(cur.LoginID + 1, _usernames[cur.LoginID + 1])); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithAtomicRef_ReaderEntry() { for (var i = 0; i < NumIterations; ++i) { var curUser = _atomicUser.Value; BenchmarkUtils.Assert(curUser.Name == _usernames[curUser.LoginID]); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithStandardLock_ReaderEntry() { for (var i = 0; i < NumIterations; ++i) { User curUser; lock (_lockObject) curUser = _standardLockUser; BenchmarkUtils.Assert(curUser.Name == _usernames[curUser.LoginID]); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithAtomicVal_EntryA() { while (_atomicValRemainingThreadCount > 0) { var curVal = _atomicVal.Value; _atomicVal.TryExchange(new Vector2(curVal.Y, curVal.X), curVal); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithRWLS_WriterEntry() { for (var i = 0; i < NumIterations; ++i) { _rwls.EnterWriteLock(); var nextID = _rwlsUser.LoginID + 1; _rwlsUser = new User(nextID, _usernames[nextID]); _rwls.ExitWriteLock(); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithStandardLock_WriterEntry() { for (var i = 0; i < NumIterations; ++i) { lock (_lockObject) { var nextID = _standardLockUser.LoginID + 1; _standardLockUser = new User(nextID, _usernames[nextID]); } BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithManualLoop_EntryA() { while (_manualLoopRemainingThreadCount > 0) { var curVal = Interlocked.Read(ref _manualLoopVector2.L); var curValAsVec = new Vector2(curVal); Interlocked.CompareExchange(ref _manualLoopVector2.L, new Vector2(curValAsVec.Y, curValAsVec.X).L, curVal); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithRWLS_ReaderEntry() { for (var i = 0; i < NumIterations; ++i) { _rwls.EnterReadLock(); var curUser = _rwlsUser; _rwls.ExitReadLock(); BenchmarkUtils.Assert(curUser.Name == _usernames[curUser.LoginID]); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithAtomicVal_EntryB() { for (var i = 0; i < NumIterations; ++i) { var curVal = _atomicVal.Value; _atomicVal.SpinWaitForValue(new Vector2(curVal.Y, curVal.X)); BenchmarkUtils.SimulateContention(ContentionLevel); _atomicVal.SpinWaitForExchange(curVal, new Vector2(curVal.Y, curVal.X)); BenchmarkUtils.SimulateContention(ContentionLevel); } _atomicValRemainingThreadCount.Decrement(); }
void WithContextualFuncs_Entry() { var usernameA = "aaaa"; var usernameB = "bbbb"; for (var i = 0; i < NumIterations; i++) { _contextualFuncsUser.Exchange((u, ctx) => new User(u.LoginID, ctx), (i & 1) == 0 ? usernameA : usernameB); _contextualFuncsUser.TryExchange((u, ctx) => new User(u.LoginID, ctx), (i & 1) == 0 ? usernameA : usernameB, (cur, next, ctx) => cur.Name == ctx || next.Name == ctx, usernameA); _contextualFuncsLong.TryBoundedExchange((l, ctx) => l + ctx, i, 0L, NumIterations); _contextualFuncsLong.TryMinimumExchange((l, ctx) => l + ctx, i, 0L); _contextualFuncsLong.TryMaximumExchange((l, ctx) => l + ctx, i, NumIterations); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithClosureCapturingFuncs_Entry() { var usernameA = "aaaa"; var usernameB = "bbbb"; for (var i = 0; i < NumIterations; i++) { _closureCapturingFuncsUser.Exchange(u => new User(u.LoginID, (i & 1) == 0 ? usernameA : usernameB)); _closureCapturingFuncsUser.TryExchange(u => new User(u.LoginID, (i & 1) == 0 ? usernameA : usernameB), (cur, next) => cur.Name == usernameA || next.Name == usernameA); _closureCapturingFuncsLong.TryBoundedExchange(l => l + i, 0L, NumIterations); _closureCapturingFuncsLong.TryMinimumExchange(l => l + i, 0L); _closureCapturingFuncsLong.TryMaximumExchange(l => l + i, NumIterations); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithManualLoops_Entry() { var usernameA = "aaaa"; var usernameB = "bbbb"; for (var i = 0; i < NumIterations; i++) { ExchangeUser((i & 1) == 0 ? usernameA : usernameB); TryExchangeUser((i & 1) == 0 ? usernameA : usernameB, usernameA); TryBoundedExchange(i, 0L, NumIterations); TryMinExchange(i, 0L); TryMaxExchange(i, NumIterations); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithAtomicVal_Entry() { for (var i = 0; i < NumIterations; i++) { var prevVal = _atomicVal.Exchange(new Vector2(i, i)).PreviousValue; var curVal = _atomicVal.TryExchange(new Vector2(prevVal.X + 2, prevVal.Y + 2), new Vector2(i, i)).CurrentValue; BenchmarkUtils.SimulateContention(ContentionLevel); prevVal = _atomicVal.Exchange(new Vector2(curVal.X + 1, curVal.Y + 1)).PreviousValue; curVal = _atomicVal.TryExchange(new Vector2(prevVal.X + 2, prevVal.Y + 2), new Vector2(i, i)).CurrentValue; BenchmarkUtils.SimulateContention(ContentionLevel); prevVal = _atomicVal.Exchange(new Vector2(curVal.X + 1, curVal.Y + 1)).PreviousValue; _atomicVal.TryExchange(new Vector2(prevVal.X + 2, prevVal.Y + 2), new Vector2(i, i)); BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithLockedLong_Entry() { for (var i = 0; i < NumIterations; ++i) { lock (_lockedLongLock) _lockedLong--; lock (_lockedLongLock) _lockedLong++; BenchmarkUtils.SimulateContention(ContentionLevel); lock (_lockedLongLock) _lockedLong++; long curVal; lock (_lockedLongLock) curVal = _lockedLong; lock (_lockedLongLock) { curVal = _lockedLong = curVal * 2L; } BenchmarkUtils.SimulateContention(ContentionLevel); lock (_lockedLongLock) { if (_lockedLong == curVal) { _lockedLong = curVal / 2L; } curVal = _lockedLong; } long prevVal; lock (_lockedLongLock) { prevVal = _lockedLong; if (_lockedLong >= curVal - 3L && _lockedLong < curVal + 3L) { _lockedLong = curVal + 10L; } } if (prevVal == curVal) { lock (_lockedLongLock) _lockedLong -= 10L; } BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithLessGranularLock_Entry() { for (var i = 0; i < NumIterations; i++) { Vector2 prevVal, curVal; lock (_lessGranularLock) { prevVal = _lessGranularLockVal; _lessGranularLockVal = new Vector2(i, i); if (_lessGranularLockVal == new Vector2(i, i)) { _lessGranularLockVal = new Vector2(prevVal.X + 2, prevVal.Y + 2); } curVal = _lessGranularLockVal; BenchmarkUtils.SimulateContention(ContentionLevel); prevVal = _lessGranularLockVal; _lessGranularLockVal = new Vector2(curVal.X + 1, curVal.Y + 1); if (_lessGranularLockVal == new Vector2(i, i)) { _lessGranularLockVal = new Vector2(prevVal.X + 2, prevVal.Y + 2); } curVal = _lessGranularLockVal; BenchmarkUtils.SimulateContention(ContentionLevel); prevVal = _lessGranularLockVal; _lessGranularLockVal = new Vector2(curVal.X + 1, curVal.Y + 1); if (_lessGranularLockVal == new Vector2(i, i)) { _lessGranularLockVal = new Vector2(prevVal.X + 2, prevVal.Y + 2); } } BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithLockedLongLessGranular_Entry() { for (var i = 0; i < NumIterations; ++i) { lock (_lockedLessGranularLongLock) { _lockedLessGranularLong--; _lockedLessGranularLong++; } BenchmarkUtils.SimulateContention(ContentionLevel); long curVal; lock (_lockedLessGranularLongLock) { _lockedLessGranularLong++; curVal = _lockedLessGranularLong; curVal = _lockedLessGranularLong = curVal * 2L; } BenchmarkUtils.SimulateContention(ContentionLevel); lock (_lockedLessGranularLongLock) { if (_lockedLessGranularLong == curVal) { _lockedLessGranularLong = curVal / 2L; } curVal = _lockedLessGranularLong; var prevVal = _lockedLessGranularLong; if (_lockedLessGranularLong >= curVal - 3L && _lockedLessGranularLong < curVal + 3L) { _lockedLessGranularLong = curVal + 10L; } if (prevVal == curVal) { _lockedLessGranularLong -= 10L; } } BenchmarkUtils.SimulateContention(ContentionLevel); } }
void WithManualLoop_EntryB() { for (var i = 0; i < NumIterations; ++i) { var curVal = Interlocked.Read(ref _manualLoopVector2.L); var curValAsVec = new Vector2(curVal); var spinner = new SpinWait(); var targetVal = new Vector2(curValAsVec.Y, curValAsVec.X).L; while (true) { if (Interlocked.Read(ref _manualLoopVector2.L) == targetVal) { break; } spinner.SpinOnce(); } BenchmarkUtils.SimulateContention(ContentionLevel); spinner = new SpinWait(); while (true) { if (Interlocked.CompareExchange(ref _manualLoopVector2.L, targetVal, curVal) == curVal) { break; } spinner.SpinOnce(); } BenchmarkUtils.SimulateContention(ContentionLevel); } _manualLoopRemainingThreadCount.Decrement(); }
void WithAtomicVal_Entry() { var result = 0L; for (var i = 0; i < NumIterations; i++) { if (_atomicVal.Value.A < i) { result += _atomicVal.Get().A; } else { result -= _atomicVal.Get().A; } BenchmarkUtils.SimulateContention(ContentionLevel); var curVal = _atomicVal.Get(); BenchmarkUtils.SimulateContention(ContentionLevel); if (curVal.A >= _atomicVal.Get().A) { if (_atomicVal.Get().B > _atomicVal.Get().C) { result += _atomicVal.Get().C; } else { result += _atomicVal.Get().B; } } else { if (_atomicVal.Get().B > _atomicVal.Get().C) { result += _atomicVal.Get().B; } else { result += _atomicVal.Get().C; } } if (_atomicVal.Value.A < i) { result += _atomicVal.Get().A; } else { result -= _atomicVal.Get().A; } curVal = _atomicVal.Get(); if (curVal.A >= _atomicVal.Get().A) { if (_atomicVal.Get().B > _atomicVal.Get().C) { result += _atomicVal.Get().C; } else { result += _atomicVal.Get().B; } } else { if (_atomicVal.Get().B > _atomicVal.Get().C) { result += _atomicVal.Get().B; } else { result += _atomicVal.Get().C; } } BenchmarkUtils.SimulateContention(ContentionLevel); if (i % IterationsPerBarrier == 0) { if (_atomicVal.Get().B < curVal.A) { result += _atomicVal.TryExchange(new Val64(curVal.A - 1L), curVal).CurrentValue.A; } else { result += _atomicVal.TryExchange(new Val64(curVal.A + 1L), curVal).CurrentValue.A; } _atomicValSyncBarrier.SignalAndWait(); } BenchmarkUtils.SimulateContention(ContentionLevel); } if (result == 0L) { Console.Beep(1000, 100); } }
void WithRWLS_Entry() { var result = 0L; for (var i = 0; i < NumIterations; i++) { _rwls.EnterReadLock(); if (_rwlsVal.A < i) { result += _rwlsVal.A; } else { result -= _rwlsVal.A; } _rwls.ExitReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); _rwls.EnterReadLock(); var curVal = _rwlsVal; _rwls.ExitReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); _rwls.EnterReadLock(); if (curVal.A >= _rwlsVal.A) { if (_rwlsVal.B > _rwlsVal.C) { result += _rwlsVal.C; } else { result += _rwlsVal.B; } } else { if (_rwlsVal.B > _rwlsVal.C) { result += _rwlsVal.B; } else { result += _rwlsVal.C; } } if (_rwlsVal.A < i) { result += _rwlsVal.A; } else { result -= _rwlsVal.A; } curVal = _rwlsVal; if (curVal.A >= _rwlsVal.A) { if (_rwlsVal.B > _rwlsVal.C) { result += _rwlsVal.C; } else { result += _rwlsVal.B; } } else { if (_rwlsVal.B > _rwlsVal.C) { result += _rwlsVal.B; } else { result += _rwlsVal.C; } } _rwls.ExitReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); if (i % IterationsPerBarrier == 0) { _rwls.EnterWriteLock(); if (_rwlsVal.B < curVal.A) { if (_rwlsVal == curVal) { _rwlsVal = new Val64(curVal.A - 1L); } result += _rwlsVal.A; } else { if (_rwlsVal == curVal) { _rwlsVal = new Val64(curVal.A + 1L); } result += _rwlsVal.A; } _rwls.ExitWriteLock(); _rwlsSyncBarrier.SignalAndWait(); } BenchmarkUtils.SimulateContention(ContentionLevel); } if (result == 0L) { Console.Beep(1000, 100); } }
void WithLessGranularLock_Entry() { var result = 0L; for (var i = 0; i < NumIterations; i++) { Val64 curVal; lock (_lessGranularLock) { if (_lessGranularLockVal.A < i) { result += _lessGranularLockVal.A; } else { result -= _lessGranularLockVal.A; } BenchmarkUtils.SimulateContention(ContentionLevel); curVal = _lessGranularLockVal; BenchmarkUtils.SimulateContention(ContentionLevel); if (curVal.A >= _lessGranularLockVal.A) { if (_lessGranularLockVal.B > _lessGranularLockVal.C) { result += _lessGranularLockVal.C; } else { result += _lessGranularLockVal.B; } } else { if (_lessGranularLockVal.B > _lessGranularLockVal.C) { result += _lessGranularLockVal.B; } else { result += _lessGranularLockVal.C; } } if (_lessGranularLockVal.A < i) { result += _lessGranularLockVal.A; } else { result -= _lessGranularLockVal.A; } curVal = _lessGranularLockVal; if (curVal.A >= _lessGranularLockVal.A) { if (_lessGranularLockVal.B > _lessGranularLockVal.C) { result += _lessGranularLockVal.C; } else { result += _lessGranularLockVal.B; } } else { if (_lessGranularLockVal.B > _lessGranularLockVal.C) { result += _lessGranularLockVal.B; } else { result += _lessGranularLockVal.C; } } } BenchmarkUtils.SimulateContention(ContentionLevel); if (i % IterationsPerBarrier == 0) { lock (_lessGranularLock) { if (_lessGranularLockVal.B < curVal.A) { if (_lessGranularLockVal == curVal) { _lessGranularLockVal = new Val64(curVal.A - 1L); } result += _lessGranularLockVal.A; } else { if (_lessGranularLockVal == curVal) { _lessGranularLockVal = new Val64(curVal.A + 1L); } result += _lessGranularLockVal.A; } } _lessGranularLockSyncBarrier.SignalAndWait(); } BenchmarkUtils.SimulateContention(ContentionLevel); } if (result == 0L) { Console.Beep(1000, 100); } }
void WithAtomicVal_Entry() { var result = 0L; for (var i = 0; i < NumIterations; i++) { if (_atomicVal.Value.L < i) { result += _atomicVal.Get().L; } else { result -= _atomicVal.Get().L; } BenchmarkUtils.SimulateContention(ContentionLevel); var curVal = _atomicVal.Get(); BenchmarkUtils.SimulateContention(ContentionLevel); if (curVal.L >= _atomicVal.Get().L) { if (_atomicVal.Get().X > _atomicVal.Get().Y) { result += (long)_atomicVal.Get().Y; } else { result += (long)_atomicVal.Get().X; } } else { if (_atomicVal.Get().X > _atomicVal.Get().Y) { result += (long)_atomicVal.Get().X; } else { result += (long)_atomicVal.Get().Y; } } if (_atomicVal.Value.L < i) { result += _atomicVal.Get().L; } else { result -= _atomicVal.Get().L; } curVal = _atomicVal.Get(); if (curVal.L >= _atomicVal.Get().L) { if (_atomicVal.Get().X > _atomicVal.Get().Y) { result += (long)_atomicVal.Get().Y; } else { result += (long)_atomicVal.Get().X; } } else { if (_atomicVal.Get().X > _atomicVal.Get().Y) { result += (long)_atomicVal.Get().X; } else { result += (long)_atomicVal.Get().Y; } } BenchmarkUtils.SimulateContention(ContentionLevel); if (i % IterationsPerBarrier == 0) { if (_atomicVal.Get().X < curVal.L) { result += _atomicVal.TryExchange(new Vector2(curVal.L - 1L), curVal).CurrentValue.L; } else { result += _atomicVal.TryExchange(new Vector2(curVal.L + 1L), curVal).CurrentValue.L; } _atomicValSyncBarrier.SignalAndWait(); } BenchmarkUtils.SimulateContention(ContentionLevel); } if (result == 0L) { Console.Beep(1000, 100); } }
void WithRWLS_Entry() { var result = 0L; for (var i = 0; i < NumIterations; i++) { _rwls.EnterReadLock(); if (_rwlsVal.L < i) { result += _rwlsVal.L; } else { result -= _rwlsVal.L; } _rwls.ExitReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); _rwls.EnterReadLock(); var curVal = _rwlsVal; _rwls.ExitReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); _rwls.EnterReadLock(); if (curVal.L >= _rwlsVal.L) { if (_rwlsVal.X > _rwlsVal.Y) { result += (long)_rwlsVal.Y; } else { result += (long)_rwlsVal.X; } } else { if (_rwlsVal.X > _rwlsVal.Y) { result += (long)_rwlsVal.X; } else { result += (long)_rwlsVal.Y; } } if (_rwlsVal.L < i) { result += _rwlsVal.L; } else { result -= _rwlsVal.L; } curVal = _rwlsVal; if (curVal.L >= _rwlsVal.L) { if (_rwlsVal.X > _rwlsVal.Y) { result += (long)_rwlsVal.Y; } else { result += (long)_rwlsVal.X; } } else { if (_rwlsVal.X > _rwlsVal.Y) { result += (long)_rwlsVal.X; } else { result += (long)_rwlsVal.Y; } } _rwls.ExitReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); if (i % IterationsPerBarrier == 0) { _rwls.EnterWriteLock(); if (_rwlsVal.X < curVal.L) { if (_rwlsVal == curVal) { _rwlsVal = new Vector2(curVal.L - 1L); } result += _rwlsVal.L; } else { if (_rwlsVal == curVal) { _rwlsVal = new Vector2(curVal.L + 1L); } result += _rwlsVal.L; } _rwls.ExitWriteLock(); _rwlsSyncBarrier.SignalAndWait(); } BenchmarkUtils.SimulateContention(ContentionLevel); } if (result == 0L) { Console.Beep(1000, 100); } }
void WithLessGranularLock_Entry() { var result = 0L; for (var i = 0; i < NumIterations; i++) { Vector2 curVal; lock (_lessGranularLock) { if (_lessGranularLockVal.L < i) { result += _lessGranularLockVal.L; } else { result -= _lessGranularLockVal.L; } BenchmarkUtils.SimulateContention(ContentionLevel); curVal = _lessGranularLockVal; BenchmarkUtils.SimulateContention(ContentionLevel); if (curVal.L >= _lessGranularLockVal.L) { if (_lessGranularLockVal.X > _lessGranularLockVal.Y) { result += (long)_lessGranularLockVal.Y; } else { result += (long)_lessGranularLockVal.X; } } else { if (_lessGranularLockVal.X > _lessGranularLockVal.Y) { result += (long)_lessGranularLockVal.X; } else { result += (long)_lessGranularLockVal.Y; } } if (_lessGranularLockVal.L < i) { result += _lessGranularLockVal.L; } else { result -= _lessGranularLockVal.L; } curVal = _lessGranularLockVal; if (curVal.L >= _lessGranularLockVal.L) { if (_lessGranularLockVal.X > _lessGranularLockVal.Y) { result += (long)_lessGranularLockVal.Y; } else { result += (long)_lessGranularLockVal.X; } } else { if (_lessGranularLockVal.X > _lessGranularLockVal.Y) { result += (long)_lessGranularLockVal.X; } else { result += (long)_lessGranularLockVal.Y; } } } BenchmarkUtils.SimulateContention(ContentionLevel); if (i % IterationsPerBarrier == 0) { lock (_lessGranularLock) { if (_lessGranularLockVal.X < curVal.L) { if (_lessGranularLockVal == curVal) { _lessGranularLockVal = new Vector2(curVal.L - 1L); } result += _lessGranularLockVal.L; } else { if (_lessGranularLockVal == curVal) { _lessGranularLockVal = new Vector2(curVal.L + 1L); } result += _lessGranularLockVal.L; } } _lessGranularLockSyncBarrier.SignalAndWait(); } BenchmarkUtils.SimulateContention(ContentionLevel); } if (result == 0L) { Console.Beep(1000, 100); } }
void WithRWLS_Entry() { for (var i = 0; i < NumIterations; i++) { Vector2 prevVal, curVal; _rwls.EnterUpgradeableReadLock(); prevVal = _rwlsVal; _rwls.EnterWriteLock(); _rwlsVal = new Vector2(i, i); _rwls.ExitWriteLock(); _rwls.ExitUpgradeableReadLock(); _rwls.EnterUpgradeableReadLock(); if (_rwlsVal == new Vector2(i, i)) { _rwls.EnterWriteLock(); _rwlsVal = new Vector2(prevVal.X + 2, prevVal.Y + 2); _rwls.ExitWriteLock(); } curVal = _rwlsVal; _rwls.ExitUpgradeableReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); _rwls.EnterUpgradeableReadLock(); prevVal = _rwlsVal; _rwls.EnterWriteLock(); _rwlsVal = new Vector2(curVal.X + 1, curVal.Y + 1); _rwls.ExitWriteLock(); _rwls.ExitUpgradeableReadLock(); _rwls.EnterUpgradeableReadLock(); if (_rwlsVal == new Vector2(i, i)) { _rwls.EnterWriteLock(); _rwlsVal = new Vector2(prevVal.X + 2, prevVal.Y + 2); _rwls.ExitWriteLock(); } curVal = _rwlsVal; _rwls.ExitUpgradeableReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); _rwls.EnterUpgradeableReadLock(); prevVal = _rwlsVal; _rwls.EnterWriteLock(); _rwlsVal = new Vector2(curVal.X + 1, curVal.Y + 1); _rwls.ExitWriteLock(); _rwls.ExitUpgradeableReadLock(); _rwls.EnterUpgradeableReadLock(); if (_rwlsVal == new Vector2(i, i)) { _rwls.EnterWriteLock(); _rwlsVal = new Vector2(prevVal.X + 2, prevVal.Y + 2); _rwls.ExitWriteLock(); } _rwls.ExitUpgradeableReadLock(); BenchmarkUtils.SimulateContention(ContentionLevel); } }