public void SetStreamBlock(StreamBlock newBlock) { // The new block is already rented from shared memory, // this object owns the reference on behalf of the current process. // Proxy usage is tracked by _rc field. lock (this) { if (AtomicCounter.GetIsDisposed(ref _rc)) { // because we inside the lock that protects from concurrent call to dispose, // the proxy could be disposed by now and the new block is not needed #pragma warning disable 618 newBlock.DisposeFree(); #pragma warning restore 618 } else { var previous = Block; Block = newBlock; if (previous.IsValid) { #pragma warning disable 618 previous.DisposeFree(); #pragma warning restore 618 } } } }
public static StreamBlockProxy Create(BlockKey key, ReaderBlockCache cache) { var instance = _pool.Allocate(); ThrowHelper.AssertFailFast(AtomicCounter.GetIsDisposed(ref instance._rc), "Pooled proxy must be in disposed state."); instance._key = key; instance._cache = cache; // cache owns one ref instance._rc = 1; return(instance); }
public void CouldDispose() { var counter = 0; Assert.IsFalse(AtomicCounter.GetIsDisposed(ref counter)); Assert.AreEqual(1, AtomicCounter.Increment(ref counter)); Assert.AreEqual(2, AtomicCounter.Increment(ref counter)); Assert.Throws <InvalidOperationException>(() => { AtomicCounter.Dispose(ref counter); }); Assert.AreEqual(1, AtomicCounter.Decrement(ref counter)); Assert.AreEqual(0, AtomicCounter.DecrementIfOne(ref counter)); Assert.IsFalse(AtomicCounter.GetIsDisposed(ref counter)); AtomicCounter.Dispose(ref counter); Assert.IsTrue(AtomicCounter.GetIsDisposed(ref counter)); }
public void CouldTryDispose() { var counter = 0; Assert.IsFalse(AtomicCounter.GetIsDisposed(ref counter)); Assert.AreEqual(1, AtomicCounter.Increment(ref counter)); Assert.AreEqual(2, AtomicCounter.Increment(ref counter)); Assert.AreEqual(2, AtomicCounter.TryDispose(ref counter)); Assert.AreEqual(1, AtomicCounter.Decrement(ref counter)); Assert.AreEqual(0, AtomicCounter.DecrementIfOne(ref counter)); Assert.IsFalse(AtomicCounter.GetIsDisposed(ref counter)); Assert.AreEqual(0, AtomicCounter.TryDispose(ref counter)); Assert.IsTrue(AtomicCounter.GetIsDisposed(ref counter)); Assert.AreEqual(-1, AtomicCounter.TryDispose(ref counter)); counter = AtomicCounter.Disposed - 1; Assert.Throws <InvalidOperationException>(() => { AtomicCounter.TryDispose(ref counter); }); counter = AtomicCounter.Disposed | (123 << 24); Assert.AreEqual(-1, AtomicCounter.TryDispose(ref counter)); Assert.AreEqual(AtomicCounter.Disposed | (123 << 24), counter); counter = (123 << 24); Assert.AreEqual(0, AtomicCounter.TryDispose(ref counter)); Assert.AreEqual((123 << 24), counter & ~AtomicCounter.Disposed); }