Example #1
0
        public override async Task <bool> ProcessSharkData(BlockData block)
        {
            if (block.Type == BlockType.CONNECTED)
            {
                if (_request.IsConnect)
                {
                    var resp = new HttpProxyResponse
                    {
                        Status = HttpProxyStatus.CONNECTION_ESTABLISHED
                    };

                    var respData = Encoding.ASCII.GetBytes(resp.ToString());
                    await WriteAsync(respData);
                    await FlushAsync();
                }
                else
                {
                    var headerBlock = new BlockData()
                    {
                        Id = Id, BlockNumber = 0, Type = BlockType.DATA
                    };
                    headerBlock.Data = _request.GenerateHttpHeader();
                    Shark.EncryptBlock(ref headerBlock);
                    await Shark.WriteBlock(headerBlock);
                }

                Logger.LogInformation($"{_request.HostData} connected, {Id}");

#pragma warning disable CS4014
                ProcessData(_request.IsConnect ? 0 : 1);
#pragma warning restore CS4014
            }
            else if (block.Type == BlockType.CONNECT_FAILED)
            {
                var resp = new HttpProxyResponse
                {
                    Status = HttpProxyStatus.BAD_GATEWAY
                };
                var respData = Encoding.ASCII.GetBytes(resp.ToString());

                await WriteAsync(respData);
                await FlushAsync();

                _pipe.Reader.Complete();

                Logger.LogWarning($"Connect to {_request.HostData} failed, {Id}");

                return(false);
            }
            else if (block.Type == BlockType.DATA)
            {
                await WriteAsync(block.Data);
                await FlushAsync();
            }

            return(!_httpFailed);
        }
Example #2
0
        private async Task <HostData> ProcessRequest()
        {
            var        resp          = new HttpProxyResponse();
            var        reader        = _pipe.Reader;
            var        valid         = false;
            var        firstLineDone = false;
            var        noValidData   = false;
            var        headerParsed  = false;
            ReadResult result;

            while (true)
            {
                result = await reader.ReadAsync();

                var buffer   = result.Buffer;
                var position = buffer.PositionOf((byte)'\n');

                // check first char valid
                if (!firstLineDone && buffer.Length > 0)
                {
                    var start = buffer.Start;
                    if (buffer.TryGet(ref start, out ReadOnlyMemory <byte> mem, false))
                    {
                        var first = mem.Span[0];
                        if (first < 'A' || first > 'Z')
                        {
                            break;
                        }
                    }
                }

                while (position != null)
                {
                    var line = Encoding.UTF8.GetString(buffer.Slice(0, position.Value).ToArray()).Replace("\r", "");
                    buffer = buffer.Slice(buffer.GetPosition(1, position.Value));
                    if (!firstLineDone)
                    {
                        valid         = _request.ParseFirstLine(line);
                        firstLineDone = true;
                    }
                    else if (valid)
                    {
                        if (string.IsNullOrEmpty(line))
                        {
                            headerParsed = true;
                            break;
                        }
                        _request.ParseHeader(line);
                    }
                    position = buffer.PositionOf((byte)'\n');
                }

                reader.AdvanceTo(buffer.Start);

                if (headerParsed)
                {
                    break;
                }

                if (result.IsCompleted)
                {
                    noValidData = true;
                    break;
                }
            }

            if (valid && !noValidData)
            {
                Logger.LogInformation($"Connecting to {_request.HostData}, {Id}");
                return(_request.HostData);
            }
            else if (noValidData)
            {
                resp.Status = HttpProxyStatus.BAD_GATEWAY;
                var respData = Encoding.ASCII.GetBytes(resp.ToString());
                await WriteAsync(respData);
                await FlushAsync();

                reader.Complete();

                throw new InvalidOperationException("Http proxy failed, data ended");
            }
            else
            {
                resp.Status = HttpProxyStatus.NOT_IMPLEMENTED;
                var respData = Encoding.ASCII.GetBytes(resp.ToString());
                await WriteAsync(respData);
                await FlushAsync();

                reader.Complete();

                throw new InvalidOperationException("Http proxy failed, not supported");
            }
        }