/// <summary>
        /// Reads specified number of bytes from source stream into this <see cref="BlockAllocatedMemoryStream"/>
        /// starting at the current position.
        /// </summary>
        /// <param name="source">The stream containing the data to copy</param>
        /// <param name="length">The number of bytes to copy</param>
        /// <exception cref="ObjectDisposedException">The stream is closed.</exception>
        public void ReadFrom(Stream source, long length)
        {
            // Note: A faster way would be to write directly to the BlockAllocatedMemoryStream
            if (m_disposed)
            {
                throw new ObjectDisposedException("BlockAllocatedMemoryStream", "The stream is closed.");
            }

            byte[] buffer = MemoryBlockPool.Dequeue();

            do
            {
                int bytesRead = source.Read(buffer, 0, (int)Math.Min(BlockSize, length));

                if (bytesRead == 0)
                {
                    throw new EndOfStreamException();
                }

                length -= bytesRead;
                Write(buffer, 0, bytesRead);
            }while (length > 0);

            MemoryBlockPool.Enqueue(buffer);
        }
 /// <summary>
 /// Makes sure desired <paramref name="length"/> can be accommodated by future data accesses.
 /// </summary>
 /// <param name="length">Minimum desired stream capacity.</param>
 private void EnsureCapacity(long length)
 {
     while (m_capacity < length)
     {
         m_blocks.Add(MemoryBlockPool.Dequeue());
         m_capacity += BlockSize;
     }
 }
Beispiel #3
0
        public GlfwMouseState()
        {
            var buttonsLength = (int)(MouseButton.Last + 1);

            _mb = MemoryBlockPool.Get(sizeof(KeyEvent) * buttonsLength * 2);

            _buttons         = _mb.AllocPinnedMemory <KeyEvent>(buttonsLength);
            _previousButtons = _mb.AllocPinnedMemory <KeyEvent>(buttonsLength);
        }
Beispiel #4
0
        internal GlfwKeyboardState()
        {
            var keyEventsLength = ((int)Key.LastKey + 1);
            var size            = sizeof(KeyEvent) * keyEventsLength * 2;

            _mb = MemoryBlockPool.Get(size);

            _keyEvents         = _mb.AllocPinnedMemory <KeyEvent>(keyEventsLength);
            _previousKeyEvents = _mb.AllocPinnedMemory <KeyEvent>(keyEventsLength);
        }
Beispiel #5
0
 /// <summary>
 /// Return the <see cref="EphemeralMemoryBlock"/> to the <see cref="MemoryBlockPool"/>.
 /// </summary>
 /// <param name="disposing"><see langword="true"/> to release both managed and
 /// unmanaged resources; <see langword="false"/> to release only unmanaged resources.</param>
 protected override void Dispose(bool disposing)
 {
     if (!_disposed)
     {
         if (_memoryBlock != MemoryBlock.Empty)
         {
             MemoryBlockPool.Return(_memoryBlock);
         }
         _memoryBlock = null;
         _disposed    = true;
     }
 }
        /// <summary>
        /// Clears the entire <see cref="BlockAllocatedMemoryStream"/> contents and releases any allocated memory blocks.
        /// </summary>
        public void Clear()
        {
            m_position = 0;
            m_length   = 0;
            m_capacity = 0;

            // In the event that an exception occurs, we don't want to have released blocks that are still in this memory stream.
            List <byte[]> blocks = m_blocks;

            m_blocks = new List <byte[]>();

            foreach (var block in blocks)
            {
                MemoryBlockPool.Enqueue(block);
            }
        }