使用SO_LINGER缩短TIME_WAIT的时间,减少大量短链接堆积TIME_WAIT

Posted BBinChina

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了使用SO_LINGER缩短TIME_WAIT的时间,减少大量短链接堆积TIME_WAIT相关的知识,希望对你有一定的参考价值。

经常会听到socket的优雅关闭问题:


struct linger {

     int l_onoff; /* 0 = off, nozero = on */

     int l_linger; /* linger time */

};

setsockopt(m_listenfd, SOL_SOCKET, SO_LINGER, &tmp, sizeof(tmp));

通过setsockopt方法设置socket的配置项SO_LINGER

何为优雅:
SO_LINGER选项用来设置延迟关闭的时间,等待套接字发送缓冲区中的数据发送完成。

没有设置该选项时,在调用close()后,在发送完FIN后会立即进行一些清理工作并返回。如果设置了SO_LINGER选项,并且等待时间为正值,则在清理之前会等待一段时间。

有下列三种情况:

1、设置 l_onoff为0,则该选项关闭,l_linger的值被忽略,等于内核缺省情况,close调用会立即返回给调用者,如果可能将会传输任何未发送的数据;

2、设置 l_onoff为非0,l_linger为0,则套接口关闭时TCP夭折连接,TCP将丢弃保留在套接口发送缓冲区中的任何数据并发送一个RST给对方,而不是通常的四分组终止序列,这避免了TIME_WAIT状态;

3、设置 l_onoff 为非0,l_linger为非0,当套接口关闭时内核将拖延一段时间(由l_linger决定)。如果套接口缓冲区中仍残留数据,进程将处于睡眠状态,直 到(a)所有数据发送完且被对方确认,之后进行正常的终止序列(描述字访问计数为0)或(b)延迟时间到。此种情况下,应用程序检查close的返回值是非常重要的,如果在数据发送完并被确认前时间到,close将返回EWOULDBLOCK错误且套接口发送缓冲区中的任何数据都丢失。close的成功返回仅告诉我们发送的数据(和FIN)已由对方TCP确认,它并不能告诉我们对方应用进程是否已读了数据。如果套接口设为非阻塞的,它将不等待close完成。

注释:l_linger的单位依赖于实现: 4.4BSD假设其单位是时钟滴答(百分之一秒),但Posix.1g规定单位为秒。

下面的代码是一个使用SO_LINGER选项的例子,使用30秒的超时时限:

#define TRUE     1
 
#define FALSE    0
int z;       //Status code
 
int s;       //Socket s
struct linger so_linger;
...
so_linger.l_onoff = TRUE;
so_linger.l_linger = 30;
z = setsockopt(s,
    SOL_SOCKET,
    SO_LINGER,
    &so_linger,
    sizeof so_linger);
if ( z )
   perror("setsockopt(2)");
 

下面的例子显示了如何设置SO_LINGER的值来中止套接口s上的当前连接:

#define TRUE     1
#define FALSE    0
int z; /* Status code */
int s;       /* Socket s */
struct linger so_linger;
...
so_linger.l_onoff = TRUE;
so_linger.l_linger = 0;
z = setsockopt(s,
    SOL_SOCKET,
    SO_LINGER,
    &so_linger,
    sizeof so_linger);
if ( z )
    perror("setsockopt(2)");
    close(s); /* Abort connection */

 

在上面的这个例子中,当调用close函数时,套接口s会立即中止。中止的语义是通过将超时值设置为0来实现的。

以上是关于使用SO_LINGER缩短TIME_WAIT的时间,减少大量短链接堆积TIME_WAIT的主要内容,如果未能解决你的问题,请参考以下文章

windows 下解决 Time_Wait 和 CLOSE_WAIT 方法

Windows操作系统TIME_WAIT状态的TCP连接快速回收时间(性能测试时端口不够用)

Windows操作系统TIME_WAIT状态的TCP连接快速回收时间(性能测试时端口不够用)

提高网络效率的总结

TCP协议中的SO_LINGER选项

setsockopt 设置TCP的选项SO_LINGER