예제 #1
0
        /// <summary>
        /// Tries to parse a chunk size line for the message
        /// </summary>
        /// <returns></returns>
        private bool TryAndParseChunkSizeLine(ref HttpMessage message, EventHandler <HttpMessageProgressEventArgs> onProgress, object stateObject)
        {
            // try and parse a token from the data
            HttpByteParserToken token = _parser.GetNextToken();

            if (token == null)
            {
                return(false);
            }

            // the first line of any message is never empty
            if (token.IsEmpty)
            {
                return(false);
            }

            // success! this line is a header
            string line = token.ToString(HttpUtils.Encoding);

            // parse the size line
            HttpChunkSizeLine chunkSizeLine = HttpChunkSizeLine.Parse(line);

            // create a new chunk
            _chunk = new HttpChunk(chunkSizeLine, null);

            // change state to processing chunk data
            _state = Processing.ChunkData;

            return(true);
        }
예제 #2
0
 /// <summary>
 /// Destroys the internal variables used to read the message
 /// </summary>
 private void CleanupVars()
 {
     // reset our internal vars
     _chunk             = null;
     _chunkedBody       = null;
     _parser            = null;
     _receivedBytes     = null;
     _headerOffsetStart = -1;
     _headerOffsetEnd   = -1;
 }
예제 #3
0
 /// <summary>
 /// Initializes internal variables used to read the message
 /// </summary>
 private void InitVars()
 {
     // reset our internal vars
     _state             = Processing.FirstLine;
     _chunk             = null;
     _chunkedBody       = null;
     _parser            = new HttpByteParser();
     _receivedBytes     = null;
     _headerOffsetStart = -1;
     _headerOffsetEnd   = -1;
 }
예제 #4
0
        /// <summary>
        /// Tries to parse some chunk data for the message
        /// </summary>
        /// <returns></returns>
        private bool TryAndParseChunkData(ref HttpMessage message, EventHandler <HttpMessageProgressEventArgs> onProgress, object stateObject)
        {
            // get bytes, and update the index...
            int waitingOn = _chunk.Size;
            int received  = _receivedBytes.Length - 2 - _parser.Index;

            // if we received enough data to pull in a chunk, do that now
            if (received >= waitingOn)
            {
                // copy the end of the data out as chunk data
                byte[] data = HttpUtils.Clone(_receivedBytes, _parser.Index, _chunk.Size);

                // bump the parser past the end of the next \r\n
                _parser.Index += _chunk.Size + 2;

                // create a new chunked body
                if (_chunkedBody == null)
                {
                    _chunkedBody = new HttpChunkedBody();
                }

                // assign the data to the chunk
                _chunk.Data = data;

                // todo:

                // add the chunk to the body
                _chunkedBody.Chunks.Add(_chunk);

                // if the chunk is empty, it's the last chunk
                bool empty = _chunk.IsEmpty;

                // destroy the chunk
                _chunk = null;

                if (empty)
                {
                    // change state to processing chunk data
                    _state = Processing.ChunkTrailerHeaderLine;
                }
                else
                {
                    // go back to processing a chunk size line
                    _state = Processing.ChunkSizeLine;
                }

                return(true);
            }

            return(false);
        }
		/// <summary>
		/// Tries to parse some chunk data for the message
		/// </summary>
		/// <returns></returns>
		private bool TryAndParseChunkData(ref HttpMessage message, EventHandler<HttpMessageProgressEventArgs> onProgress, object stateObject)
		{
			// get bytes, and update the index...
			int waitingOn = _chunk.Size;
			int received = _receivedBytes.Length - 2 - _parser.Index;
			
			// if we received enough data to pull in a chunk, do that now
			if (received >= waitingOn)
			{
				// copy the end of the data out as chunk data
				byte[] data = HttpUtils.Clone(_receivedBytes, _parser.Index, _chunk.Size);

				// bump the parser past the end of the next \r\n
				_parser.Index += _chunk.Size + 2;

				// create a new chunked body
				if (_chunkedBody == null)
					_chunkedBody = new HttpChunkedBody();

				// assign the data to the chunk
				_chunk.Data = data;

				// todo: 

				// add the chunk to the body
				_chunkedBody.Chunks.Add(_chunk);

				// if the chunk is empty, it's the last chunk		
				bool empty = _chunk.IsEmpty;
				
				// destroy the chunk
				_chunk = null;

				if (empty)
				{
					// change state to processing chunk data
					_state = Processing.ChunkTrailerHeaderLine;
				}
				else
				{
					// go back to processing a chunk size line
					_state = Processing.ChunkSizeLine;
				}

				return true;				
			}

			return false;
		}
		/// <summary>
		/// Initializes internal variables used to read the message
		/// </summary>
		private void InitVars()
		{
			// reset our internal vars
			_state = Processing.FirstLine;
			_chunk = null;
			_chunkedBody = null;
            _parser = new HttpByteParser();
			_receivedBytes = null;
			_headerOffsetStart = -1;
			_headerOffsetEnd = -1;			
		}
		/// <summary>
		/// Destroys the internal variables used to read the message
		/// </summary>
		private void CleanupVars()
		{
			// reset our internal vars
			_chunk = null;
			_chunkedBody = null;
			_parser = null;
			_receivedBytes = null;
			_headerOffsetStart = -1;
			_headerOffsetEnd = -1;	
		}
		/// <summary>
		/// Tries to parse a chunk size line for the message
		/// </summary>
		/// <returns></returns>
		private bool TryAndParseChunkSizeLine(ref HttpMessage message, EventHandler<HttpMessageProgressEventArgs> onProgress, object stateObject)
		{
			// try and parse a token from the data
			HttpByteParserToken token = _parser.GetNextToken();						
			if (token == null)
				return false;
			
			// the first line of any message is never empty
			if (token.IsEmpty)
				return false;

			// success! this line is a header
			string line = token.ToString(HttpUtils.Encoding);

			// parse the size line
			HttpChunkSizeLine chunkSizeLine = HttpChunkSizeLine.Parse(line);

			// create a new chunk
			_chunk = new HttpChunk(chunkSizeLine, null);
			
			// change state to processing chunk data
			_state = Processing.ChunkData;

			return true;
		}
