在进行数据传输时,会将数据结构体打包生成字节流,在服务端通过对应的结构体进行接收,所以了解字节流生成的特性对数据的通信尤为关键。
结构体打包
为了陈述问题需要,在python下就简单打包一个sls的结构体,其中stringData为视频帧的字节流
fhead = struct.pack(b'sls',
bytes("MyVideo",encoding="utf-8"),
len(stringData),
bytes(boxInfoStr, encoding='utf-8')
)
win下pack
在64位win下的结果:
b’1\x00\x00\x00NL\x01\x001’
这个形式和想象中是一致的x00\x00\x00NL\x01为帧流长度85070,四字节的 l 类型,对应C++接收的结构体:
struct Data { //sls
char filename[1];
long imgStrSize;
char boxInfo[1];
}data;
arm下pack
而64位arm下的结果:
b’1\x00\x00\x00\x00\x00\x00\x00pM\x01\x00\x00\x00\x00\x001’
其中x00\x00\x00pM\x01为帧流长度85360,四字节的 l 类型
值得注意的是arm生成的字节流各数据变量间都有四字节的x00\x00\x00\x00间隔开,故对应C++接收的结构体:
struct Data { //sls
char filename[1];
int temp1;//间隔填充,int类型占四字节
long imgStrSize;
char boxInfo[1];
int temp2;//间隔填充
}data;
PS:同一视频帧生成的视频流长度竟然也是不一样的,还是比较有意思,具体结构体类型对应,socket通信见博文
图片的生成的字节流开头结尾具有固定格式:
b'\xff\xd8\xff\xe0\x00\x10JFIF\x00\x01\x01\x00\x00\x01\x00\x01\x00\x00\xff\xdb\x00C\x00\x02\x01\x01\x01\x01\x01\x02\x01\x01\x01\x02\x02\x02\x02\x02\x04\x03\x02\x02\x02\x02\x05\x04\x04\x03\x04\x06\x05\x06\x06\x06\x05\x06\x06\x06\x07\t\x08\x06\x07\t\x07\x06\x06\x08\x0b\x08\t\n\n\n\n\n\x06\...
\xff\xd9'
或许你该说,知道这有啥用,我们完全可以根据这个去排查图片是否正确接收,没有则会在显示时报错:
服务端接收
依据对应的结构体进行数据接收
recv_len = recv(s_accept, (char*)&data, sizeof(struct Data), 0);