我正在开发一个在linux系统上运行的C应用程序(内核3.4.11 )
在我的应用程序中,我在一个线程上打开一个服务器套接字。我打开一个fork()
,我在主线程中用execvp()
执行shell命令。
打开fork()
将继承子项中的套接字文件描述符。根据网上的许多主题,这可能会导致问题。在我的情况下如果我关闭我的应用程序,我可以看到netstat
套接字被分配给另一个守护进程(另一个随机守护进程)。
事实上,针对此类问题有许多解决方案:
1)关闭fork()
孩子开头的套接字:
if ((pid = fork()) == -1)
return -1;
if (pid == 0) {
/* child */
close(socket_desc);
2)在父级中打开套接字时使用fcntl()
和FD_CLOEXEC
socket_desc = socket(AF_INET , SOCK_STREAM , 0);
fcntl(socket_desc, F_SETFD, fcntl(fd, F_GETFD) | FD_CLOEXEC);
3)在O_CLOEXEC
函数中使用socket()
:
socket_desc = socket(AF_INET , SOCK_STREAM|O_CLOEXEC , 0);
什么是最好的解决方案?为什么?
欢迎任何其他更好的解决方案。
答案 0 :(得分:3)
如果您控制所有代码,这些没有区别。
如果其他人为您提供socket
您不知道如何创建该解决方案,请使用第一个解决方案。
使用第二个,如果您编写了其他人向您发送套接字的模块,并且您希望将其传递给另一个您无法控制的模块,但您怀疑是fork()/exec()
。
如果您是套接字的创建者,请使用第三个,并且需要将其传递给您怀疑为fork()/exec()
的其他模块。