/// <summary> /// 通过网络包创建Message对象 /// </summary> /// <param name="package"></param> /// <returns></returns> public static CMessage CreateMessage(CPackageBase package) { // 将物理对象转化为Message CMessage message = new CMessage(); //填充OpCode Type type = package.GetType(); Object[] attrs = type.GetCustomAttributes(false); foreach (Object item in attrs) { // 符合特性的才注册 if (item.GetType() == typeof(CAttrPackage)) { message.OpCode = (item as CAttrPackage).OpCode; break; } } // 填充身体数据 package.ToMessage(ref message); //设置长度 message.BodyLength = ( ushort )message.Body.Position; return(message); }
/// <summary> /// 伪造一个对象发送到收线程来伪造服务器消息 /// 一般情况下 /// 收线程收到字节流 -> 反序列化到CMessage -> 反射创建对象 -> FromMessage填充数据 -> 执行委托 /// 这里是 /// 伪造一个对象 -> ToMessage()得到CMessage -> 反射创建对象 -> FromMessage填充数据 -> 执行委托 /// </summary> /// <param name="package">消息对象</param> /// <param name="Length">消息数据长度 /// 正常收消息时 /// 字节流的大小由包头提供了 /// 属于精确的分配内存空间 /// 不会有问题 /// /// 而伪造消息进行收取时 /// 没有包头提供消息大小 /// 因此提供默认的第二个参数来指定消息大小 /// 如果伪造的消息过大 /// 可以增大本值来确保不会产生数组越界的问题 /// </param> public void FakePackageToReceive(CPackageBase package) { CMessage msg = CPackageBase.CreateMessage(package); // 加入待收队列 FakeMessageToReceive(ref msg); }
/// <summary> /// 处理收到的包 /// </summary> private void ProcessReceviedPackage() { CMessage message = null; while ((message = m_Receiver.PopReadyToHandlerPackage()) != null) { // 如果是伪造的消息,则创建时会导致读写位置到包的末尾了 // 因此需要在这里重置归0 message.Body.ResetPosition(); // 包ID int OpCode = message.OpCode; // 反射出类型 Type type = CPackageManager.Instance.ReflectionClassNameByActionID(OpCode); //安全处理 if (type == null) { CLOG.E("Reflection class name by OpCode error! OpCode={0} reflection class name = null!! please check the code", OpCode); return; } // 得到该类型的处理委托 DelegatePackageHandler DP = CPackageManager.Instance.GetPackageHandler(type); // 创建反射类型实例 CPackageBase package = Activator.CreateInstance(type) as CPackageBase; //安全处理 if (package == null) { CLOG.E("create package instance error! OpCode = {0} type = {1}", OpCode, type.ToString()); return; } // 从message的身体中获取数据实例化对象 try { package.FromMessage(ref message); } catch (Exception ex) { CLOG.E("from message error! Exception!! OpCode = {0} type={1} message={2} ", OpCode, type.ToString(), message.ToString()); CLOG.E(ex.ToString()); return; } // 调用委托,传入参数 if (DP != null) { DP(package); } else { CLOG.W("ths OpCode {0} was not register handler!", OpCode); } } }
/// <summary> /// 发送消息到服务器 /// </summary> /// <param name="package">要发送的消息</param> public void Send(CPackageBase package) { if (m_Sender != null) { CMessage message = CPackageBase.CreateMessage(package); // 加入待发队列 m_Sender.PushMessageToSend(message); } }
/// <summary> /// 从body中获取数据,写入参数中去 /// </summary> /// <typeparam name="T">泛型</typeparam> public T PopData <T>(ref CMessage msg) { Type TType = typeof(T); if (TType == typeof(byte)) { return(( T )( Object )PopByte()); } if (TType == typeof(sbyte)) { return(( T )( Object )PopSByte()); } if (TType == typeof(bool)) { return(( T )( Object )PopBoolean()); } if (TType == typeof(short)) { return(( T )( Object )PopShort()); } if (TType == typeof(ushort)) { return(( T )( Object )PopUShort()); } if (TType == typeof(int)) { return(( T )( Object )PopInt()); } if (TType == typeof(uint)) { return(( T )( Object )PopUInt()); } if (TType == typeof(float)) { return(( T )( Object )PopFloat()); } if (TType == typeof(long)) { return(( T )( Object )PopLong()); } if (TType == typeof(ulong)) { return(( T )( Object )PopULong()); } if (TType == typeof(string)) { return(( T )( Object )PopString()); } // 如果反射对象是 CPackageBase 的子类 if (TType.IsSubclassOf(typeof(CPackageBase))) { // 创建反射类型实例 CPackageBase MemberPackageBase = Activator.CreateInstance(TType) as CPackageBase; MemberPackageBase.FromMessage(ref msg); return(( T )( Object )MemberPackageBase); } // 如果反射对象是 List if (TType.IsGenericType) { Type[] GenericTypes = TType.GetGenericArguments(); object[] param = { msg }; return(( T )( Object )CFunction.CallGenericArrayFunction("PopList", this, GenericTypes, param)); } // 如果反射对象是数组 if (TType.IsArray) { Type ElementType = TType.GetElementType(); object[] param = { msg }; return(( T )( Object )CFunction.CallGenericFunction("PopArray", this, ElementType, param)); } CLOG.E("the type {0} has no serilize methon", TType.ToString()); return(default(T)); }
/// <summary> /// 压入数据 /// </summary> /// <typeparam name="T">泛型</typeparam> /// <param name="data">要压入的值></param> /// <param name="msg">要压入的目标消息></param> public void PushData <T>(T data, ref CMessage msg) { Type dataType = typeof(T); if (dataType == typeof(byte)) { PushByte(( byte )( Object )data); return; } if (dataType == typeof(sbyte)) { PushByte(( sbyte )( Object )data); return; } if (dataType == typeof(bool)) { PushBoolean(( bool )( Object )data); return; } if (dataType == typeof(int)) { PushInt(( int )( Object )data); return; } if (dataType == typeof(uint)) { PushInt(( uint )( Object )data); return; } if (dataType == typeof(short)) { PushShort(( short )( Object )data); return; } if (dataType == typeof(ushort)) { PushInt(( ushort )( Object )data); return; } if (dataType == typeof(float)) { PushFloat(( float )( Object )data); return; } if (dataType == typeof(long)) { PushLong(( long )( Object )data); return; } if (dataType == typeof(ulong)) { PushLong(( ulong )( Object )data); return; } if (dataType == typeof(string)) { PushString(( string )( Object )data); return; } // 如果反射对象是 CPackageBase 的子类 if (data is CPackageBase) { CPackageBase tempData = ( CPackageBase )( Object )data; if (tempData == null) { return; } tempData.ToMessage(ref msg); return; } // 如果反射对象是 List if (dataType.IsGenericType) { Type[] GenericType = dataType.GetGenericArguments(); object[] param = { data, msg }; CFunction.CallGenericArrayFunction("PushList", this, GenericType, param); return; } // 如果反射对象是数组 if (dataType.IsArray) { Type ElementType = dataType.GetElementType(); object[] param = { data, msg }; CFunction.CallGenericFunction("PushArray", this, ElementType, param); return; } CLOG.E("the type {0} has no serilize methon", dataType.ToString()); }