protected bool ProcessBean(NetSession session, IBean bean) // 同步处理bean,异常会抛出; { int serial = bean.Serial; if (serial < 0) { BeanContext beanCtx; if (_beanCtxMap.TryGetValue(-serial, out beanCtx)) { _beanCtxMap.Remove(-serial); AnswerDelegate onAnswer = beanCtx.onAnswer; if (onAnswer != null) { try { onAnswer(bean); } catch (Exception) {} return(true); } } } HandlerDelegate handler; if (HandlerMap == null || !HandlerMap.TryGetValue(bean.Type(), out handler)) { return(false); } handler(session, bean); return(true); }
public Client(int account_id, Core core, Socket socket) { m_account_id = account_id; m_core = core; m_name = socket.RemoteEndPoint.ToString(); m_netSession = new NetSession(new NetSocket(socket)); m_netSession.MsgProcesser = ProcessMsg; }
/** * 在刚刚接收网络数据后做的数据解码过滤; * 一般用来做解密和解压; */ protected override OctetsStream OnDecode(NetSession session, byte[] buf, int pos, int len) { if (_filter != null) { _filter.UpdateInput(buf, pos, len); } return(null); }
protected virtual void OnRecvBean(NetSession session, IBean bean) // 在Tick解协议过程中解出一个bean时回调,默认会同步处理bean并忽略异常; { try { ProcessBean(session, bean); } catch (Exception) {} }
void OnEventSend(IAsyncResult res) { NetSession session = (NetSession)res.AsyncState; Exception ex = null; int size; try { SocketError errCode; size = session.socket.EndSend(res, out errCode); if (errCode != SocketError.Success) { throw new Exception(errCode.ToString()); } } catch (Exception e) { ex = e; size = 0; } if (size <= 0) { Close(session, CLOSE_WRITE, ex); return; } Queue <OctetsStream> sendQueue = session.sendQueue; OctetsStream buf = sendQueue.Peek(); int pos = session.sendPos + size; int leftSize = buf.Size() - pos; if (leftSize <= 0) { sendQueue.Dequeue(); try { OnSent(session, buf.Remain()); } catch (Exception) {} if (sendQueue.Count <= 0) { session.sendPos = 0; return; } buf = sendQueue.Peek(); pos = buf.Position(); leftSize = buf.Size() - pos; } session.sendPos = pos; try { session.socket.BeginSend(buf.Array(), pos, leftSize, SocketFlags.None, AddEventSend, session); } catch (Exception e) { Close(session, CLOSE_WRITE, e); } }
} // 由Tick方法回调,异常会触发Close(CLOSE_DECODE); void OnRecv(NetSession session, int size) { OctetsStream recvBuf = session.recvBuf; OctetsStream os = OnDecode(session, recvBuf.Array(), recvBuf.Size(), size); if (os != null) { recvBuf.Append(os.Array(), os.Position(), os.Remain()); } else { recvBuf.Resize(recvBuf.Size() + size); } int pos = 0; try { while (recvBuf.Remain() >= 4) // type+serial+size+bean; { int ptype = recvBuf.UnmarshalUInt(); int pserial = recvBuf.UnmarshalInt(); int psize = recvBuf.UnmarshalUInt(); if (psize > recvBuf.Remain()) { break; } int ppos = recvBuf.Position(); pos = ppos + psize; BeanDelegate create; if (BeanMap == null || !BeanMap.TryGetValue(ptype, out create)) { OnRecvUnknownBean(session, ptype, pserial, psize); recvBuf.SetPosition(pos); } else { IBean bean = create(); bean.Unmarshal(recvBuf); int realsize = recvBuf.Position() - ppos; if (realsize > psize) { throw new Exception("bean realsize overflow: type=" + ptype + ",serial=" + pserial + ",size=" + psize + ",realsize=" + realsize); } bean.Serial = pserial; OnRecvBean(session, bean); } } } catch (MarshalEOFException) {} finally { recvBuf.Erase(0, pos); recvBuf.SetPosition(0); } }
/** * 接收到每个完整的bean都会调用此方法; * 一般在这里立即同步处理协议,也可以先放到接收队列里,合适的时机处理; */ protected override void OnRecvBean(NetSession session, IBean bean) { try { ProcessBean(session, bean); } catch (Exception e) { LogException(e); } }
// Use this for initialization void Start() { Console.Init(); Console.WriteLine(""); button = transform.GetComponentInChildren <Button> (); button.onClick.AddListener(DDD); session = new NetSession(); session.Connect(); new EnterRoomAction(); }
public LocalServer() { LocalSocket clientSocket = new LocalSocket(); LocalSocket serverSocket = new LocalSocket(); m_clientSession = new NetSession(clientSocket); m_serverSession = new NetSession(serverSocket); clientSocket.Init(m_serverSession.Out, m_serverSession.In); serverSocket.Init(m_clientSession.Out, m_clientSession.In); m_serverSession.MsgProcesser = ProcessMsg; m_database = new Database(this); m_database.LoadConfigs(); }
public PollIO( ) { if (m_poSession == null) { m_poSession = new NetSession(this); } if (readMsgCallBack == null) { readMsgCallBack = new ReadMsgCallBack(asyncread); } m_bRun = true; }
void BeginRecv(NetSession session) { try { OctetsStream recvBuf = session.recvBuf; int pos = recvBuf.Size(); recvBuf.Reserve(pos + RECV_BUFSIZE); session.socket.BeginReceive(recvBuf.Array(), pos, RECV_BUFSIZE, SocketFlags.None, AddEventRecv, session); } catch (Exception e) { Close(session, CLOSE_READ, e); } }
void AddSession(Socket soc) { NetSession session = new NetSession(this, soc); try { OnAddSession(session); BeginRecv(session); } catch (Exception e) { Close(session, CLOSE_ACTIVE, e); } }
public void Close(NetSession session, int code = CLOSE_ACTIVE, Exception e = null) // 除了主动调用外,Connect/Tick也会调用; { try { // session.socket.Shutdown(SocketShutdown.Receive); // session.socket.Dispose(); session.socket.Close(); } catch (Exception) {} if (!session.Closed) { session.Closed = true; OnDelSession(session, code, e); } }
public void UnInit() { m_bRun = false; stop(); if (m_poSession != null) { m_poSession.Uninit(); m_poSession = null; } if (readMsgCallBack != null) { readMsgCallBack = null; } myTcpClient.Close(); }
IEnumerator ConnectAndLogin(string name, string password) { m_socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); IPEndPoint endPoint = new IPEndPoint(IPAddress.Parse(m_ip), m_port); yield return(m_socket.BeginConnect(endPoint, null, null)); if (!m_socket.Connected) { Debug.LogFormat("连接失败"); } else { NetSession session = new NetSession(new NetSocket(m_socket)); m_client = new Client(session); Debug.LogFormat("连接成功!"); m_client.Login(name, password); } }
// buf不会经过OnEncode处理,直接放入待发送队列准备发送,回调了本次发送对应的OnSent确保发送完成后才能修改buf; public virtual void SendDirect(NetSession session, OctetsStream buf) { if (buf == null || buf.Remain() <= 0) { return; } session.sendQueue.Enqueue(buf); if (session.sendQueue.Count > 1) { return; } session.sendPos = buf.Position(); try { session.socket.BeginSend(buf.Array(), session.sendPos, buf.Remain(), SocketFlags.None, AddEventSend, session); } catch (Exception e) { Close(session, CLOSE_WRITE, e); } }
// 序列化bean,经过OnEncode处理后,放入待发送队列准备发送,调用后可以修改bean; public virtual void Send(NetSession session, IBean bean) { if (session.Closed || bean == null) { return; } int type = bean.Type(); int serial = bean.Serial; int reserveLen = OctetsStream.MarshalUIntLen(type) + OctetsStream.MarshalLen(serial) + 5; OctetsStream buf = new OctetsStream(reserveLen + bean.InitSize()); buf.Resize(reserveLen); int len = bean.Marshal(buf).Size(); int pos = 5 - buf.MarshalUIntBack(reserveLen, len - reserveLen); buf.Resize(pos); buf.MarshalUInt(type).Marshal(serial); buf.SetPosition(pos); buf.Resize(len); OctetsStream os = OnEncode(session, buf.Array(), buf.Position(), buf.Remain()); SendDirect(session, os ?? buf); }
public bool Ask(NetSession session, IBean bean, AnswerDelegate onAnswer = null) { if (session.Closed || bean == null) { return(false); } for (BeanContext beanCtx;;) { int serial = ++_serialCounter; if (serial > 0) { if (_beanCtxMap.ContainsKey(serial)) { continue; // 确保一下; } _beanCtxMap.Add(serial, beanCtx = new BeanContext(serial, onAnswer)); _beanCtxQueue.Enqueue(beanCtx); bean.Serial = serial; Send(session, bean); return(true); } _serialCounter = 0; } }
void OnEventRecv(IAsyncResult res) { NetSession session = (NetSession)res.AsyncState; Exception ex = null; int size; try { SocketError errCode; size = session.socket.EndReceive(res, out errCode); if (errCode != SocketError.Success) { throw new SocketException((int)errCode); } } catch (Exception e) { ex = e; size = 0; } if (size <= 0) { Close(session, CLOSE_READ, ex); return; } try { OnRecv(session, size); } catch (Exception e) { Close(session, CLOSE_DECODE, e); return; } BeginRecv(session); }
} // 由Send方法回调,异常会抛出; protected virtual OctetsStream OnDecode(NetSession session, byte[] buf, int pos, int len) { return(null); } // 由Tick方法回调,异常会触发Close(CLOSE_DECODE);
public Client(NetSession session) { m_netSession = session; m_netSession.MsgProcesser = ProcessMsg; }
Socket _listener; // 当前监听的socket; protected virtual void OnAddSession(NetSession session) { } // 执行Listen/Connect后,异步由Tick方法回调,异常会触发Close(CLOSE_ACTIVE);
protected virtual void OnRecvUnknownBean(NetSession session, int ptype, int pserial, int psize) // 在Tick解协议过程中解出一个bean时回调,默认会抛出异常; { throw new Exception("unknown bean: type=" + ptype + ",pserial=" + pserial + ",size=" + psize); }
} // 执行Listen/Connect后,异步由Tick方法回调,异常会触发Close(CLOSE_ACTIVE); protected virtual void OnDelSession(NetSession session, int code, Exception e) { } // 由Close(主动/Connect/SendDirect/Tick)方法调用,异常会抛出;
/// <summary>收到数据时</summary> /// <param name="session"></param> /// <param name="stream"></param> protected override void OnReceive(INetSession session, Stream stream) { var remoteEP = session.Remote.EndPoint; var str = stream.ToStr(); WriteLog(""); WriteLog(remoteEP + "=>" + session.Session.Local.EndPoint + " " + str); var ss = str.Split(":"); ss[0] = ss[0].ToLower(); if (ss[0] == "reg") { var name = ss[1]; INetSession ns = null; if (!Clients.TryGetValue(name, out ns)) { // 集合里面没有,认为是发起邀请方,做好记录 ns = new NetSession(); //ns.Server = sender as ISocketServer; ns.Session = session.Session; //ns.ClientEndPoint = remoteEP; Clients[name] = ns; session.OnDisposed += (s, e2) => ns.Dispose(); ns.OnDisposed += (s, e2) => Clients.Remove(name); //session.Send("注册成功!你的公网地址是:" + client, null, client); session.Send("注册成功!你的公网地址是:" + remoteEP, null); WriteLog("邀请已建立:{0}", name); } else { // 如果连续注册两次可能会有问题,这里要处理一下 //if ("" + ns.ClientEndPoint == "" + remoteEP) // session.Send("Has Register!", null); //else { // 到这里,应该是被邀请方到来,同时响应双方 session.Send(remoteEP.ToString(), null); // 同时还要通知对方 ns.Session.Send(remoteEP.ToString(), null); WriteLog("邀请已接受:{0} {1} {2}", name, remoteEP, remoteEP); Clients.Remove(name); Thread.Sleep(1000); //session.Disconnect(); //if (ns.Session != null) ns.Session.Disconnect(); session.Dispose(); ns.Session.Dispose(); } } } else if (ss[0] == "invite") { INetSession ns = null; if (Clients.TryGetValue(ss[1], out ns)) { session.Send("invite:" + remoteEP, null); // 同时还要通知对方 ns.Session.Send("invite:" + remoteEP.ToString(), null); } else { session.Send("Not Found!", null); } } else { if (!str.Contains("P2P")) { session.Send("无法处理的信息:" + str, null); } } }
void OnDisable() { ActionFactory.Instance.Clear(); session.DisConnect(); session = null; }
public Stream(NetSession paramSession, int paramInt) : base(paramInt) { this.session = paramSession; }
public Stream(NetSession paramSession) { this.session = paramSession; }
} // 主动连接失败的回调,由Connect/Tick方法调用,异常会抛出; protected virtual void OnSent(NetSession session, int sendSize) { } // sendSize是已发送的Encode后的大小,由Tick方法调用,异常会忽略;
} // sendSize是已发送的Encode后的大小,由Tick方法调用,异常会忽略; protected virtual OctetsStream OnEncode(NetSession session, byte[] buf, int pos, int len) { return(null); } // 由Send方法回调,异常会抛出;