コード例 #1
0
        /// <summary>
        /// Create a secure <see cref="IHttpClientContext"/>.
        /// </summary>
        /// <param name="socket">Client socket (accepted by the <see cref="HttpListener"/>).</param>
        /// <param name="certificate">HTTPS certificate to use.</param>
        /// <param name="protocol">Kind of HTTPS protocol. Usually TLS or SSL.</param>
        /// <param name="requireClientCert">Require an SSL client certificate</param>
        /// <returns>
        /// A created <see cref="IHttpClientContext"/>.
        /// </returns>
        public IHttpClientContext CreateSecureContext(Socket socket, X509Certificate certificate, SslProtocols protocol, bool requireClientCert)
        {
            var networkStream  = new ReusableSocketNetworkStream(socket, true);
            var remoteEndPoint = (IPEndPoint)socket.RemoteEndPoint;

            ClientCertificate clientCertificate = null;

            SslStream sslStream = new SslStream(networkStream, false,
                                                delegate(object sender, X509Certificate receivedCertificate, X509Chain chain, SslPolicyErrors sslPolicyErrors)
            {
                clientCertificate = new ClientCertificate(receivedCertificate, chain, sslPolicyErrors);
                return(!(requireClientCert && receivedCertificate == null));
            }
                                                );

            try
            {
                sslStream.AuthenticateAsServer(certificate, requireClientCert, protocol, false);
                return(CreateContext(true, remoteEndPoint, clientCertificate, sslStream, socket));
            }
            catch (IOException err)
            {
                if (UseTraceLogs)
                {
                    _logWriter.Write(this, LogPrio.Trace, err.Message);
                }
            }
            catch (ObjectDisposedException err)
            {
                if (UseTraceLogs)
                {
                    _logWriter.Write(this, LogPrio.Trace, err.Message);
                }
            }
            catch (AuthenticationException err)
            {
                _logWriter.Write(this, LogPrio.Warning, (err.InnerException != null) ? err.InnerException.Message : err.Message);
            }

            return(null);
        }
コード例 #2
0
        /// <summary>
        /// Initializes a new instance of the <see cref="HttpClientContext"/> class.
        /// </summary>
        /// <param name="secured">true if the connection is secured (SSL/TLS)</param>
        /// <param name="remoteEndPoint">client that connected.</param>
        /// <param name="stream">Stream used for communication</param>
        /// <param name="clientCertificate">Client security certificate</param>
        /// <param name="parserFactory">Used to create a <see cref="IHttpRequestParser"/>.</param>
        /// <param name="bufferSize">Size of buffer to use when reading data. Must be at least 4096 bytes.</param>
        /// <param name="socket">Client socket</param>
        /// <exception cref="SocketException">If <see cref="Socket.BeginReceive(byte[],int,int,SocketFlags,AsyncCallback,object)"/> fails</exception>
        /// <exception cref="ArgumentException">Stream must be writable and readable.</exception>
        public HttpClientContext(bool secured, IPEndPoint remoteEndPoint, Stream stream,
                                 ClientCertificate clientCertificate, IRequestParserFactory parserFactory, int bufferSize, Socket socket)
        {
            Check.Require(remoteEndPoint, "remoteEndPoint");
            Check.NotEmpty(remoteEndPoint.Address.ToString(), "remoteEndPoint.Address");
            Check.Require(stream, "stream");
            Check.Require(parserFactory, "parser");
            Check.Min(4096, bufferSize, "bufferSize");
            Check.Require(socket, "socket");

            if (!stream.CanWrite || !stream.CanRead)
            {
                throw new ArgumentException("Stream must be writable and readable.");
            }

            _bufferSize                  = bufferSize;
            RemoteAddress                = remoteEndPoint.Address.ToString();
            RemotePort                   = remoteEndPoint.Port.ToString();
            _log                         = NullLogWriter.Instance;
            _parser                      = parserFactory.CreateParser(_log);
            _parser.RequestCompleted    += OnRequestCompleted;
            _parser.RequestLineReceived += OnRequestLine;
            _parser.HeaderReceived      += OnHeaderReceived;
            _parser.BodyBytesReceived   += OnBodyBytesReceived;
            _localEndPoint               = (IPEndPoint)socket.LocalEndPoint;

            HttpRequest request = new HttpRequest();

            request._remoteEndPoint = remoteEndPoint;
            request.Secure          = secured;
            _currentRequest         = request;

            IsSecured          = secured;
            _stream            = stream;
            _clientCertificate = clientCertificate;
            _buffer            = new byte[bufferSize];
        }
コード例 #3
0
 /// <summary>
 /// Create a new context.
 /// </summary>
 /// <param name="isSecured">true if HTTPS is used.</param>
 /// <param name="endPoint">Remote client</param>
 /// <param name="clientCertificate">Client security certificate</param>
 /// <param name="stream">Network stream, <see cref="HttpClientContext"/> uses <see cref="ReusableSocketNetworkStream"/>.</param>
 /// <param name="socket">Client socket</param>
 /// <returns>A new context (always).</returns>
 protected virtual HttpClientContext CreateNewContext(bool isSecured, IPEndPoint endPoint, ClientCertificate clientCertificate,
                                                      Stream stream, Socket socket)
 {
     return(new HttpClientContext(isSecured, endPoint, stream, clientCertificate, _factory, _bufferSize, socket));
 }
コード例 #4
0
        /// <summary>
        /// Create a new context.
        /// </summary>
        /// <param name="isSecured">true if socket is running HTTPS.</param>
        /// <param name="endPoint">Client that connected</param>
        /// <param name="clientCertificate">Client security certificate</param>
        /// <param name="stream">Network/SSL stream.</param>
        /// <param name="socket">Client socket</param>
        /// <returns>A context.</returns>
        protected HttpClientContext CreateContext(bool isSecured, IPEndPoint endPoint, ClientCertificate clientCertificate, Stream stream, Socket socket)
        {
            HttpClientContext context;

            lock (_contextQueue)
            {
                if (_contextQueue.Count > 0)
                {
                    context = _contextQueue.Dequeue();
                    if (!context.IsAvailable)
                    {
                        context = CreateNewContext(isSecured, endPoint, clientCertificate, stream, socket);
                        context.Disconnected    += OnFreeContext;
                        context.RequestReceived += OnRequestReceived;
                        context.EndWhenDone      = true;
                    }
                }
                else
                {
                    context = CreateNewContext(isSecured, endPoint, clientCertificate, stream, socket);
                    context.Disconnected    += OnFreeContext;
                    context.RequestReceived += OnRequestReceived;
                }
            }

            context.Assign(stream, (IPEndPoint)socket.LocalEndPoint);
            context.IsSecured     = isSecured;
            context.RemotePort    = endPoint.Port.ToString();
            context.RemoteAddress = endPoint.Address.ToString();
            context.Start();
            return(context);
        }