Esempio n. 1
0
            void FreeEntry(Entry entry)
            {
                PoolChunk <T> chunk  = entry.Chunk;
                long          handle = entry.Handle;

                // recycle now so PoolChunk can be GC'ed.
                entry.Recycle();

                chunk.Arena.FreeChunk(chunk, handle, this.sizeClass);
            }
Esempio n. 2
0
        /**
         * Add {@link PoolChunk} and {@code handle} to the cache if there is enough room.
         * Returns {@code true} if it fit into the cache {@code false} otherwise.
         */

        internal bool Add(PoolArena <T> area, PoolChunk <T> chunk, long handle, int normCapacity, SizeClass sizeClass)
        {
            MemoryRegionCache c = this.Cache(area, normCapacity, sizeClass);

            if (c == null)
            {
                return(false);
            }
            return(c.Add(chunk, handle));
        }
 internal bool Free(PoolChunk <T> chunk, long handle)
 {
     chunk.Free(handle);
     if (chunk.Usage < this.minUsage)
     {
         this.Remove(chunk);
         // Move the PoolChunk down the PoolChunkList linked-list.
         return(this.Move0(chunk));
     }
     return(true);
 }
 /// Moves the {@link PoolChunk} down the {@link PoolChunkList} linked-list so it will end up in the right
 /// {@link PoolChunkList} that has the correct minUsage / maxUsage in respect to {@link PoolChunk#usage()}.
 bool Move0(PoolChunk <T> chunk)
 {
     if (this.prevList == null)
     {
         // There is no previous PoolChunkList so return false which result in having the PoolChunk destroyed and
         // all memory associated with the PoolChunk will be released.
         Debug.Assert(chunk.Usage == 0);
         return(false);
     }
     return(this.prevList.Move(chunk));
 }
Esempio n. 5
0
 internal bool Free(PoolChunk <T> chunk, long handle)
 {
     chunk.Free(handle);
     if (chunk._freeBytes > _freeMaxThreshold)
     {
         Remove(chunk);
         // Move the PoolChunk down the PoolChunkList linked-list.
         return(Move0(chunk));
     }
     return(true);
 }
Esempio n. 6
0
 protected internal sealed override void Deallocate()
 {
     if (this.Handle >= 0)
     {
         long handle = this.Handle;
         this.Handle = -1;
         this.Memory = default(T);
         this.Chunk.Arena.Free(this.Chunk, handle, this.MaxLength, this.Cache);
         this.Chunk = null;
         this.Recycle();
     }
 }
        IEnumerator <IPoolChunkMetric> GetEnumeratorInternal()
        {
            lock (this.arena)
            {
                for (PoolChunk <T> cur = this.head; cur != null;)
                {
                    yield return(cur);

                    cur = cur.Next;
                }
            }
        }
Esempio n. 8
0
        internal void Destroy(PoolArena <T> poolArena)
        {
            PoolChunk <T> chunk = _head;

            while (chunk is object)
            {
                poolArena.DestroyChunk(chunk);
                chunk = chunk.Next;
            }

            _head = null;
        }
        internal void Destroy(PoolArena <T> poolArena)
        {
            PoolChunk <T> chunk = this.head;

            while (chunk != null)
            {
                poolArena.DestroyChunk(chunk);
                chunk = chunk.Next;
            }

            this.head = null;
        }
Esempio n. 10
0
        internal void InitUnpooled(PoolChunk <T> chunk, int length)
        {
            Contract.Assert(chunk != null);

            this.Chunk  = chunk;
            this.Handle = 0;
            this.Memory = chunk.Memory;
            this.Offset = 0;
            this.Length = this.MaxLength = length;
            this.SetIndex(0, 0);
            //tmpNioBuf = null;
            this.Cache = null;
        }
Esempio n. 11
0
 protected internal override void DestroyChunk(PoolChunk <byte[]> chunk)
 {
     for (int i = 0; i < _memoryChunks.Count; i++)
     {
         MemoryChunk memoryChunk = _memoryChunks[i];
         if (ReferenceEquals(chunk.Memory, memoryChunk.Bytes))
         {
             _ = _memoryChunks.Remove(memoryChunk);
             memoryChunk.Dispose();
             break;
         }
     }
 }
