Linux内核在进程死后会在哪里进行处理和TCP连接清理?

时间:2010-12-14 10:28:55

标签: linux process linux-kernel

我试图在linux内核中找到它在进程死后进行清理的地方。具体来说,我想知道在使用-9信号杀死进程后它是否/如何处理打开的TCP连接。我很确定它会关闭所有连接,但我想查看详细信息,如果连接没有正确关闭的话。

欢迎使用指向Linux内核源代码的指针。

2 个答案:

答案 0 :(得分:11)

流程终止的关键由exit.c:do_exit()处理。此函数调用exit_files(),然后调用put_files_struct(),调用close_files()

close_files()遍历进程已打开的所有文件描述符(包括所有套接字),在每个文件描述符上调用filp_close(),在fput()对象上调用struct file。在放置struct file的最后一个引用时,fput()调用文件对象的.release()方法,对于套接字,该方法是sock_close()中的net/socket.c函数。

答案 1 :(得分:6)

我很确定套接字清理更多的是在进程终止后释放所有文件描述符的副作用,而不是由进程清理直接完成。

虽然我打算走出困境,并假设你在网络编程上遇到了常见的陷阱。如果我正确地猜测你的问题是你在一个进程被杀死后尝试绑定到一个地址时遇到“正在使用的地址”错误(EADDRINUSE),那么你正在运行套接字的TIME_WAIT。

如果是这种情况,您可以等待超时,通常是60秒,或者您可以修改套接字以允许立即重复使用。

int sock, ret, on;
struct sockaddr_in servaddr;

sock = socket( AF_INET, SOCK_STREAM, 0 ):

/* Enable address reuse */
on = 1;
ret = setsockopt( sock, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on) );

[编辑]

根据您的评论,听起来您有半开放连接的问题,并且不完全了解TCP的工作原理。 TCP无法知道客户端是死了还是空闲。如果kill -9是客户端进程,则四向关闭握手永远不会完成。这不应该在您的服务器上留下开放的连接,因此您仍然可能需要进行网络转储以确保发生了什么。

我不能确定如何在不知道你在做什么的情况下处理这个问题,但你可以阅读TCP Keepalive here。其他几个选项是定期向客户端发送空消息或空消息(可能需要修改协议),或者在空闲连接上设置硬定时器(可能导致有效连接中断)。