mirror of
https://github.com/tiennm99/zfoo.git
synced 2026-06-01 02:19:00 +00:00
perf[protocol]: 使用模板生成协议
This commit is contained in:
@@ -0,0 +1,74 @@
|
||||
namespace CsProtocol.Buffer
|
||||
{
|
||||
public class BigEndianByteBuffer : ByteBuffer
|
||||
{
|
||||
// fast int to byte[] conversion and vice versa
|
||||
// -> test with 100k conversions:
|
||||
// BitConverter.GetBytes(ushort): 144ms
|
||||
// bit shifting: 11ms
|
||||
// -> 10x speed improvement makes this optimization actually worth it
|
||||
// -> this way we don't need to allocate BinaryWriter/Reader either
|
||||
// -> 4 bytes because some people may want to send messages larger than
|
||||
// 64K bytes
|
||||
// => big endian is standard for network transmissions, and necessary
|
||||
// for compatibility with erlang
|
||||
public static byte[] IntToBytesBigEndian(int value)
|
||||
{
|
||||
return new byte[]
|
||||
{
|
||||
(byte) (value >> 24),
|
||||
(byte) (value >> 16),
|
||||
(byte) (value >> 8),
|
||||
(byte) value
|
||||
};
|
||||
}
|
||||
|
||||
public static int BytesToIntBigEndian(byte[] bytes)
|
||||
{
|
||||
return (bytes[0] << 24) |
|
||||
(bytes[1] << 16) |
|
||||
(bytes[2] << 8) |
|
||||
bytes[3];
|
||||
}
|
||||
|
||||
public override void WriteShort(short value)
|
||||
{
|
||||
WriteBytes(GetBytes(value));
|
||||
}
|
||||
|
||||
public override short ReadShort()
|
||||
{
|
||||
return GetInt16(ReadBytes(2));
|
||||
}
|
||||
|
||||
public override void WriteRawInt(int value)
|
||||
{
|
||||
WriteBytes(IntToBytesBigEndian(value));
|
||||
}
|
||||
|
||||
public override int ReadRawInt()
|
||||
{
|
||||
return BytesToIntBigEndian(ReadBytes(4));
|
||||
}
|
||||
|
||||
public override void WriteFloat(float value)
|
||||
{
|
||||
WriteBytes(GetBytes(value));
|
||||
}
|
||||
|
||||
public override float ReadFloat()
|
||||
{
|
||||
return GetSingle(ReadBytes(4));
|
||||
}
|
||||
|
||||
public override void WriteDouble(double value)
|
||||
{
|
||||
WriteBytes(GetBytes(value));
|
||||
}
|
||||
|
||||
public override double ReadDouble()
|
||||
{
|
||||
return GetDouble(ReadBytes(8));
|
||||
}
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,56 @@
|
||||
using System;
|
||||
|
||||
namespace CsProtocol.Buffer
|
||||
{
|
||||
public class LittleEndianByteBuffer : ByteBuffer
|
||||
{
|
||||
/**
|
||||
* 翻转字节数组,如果本地字节序列为低字节序列,则进行翻转以转换为高字节序列
|
||||
*/
|
||||
private static byte[] reverse(byte[] bytes)
|
||||
{
|
||||
Array.Reverse(bytes);
|
||||
return bytes;
|
||||
}
|
||||
|
||||
public override void WriteShort(short value)
|
||||
{
|
||||
WriteBytes(reverse(GetBytes(value)));
|
||||
}
|
||||
|
||||
public override short ReadShort()
|
||||
{
|
||||
return GetInt16(reverse(ReadBytes(2)));
|
||||
}
|
||||
|
||||
public override void WriteRawInt(int value)
|
||||
{
|
||||
WriteBytes(reverse(GetBytes(value)));
|
||||
}
|
||||
|
||||
public override int ReadRawInt()
|
||||
{
|
||||
return GetInt32(reverse(ReadBytes(4)));
|
||||
}
|
||||
|
||||
public override void WriteFloat(float value)
|
||||
{
|
||||
WriteBytes(reverse(GetBytes(value)));
|
||||
}
|
||||
|
||||
public override float ReadFloat()
|
||||
{
|
||||
return GetSingle(reverse(ReadBytes(4)));
|
||||
}
|
||||
|
||||
public override void WriteDouble(double value)
|
||||
{
|
||||
WriteBytes(reverse(GetBytes(value)));
|
||||
}
|
||||
|
||||
public override double ReadDouble()
|
||||
{
|
||||
return GetDouble(reverse(ReadBytes(8)));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
namespace CsProtocol.Buffer
|
||||
{
|
||||
public interface IPacket
|
||||
{
|
||||
short ProtocolId();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
namespace CsProtocol.Buffer
|
||||
{
|
||||
public interface IProtocolRegistration
|
||||
{
|
||||
short ProtocolId();
|
||||
|
||||
void Write(ByteBuffer buffer, IPacket packet);
|
||||
|
||||
IPacket Read(ByteBuffer buffer);
|
||||
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,69 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using CsProtocol.Buffer;
|
||||
|
||||
namespace CsProtocol
|
||||
{
|
||||
public class ProtocolManager
|
||||
{
|
||||
public static readonly short MAX_PROTOCOL_NUM = short.MaxValue;
|
||||
|
||||
|
||||
private static readonly IProtocolRegistration[] protocolList = new IProtocolRegistration[MAX_PROTOCOL_NUM];
|
||||
|
||||
|
||||
public static void InitProtocol()
|
||||
{
|
||||
var protocolRegistrationTypeList = new List<Type>();
|
||||
|
||||
foreach (var assembly in AppDomain.CurrentDomain.GetAssemblies())
|
||||
{
|
||||
if (assembly.Equals(typeof(ProtocolManager).Assembly))
|
||||
{
|
||||
var results = new List<Type>();
|
||||
results.AddRange(assembly.GetTypes());
|
||||
foreach (var type in results)
|
||||
{
|
||||
if (type.IsClass && !type.IsAbstract && typeof(IProtocolRegistration).IsAssignableFrom(type))
|
||||
{
|
||||
protocolRegistrationTypeList.Add(type);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
foreach (var protocolRegistrationType in protocolRegistrationTypeList)
|
||||
{
|
||||
var protocolRegistration = (IProtocolRegistration) Activator.CreateInstance(protocolRegistrationType);
|
||||
protocolList[protocolRegistration.ProtocolId()] = protocolRegistration;
|
||||
}
|
||||
}
|
||||
|
||||
public static IProtocolRegistration GetProtocol(short protocolId)
|
||||
{
|
||||
var protocol = protocolList[protocolId];
|
||||
if (protocol == null)
|
||||
{
|
||||
throw new Exception("[protocolId:" + protocolId + "]协议不存在");
|
||||
}
|
||||
|
||||
return protocol;
|
||||
}
|
||||
|
||||
public static void Write(ByteBuffer buffer, IPacket packet)
|
||||
{
|
||||
var protocolId = packet.ProtocolId();
|
||||
// 写入协议号
|
||||
buffer.WriteShort(protocolId);
|
||||
|
||||
// 写入包体
|
||||
GetProtocol(protocolId).Write(buffer, packet);
|
||||
}
|
||||
|
||||
public static IPacket Read(ByteBuffer buffer)
|
||||
{
|
||||
var protocolId = buffer.ReadShort();
|
||||
return GetProtocol(protocolId).Read(buffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using CsProtocol.Buffer;
|
||||
|
||||
namespace CsProtocol
|
||||
{
|
||||
{}
|
||||
public class {} : IPacket
|
||||
{
|
||||
{}
|
||||
|
||||
public static {} ValueOf({})
|
||||
{
|
||||
var packet = new {}();
|
||||
{}
|
||||
return packet;
|
||||
}
|
||||
|
||||
|
||||
public short ProtocolId()
|
||||
{
|
||||
return {};
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public class {}Registration : IProtocolRegistration
|
||||
{
|
||||
public short ProtocolId()
|
||||
{
|
||||
return {};
|
||||
}
|
||||
|
||||
public void Write(ByteBuffer buffer, IPacket packet)
|
||||
{
|
||||
if (buffer.WritePacketFlag(packet))
|
||||
{
|
||||
return;
|
||||
}
|
||||
{} message = ({}) packet;
|
||||
{}
|
||||
}
|
||||
|
||||
public IPacket Read(ByteBuffer buffer)
|
||||
{
|
||||
if (!buffer.ReadBool())
|
||||
{
|
||||
return null;
|
||||
}
|
||||
{} packet = new {}();
|
||||
{}
|
||||
return packet;
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user