关于close-on-exec的FD_CLOEXEC标志问题

发布于 2021-11-11 09:18:59 字数 887 浏览 951 评论 2

在看关于网络编程的东西。

经常看到有写这下面这段的。但是一直搞不明白什么意思。

int flags = fcntl(fd, F_GETFD);  
flags |= FD_CLOEXEC;  
fcntl(fd, F_SETFD, flags);  

baidu了下,大约是这么说的。

1,“如果调用了exec(),应该关闭指定的套接字” (Libevent手册中)

2,“如果设置了此选项,则连接监听器设置所涉及的监听器套接字以close-on-exec标志。”(Libevent手册中解释参数‘LEV_OPT_CLOSE_ON_EXEC’)

3,“一般我们会调用exec执行另一个程序,此时会用全新的程序替换子进程的正文,数据,堆和栈等。此时保存文件描述符的变量当然也不存在了,我们就无法关闭无用的文件描述符了。所以通常我们会fork子进程后在子进程中直接执行close关掉无用的文件描述符,然后再执行exec。”(另一个网页文章的解释)

[此解释有疑问。如果按此解释,那系统都直接每次设置FD_CLOEXEC就行了。可以去除此设置标志了,系统只要一发现调用exec就关闭所有文件描述符,多简单,没必要有此标志位了。]

我理解和疑惑的是:

假设A程序有1,2子进程。子进程2可能打开了网络端口或是文件,已经生成有文件描述符x,然后子进程2需要调用exec加载另一个程序。一般情况下,我们会按自己的需要给子进程的文件描述符x写上销毁指令,比如关闭端口等,所以一般FD_CLOEXEC标志是不用管的。难道有一些情况我们没办法销毁造成文件描述符耗尽?啥情况?

有达人指教吗。。迷糊了一天了。

 

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

复古式 2021-11-16 03:36:06

我想我知道原因了。这里分享一下我的理解。按照我所看到那份源码来说明。

程序设置了FD_CLOEXEC,可能是为了调用exec重新载入本进程以便更新。该程序中可能打开了大量接口与外面通讯。使用exec重新加载后,并没有释放文件描述符,而重新加载的程序不知道前一个程序都有哪些文件描述符打开了。这样多次重载后会快速耗尽文件描述符。

不知这样理解是否正确。不过如果程序不是很复杂的话,倒是应该可以把文件描述符放在一起,调用exec之前先检查文件描述符并关闭。

风苍溪 2021-11-11 10:57:23

假设在某个情况下,父进程需要将子进程的标准I/O重定向到某个文件,但子进程无需或不能或没法知道此文件,总之就是不能通过open来打开。如果父进程打开的文件描述符都在exec时关闭的话,那子进程就没法访问这个文件了?

上面只是一种情况而已!

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文