为什么select系统调用中需要加1?

为什么select系统调用中需要加1?

man select

int select(int nfds, fd_set *readfds, fd_set *writefds,
           fd_set *exceptfds, struct timeval *timeout);

nfds 应设置为三个集合中任意一个中编号最大的文件描述符,再加上 1。

我很好奇:

  1. 为什么plus 1需要而不是最大编号的文件描述符本身?
  2. 为什么在用户输入中请求plus 1操作,而不是在系统内部处理它?

sys_generic.c,它似乎相关__NFDBITS,但我无法进一步。

static int max_select_fd(unsigned long n, fd_set_bits *fds)
 339{
 340        unsigned long *open_fds;
 341        unsigned long set;
 342        int max;
 343        struct fdtable *fdt;
 344
 345        /* handle last in-complete long-word first */
 346        set = ~(~0UL << (n & (__NFDBITS-1)));
 347        n /= __NFDBITS;
 348        fdt = files_fdtable(current->files);
 349        open_fds = fdt->open_fds->fds_bits+n;
 350        max = 0;
 351        if (set) {
 352                set &= BITS(fds, n);
 353                if (set) {
 354                        if (!(set & ~*open_fds))
 355                                goto get_max;
 356                        return -EBADF;
 357                }
 358        }
 359        while (n) {
 360                open_fds--;
 361                n--;
 362                set = BITS(fds, n);

相似但不一样的主题:

选择系统调用的第一个参数的目的是什么?

答案1

论点nfdsselect 指定如下

国家食品药品监督管理局参数指定要测试的描述符的范围。首先国家食品药品监督管理局应检查每组描述符;也就是说,描述符从零到国家食品药品监督管理局应检查描述符集中的-1。

换句话说,nfds给出文件描述符的计数,它本身不是文件描述符。它的最小意义值是 1,而不是 0(从技术上讲,nfds可以是 0;select在这种情况下不会执行任何操作,并且可能根本不会被调用,除非您对它的副作用之一感兴趣,例如等待暂停)。

nfds值指定多少调用者想要观看的文件描述符;由于文件描述符从 0 开始,如果nfdsn,文件描述符从0到n–1会被考虑。

相关内容