예제 #9
0
 /// <summary>
 /// Adds a chunk to the list
 /// </summary>
 /// <param name="chunk"></param>
 public void Add(HttpChunk chunk)
 {
     base.InnerList.Add(chunk);
 }
예제 #10
0
 /// <summary>
 /// Removes a chunk from the list
 /// </summary>
 /// <param name="chunk"></param>
 public void Remove(HttpChunk chunk)
 {
 }
		/// <summary>
		/// Removes a chunk from the list
		/// </summary>
		/// <param name="chunk"></param>
		public void Remove(HttpChunk chunk)
		{

		}		
		/// <summary>
		/// Adds an array of chunks to the list
		/// </summary>
		/// <param name="chunks"></param>
		public void AddRange(HttpChunk[] chunks)
		{
			foreach(HttpChunk chunk in chunks)
				this.Add(chunk);
		}
		/// <summary>
		/// Adds a chunk to the list
		/// </summary>
		/// <param name="chunk"></param>
		public void Add(HttpChunk chunk)
		{
			base.InnerList.Add(chunk);
		}
        /// <summary>
        /// Sends the body of a chunked transfer-encoded message
        /// </summary>
        /// <param name="socket"></param>
        /// <param name="abortEvent"></param>
        /// <param name="message"></param>
        internal protected void SendBodyChunked(Socket socket, ManualResetEvent abortEvent, HttpMessage message, EventHandler <HttpMessageProgressEventArgs> onProgress, object stateObject)
        {
            int segmentNumber  = 0;
            int totalBytesSent = 0;

            byte[] body = message.ToByteArray(false /* no headers */, true /* just the body */);

            while (true)
            {
                // if we have sent the entire message then we can abortEvent
                if (totalBytesSent > body.Length)
                {
                    break;
                }

                // start out with a full segment size (this is just the buffer size by which we will send - 8k seems to be really common although i have no idea why other than that it's a power of 2...)
                int chunkSize = MAX_SEGMENT_SIZE_CHUNKED;

                // adjust how much we need to send to complete the message
                if (chunkSize > (body.Length - totalBytesSent))
                {
                    chunkSize = (body.Length - totalBytesSent);
                }

                // bump up the segment number
                segmentNumber++;

                // create a chunk of data to send
                byte[] bytes = new byte[chunkSize];
                Buffer.BlockCopy(body, totalBytesSent, bytes, 0, chunkSize);

                // create a chunk around the data
                HttpChunk chunk = new HttpChunk(bytes);

                // send the data
                int bytesSent = HttpUtils.SendBytes(socket, chunk.ToByteArray());

                // if any data was sent
                if (bytesSent > 0)
                {
                    // figure out how much as data, minus the chunks control chars
                    int actualBytesSent = bytesSent - chunk.GetNonDataByteCount();

                    // if the chunksize is zero or less then we'll return what was sent
                    if (chunkSize > 0)
                    {
                        // all other times it'll not count the non data byte count in the chunk
                        bytesSent = actualBytesSent;
                    }
                }

                // tally the number of bytes we have sent
                totalBytesSent += bytesSent;

                // notify the callback of our progress
                this.OnProgress(onProgress, this, new HttpMessageProgressEventArgs(message, false, bytes, totalBytesSent, stateObject));

                // clear that buffer immediately
                bytes = null;

                // see if we have been instructed to abortEvent reading
                if (abortEvent != null)
                {
                    if (abortEvent.WaitOne(1, false))
                    {
                        throw new HttpMessageWriterAbortedException(message);
                    }
                }
            }
        }
		/// <summary>
		/// Sends the body of a chunked transfer-encoded message
		/// </summary>
		/// <param name="socket"></param>
		/// <param name="abortEvent"></param>
		/// <param name="message"></param>
		internal protected void SendBodyChunked(Socket socket, ManualResetEvent abortEvent, HttpMessage message, EventHandler<HttpMessageProgressEventArgs> onProgress, object stateObject)
		{
			int segmentNumber = 0;
			int totalBytesSent = 0;
			byte[] body = message.ToByteArray(false /* no headers */, true /* just the body */);

			while(true)
			{				
				// if we have sent the entire message then we can abortEvent
				if (totalBytesSent > body.Length)
					break;

				// start out with a full segment size (this is just the buffer size by which we will send - 8k seems to be really common although i have no idea why other than that it's a power of 2...)
				int chunkSize = MAX_SEGMENT_SIZE_CHUNKED;

				// adjust how much we need to send to complete the message
				if (chunkSize > (body.Length - totalBytesSent))
					chunkSize = (body.Length - totalBytesSent);
					
				// bump up the segment number
				segmentNumber++;

				// create a chunk of data to send
				byte[] bytes = new byte[chunkSize];
				Buffer.BlockCopy(body, totalBytesSent, bytes, 0, chunkSize);

				// create a chunk around the data
				HttpChunk chunk = new HttpChunk(bytes);

				// send the data
				int bytesSent = HttpUtils.SendBytes(socket, chunk.ToByteArray());
				
				// if any data was sent
				if (bytesSent > 0)
				{
					// figure out how much as data, minus the chunks control chars
					int actualBytesSent = bytesSent - chunk.GetNonDataByteCount();

					// if the chunksize is zero or less then we'll return what was sent
					if (chunkSize > 0)
						// all other times it'll not count the non data byte count in the chunk
						bytesSent = actualBytesSent;           
				}

				// tally the number of bytes we have sent
				totalBytesSent += bytesSent;

				// notify the callback of our progress
				this.OnProgress(onProgress, this, new HttpMessageProgressEventArgs(message, false, bytes, totalBytesSent, stateObject));
				
				// clear that buffer immediately
				bytes = null;				
							
				// see if we have been instructed to abortEvent reading
				if (abortEvent != null)
					if (abortEvent.WaitOne(1, false))						
						throw new HttpMessageWriterAbortedException(message);									
			}
		}