This commit is contained in:
WangQiang 2016-07-29 15:21:01 +00:00
parent f7aa152393
commit cb9f744a62
2 changed files with 59 additions and 34 deletions

View File

@ -1,33 +1,50 @@
#include "UTPacket.h" #include "UTPacket.h"
UTRet UTCom::DoFunc(Buffer & line, MemoryStream & ret) void UTCom::DoFunc(Buffer & packet, MemoryStream & ret)
{ {
return Good;
} }
typedef struct
{
byte PortID; // 端口号
byte Type; // 数据类型
ushort Length; // 数据长度
void * Next()const { return (void*)(&Length + Length + 1); };
}PacketHead;
bool UTPacket::PressTMsg(const BinaryPair& args, Stream& result) bool UTPacket::PressTMsg(const BinaryPair& args, Stream& result)
{ {
byte data[2048]; Buffer buff = args.Get("Data"); // 引用源数据区,后面使用要小心,不能修改任何值。
Buffer buff(data,sizeof(data)); if (buff.Length() < sizeof(PacketHead))return false;
args.Get("Data", buff);
PacketHead * head = (PacketHead*)buff.GetBuffer(); PacketHead * head = (PacketHead*)buff.GetBuffer();
void * tail = head + buff.Length(); // 结尾位置
UTPort * port = nullptr;
while (head<tail)
{
if ((uint)head->Next() >(uint)tail)break; // 要么越界,要么数据包错
MemoryStream resms;
if (!Ports.TryGetValue((uint)head->PortID, port) || !port) // 获取端口
{
PacketHead err; // 获取失败 返回错误信息
err.Seq = head->Seq;
err.Length = 0;
err.Error = NoPort; // 无端口的错误 需要定义类型
err.PortID = head->PortID;
err.Type = head->Type;
Buffer errbuf(&err, sizeof(PacketHead));
result.Write(errbuf);
continue;
}
Buffer packet(head, head->Length + sizeof(PacketHead));
port->DoFunc(packet, resms); // 执行 返回相应的信息
result.Write(Buffer(resms.GetBuffer(), resms.Position())); // 写入响应
head = (PacketHead*)head->Next();
port = nullptr;
}
return true; return true;
} }
#if DEBUG
String& UTPacket::ToStr(String& str) const
{
return str;
}
#endif

View File

@ -6,49 +6,57 @@
#include "Message\BinaryPair.h" #include "Message\BinaryPair.h"
enum UTRet :int enum EorrCode : byte
{ {
Good = 1, Good = 1,
CmdError = 2, CmdError = 2,
PortError =3, NoPort = 3,
NoPort = 4, Error = 4,
Error = -1,
}; };
typedef struct
{
byte PortID; // 端口号
byte Seq; // paket序列号 回复消息的时候原样返回不做校验
byte Type; // 数据类型
EorrCode Error; // 错误编码返回时候使用 (凑对齐)
ushort Length; // 数据长度
void * Next()const { return (void*)(&Length + Length + sizeof(Length)); };
}PacketHead;
// unvarnished transmission 透传端口基类 // unvarnished transmission 透传端口基类
class UTPort class UTPort
{ {
public: public:
String * Name; // 传输口名称 String * Name; // 传输口名称
byte ID; virtual void DoFunc(Buffer & packet, MemoryStream & ret) = 0; // packet 为输入命令ret为返回值。
virtual UTRet DoFunc(Buffer & line, MemoryStream & ret) = 0; // line 为输入命令ret为返回值。
private: private:
}; };
// 放到其他地方去 不要放在此处。 // 放到其他地方去 不要放在此处。
class UTCom:public UTPort class UTCom : public UTPort
{ {
public: public:
// SerialPort * Port; // SerialPort * Port;
virtual UTRet DoFunc(Buffer & line, MemoryStream & ret); virtual void DoFunc(Buffer & packet, MemoryStream & ret);
}; };
// unvarnished transmission 透传报文 // unvarnished transmission 透传报文
class UTPacket // 由bsp注册端口到 Ports ID和对应的类
// C++ 没有反射 找不到由UTPort派生的子类。
// 为了节省内存UTPort只包含Port指针 Name指针 和一个虚函数 在没有create之前只占用12字节3个指针
class UTPacket : public Object
{ {
public: public:
// List<UTPort*> Ports; // 透传传输口集合 Dictionary<uint, UTPort*> Ports; // 端口集合 Dic不支持byte 所以用uint替代
bool PressTMsg(const BinaryPair& args, Stream& result); bool PressTMsg(const BinaryPair& args, Stream& result);
// Client.Register("UTPacket",&UTPacket::PressTMsg,this); // Client.Register("UTPacket",&UTPacket::PressTMsg,this);
#if DEBUG
virtual String& ToStr(String& str) const;
#endif
//UTPort * CreateUTPort(byte portid);
virtual void Show() const = 0;
}; };
#endif #endif