在UDP套接字中使用标志MSG_TRUNC,MSG_CTRUNC

时间:2012-08-08 11:10:27

标签: sockets udp flags

我希望C中的完整示例在UDP套接字中使用标志MSG_TRUNC,MSG_CTRUNC 以及对这些标志的一些解释

recvmsg(udpSocket, &msg, flags);
if (msg.msg_flags & MSG_TRUNC)
printf("MSG_TRUNC\n");

感谢

1 个答案:

答案 0 :(得分:3)

MSG_TRUNC表示为接收提供的缓冲区空间不足,因此部分数据包丢失。 当您想要发现截断的数据量时,将使用此标志。 recvmsg函数将为结构msg_flags设置此标志(msghdr)(用于发送UDP数据包)

struct msghdr {
       void                  *msg_name;
       int                   msg_namelen;
       struct iovec          *msg_iov;
       __kernel_size_t       msg_iovlen;
       void                  *msg_control;
       __kernel_size_t       msg_controllen;
       unsigned              msg_flags;
};

您需要将此结构添加到您的代码中:

struct msghdr msg;
struct iovec iov;

你的接收缓冲区:

char buffer[BUFFER_SIZE];

初始化所有这些东西:

iov.iov_base = buffer;
iov.iov_len = sizeof(buffer);

msg.msg_iov = iov;

当您调用缓冲区的最大大小和设置的标志MSG_TRUNC时:

recvmsg(udpSocket, &msg, flags);

此调用后将填充struct头,您可以使用以下命令检查收到的缓冲区是否被截断:

if (msg.msg_flags & MSG_TRUNC)
printf("MSG_TRUNC\n");

编辑:使用recvfrom

这是关于如何使用带有标志的recvfrom的示例:

char *buffer[BUFFER_MAX_SIZE]; 
struct sockaddr from;
socklen_t from_len;
int available_data;
int socket;

socket = socket(AF_INET, SOCK_DGRAM, 0);

available_data = recvfrom(socket, (char*)buffer,0, MSG_TRUNC, &from, &fromlen);
if(available_data > 0)
{
    if (available_data > BUFFER_MAX_SIZE) 
    {
        fprintf(stderr, "UDP Packet is bigger than expected\n"); 

        exit(EXIT_FAILURE);
    }

    else 
    { 
        /* Process receiving data */ 
    }
}
else
{
    /* Handle error */
}