예제 #1
0
        /// <summary>
        /// Attempts to read a whole message from fromstream
        /// </summary>
        /// <param name="fromstream"></param>
        /// <returns></returns>
        public static void ReadStreamToMessageStream(MemoryBuffer fromstream, out ChatMessage message)
        {
            message = null;

            //check that we have at least 4 bytes in the buffer, it contains the length of the message
            if (fromstream.Length > 4)
            {
                byte[] lenbuf  = new byte[4];
                var    peeklen = fromstream.Peek(lenbuf, 0, lenbuf.Length);
                if (peeklen == 4)
                {
                    //check that we have the whole message in the buffer
                    var messagelength = BitConverter.ToInt32(lenbuf, 0);
                    if (fromstream.Length >= messagelength + 4)
                    {
                        var messagebuffer = new byte[messagelength];

                        //clear the length from the buffer
                        fromstream.Read(lenbuf, 0, lenbuf.Length);

                        //read the message from the buffer
                        fromstream.Read(messagebuffer, 0, messagelength);

                        var messagestream = new MemoryStream(messagebuffer, 0, messagelength);
                        message = DecodeMessage(messagestream);
                    }
                }
            }
        }
예제 #2
0
        public void ReadWriteMultiplTest()
        {
            MemoryBuffer target = new MemoryBuffer(251);
            byte[] buffer = new byte[10];
            for (byte i = 0; i < buffer.Length; i++)
                buffer[i] = i;

            for (byte i = 0; i < 50; i++)
            {
                target.Write(buffer, 0, buffer.Length);
                var tempbuf = new byte[10];
                var readcount = target.Read(tempbuf, 0, tempbuf.Length /2);
                readcount += target.Read(tempbuf, tempbuf.Length / 2, tempbuf.Length / 2);
                CollectionAssert.AreEqual(buffer, tempbuf, "Input not equal output");
                Assert.AreEqual(tempbuf.Length, readcount, "Read count is not write count");
            }
        }
예제 #3
0
        /// <summary>
        /// Reads a sequence of bytes from the uncompressed stream and removes the bytes read from the buffer
        /// </summary>
        public override int Read(byte[] buffer, int offset, int count)
        {
            bool locktaken = false;

            _readbufferlock.Enter(ref locktaken);
            int readbuflen = _readbuffer.Read(buffer, offset, count);

            _readbufferlock.Exit();
            return(readbuflen);
        }
예제 #4
0
        /// <summary>
        /// Reads a stream, prevents blocking streams from interrupting flow
        /// </summary>
        /// <param name="buffer"></param>
        /// <param name="offset"></param>
        /// <param name="count"></param>
        /// <returns></returns>
        public override int Read(byte[] buffer, int offset, int count)
        {
            //read available bytes from buffer
            var locktaken = false;

            _readbufferlock.Enter(ref locktaken);
            {
                if (_readthread == null)
                {
                    _readthread = new Thread(new ThreadStart(ReadThread));
                    _readthread.Start();
                }
                var readcount = _readbuffer.Read(buffer, offset, count);

                _readbufferlock.Exit();

                return(readcount);
            }
        }
예제 #5
0
        /// <summary>
        /// Write Thread, responsible for compressing and sending the compressed blocks to the base stream
        /// </summary>
        private void WriteThread()
        {
            while (true)
            {
                //writebuffer is either 16mb or flush requested
                if (((_writebuffer.Length >= _maxbuffersize) || (_flush)) && (_writebuffer.Length > 0))
                {
                    _flush = false;
                    //compress the buffer, but also store the original buffer so later we can decide which one is smaller.

                    MemoryStream compressed   = new MemoryStream();
                    MemoryStream uncompressed = new MemoryStream();

                    byte[] buffer    = new byte[_tempbuffersize];
                    bool   locktaken = false;
                    _writebufferlock.Enter(ref locktaken);
                    int readbytes = 0;
                    do
                    {
                        readbytes = _writebuffer.Read(buffer, 0, buffer.Length);
                        uncompressed.Write(buffer, 0, readbytes);
                    } while (readbytes > 0);
                    _writebufferlock.Exit();

                    //compress the block
                    uncompressed.Seek(0, SeekOrigin.Begin);
                    using (GZipStream gzcompression = new GZipStream(compressed, CompressionMode.Compress, true))
                    {
                        uncompressed.CopyTo(gzcompression);
                        gzcompression.Close();
                    }


                    //check if we rather use the compressed or the uncompressed byte stream
                    MemoryStream selectedstream = null;

                    //check if compressed buffer is bigger than uncompressed buffer.
                    if (compressed.Length > uncompressed.Length)
                    {
                        selectedstream = uncompressed;
                    }
                    else
                    {
                        selectedstream = compressed;
                    }

                    //write to writecompressed
                    //first, write 3 bytes of the length, so later the reading stream can determine the block size.
                    byte[] lenint = BitConverter.GetBytes((int)selectedstream.Length);
                    _basestream.Write(lenint, 0, 3);

                    //write which stream we selected, either the compressed or the uncompressed.
                    if (compressed.Length > uncompressed.Length)
                    {
                        _basestream.WriteByte(0);
                    }
                    else
                    {
                        _basestream.WriteByte(1);
                    }

                    //write writecompressed to underlying stream
                    selectedstream.Seek(0, SeekOrigin.Begin);
                    do
                    {
                        readbytes = selectedstream.Read(buffer, 0, buffer.Length);
                        _basestream.Write(buffer, 0, readbytes);
                    } while (readbytes > 0);
                    _basestream.Flush();
                }
                else
                {
                    Thread.Sleep(1);
                }
            }
        }
예제 #6
0
파일: Common.cs 프로젝트: kiszu/ForBlog
        /// <summary>
        /// Attempts to read a whole message from fromstream
        /// </summary>
        /// <param name="fromstream"></param>
        /// <returns></returns>
        public static void ReadStreamToMessageStream(MemoryBuffer fromstream, out ChatMessage message)
        {
            message = null;

            //check that we have at least 4 bytes in the buffer, it contains the length of the message
            if (fromstream.Length > 4)
            {
                byte[] lenbuf = new byte[4];
                var peeklen = fromstream.Peek(lenbuf, 0, lenbuf.Length);
                if (peeklen == 4)
                {
                    //check that we have the whole message in the buffer
                    var messagelength = BitConverter.ToInt32(lenbuf, 0);
                    if (fromstream.Length >= messagelength + 4)
                    {
                        var messagebuffer = new byte[messagelength];

                        //clear the length from the buffer
                        fromstream.Read(lenbuf, 0, lenbuf.Length);

                        //read the message from the buffer
                        fromstream.Read(messagebuffer, 0, messagelength);

                        var messagestream = new MemoryStream(messagebuffer, 0, messagelength);
                        message = DecodeMessage(messagestream);


                    }
                }
            }
        }