public void PrintState(SocketClientStateOptions state, bool isError) { string str = "[" + Thread.CurrentThread.ManagedThreadId.ToString("X2") + "] " + (isError ? "!" : " ") + this.State + ">" + state + "\tSN:" + this.SN + "\tCID:" + this.SocketClientIndex + "\tCloseCount:" + this.CloseCount + "\tAddress:" + this.Address + "\t" + this.GetCollectionName() + "\tLength:" + this.m_Args.BytesTransferred + "\tOperation:" + this.m_Args.LastOperation + "\tError:" + this.m_Args.SocketError; if (this.m_Args.AcceptSocket != null) { str += "\tConnected:" + this.m_Args.AcceptSocket.Connected; if (this.m_Args.AcceptSocket.RemoteEndPoint != null) { str += " IP:" + this.m_Args.AcceptSocket.RemoteEndPoint; } } //System.Diagnostics.Debug.WriteLine(str); }
private void Close() { this.CloseCount++; if (this.CloseCount > 1) { this.m_Server.DoException(this.m_Args, new Exception("关闭了 " + this.CloseCount + " 次")); } this.m_Args.Completed -= new EventHandler <SocketAsyncEventArgs>(this.m_Server.SocketAsyncEventArgs_Completed); this.Address = default(ADDRESS); if (this.m_Args.AcceptSocket != null) { if (this.m_Args.AcceptSocket.Connected) { try { this.m_Args.AcceptSocket.Shutdown(SocketShutdown.Both); } catch (Exception) { } } this.m_Args.AcceptSocket.Close(); //Thread.Sleep(10); //(必须!)等待 AcceptSocket 释放,如果出现“现在已经正在使用此 SocketAsyncEventArgs 实例进行异步套接字操作”的错误,则还需增大延时。 this.m_Args.AcceptSocket = null; } if (this.m_Args.Buffer != null) { this.m_Args.SetBuffer(null, 0, 0); } this.State = SocketClientStateOptions.Free; }
/// <summary> /// 改变状态。 /// </summary> /// <param name="state"></param> public void ChangeState(SocketClientStateOptions state) { lock (this) { PrintState(state, false); if (state != this.State) { switch (this.State) { case SocketClientStateOptions.Free: if (state == SocketClientStateOptions.Connected) { if (this.m_Server.m_Connecteds.Contains(this.m_Args) == false) { this.m_Server.m_Connecteds.Add(this.m_Args); this.State = state; } else { this.m_Server.DoException(this.m_Args, new Exception("状态从 " + this.State + " 变更为 " + state + " 时,连接队列中已存在当前异步套接字操作")); } } else { if (this.CloseCount != 0) { PrintState(state, true); } } break; case SocketClientStateOptions.Connected: SocketAsyncEventArgs argsOut; if (this.m_Server.m_Connecteds.TryTake(out argsOut) == false) { this.m_Server.DoException(this.m_Args, new Exception("从异步套接字连接集合中移除连接时发生错误:未发现该套接字的连接信息。")); } if (state == SocketClientStateOptions.Online) { while (this.m_Server.m_Onlines.TryAdd(this.Address, this.m_Args) == false) { //如果加入登录后的集合中失败,则表示已有相同地址的连接已经登录 if (this.m_Server.m_Onlines.TryGetValue(this.Address, out argsOut)) { SocketClient _SocketClientOut = argsOut.UserToken as SocketClient; _SocketClientOut.ChangeState(SocketClientStateOptions.Free); } } this.State = state; } else if (state == SocketClientStateOptions.Free) { this.Close(); } break; case SocketClientStateOptions.Online: if (state == SocketClientStateOptions.Free) { SocketAsyncEventArgs argsDis; if (this.m_Server.m_Onlines.TryRemove(this.Address, out argsDis) == false) { this.m_Server.DoException(this.m_Args, new Exception("从异步套接字在线集合中移除连接时发生错误:未发现该套接字的在线信息。(该异常通常为强制关闭连接后出现,不影响后续操作)")); } this.Close(); } else { PrintState(state, true); } break; } } else { PrintState(state, true); } } }