public void remove(AsyncSocketUserToken userToken)
 {
     lock (userTokenList)
     {
         this.userTokenList.Remove(userToken);
     }
 }
 public void add(AsyncSocketUserToken userToken)
 {
     lock (userTokenList)
     {
         this.userTokenList.Add(userToken);
     }
 }
 public void copyList(ref AsyncSocketUserToken[] array)
 {
     lock (userTokenList)
     {
         array = new AsyncSocketUserToken[this.userTokenList.Count];
         this.userTokenList.CopyTo(array);
     }
 }
        private void processReceive(SocketAsyncEventArgs args)
        {
            AsyncSocketUserToken token = args.UserToken as AsyncSocketUserToken;

            if (token.ConnectedSocket == null)
            {
                return;
            }
            try
            {
                //接收数据缓冲区的偏移量
                int offset = token.ReceiveAysncEventArgs.Offset;
                //当前缓冲区接收到数据的总量
                int count = token.ReceiveAysncEventArgs.BytesTransferred;
                //接收到数据后,更新活动时间
                token.ActiveDateTime = DateTime.Now;

                if (token.ReceiveAysncEventArgs.BytesTransferred > 0 && token.ReceiveAysncEventArgs.SocketError == SocketError.Success)
                {
                    if (count > 0)
                    {
                        if (!token.InvokeElement.processReceive(token.ReceiveAysncEventArgs.Buffer, offset, count))
                        {
                            closeClientSocket(token, true);
                        }
                        else
                        {
                            bool willRaiseEvent = token.ConnectedSocket.ReceiveAsync(token.ReceiveAysncEventArgs);
                            if (!willRaiseEvent)
                            {
                                processReceive(token.ReceiveAysncEventArgs);
                            }
                        }
                    }
                    else
                    {
                        bool willRaiseEvent = token.ConnectedSocket.ReceiveAsync(token.ReceiveAysncEventArgs);
                        if (!willRaiseEvent)
                        {
                            processReceive(token.ReceiveAysncEventArgs);
                        }
                    }
                }
                else
                {
                    closeClientSocket(token, true);
                }
            }
            catch (Exception e)
            {
                if (SysCache.ShowErrorLog)
                {
                    string error = string.Format("程序处理接收时出错,错误信息:{0}", e.Message);
                    LogHelper.Error(error);
                }
                closeClientSocket(token, true);
            }
        }
 public void push(AsyncSocketUserToken item)
 {
     if (item == null)
     {
         throw new ArgumentException("item added to a AsyncSocketUserToken is not null!");
     }
     lock (userTokenPool)
     {
         this.userTokenPool.Push(item);
     }
 }
        private void init()
        {
            AsyncSocketUserToken userToken;

            for (int i = 0; i < numConnections; i++)
            {
                userToken = new AsyncSocketUserToken(asyncReceiveBufferSize);
                userToken.ReceiveAysncEventArgs.Completed += new EventHandler <SocketAsyncEventArgs>(IO_Complete);
                userToken.SendAysncEvetnArgs.Completed    += new EventHandler <SocketAsyncEventArgs>(IO_Complete);
                this.asyncSocketUserTokenPool.push(userToken);
            }
        }
        private void IO_Complete(Object sender, SocketAsyncEventArgs args)
        {
            AsyncSocketUserToken userToken = args.UserToken as AsyncSocketUserToken;

            userToken.ActiveDateTime = DateTime.Now;
            try
            {
                lock (userToken)
                {
                    if (args.LastOperation == SocketAsyncOperation.Receive)
                    {
                        processReceive(args);
                    }
                    else if (args.LastOperation == SocketAsyncOperation.Send)
                    {
                        processSend(args);
                    }
                    else
                    {
                        if (SysCache.ShowErrorLog)
                        {
                            if (userToken.ConnectedSocket.RemoteEndPoint != null)
                            {
                                string error = string.Format("程序的最后一次操作在{0}并不是receive或者send", userToken.ConnectedSocket.RemoteEndPoint.ToString());
                                LogHelper.Error(error);
                            }
                        }
                    }
                }
            }
            catch (Exception e)
            {
                if (SysCache.ShowErrorLog)
                {
                    string error = string.Format("程序处理IO时出错,错误信息{0}", e.Message);
                    LogHelper.Error(error);
                }
                closeClientSocket(userToken, true);
            }
        }
        private bool processSend(SocketAsyncEventArgs args)
        {
            AsyncSocketUserToken token = args.UserToken as AsyncSocketUserToken;

            if (token.ConnectedSocket == null)
            {
                return(false);
            }
            try
            {
                if (args.SocketError == SocketError.Success)
                {
                    //设置发送的数据
                    //接收到什么数据就发送什么数据
                    //args.SetBuffer(args.Offset, args.BytesTransferred);
                    //设置数据发送缓冲区后,可以在这里进行下一次的数据发送
                    return(token.InvokeElement.sendComplete());
                    //return false;
                }
                else
                {
                    closeClientSocket(token, true);
                    return(false);
                }
            }
            catch (Exception e)
            {
                if (SysCache.ShowErrorLog)
                {
                    string error = string.Format("程序处理发送时出错,错误信息{0}", e.Message);
                    LogHelper.Error(error);
                }
                closeClientSocket(token, true);
                return(false);
            }
        }
        public void closeClientSocket(AsyncSocketUserToken token, bool isUpdate)
        {
            if (token.DeviceList != null)
            {
                if (token.isClose)
                {
                    if (SysCache.ShowInfoLog)
                    {
                        string info = string.Format(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ":[" + token.ConnectedSocket.RemoteEndPoint.ToString() + "]:DTU通信服务,客户端{0}正在关闭", token.DeviceList.DeviceNo);
                        ShowLogData.add(info);
                        LogHelper.Info(info);
                    }
                    return;
                }
                token.isClose = true;

                if (SysCache.ShowInfoLog)
                {
                    string info = string.Format(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ":[" + token.ConnectedSocket.RemoteEndPoint.ToString() + "]:DTU通信服务,客户端{0},断开连接", token.DeviceList.DeviceNo);
                    ShowLogData.add(info);
                    LogHelper.Info(info);
                }

                if (isUpdate)
                {
                    token.DeviceList.Online        = 0;
                    token.DeviceList.LastUpdate    = DateTime.Now;
                    token.DeviceList.TerminalState = "设备断开连接";
                    token.InvokeElement.proxySendDeviceList(token.DeviceList, null);

                    /*未完成 更新终端状态*/
                    token.InvokeElement.updateDeviceList(token.DeviceList);
                }

                List <string> list = OnlineDeviceService.GetDeviceNoSubList(token.DeviceList.Id);
                if (list != null && list.Count > 0)
                {
                    foreach (string str in list)
                    {
                        Device device = OnlineDeviceService.GetOnline(str);
                        if (device != null)
                        {
                            if (SysCache.ShowInfoLog)
                            {
                                string info = string.Format(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ":[" + token.ConnectedSocket.RemoteEndPoint.ToString() + "]:DTU通信服务,客户端{0},从站断开连接,主站{1}断开", device.DeviceNo, token.DeviceList.DeviceNo);
                                ShowLogData.add(info);
                                LogHelper.Info(info);
                            }

                            device.Online        = 0;
                            device.LastUpdate    = DateTime.Now;
                            device.TerminalState = "设备断开连接";
                            token.InvokeElement.proxySendDeviceList(device, null);

                            token.InvokeElement.updateDeviceList(device);
                        }
                    }
                }

                string deviceNo = DeviceModule.GetFullDeviceNoByID(token.DeviceList.Id);
                OnlineDeviceService.RemoveOnline(deviceNo);
            }

            //修改于 2015-4-20
            if (token.ConnectedSocket == null)
            {
                return;
            }

            try
            {
                token.ConnectedSocket.Shutdown(SocketShutdown.Both);
            }
            catch (SocketException)
            {
            }
            catch (NullReferenceException e)
            {
                if (SysCache.ShowErrorLog)
                {
                    string error = string.Format("程序关闭连接时出错,错误信息{0}", e.Message);
                    LogHelper.Error(error);
                }
            }

            /*
             *
             * if (showInfoLog)
             * {
             *  string info = string.Format(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ":[" + token.ConnectedSocket.RemoteEndPoint.ToString() + "]:DTU通信服务,释放信号量资源");
             *  ShowLogData.add(info);
             *  LogHelper.Info(info);
             * }
             */
            //start update by kqz 2017-2-3修改,由之前的注释修改成不注释
            //由于在关闭掉客户端的时候,没有将此连接上来的客户端从已经连接的客户端集合中删除掉,所以导致一个客户端成功连接上后,再次断开
            //下次连接,如果IP地址不同则连接不成功现象。
            //并将此客户端资源回收到池中
            //释放信号量资源
            this.maxConnection.Release();//update by kqz 2017-3-28 9:34 将原来的注释取消
            this.asyncSocketUserTokenPool.push(token);
            if (showInfoLog)
            {
                string info = string.Format(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ":[" + token.ConnectedSocket.RemoteEndPoint.ToString() + "]:DTU通信服务,并将此客户端资源回收到池中,池中剩余数量{0}", asyncSocketUserTokenPool.Count);
                ShowLogData.add(info);
                LogHelper.Info(info);
            }

            //正在连接的集合中祛除此客户端信息
            this.asyncSocketUserTokenList.remove(token);
            if (showInfoLog)
            {
                string info = string.Format(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ":[" + token.ConnectedSocket.RemoteEndPoint.ToString() + "]:DTU通信服务,正在连接的集合中祛除此客户端信息,剩余连接数量{0}", asyncSocketUserTokenList.count());
                ShowLogData.add(info);
                LogHelper.Info(info);
            }
            // end update by kqz 2017-2-3修改,由之前的注释修改成不注释
            token.ConnectedSocket.Close();
            token.ConnectedSocket = null;
            token.isClose         = false;
        }
        private void processAccepte(SocketAsyncEventArgs args)
        {
            //update by kqz 2017-3-27
            try
            {
                //从池中取出一个空闲的异步操作对象
                AsyncSocketUserToken token = this.asyncSocketUserTokenPool.pop();
                //将此对象添加到正在连接集合中
                this.asyncSocketUserTokenList.add(token);

                //设置保存连接socket
                token.ConnectedSocket = args.AcceptSocket;
                token.ConnectedTime   = DateTime.Now;
                token.ActiveDateTime  = DateTime.Now;

                try
                {
                    //对连接后的socket对象投递接收请求
                    //投递异步操作对象AsyncSocketUserToken中的ReceiveAysncEventArgs
                    //进行数据接收处理时,也是用这个ReceiveAysncEventArgs
                    if (SysCache.ShowInfoLog)
                    {
                        if (token.ConnectedSocket.RemoteEndPoint != null)
                        {
                            LogHelper.Info(string.Format("DTU通信服务连接上一个客户端,信息为{0}", token.ConnectedSocket.RemoteEndPoint.ToString()));
                            ShowLogData.add(string.Format("DTU通信服务连接上一个客户端,信息为{0}", token.ConnectedSocket.RemoteEndPoint.ToString()));
                        }
                    }

                    //ShowLogData.add(string.Format("剩余线程池数量:{0}", this.asyncSocketUserTokenPool.Count));

                    #region add 2015-4-21 当连接上来后,回传一个"%"
                    if (token.InvokeElement == null)
                    {
                        token.InvokeElement = new DTUInvokeElement(this, token);
                    }
                    //token.InvokeElement.SendData.addData(ProtocolKey.SendHeartThrob);
                    //token.InvokeElement.send();
                    #endregion
                    bool willRaiseEvent = token.ConnectedSocket.ReceiveAsync(token.ReceiveAysncEventArgs);

                    if (!willRaiseEvent)
                    {
                        lock (token)
                        {
                            processReceive(token.ReceiveAysncEventArgs);
                        }
                    }
                }
                catch (Exception e)
                {
                    if (SysCache.ShowErrorLog)
                    {
                        string error = "";
                        if (token.ConnectedSocket.RemoteEndPoint != null)
                        {
                            error = string.Format("DTU通信服务客户端{0}在投递接收请求时出错,错误信息为{1}", token.ConnectedSocket.RemoteEndPoint.ToString(), e.Message);
                        }
                        else
                        {
                            error = string.Format("在投递接收请求时出错,错误信息为{0}", e.Message);
                        }
                        LogHelper.Error(error);
                    }
                    closeClientSocket(token, true);
                }
                finally
                {
                    //数据是否处理成功,都要进行下一次的异步接收
                    startAccept(args);
                }
            }
            catch (Exception ex)
            {
                LogHelper.Error("----------------异常信息为---------" + ex.Message + "===" + ex.InnerException.Message);
            }
        }