Esempio n. 12
0
            /// <summary>
            /// Add to cache if not already full.
            /// </summary>
            public bool Add(PoolChunk <T> chunk, long handle)
            {
                Entry entry  = NewEntry(chunk, handle);
                bool  queued = _queue.TryEnqueue(entry);

                if (!queued)
                {
                    // If it was not possible to cache the chunk, immediately recycle the entry
                    entry.Recycle();
                }

                return(queued);
            }
Esempio n. 13
0
        internal void Reallocate(PooledByteBuffer <T> buf, int newCapacity, bool freeOldMemory)
        {
            Contract.Requires(newCapacity >= 0 && newCapacity <= buf.MaxCapacity);

            int oldCapacity = buf.Length;

            if (oldCapacity == newCapacity)
            {
                return;
            }

            PoolChunk <T> oldChunk     = buf.Chunk;
            long          oldHandle    = buf.Handle;
            T             oldMemory    = buf.Memory;
            int           oldOffset    = buf.Offset;
            int           oldMaxLength = buf.MaxLength;
            int           readerIndex  = buf.ReaderIndex;
            int           writerIndex  = buf.WriterIndex;

            this.Allocate(this.Parent.ThreadCache <T>(), buf, newCapacity);
            if (newCapacity > oldCapacity)
            {
                this.MemoryCopy(
                    oldMemory, oldOffset,
                    buf.Memory, buf.Offset, oldCapacity);
            }
            else if (newCapacity < oldCapacity)
            {
                if (readerIndex < newCapacity)
                {
                    if (writerIndex > newCapacity)
                    {
                        writerIndex = newCapacity;
                    }
                    this.MemoryCopy(
                        oldMemory, oldOffset + readerIndex,
                        buf.Memory, buf.Offset + readerIndex, writerIndex - readerIndex);
                }
                else
                {
                    readerIndex = writerIndex = newCapacity;
                }
            }

            buf.SetIndex(readerIndex, writerIndex);

            if (freeOldMemory)
            {
                this.Free(oldChunk, oldHandle, oldMaxLength, buf.Cache);
            }
        }
        bool Move(PoolChunk <T> chunk)
        {
            Contract.Assert(chunk.Usage < this.maxUsage);

            if (chunk.Usage < this.minUsage)
            {
                // Move the PoolChunk down the PoolChunkList linked-list.
                return(this.Move0(chunk));
            }

            // PoolChunk fits into this PoolChunkList, adding it here.
            this.Add0(chunk);
            return(true);
        }
Esempio n. 15
0
        bool Move(PoolChunk <T> chunk)
        {
            Debug.Assert(chunk.Usage < _maxUsage);

            if (chunk._freeBytes > _freeMaxThreshold)
            {
                // Move the PoolChunk down the PoolChunkList linked-list.
                return(Move0(chunk));
            }

            // PoolChunk fits into this PoolChunkList, adding it here.
            Add0(chunk);
            return(true);
        }
Esempio n. 16
0
        void Init0(PoolChunk <T> chunk, long handle, int offset, int length, int maxLength, PoolThreadCache <T> cache)
        {
            Debug.Assert(handle >= 0);
            Debug.Assert(chunk != null);

            this.Chunk     = chunk;
            this.Memory    = chunk.Memory;
            this.allocator = chunk.Arena.Parent;
            this.Cache     = cache;
            this.Handle    = handle;
            this.Offset    = offset;
            this.Length    = length;
            this.MaxLength = maxLength;
        }
Esempio n. 17
0
        unsafe void Init0(PoolChunk <T> chunk, long handle, int offset, int length, int maxLength, PoolThreadCache <T> cache)
        {
            Debug.Assert(handle >= 0);
            Debug.Assert(chunk is object);

            Chunk      = chunk;
            Memory     = chunk.Memory;
            _allocator = chunk.Arena.Parent;
            Origin     = chunk.NativePointer;
            Cache      = cache;
            Handle     = handle;
            Offset     = offset;
            Length     = length;
            MaxLength  = maxLength;
        }
