我有一个C ++ - Linux应用程序,它应该在我公司设计的某个协议中发送UDP数据包 协议声明每个数据块应该连接到开头和页脚的头部,而header + data + footer应该作为单个UDP数据包发送到远程端。例如: 开口插座:
struct hostent *udphost;
udphost = gethostbyname(_remoteIp.c_str());
if(udphost == NULL)
{
ESPFS_DEBUG ("invalid host address format\n" );
return;
}
bzero((char *) &_udpSockAddr, sizeof(_udpSockAddr));
_udpSockAddr.sin_family = AF_INET;
bcopy((char *)udphost->h_addr, (char *)&_udpSockAddr.sin_addr.s_addr, udphost->h_length);
_udpSockAddr.sin_port = htons(UDP_PORT);
发送数据:
protocol_header hdr;
protocol_footer ftr;
sendto(_udpSocket, hdr, sizeof(hdr), 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
sendto(_udpSocket, data, data_size, 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
sendto(_udpSocket, ftr, sizeof(ftr), 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
现在我的问题是:
答案 0 :(得分:2)
每个sendto
创建一个UDP数据包(可以将其分段为多个IP数据包,而这些数据包又可以通过链路层进行分段,依此类推)。这几乎就是数据报套接字的定义。
如果您想在发送前连接多个缓冲区,则可以使用sendmsg
代替sendto
。 sendmsg
处理struct msghdr
,其中包含msg_iov
和msg_iovlen
个成员,您可以在其中指定要发送的缓冲区数组。
答案 1 :(得分:1)
如果你真的想打三次发送到,你有以下方法
发送函数的标志参数。标记 MSG_MORE 。
sendto(_udpSocket, hdr, sizeof(hdr), MSG_MORE, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
sendto(_udpSocket, data, data_size, MSG_MORE, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
sendto(_udpSocket, ftr, sizeof(ftr), 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
udp socket的套接字选项。选项 UDP_CORK 。
int zero = 0;
int one = 1;
setsockopt(_udpSocket, IPPROTO_UDP, UDP_CORK, &one, sizeof(one));
sendto(_udpSocket, hdr, sizeof(hdr), 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
sendto(_udpSocket, data, data_size, 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
sendto(_udpSocket, ftr, sizeof(ftr), 0, (const struct sockaddr *)&_udpSockAddr, sizeof(_udpSockAddr));
setsockopt(_udpSocket, IPPROTO_UDP, UDP_CORK, &zero, sizeof(zero));