Ejemplo n.º 1
0
        /// <summary>创建会话</summary>
        /// <param name="client"></param>
        /// <returns></returns>
        protected virtual TcpSession CreateSession(Socket client)
        {
            var session = new TcpSession(this, client);

            // 服务端不支持掉线重连
            session.AutoReconnect      = 0;
            session.Log                = Log;
            session.LogSend            = LogSend;
            session.LogReceive         = LogReceive;
            session.StatSend.Parent    = StatSend;
            session.StatReceive.Parent = StatReceive;
            session.Packet             = SessionPacket?.Create();
            session.ProcessAsync       = ProcessAsync;

            return(session);
        }
Ejemplo n.º 2
0
        /// <summary>创建会话</summary>
        /// <param name="remoteEP"></param>
        /// <returns></returns>
        public virtual ISocketSession CreateSession(IPEndPoint remoteEP)
        {
            if (Disposed)
            {
                throw new ObjectDisposedException(GetType().Name);
            }

            var sessions = _Sessions;

            if (sessions == null)
            {
                return(null);
            }

            // 平均执行耗时260.80ns,其中55%花在sessions.Get上面,Get里面有加锁操作

            if (!Active)
            {
                // 根据目标地址适配本地IPv4/IPv6
                Local.Address = Local.Address.GetRightAny(remoteEP.AddressFamily);

                if (!Open())
                {
                    return(null);
                }
            }

            // 需要查找已有会话,已有会话不存在时才创建新会话
            var session = sessions.Get(remoteEP + "");

            if (session != null)
            {
                return(session);
            }

            // 相同远程地址可能同时发来多个数据包,而底层采取多线程方式同时调度,导致创建多个会话
            lock (sessions)
            {
                // 需要查找已有会话,已有会话不存在时才创建新会话
                session = sessions.Get(remoteEP + "");
                if (session != null)
                {
                    return(session);
                }

                var us = new UdpSession(this, remoteEP);
                us.Log        = Log;
                us.LogSend    = LogSend;
                us.LogReceive = LogReceive;
                // UDP不好分会话统计
                //us.StatSend.Parent = StatSend;
                //us.StatReceive.Parent = StatReceive;
                us.Packet = SessionPacket?.Create();

                session = us;
                if (sessions.Add(session))
                {
                    //us.ID = g_ID++;
                    // 会话改为原子操作,避免多线程冲突
                    us.ID = Interlocked.Increment(ref g_ID);
                    us.Start();

                    if (StatSession != null)
                    {
                        StatSession.Increment(1);
                    }

                    // 触发新会话事件
                    NewSession?.Invoke(this, new SessionEventArgs {
                        Session = session
                    });
                }
            }

            return(session);
        }