【Linux】I/O多路复用—select和pselect

select函数

#include <sys/select.h>
int select(int maxfdp1, fd_set *restrict readfds, fd_set *restrict writefds,
            fd_set *restrict exceptfds, struct timeval *restrict tvptr);
        返回值:准备就绪的描述符数目;若超时,则返回0;若出错,返回-1

参数:

  • tvptr

    • tvptr == NULL
      永远等待。当所指定的描述符中有一个准备好或捕捉到一个信号则返回。如果捕捉到信号,则返回-1,errno置为EINTR。

    • tvptr->tv_sec == 0 && tvptr->tv_usec == 0
      根本不等待。测试所有指定的描述符并立即返回。

    • tvptr->tv_sec != 0 || tvptr->tv_usec != 0
      等待指定的秒数和微秒数。当有描述符准备好,或者当指定的时间值已超时则立即返回。如果超时,返回0。和第一种情况一样,这种等待会被信号中断。

  • readfds, writefds, exceptfds
    指向描述符集的指针,分别是我们关心的可读、可写或处于异常条件的描述符集合。每个描述符集存储在一个fd_set数据类型中。任意一个指针都可以为空。

  • fd_set类型
    这个类型由实现决定,它可以为每个描述符保持一位,我们可以把它看作一个很大的字节数组。
    对于该数据类型,只能进行如下处理:

    1. 分配一个该类型变量
    2. 将一个该类型变量赋值给另一该类型变量
    3. 对该类型变量使用如下四个函数:

      
      #include <sys/select.h>
      
      int FD_ISSET(int fd, fd_set *fdset);
                  返回值:fd在描述符集中,则返回非0值;否则,返回0
      int FD_CLR(int fd, fd_set *fdset); //清除一位
      int FD_SET(int fd, fd_set *fdset); //开启一位
      int FD_ZERO(fd_set *fd_set);    //将描述符集的所有位设置为0

      这些接口可实现为宏或者函数。在声明一个描述符集之后,必须用FD_ZERO将该描述符集清零,然后再设置我们关心的描述符的位。
      在select返回后,可使用FD_ISSET检查各描述符集中的指定位是否仍处于打开状态。

  • maxfdp1

    该参数的意思是”最大文件描述符编号加1“。考虑所有3个描述符集,其中最大的描述符编号加1,就是该参数的值。通过指定该位,内核只在指定范围内寻找大开的位,而不必关心三个描述符集中没有使用的那些位。因为描述符编号从0开始,所以要给最大描述符编号加1,实际上该参数是要检查的描述符数。

返回值:

  1. 返回-1表示出错,这是可能的。例如在有描述符准备好之前,捕捉到一个信号。此时一个描述符集都不会被修改。

  2. 返回0,表示没有描述符准备好。此时,所有描述符集都会被置0。

  3. 一个正的返回值表明已经准备好的描述符数。该值是3个描述符集中准备好的描述符数之和,如果一个描述符既准备好读又准备好写,则在返回值中会计数两次。这种情况下,3个描述符集中仍旧打开的位对应已准备好的描述符。

注意:

  1. 一个描述符阻塞与否不影响select是否阻塞。
  2. 如果在一个描述符上遇到了文件末尾,select认为它是可读的。也就是说,到达文件末尾时,select并不会给一个异常提示

pselect函数

#include <sys/select.h>
int pselect(int maxfdp1, fd_set *restrict readfds, fd_set *restrict writefds,
fd_set *restrict exceptfds, const struct timespec *restrict tsptr
const sigset_t *restrict sigmask);
        返回值:准备就绪的描述符数目;若超时,则返回0;若出错,返回-1

除下面几点外,pselect和select相同:

  1. pselect的超时值使用timespec结构,该结构以秒和纳秒表示超时值,能够提供更精确的超时时间。
  2. pselect的超时值被声明为const,这保证了超时值不会在调用时被修改。 pselect使用可选的信号屏蔽字。如果参数sigmask非空,则在函数被调用时,以原子的方式安装该屏蔽字,再返回时,恢复以前的屏蔽字。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值