在 Linux 中,recv() 有效但 recvmsg() 无效
In Linux, recv() works but recvmsg() doesn't
我在一个函数中得到了这段代码,运行 在 raspberry Pi:
struct sockaddr_in addr_buffer;
struct cmsghdr control_buffer;
struct msghdr msghdr;
struct iovec iov[1];
char msg_buffer[1458];
memset(&msg_buffer, 0, sizeof(msg_buffer));
memset(iov, 0, sizeof(iov));
memset(&msghdr, 0, sizeof(msghdr));
iov[0].iov_base = msg_buffer;
iov[0].iov_len = sizeof(msg_buffer);
msg.msg_iov = iov;
msg.msg_iovlen = 1;
msghdr.msg_name = &addr_buffer;
msghdr.msg_namelen = sizeof(addr_buffer);
msghdr.msg_control = &control_buffer;
msghdr.msg_controllen = sizeof(control_buffer);
msghdr.msg_flags = 0;
//int msgsize = recv(udpsocket_fd, &msg_buffer, 4, 0);
int msgs_received = recvmsg(udpsocket_fd, &msghdr, 0);
根据我读到的内容,recvmsg() 系统调用应该 return 进入 msghdr 指向的 iovec,一次一条消息(因为 iovec 数组是 1 个单位长)。但是,它不起作用:我正确收到 headers,因为我可以使用 IP 发送数据包的调试器读取,但 msg_buffer 仍然为空。该函数也 returns 0,这很奇怪,因为它意味着没有发生错误(return -1),但也意味着没有收到任何消息(尽管 headers 已更新)
但是,如果我取消对 recv() 行的注释,它会按预期工作,并且消息在 msg_buffer 中。但是,显然,没有收到额外的信息。我已经挠头两个小时了,看不出代码有什么问题。非常感谢您的帮助!
从您所展示的情况来看,您只是在不正确地初始化 msghdr
。尝试在 recvmsg
调用之前添加:
mhdr.msg_iov = iov;
mhdr.msg_iovlen = 1;
我在一个函数中得到了这段代码,运行 在 raspberry Pi:
struct sockaddr_in addr_buffer;
struct cmsghdr control_buffer;
struct msghdr msghdr;
struct iovec iov[1];
char msg_buffer[1458];
memset(&msg_buffer, 0, sizeof(msg_buffer));
memset(iov, 0, sizeof(iov));
memset(&msghdr, 0, sizeof(msghdr));
iov[0].iov_base = msg_buffer;
iov[0].iov_len = sizeof(msg_buffer);
msg.msg_iov = iov;
msg.msg_iovlen = 1;
msghdr.msg_name = &addr_buffer;
msghdr.msg_namelen = sizeof(addr_buffer);
msghdr.msg_control = &control_buffer;
msghdr.msg_controllen = sizeof(control_buffer);
msghdr.msg_flags = 0;
//int msgsize = recv(udpsocket_fd, &msg_buffer, 4, 0);
int msgs_received = recvmsg(udpsocket_fd, &msghdr, 0);
根据我读到的内容,recvmsg() 系统调用应该 return 进入 msghdr 指向的 iovec,一次一条消息(因为 iovec 数组是 1 个单位长)。但是,它不起作用:我正确收到 headers,因为我可以使用 IP 发送数据包的调试器读取,但 msg_buffer 仍然为空。该函数也 returns 0,这很奇怪,因为它意味着没有发生错误(return -1),但也意味着没有收到任何消息(尽管 headers 已更新)
但是,如果我取消对 recv() 行的注释,它会按预期工作,并且消息在 msg_buffer 中。但是,显然,没有收到额外的信息。我已经挠头两个小时了,看不出代码有什么问题。非常感谢您的帮助!
从您所展示的情况来看,您只是在不正确地初始化 msghdr
。尝试在 recvmsg
调用之前添加:
mhdr.msg_iov = iov;
mhdr.msg_iovlen = 1;