gpt4 book ai didi

linux - 套接字在被 select() 轮询之前是否应该设置为非阻塞?

转载 作者:太空狗 更新时间:2023-10-29 11:45:49 24 4
gpt4 key购买 nike

我记得当我们想在一个套接字描述符上使用 select() 时,这个套接字应该提前设置为 NONBLOCKING。

但是今天,我读了一个源文件,其中似乎没有将套接字设置为非阻塞的行我的内存对不对?

谢谢!

最佳答案

duskwuff 说的很对

In general, you do not need to set a socket as non-blocking to use itin select().

如果您的内核在 select() 方面符合 POSIX,则为真。不幸的是,有些人使用 Linux,但事实并非如此,正如 Linux select() 手册页所说:

Under Linux, select() may report a socket file descriptor as "ready forreading", while nevertheless a subsequent read blocks. This could forexample happen when data has arrived but upon examination has wrongchecksum and is discarded. There may be other circumstances in which afile descriptor is spuriously reported as ready. Thus it may be saferto use O_NONBLOCK on sockets that should not block.

2011 年 6 月 18 日星期六或前后,在 lkml 上对此进行了讨论。一位内核黑客试图证明不符合 POSIX。他们在方便时尊重 POSIX,在不方便时亵渎它。

他争辩说“可能有两个读者,第二个会阻塞。”但是这样的应用程序缺陷是不合理的。预计内核不会防止应用程序缺陷。内核有明确的职责:在select() 之后的第一个read() 的所有情况下,内核必须至少返回1 个字节、EOF 或错误;但永远不要阻止。至于 write(),在写入之前,您应该始终测试 select() 是否报告套接字可写。这保证您至少可以写入一个字节,否则会出错;但永远不要阻止。让 select() 来帮你,不要盲目写希望你不会阻塞。 Linux 黑客对极端情况等的提示是“我们懒得解决难题”的委婉说法。

假设您读取一个串行端口集:

min N; with -icanon, set N characters minimum for a completed read

time N; with -icanon, set read timeout of N tenths of a second

min 250 time 1

此处您需要 250 个字符的 block ,或十分之一秒的超时。当我在 Linux 上以非阻塞模式尝试此操作时,读取每个字符都会返回,从而影响 CPU。必须将其置于阻塞模式才能获得记录的行为。

因此有充分的理由将阻塞模式与 select() 一起使用,并期望您的内核符合 POSIX。

但如果您必须使用 Linux,Jeremy 的建议可能会帮助您应对其内核的一些缺陷。

关于linux - 套接字在被 select() 轮询之前是否应该设置为非阻塞?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16628743/

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