Ejemplo n.º 1
0
        /// <summary>
        /// Tcp Listen thread
        /// </summary>
        private void ListenLoop(object o)
        {
            ManageListeningContext context = o as ManageListeningContext;

            Trace.WriteLine("Server listener started");

            while (this.running)
            {
                TcpClient client = null;
                try
                {
                    client = context.Listener.AcceptTcpClient();
                }
                catch
                {
                    Trace.TraceError("client side may disconnected");
                    return;
                }

                Trace.WriteLine(string.Format("Client {0} connected",
                                              (client.Client.RemoteEndPoint as IPEndPoint).ToString()));

                lock (context)
                {
                    ManagedStream ms = new ManagedStream();
                    ms.LocalTcpClient = client;
                    ms.PortInfo       = context.PortInfo;
                    ms.RemoteEndpoint = client.Client.RemoteEndPoint as IPEndPoint;
                    Thread task = new Thread(new ParameterizedThreadStart(ReceiveLoop));
                    task.Start(ms);
                    lock (clientStreams)
                    {
                        clientStreams.Add(ms);
                    }
                    context.ReceiveThreads.Add(task);
                }
            }
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Tcp Client thread
        /// </summary>
        /// <param name="o"></param>
        private void ReceiveLoop(object o)
        {
            ManagedStream    ms        = o as ManagedStream;
            TimeSpan         idleTime  = TimeSpan.FromMilliseconds(0);
            TimeSpan         sleepTime = TimeSpan.FromMilliseconds(200);
            Stream           s;
            HttpEndpointBase usedEndpoint = null;

            TcpClient c = ms.LocalTcpClient;

            // id it's using SSL, must authenticate self as server firstly
            if (ms.PortInfo.IsSSL)
            {
                SslStream ssl = new SslStream(c.GetStream(), true);
                try
                {
                    ssl.AuthenticateAsServer(ms.PortInfo.ServerCertificate, false,
                                             System.Security.Authentication.SslProtocols.Tls, false);
                }
                catch (Exception e)
                {
                    lock (eventPipe)
                    {
                        ManagedEvent exp = new ManagedEvent();
                        exp.EventType = EventType.Exception;
                        exp.Exception = e;
                        eventPipe.Enqueue(exp);
                        return;
                    }
                }
                s = ssl;
            }
            else
            {
                s = c.GetStream();
            }
            ms.LocalStream = s;

            using (s)
            {
                while (this.running && idleTime < this.idleTimeout)
                {
                    // if no data available, wait for a while
                    if (c.Available == 0)
                    {
                        Thread.Sleep(sleepTime);
                        idleTime += sleepTime;
                    }
                    // if data coming
                    else
                    {
                        idleTime = TimeSpan.FromMilliseconds(0);

                        byte[] data;

                        // receive data
                        using (var t = new MemoryStream())
                        {
                            var buf = new byte[c.ReceiveBufferSize];

                            lock (ms)
                            {
                                do
                                {
                                    var bytes = s.Read(buf, 0, buf.Length);
                                    t.Write(buf, 0, bytes);
                                } while (c.Available > 0);

                                ms.LastUsed = DateTime.Now;
                            }

                            data = t.ToArray();
                        }

                        // pack as ManagedEvent
                        var e = new ManagedEvent();
                        e.Data      = data;
                        e.Sender    = c.Client.RemoteEndPoint as IPEndPoint;
                        e.EventType = EventType.IncomingRequest;

                        //parse the endpoint
                        string str = Encoding.UTF8.GetString(data);
                        e.Text = str;
                        // try to parse as http
                        try
                        {
                            HttpRequest req = new HttpRequest();
                            req.Parse(e.Text);
                            e.ParsedHttpRequest = req;
                        }
                        catch
                        {
                        }
                        if (usedEndpoint == null)
                        {
                            if (e.ParsedHttpRequest == null)
                            {
                                //first message is not http
                                e.EventType = EventType.Exception;
                                e.Exception = new Exception("The 1st request from this context is not an HTTP Request");
                            }
                            else
                            {
                                lock (m_endpoints)
                                {
                                    if (m_endpoints.ContainsKey(ms.PortInfo.Port))
                                    {
                                        List <HttpEndpointBase> hebs = m_endpoints[ms.PortInfo.Port];
                                        // find specific endpoint
                                        var q =
                                            from r in hebs
                                            where (
                                                from u in r.Urls
                                                where e.ParsedHttpRequest.RequestUrl.Path.ToLower().Contains(u.ToLower())
                                                select u
                                                ).Count() > 0
                                            select r;
                                        // if found
                                        if (q.Any())
                                        {
                                            e.ServiceEndpoint = (HttpEndpointBase)q.First();
                                            usedEndpoint      = e.ServiceEndpoint;
                                        }
                                    }
                                }
                            }
                        }
                        else
                        {
                            e.ServiceEndpoint = usedEndpoint;
                        }
                        // if service is auto-run, dispatch to its own pipe
                        if (e.ServiceEndpoint != null && e.ServiceEndpoint.AutoRun)
                        {
                            lock (e.ServiceEndpoint.eventPipe)
                            {
                                e.ServiceEndpoint.eventPipe.Enqueue(e);
                            }
                        }
                        else
                        {
                            lock (eventPipe)
                            {
                                eventPipe.Enqueue(e);
                            }
                        }
                    }
                }
            }
        }