最近本人利用template的偏特化编制了一个通用协议数据单元类CPdu。
CPdu的通用包头定义如下:
#pragma pack(push,__PDU__,1)
template<long min_unknown,long max_unknown>
struct CommPduHeader
{
long len ; //pdu length,include 'len' filed
short type ; //pdu type
...
};
#pragma pack(pop,__PDU__)
根据设计,CommPduHeader的实例的尺寸应该是6,例如:
sizeof(CommPduHeader<1,100>)应该为6。在VC7下进行测试,
sizeof(CommPduHeader<1,100>)等于我们的预期值6。在将CPdu移植到
linux是发现sizeof(CommPduHeader<1,100>)则返回的是8,而不是我们预期
的6。这意味着同样采用CPdu定义的通信协议,运行在linux与win32平台上的
通信双方无法正常通信。这直接导致CPdu的设计失效。
显然,sizeof(CommPduHeader<1,100>)=6才是正确的结果,如果修改
CommPduHeader的定义是的sizeof(CommPduHeader<1,100>)在gcc下也返回6呢?
经过一段时间琢磨和测试,发现以下面的方式重定义CommPduHeader,gcc下
sizeof(CommPduHeader<1,100>)也返回我们的预期值6。
#pragma pack(push,__PDU__,1)
struct CommPduHeaderBase
{
long len ; //pdu length,include 'len' filed
short type ; //pdu type
};
template<long min_unknown,long max_unknown>
struct CommPduHeader : public CommPduHeaderBase
{
...
};
#pragma pack(pop,__PDU__)
修改好的定义,CommPduHeader的用法完全保持不变,而
sizeof(CommPduHeader<1,100>)=6。新的定义在VC7中也返回预期值。
这样,通过调整引入CommPduHeaderBase,CPdu就可以适用于linux和
win32上了。