Ejemplo n.º 1
0
        /// <summary>
        /// Releases a reference to a doorman. If the ref-count hits zero, then the doorman is
        /// returned to the pool (or is simply left for the garbage collector to cleanup if the
        /// pool is already full).
        /// </summary>
        /// <param name="doorman">The <see cref="Doorman"/>.</param>
        private static void ReleaseDoorman(Doorman doorman)
        {
            bool lockTaken = false;

            try
            {
                spinLock.Enter(ref lockTaken);

                if (--doorman.RefCount == 0)
                {
                    Keys.Remove(doorman.Key);
                    if (Pool.Count < MaxPoolSize)
                    {
                        doorman.Key = null;
                        Pool.Push(doorman);
                    }
                }
            }
            finally
            {
                if (lockTaken)
                {
                    spinLock.Exit();
                }
            }
        }
Ejemplo n.º 2
0
            /// <inheritdoc />
            public void Dispose()
            {
                lock (Keys)
                {
                    Doorman doorman = Keys[this.key];
                    --doorman.RefCount;
                    if (doorman.RefCount == 0)
                    {
                        Keys.Remove(this.key);
                        doorman.Reset();
                        DoormanPool.Return(doorman);
                    }

                    doorman.Semaphore.Release();
                }
            }
Ejemplo n.º 3
0
        /// <summary>
        /// Locks the current thread in write mode asynchronously.
        /// </summary>
        /// <param name="key">The key identifying the specific object to lock against.</param>
        /// <returns>
        /// The <see cref="Task{IDisposable}"/> that will release the lock.
        /// </returns>
        public async Task <IDisposable> WriterLockAsync(string key)
        {
            Doorman doorman = GetDoorman(key);

            return(await doorman.WriterLockAsync().ConfigureAwait(false));
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Locks the current thread in read mode asynchronously.
        /// </summary>
        /// <param name="key">The key identifying the specific object to lock against.</param>
        /// <returns>
        /// The <see cref="Task{IDisposable}"/> that will release the lock.
        /// </returns>
        public async Task <IDisposable> ReaderLockAsync(string key)
        {
            Doorman doorman = GetDoorman(key);

            return(await doorman.ReaderLockAsync());
        }
Ejemplo n.º 5
0
 internal Releaser(Doorman toRelease, bool writer)
 {
     this.toRelease = toRelease;
     this.writer    = writer;
 }
Ejemplo n.º 6
0
 /// <summary>
 /// Returns an doorman to the pool that was previously obtained using the <see cref="Rent"></see>
 /// method on the same <see cref="DoormanPool"></see> instance.
 /// </summary>
 /// <param name="doorman">The doorman to return</param>
 public static void Return(Doorman doorman)
 {
     Guard.NotNull(doorman, nameof(doorman));
     Pool.Add(doorman);
 }
Ejemplo n.º 7
0
        /// <summary>
        /// Locks the current thread in read mode asynchronously.
        /// </summary>
        /// <param name="key">The key identifying the specific object to lock against.</param>
        /// <returns>
        /// The <see cref="Task{IDisposable}"/> that will release the lock.
        /// </returns>
        public async Task <IDisposable> ReaderLockAsync(string key)
        {
            Doorman doorman = Keys.GetOrAdd(key, GetDoorman);

            return(await doorman.ReaderLockAsync().ConfigureAwait(false));
        }