Esempio n. 18
0
        internal void Init(PoolChunk <T> chunk, long handle, int offset, int length, int maxLength, PoolThreadCache <T> cache)
        {
            Contract.Assert(handle >= 0);
            Contract.Assert(chunk != null);

            this.Chunk     = chunk;
            this.Handle    = handle;
            this.Memory    = chunk.Memory;
            this.Offset    = offset;
            this.Length    = length;
            this.MaxLength = maxLength;
            this.SetIndex(0, 0);
            this.DiscardMarkers();
            //tmpNioBuf = null;
            this.Cache = cache;
        }
 /// Adds the {@link PoolChunk} to this {@link PoolChunkList}.
 void Add0(PoolChunk <T> chunk)
 {
     chunk.Parent = this;
     if (this.head == null)
     {
         this.head  = chunk;
         chunk.Prev = null;
         chunk.Next = null;
     }
     else
     {
         chunk.Prev     = null;
         chunk.Next     = this.head;
         this.head.Prev = chunk;
         this.head      = chunk;
     }
 }
Esempio n. 20
0
        void AllocateNormal(PooledByteBuffer <T> buf, int reqCapacity, int normCapacity)
        {
            if (this.q050.Allocate(buf, reqCapacity, normCapacity) || this.q025.Allocate(buf, reqCapacity, normCapacity) ||
                this.q000.Allocate(buf, reqCapacity, normCapacity) || this.qInit.Allocate(buf, reqCapacity, normCapacity) ||
                this.q075.Allocate(buf, reqCapacity, normCapacity))
            {
                return;
            }

            // Add a new chunk.
            PoolChunk <T> c      = this.NewChunk(this.PageSize, this.maxOrder, this.PageShifts, this.ChunkSize);
            long          handle = c.Allocate(normCapacity);

            Debug.Assert(handle > 0);
            c.InitBuf(buf, handle, reqCapacity);
            this.qInit.Add(c);
        }
Esempio n. 21
0
 public IEnumerator <IPoolChunkMetric> GetEnumerator()
 {
     lock (_arena)
     {
         if (_head is null)
         {
             return(Enumerable.Empty <IPoolChunkMetric>().GetEnumerator());
         }
         var metrics = new List <IPoolChunkMetric>();
         for (PoolChunk <T> cur = _head; cur is object;)
         {
             metrics.Add(cur);
             cur = cur.Next;
         }
         return(metrics.GetEnumerator());
     }
 }
Esempio n. 22
0
 /// Adds the {@link PoolChunk} to this {@link PoolChunkList}.
 void Add0(PoolChunk <T> chunk)
 {
     chunk.Parent = this;
     if (_head is null)
     {
         _head      = chunk;
         chunk.Prev = null;
         chunk.Next = null;
     }
     else
     {
         chunk.Prev = null;
         chunk.Next = _head;
         _head.Prev = chunk;
         _head      = chunk;
     }
 }
Esempio n. 23
0
        void AllocateNormal(PooledByteBuffer <T> buf, int reqCapacity, int normCapacity, PoolThreadCache <T> threadCache)
        {
            if (_q050.Allocate(buf, reqCapacity, normCapacity, threadCache) ||
                _q025.Allocate(buf, reqCapacity, normCapacity, threadCache) ||
                _q000.Allocate(buf, reqCapacity, normCapacity, threadCache) ||
                _qInit.Allocate(buf, reqCapacity, normCapacity, threadCache) ||
                _q075.Allocate(buf, reqCapacity, normCapacity, threadCache))
            {
                return;
            }

            // Add a new chunk.
            PoolChunk <T> c       = NewChunk(PageSize, _maxOrder, PageShifts, ChunkSize);
            bool          success = c.Allocate(buf, reqCapacity, normCapacity, threadCache);

            Debug.Assert(success);
            _qInit.Add(c);
        }
 void Remove(PoolChunk <T> cur)
 {
     if (cur == this.head)
     {
         this.head = cur.Next;
         if (this.head != null)
         {
             this.head.Prev = null;
         }
     }
     else
     {
         PoolChunk <T> next = cur.Next;
         cur.Prev.Next = next;
         if (next != null)
         {
             next.Prev = cur.Prev;
         }
     }
 }
