c - 程序在 Linux 用户空间的 FD_SET 宏处挂起

标签 c linux sockets

我遇到了 FD_SET 的问题。我在 Linux 中使用套接字 CAN 方法和使用 recvfrom 访问 CAN。由于是阻塞调用,所以我想使用select系统调用。我的程序挂起@FD_SET 宏。它适用于 FD_CLR 宏。

代码:

FD_ZERO(&readfd);
printf("\n 1.1");
FD_CLR(s, &readfd);
printf("\n 1.2");
FD_SET(sockaddr,&readfd); //hangs here
printf("\n 1.3");

输出:

1.1
1.2

在那之后没有得到任何东西......

即使sockaddr值为3(小于FD_SETSIZE = 1024); 我可以将 FD_SET 应用于套接字可以接近套接字吗? 可能是什么原因?

最佳答案

它不太可能卡在 FD_SET() 处。更有可能的是 stdout 是一个终端,在这种情况下,您的 C 库会进行行缓冲,以便仅在看到终止换行符后才将每一行发送到终端。

尝试做例如printf("1.3\n") 代替(或者只是 puts("1.3"),这是一样的,而且更简单)。您也可以使用调试器。

(如果 stdout 是一个常规文件,在打印“1.3”之后对其执行 fflush(stdout) 5gon12eder 在评论中建议。无论 stdout 是终端还是常规文件(将使用 block 缓冲),fflush() 都会工作,因此它是一个更好的解决方案。另一种选择是使用 stderr,它默认是无缓冲的。)

顺便说一句,FD_ZERO(&readfd) 之后的

FD_CLR(s, &readfd) 是多余的。 FD_ZERO() 已经清除了 fd_set readfd

至于真正的问题(挂起):

你在 FD_ZERO(&readfd) 之后执行 FD_CLR(s, &readfd) 可能表明你误解了 select(2) 有效。如果您在这些行之后使用 select(FD_SETSIZE, &readfd, NULL, NULL, NULL),那么结果将是您一直在等待sockaddr 文件描述符变得可读(读取时不阻塞)。

还要确保 readfd 是一个 fd_set 并且 ssockaddr 是描述符(由例如 socket(2)open(2))。否则,事情就没有意义了。

关于c - 程序在 Linux 用户空间的 FD_SET 宏处挂起,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29143584/

相关文章:

c - 如何将内部包含 char 元素的二维数组的大小加倍

linux - 如何执行 x86 计算机的硬件重置?

c - 通过opengl渲染每像素图像1位

c - uint32_t 与 int 作为日常编程的约定

linux - 如何在 Debian linux 控制台上显示中文或日文?

linux - 如何在 nasm 上正确设置 execve 调用?

java - 为什么在使用 EasyMock.createMock 创建 mock 时 junit 测试失败?

c++ - 套接字客户端使用服务器接受的连接发送

c - accept() 调用时出现 Linux C Socket :"bad file descriptor"

c - 无需交叉编译的嵌入式 C 代码和单元测试