/// <summary> /// Close the socket associated with the client. /// </summary> /// <param name="e">SocketAsyncEventArg associated with the completed send/receive operation.</param> private void CloseClient(AsyncUserToken token) { lock (token) { if (token == null || _clients.ContainsKey(token.SessionId) == false) { return; } try { DynamicBufferManager.Remove(token.SessionId); var args = token.AsynSocketArgs; //释放资源 //this.semaphoreAcceptedClients.Release(); //回收到pool中 this.readWritePool.Push(args); RemoveClient(token.SessionId); ShowLog($"{token.Socket?.RemoteEndPoint?.ToString()} 连接已关闭"); token.Dispose(); } catch (Exception) { } } }
private void ProcessReceive(SocketAsyncEventArgs e) { try { if (e.SocketError == SocketError.Success && e.BytesTransferred > 0) { if (IsSplitPack) { DynamicBufferManager.WriteBuffer(_sessionId, e.Buffer, e.Offset, e.BytesTransferred); var list = DynamicBufferManager.PopPackets(_sessionId); foreach (var item in list) { RaiseOnReceive(new DataReceivedArgs(_sessionId, item)); } //int index = 0; //while (index < data.Length - 4) //{ // var lenght = BitConverter.ToInt32(data, index); // if (NetByteOrder) // lenght = System.Net.IPAddress.NetworkToHostOrder(lenght); //把网络字节顺序转为本地字节顺序 // if (lenght > 0 && index + lenght + 4 <= data.Length) // { // var splitData = new byte[lenght]; // Array.Copy(data, index + 4, splitData, 0, lenght); // index = index + lenght + 4; // RaiseOnReceive(new DataReceivedArgs(splitData)); // } // else // { // break; // } //} } else { var data = new byte[e.BytesTransferred]; Array.Copy(e.Buffer, e.Offset, data, 0, e.BytesTransferred); RaiseOnReceive(new DataReceivedArgs(data)); } if (_socket.ReceiveAsync(e) == false) { ProcessReceive(e); } } else { this.ProcessError(e); } } catch (Exception) { this.ProcessError(e); } }
/// <summary> /// 写入数据到动态缓存中 /// </summary> /// <param name="sessionId"></param> /// <param name="buffer"></param> /// <param name="offset"></param> /// <param name="count"></param> public static void WriteBuffer(string sessionId, byte[] buffer, int offset, int count) { DynamicBufferManager buffManager = null; if (_hashTable.ContainsKey(sessionId) == false) { buffManager = new DynamicBufferManager(); _hashTable.Add(sessionId, buffManager); } else { buffManager = _hashTable[sessionId] as DynamicBufferManager; } buffManager.WriteBuffer(buffer, offset, count); }
/// <summary> /// Disposes the instance of SocketClient. /// </summary> public void Dispose() { try { if (_heartBeatsTimer != null) { _heartBeatsTimer.Dispose(); _heartBeatsTimer = null; } DynamicBufferManager.Remove(_sessionId); _socket?.Disconnect(false); } catch (Exception) { } }
/// <summary> /// This method is invoked when an asynchronous receive operation completes. /// If the remote host closed the connection, then the socket is closed. /// If data was received then the data is echoed back to the client. /// </summary> /// <param name="e">SocketAsyncEventArg associated with the completed receive operation.</param> private void ProcessReceive(SocketAsyncEventArgs e) { try { AsyncUserToken token = e.UserToken as AsyncUserToken; token.LastExchangeTime = Environment.TickCount; token.AsynSocketArgs = e; // Check if the remote host closed the connection. if (e.BytesTransferred > 0) { if (e.SocketError == SocketError.Success) { if (IsSplitPack) { //if (e.BytesTransferred == 16) //{ // //组装心跳 todo:暂时使用,兼容以前的客户端,以前的通讯组件心跳包没加长度 // var buff = new byte[20]; // Array.Copy(BitConverter.GetBytes(16), 0, buff, 0, 4); // Array.Copy(e.Buffer, e.Offset, buff, 4, e.BytesTransferred); // DynamicBufferManager.WriteBuffer(token.SessionId, buff, 0, buff.Length); //} //else { DynamicBufferManager.WriteBuffer(token.SessionId, e.Buffer, e.Offset, e.BytesTransferred); } var list = DynamicBufferManager.PopPackets(token.SessionId); foreach (var item in list) { if (IsUseHeartBeatCertificate && token.IsCertified == false) { token.IsCertified = ValidHeartBeats(item); if (token.IsCertified) { continue; } else { ShowLog("客户端未通过心跳验证,关闭该连接"); CloseClient(token); return; } } else if (IsUseHeartBeatCertificate && item.Length == 16) { //若客户端发送的是心跳数据则跳过 if (ValidHeartBeats(item)) { continue; } } RaiseOnReceive(new DataReceivedArgs(token.SessionId, item)); } } else { var data = new byte[e.BytesTransferred]; Array.Copy(e.Buffer, e.Offset, data, 0, e.BytesTransferred); RaiseOnReceive(new DataReceivedArgs(token.SessionId, data)); } if (token.Socket.Connected) { if (!token.Socket.ReceiveAsync(e)) { // Read the next block of data sent by client. this.ProcessReceive(e); } } } else { this.ProcessError(e); } } else { this.CloseClient(token); } } catch (Exception ex) { this.ProcessError(e); ShowLog(ex); } }