Esempio n. 25
0
 void Remove(PoolChunk <T> cur)
 {
     if (cur == _head)
     {
         _head = cur.Next;
         if (_head is object)
         {
             _head.Prev = null;
         }
     }
     else
     {
         PoolChunk <T> next = cur.Next;
         cur.Prev.Next = next;
         if (next is object)
         {
             next.Prev = cur.Prev;
         }
     }
 }
Esempio n. 26
0
        internal void Free(PoolChunk <T> chunk, long handle, int normCapacity, PoolThreadCache <T> cache)
        {
            if (chunk.Unpooled)
            {
                int size = chunk.ChunkSize;
                this.DestroyChunk(chunk);
                Interlocked.Add(ref this.activeBytesHuge, -size);
                Interlocked.Decrement(ref this.deallocationsHuge);
            }
            else
            {
                SizeClass sc = this.SizeClass(normCapacity);
                if (cache != null && cache.Add(this, chunk, handle, normCapacity, sc))
                {
                    // cached so not free it.
                    return;
                }

                this.FreeChunk(chunk, handle, sc);
            }
        }
Esempio n. 27
0
        internal void Free(PoolChunk <T> chunk, long handle, int normCapacity, PoolThreadCache <T> cache)
        {
            if (chunk.Unpooled)
            {
                int size = chunk.ChunkSize;
                DestroyChunk(chunk);
                _ = Interlocked.Add(ref _activeBytesHuge, -size);
                _ = Interlocked.Increment(ref _deallocationsHuge);
            }
            else
            {
                SizeClass sizeClass = SizeClass(normCapacity);
                if (cache is object && cache.Add(this, chunk, handle, normCapacity, sizeClass))
                {
                    // cached so not free it.
                    return;
                }

                FreeChunk(chunk, handle, sizeClass, false);
            }
        }
Esempio n. 28
0
        internal void Reallocate(PooledByteBuffer <T> buf, int newCapacity, bool freeOldMemory)
        {
            if (/*newCapacity < 0 || */ (uint)newCapacity > (uint)buf.MaxCapacity)
            {
                ThrowHelper.ThrowIndexOutOfRangeException();
            }

            int oldCapacity = buf.Length;

            if (oldCapacity == newCapacity)
            {
                return;
            }

            PoolChunk <T> oldChunk     = buf.Chunk;
            long          oldHandle    = buf.Handle;
            T             oldMemory    = buf.Memory;
            int           oldOffset    = buf.Offset;
            int           oldMaxLength = buf.MaxLength;

            // This does not touch buf's reader/writer indices
            Allocate(Parent.ThreadCache <T>(), buf, newCapacity);
            int bytesToCopy;

            if (newCapacity > oldCapacity)
            {
                bytesToCopy = oldCapacity;
            }
            else
            {
                buf.TrimIndicesToCapacity(newCapacity);
                bytesToCopy = newCapacity;
            }
            MemoryCopy(oldMemory, oldOffset, buf.Memory, buf.Offset, bytesToCopy);

            if (freeOldMemory)
            {
                Free(oldChunk, oldHandle, oldMaxLength, buf.Cache);
            }
        }
Esempio n. 29
0
        public override string ToString()
        {
            if (this.head == null)
            {
                return("none");
            }

            var buf = new StringBuilder();

            for (PoolChunk <T> cur = this.head;;)
            {
                buf.Append(cur);
                cur = cur.Next;
                if (cur == null)
                {
                    break;
                }
                buf.Append(Environment.NewLine); // todo: StringUtil.NEWLINE
            }

            return(buf.ToString());
        }
Esempio n. 30
0
        internal bool Allocate(PooledByteBuffer <T> buf, int reqCapacity, int normCapacity, PoolThreadCache <T> threadCache)
        {
            if (_head is null || normCapacity > _maxCapacity)
            {
                // Either this PoolChunkList is empty or the requested capacity is larger then the capacity which can
                // be handled by the PoolChunks that are contained in this PoolChunkList.
                return(false);
            }

            for (PoolChunk <T> cur = _head; cur is object; cur = cur.Next)
            {
                if (cur.Allocate(buf, reqCapacity, normCapacity, threadCache))
                {
                    if (cur._freeBytes <= _freeMinThreshold)
                    {
                        Remove(cur);
                        _nextList.Add(cur);
                    }
                    return(true);
                }
            }
            return(false);
        }