gpt4 book ai didi

c++ - 由于 select() 调用返回 EBADF,是否有任何方法可以获取套接字描述符?

转载 作者:塔克拉玛干 更新时间:2023-11-03 01:43:18 26 4
gpt4 key购买 nike

我有一个代码,我在其中使用 select() 函数调用来轮询添加到 readfds 集的套接字列表,用于任何传入数据。

while(1) {
ret = select(n,&readfds,NULL,NULL,&tv);
if(ret == -1) {
perror("Select Failed");
} else if (ret == 0){
printf("Select Timeout\n");
} else {
recv(clientSocket, buffer, 1024, 0);
printf("Data received: %s",buffer);
}
}

我在 readfds 列表中添加了很多套接字。我的代码中还有另一个线程正在关闭 readfds 列表中的套接字(从列表中删除套接字不是预期的行为)。因此,如果套接字在另一个线程中被删除,则上面的 while 循环会抛出“选择失败:文件描述符错误”。

1) 避免这种情况的一种方法是修复其他线程中的错误以停止从列表中删除套接字

2) 另一种方法是获取在 select 函数调用中给出错误文件描述符错误的套接字,并将其从 readfds 中提到的套接字列表中删除(我可以在另一部分再次将相同的套接字添加到列表中程序)。

我正在尝试第一个选项。同时我也想知道,由于 select() 调用返回 EBADF,有没有办法获取套接字描述符?

最佳答案

  1. 由于 fd_set 数据结构的大小限制,Select 将不支持超过 FD_SETSIZE 数量的描述符。通常 FD_SETSIZE 是 1024。
  2. 您发布的代码使用 Select 的方式有问题。由于 select 修改了传递的 fd_sets,因此它们都不能被重用,因此您需要在每次准备 Select 调用时更新 fd_set 和 max fd number。
  3. Select 不能很好地支持多线程使用,因为它不是这样设计的。根据男士选择:

Multithreaded applications

If a file descriptor being monitored by select() is closed in another thread, the result is unspecified. On some UNIX systems, select() unblocks and returns, with an indication that the file descriptor is ready (a subsequent I/O operation will likely fail with an error, unless another the file descriptor reopened between the time select() returned and the I/O operations was performed). On Linux (and some other systems), closing the file descriptor in another thread has no effect on select(). In summary, any application that relies on a partic‐ ular behavior in this scenario must be considered buggy.

  1. 尝试使用更现代的 epoll 并使用线程池作为后盾。

一个有用的指南是 http://www.ulduzsoft.com/2014/01/select-poll-epoll-practical-difference-for-system-architects/ .

关于c++ - 由于 select() 调用返回 EBADF,是否有任何方法可以获取套接字描述符?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36980967/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com