private void ProcessHeaders() { do { var idxNewline = _buffer.IndexOf(0x0a); if (idxNewline == -1) { return; } var data = _buffer.Get(idxNewline + 1); var line = new string(Encoding.UTF8.GetChars(data)).Trim(); if (line == "") { _state = HttpParsingState.Body; ProcessBody(); break; } else { ProcessHeader(line); } } while (true); }
internal bool ProcessResponse(byte[] data) { lock (_lock) { // This makes the response object re-entrant, even though that's not how I would // use it. Change suggested by [email protected]. if (_state == HttpParsingState.Complete || _state == HttpParsingState.Error) _state = HttpParsingState.Empty; _buffer.Put(data); switch (_state) { case HttpParsingState.Empty: case HttpParsingState.ResultCode: _state = HttpParsingState.ResultCode; ProcessResultCode(); break; case HttpParsingState.Headers: ProcessHeaders(); break; case HttpParsingState.Body: ProcessBody(); break; default: // shouldn't happen, but just in case we get here with Complete or Error state return true; } // return true for completed parsing, false if we need more data return _state == HttpParsingState.Complete || _state == HttpParsingState.Error; } }
private void ProcessResultCode() { // find the first newline var idxNewline = _buffer.IndexOf(0x0a); if (idxNewline == -1) { return; // need more data } // pull out the result line var data = _buffer.Get(idxNewline + 1); var line = new string(Encoding.UTF8.GetChars(data)); // parse it var tokens = line.Trim().Split(' '); if (tokens.Length > 1) { this.StatusCode = (HttpStatusCode)int.Parse(tokens[1]); } if (tokens.Length > 2) { this.Reason = tokens[2]; } _state = HttpParsingState.Headers; // Fall through to process whatever headers we might already have in the buffer ProcessHeaders(); }
void ProcessHtmlPostBody() { //parse body int transferedBytes = _context.RecvByteTransfer; int len1 = transferedBytes - _readPos; if (!_uploadCanceled && len1 > 0) { //TODO review here //write to file first, or write to mem *** //if we upload large content, we should write to file // if (UploadTempFileName != null) { //write data to file if (_uploadTempFile == null) { _uploadTempFile = new FileStream(UploadTempFileName, FileMode.Create); } byte[] buff = new byte[len1]; //TODO: reuse the buffer _context.RecvCopyTo(_readPos, buff, len1); _uploadTempFile.Write(buff, 0, len1); _uploadTempFile.Flush();//** ensure write to disk } else { //write to mem byte[] buff = new byte[len1]; //TODO: reuse the buffer _context.RecvCopyTo(_readPos, buff, len1); AddMsgBody(buff, 0, len1); } } _contentByteCount += len1; //*** _readPos = 0; //read until end of buffer //System.Diagnostics.Debug.WriteLine("expect" + ContentLength + "tx:" + _contentByteCount + ",rem:" + (ContentLength - _contentByteCount)); if (!IsMsgBodyComplete) { return; } //finish //close the file stream if (_uploadTempFile != null) { _uploadTempFile.Close(); _uploadTempFile.Dispose(); _uploadTempFile = null; } _parseState = HttpParsingState.Complete; }
private void ProcessHeaders(string[] lines, out int i) { for (i = 0; i < lines.Length; i++) { if (lines[i] == "") { _parsingState = HttpParsingState.Data; return; } ProcessHeader(lines[i]); } }
private void ProcessCountedBody(int contentLength) { if (_buffer.Size < contentLength) { return; // need more data } try { this.SetBody(_buffer.Get(_buffer.Size)); _state = HttpParsingState.Complete; } catch (Exception) { _state = HttpParsingState.Error; } }
int ParseHttpRequestHeader() { //start from pos0 int readpos = 0; int lim = _context.RecvByteTransfer - 1; int i = 0; for (; i <= lim; ++i) { //just read if (_context.ReadByte(i) == '\r' && _context.ReadByte(i + 1) == '\n') { //each line //translate if (i - readpos < 512) { //copy _context.RecvCopyTo(readpos, _tmpReadBuffer, i - readpos); //translate string line = Encoding.UTF8.GetString(_tmpReadBuffer, 0, i - readpos); readpos = i + 2; i++; //skip \n //translate header *** if (line == "") { //complete http header _parseState = HttpParsingState.Body; return(readpos); } else { //parse header line AddReqHeader(line); } } else { //just skip? //skip too long line readpos = i + 2; i++; //skip \n } } } return(readpos); }
private void ProcessBody() { var contentLength = -1; if (this.Headers.Contains("Content-Length")) { contentLength = int.Parse((string)this.Headers["Content-Length"]); } if (contentLength == -1) { Debug.WriteLine("No content length was provided. Chunked encoding and transfer encoding are not supported."); _state = HttpParsingState.Error; } else { ProcessCountedBody(contentLength); } }
/// <exception cref="Exception"></exception> private void ProcessMetaData(string line) { if (string.IsNullOrEmpty(line)) { return; } var fields = line.Split(" "); Method = Util.ProcessMethod(fields[0]); Url = new Url(fields[1]); try { HttpVersion = float.Parse(fields[2].Split("/")[1]); } catch (Exception e) { throw new Exception("Invalid HTTP version!", e); } _parsingState = HttpParsingState.Header; }
internal bool ProcessResponse(byte[] data) { lock (_lock) { // This makes the response object re-entrant, even though that's not how I would // use it. Change suggested by [email protected]. if (_state == HttpParsingState.Complete || _state == HttpParsingState.Error) { _state = HttpParsingState.Empty; } _buffer.Put(data); switch (_state) { case HttpParsingState.Empty: case HttpParsingState.ResultCode: _state = HttpParsingState.ResultCode; ProcessResultCode(); break; case HttpParsingState.Headers: ProcessHeaders(); break; case HttpParsingState.Body: ProcessBody(); break; default: // shouldn't happen, but just in case we get here with Complete or Error state return(true); } // return true for completed parsing, false if we need more data return(_state == HttpParsingState.Complete || _state == HttpParsingState.Error); } }
void ProcessHtmlPostBody(int readpos, Internal.RecvIO recvIO) { //parse body int transferedBytes = recvIO.BytesTransferred; int remaining = transferedBytes - readpos; if (!IsMsgBodyComplete) { int wantBytes = ContentLength - contentByteCount; if (wantBytes <= remaining) { //complete here byte[] buff = new byte[wantBytes]; recvIO.CopyTo(readpos, buff, wantBytes); //add to req AddMsgBody(buff, 0, wantBytes); //complete this.parseState = HttpParsingState.Complete; return; } else { //continue read if (remaining > 0) { byte[] buff = new byte[remaining]; recvIO.CopyTo(readpos, buff, remaining); //add to req AddMsgBody(buff, 0, remaining); } return; } } this.parseState = HttpParsingState.Complete; }
private void ProcessBody() { var contentLength = -1; if (this.Headers.Contains("Content-Length")) contentLength = int.Parse((string)this.Headers["Content-Length"]); if (contentLength == -1) { Debug.Print("No content length was provided. Chunked encoding and transfer encoding are not supported."); _state = HttpParsingState.Error; } else { ProcessCountedBody(contentLength); } }
private void ProcessResultCode() { // find the first newline var idxNewline = _buffer.IndexOf(0x0a); if (idxNewline == -1) return; // need more data // pull out the result line var data = _buffer.Get(idxNewline + 1); var line = new string(Encoding.UTF8.GetChars(data)); // parse it var tokens = line.Trim().Split(' '); if (tokens.Length > 1) this.StatusCode = (HttpStatusCode)int.Parse(tokens[1]); if (tokens.Length > 2) this.Reason = tokens[2]; _state = HttpParsingState.Headers; // Fall through to process whatever headers we might already have in the buffer ProcessHeaders(); }
private void ProcessCountedBody(int contentLength) { if (_buffer.Size < contentLength) return; // need more data try { this.SetBody(_buffer.Get(_buffer.Size)); _state = HttpParsingState.Complete; } catch (Exception) { _state = HttpParsingState.Error; } }
internal override void Reset() { _parseState = HttpParsingState.Head; base.Reset();//** }
private void ProcessHeaders() { do { var idxNewline = _buffer.IndexOf(0x0a); if (idxNewline == -1) return; var data = _buffer.Get(idxNewline + 1); var line = new string(Encoding.UTF8.GetChars(data)).Trim(); if (line == "") { _state = HttpParsingState.Body; ProcessBody(); break; } else ProcessHeader(line); } while (true); }
int ParseHttpRequestHeader(Internal.RecvIO recvIO) { //start from pos0 int readpos = 0; int lim = recvIO.BytesTransferred - 1; int i = 0; for (; i <= lim; ++i) { //just read if (recvIO.ReadByte(i) == '\r' && recvIO.ReadByte(i + 1) == '\n') { //each line //translate if (i - readpos < 512) { //copy recvIO.CopyTo(readpos, tmpReadBuffer, i - readpos); //translate string line = Encoding.UTF8.GetString(tmpReadBuffer, 0, i - readpos); readpos = i + 2; i++; //skip \n //translate header *** if (line == "") { //complete http header parseState = HttpParsingState.Body; return readpos; } else { //parse header line AddReqHeader(line); } } else { //just skip? //skip too long line readpos = i + 2; i++; //skip \n } } } return readpos; }