TCP全链接队列和半链接队列已满以后的链接创建过程抓包分析[转]

最近项目须要作单机100万长链接与高并发的服务器,咱们开发完服务器之后,经过本身搭的高速压测框架压测服务端的时候,发生了奇怪的现象,就是服务端莫名其妙的少接收了链接,形成了数据包的丢失,经过网上查资料,和本身的实践,下面是我作实验,抓包分析的过程以下:服务器

总共5个链接并发

其中全链接队列somaxconn参数为1表示监听队列的总长度(实际能够完成somaxconn+1个链接的创建)框架

半链接队列tcp_max_syn_backlog为1(实际能够将tcp_max_syn_backlog+1个syn分节放入其中)tcp

当全链接队列已满且半链接队列未满的状况下:高并发

当客户端发起一个syn分节时,服务端不会丢弃该syn分节,而是直接响应ack和syn,这时客户端响应ack,并成为established状态,而服务端收到ack响应后,试图将该syn分节从半链接队列中移除,并加入全连接队列,而后因为全链接队列已经满了,这时,在默认状况下,服务端啥也不作,并且不会将该链接由SYN_RECV变成ESTABLISHED,服务端仅仅只是建立一个定时器,以固定间隔重传syn和ack到服务端,直到到达系统默认的synack重传阖值,而后服务端将处于半链接队列里面的syn分节丢弃,此时服务端只剩2个链接。这个时候客户端一侧的链接仍然有5个established测试

当全链接已满且半链接队列也满的状况下:队列

当客户端发起一个syn分节时,服务端发现半链接队列已经满了,同时该syn分节还没有重传过,服务端直接丢弃该syn分节,而后客户端过了4秒重传syn分节,这个时候服务端发现半链接队列已满同时,该syn分节已经重传过了,服务端收下了该syn分节,并响应客户端syn+ack,客户端收到syn+ack后,响应ack。客户端三次握手已经完成,而服务端收到ack以后,发现全链接队列是满的,这个时候不会将该链接从SYN_RECV转换成ESTABLISHED,服务端建立定时器,定时重传syn+ack, 直到到达系统默认的synack重传阖值,而后服务端将处于半链接队列里面的syn分节丢弃ip

 

具体以下开发

使用tcpdump -i eth0 -l -nn -S  port 8000 -c 40 -w out.txt定时器

以下所示,测试环境在Linux 2.6.18-164.el5 

全链接队列  cat /proc/sys/net/core/somaxconn  1

半链接队列  cat /proc/sys/net/ipv4/tcp_max_syn_backlog  1

监听端口 8000

以客户端创建5条链接为例

1.临时端口号为53991的客户端链接向监听端口为8000的服务端链接发起syn分节,客户端状态变为SYN_SEND状态

   服务端收到来自客户端的syn分节后,这个时候因为半链接队列未满,直接将syn分节放入半链接队列,同时向客户端发送了一个ack+syn分节,此时服务端进入SYN_RECV状态

   客户端收到服务端发送的syn分节以后,向服务端回传了ack确认分节,客户端进入ESTABLISHED状态

   服务端收到来自客户端的ack确认以后,就试图把syn分节从半链接队列中移除,并加入到全链接队列,因为全链接队列未满,此时该syn分节成功转入全链接队列,服务端的状  

   态从SYN_RECV转换成了ESTABLISHED状态

2.临时端口号为53992的客户端链接和临时端口号为53991的链接一样顺利的完成3次握手

   根据以上链接基本能够得出一个结论,能创建起全链接队列长度+1个长链接

3.临时端口号为53993的客户端链接向监听端口为8000的服务端链接发起syn分节,客户端状态变为SYN_SEND状态

   服务端收到来自客户端的syn分节后,这个时候因为半链接队列未满,直接将syn分节放入半链接队列,同时向客户端发送一个ack+syn分节,此时服务端进入SYN_RECV状态

   客户端收到服务端发送的syn分节以后,向服务端回传了ack确认分节,客户端进入ESTABLISHED状态

   服务端收到来自客户端的ack确认以后,就试图把syn分节从半链接队列中移除,并加入全链接队列,因为全链接队列已经满了,此时该syn分节没法转入全链接队列,也就不会

   从SYN_RECV转换为ESTABLISHED状态系统默认会把该syn标记为acked模式,并创建定时器,定时从服务端重传syn+ack分节,客户端此时已经处于ESTABLISHED状态,

   不过在收到服务端发送的syn+ack分节后,仍然响应服务端ack。服务端继续上面的过程,直到到达synack(cat /proc/sys/net/ipv4/tcp_synack_retries )重传的阖值,而后抛弃

   该syn分节

4.临时端口号为53994的客户端链接和临时端口号为53993的链接一样的过程

    根据以上链接基本能够得出一个结论,半链接队列能容下半链接队列长度+1个syn分节

5.临时端口号为53995的客户端链接向监听端口为8000的服务端链接发起syn分节,客户端状态变为SYN_SEND状态

   服务端收到来自客户端的syn分节后,这个时候半链接队列已经满了,服务端发现该syn分节还没有重传过,默认直接丢弃该syn分节,客户端在超时时间内并未收到来自服务端的

   ack响应,大约过了3秒,客户端重传了syn分节,这个时候服务端收到syn分节以后,发现该分节已经收到过,此次服务端收下了syn分节,并向客户端发送syn+ack。客户端

   收到来自服务端的ack+syn以后,向服务端发送ack,客户端进入ESTABLISHED状态,服务端收到来自客户端的ack以后,试图把syn分节从半链接队列中移除,并添加到全连

   接队列,因为半链接队列已满,加入全链接队列失败,和临时端口号53993以及53994的行为是同样的

 

 

1.

20:25:57.637476 IP 192.168.172.128.53991 > 192.168.172.128.8000: S 3828162025:3828162025(0) win 32792 <mss 16396,sackOK,timestamp 250818 0,nop,wscale 6>

20:25:57.637483 IP 192.168.172.128.8000 > 192.168.172.128.53991: S 3826007261:3826007261(0) ack 3828162026 win 32768 <mss 16396,sackOK,timestamp 250818 250818,nop,wscale 6>

20:25:57.637486 IP 192.168.172.128.53991 > 192.168.172.128.8000: . ack 3826007262 win 513 <nop,nop,timestamp 250818 250818>

2.

20:25:58.638894 IP 192.168.172.128.53992> 192.168.172.128.8000: S 3822825008:3822825008(0) win 32792 <mss 16396,sackOK,timestamp 251820 0,nop,wscale 6>

20:25:58.638984 IP 192.168.172.128.8000 > 192.168.172.128.53992: S 3829073969:3829073969(0) ack 3822825009 win 32768 <mss 16396,sackOK,timestamp 251820 251820,nop,wscale 6>

20:25:58.638995 IP 192.168.172.128.53992 > 192.168.172.128.8000: . ack 3829073970 win 513 <nop,nop,timestamp 251820 251820>

3.

20:25:59.640701 IP 192.168.172.128.53993> 192.168.172.128.8000: S 3828629154:3828629154(0) win 32792 <mss 16396,sackOK,timestamp 252821 0,nop,wscale 6>

20:25:59.640713 IP 192.168.172.128.8000 > 192.168.172.128.53993: S 3833556338:3833556338(0) ack 3828629155 win 32768 <mss 16396,sackOK,timestamp 252821 252821,nop,wscale 6>

20:25:59.640719 IP 192.168.172.128.53993 > 192.168.172.128.8000: . ack 3833556339 win 513 <nop,nop,timestamp 252821 252821>

4.

20:26:00.642260 IP 192.168.172.128.53994 > 192.168.172.128.8000: S 3820886884:3820886884(0) win 32792 <mss 16396,sackOK,timestamp 253823 0,nop,wscale 6>

20:26:00.642345 IP 192.168.172.128.8000> 192.168.172.128.53994: S 3831669364:3831669364(0) ack 3820886885 win 32768 <mss 16396,sackOK,timestamp 253823 253823,nop,wscale 6>

20:26:00.642356 IP 192.168.172.128.53994> 192.168.172.128.8000: . ack 3831669365 win 513 <nop,nop,timestamp 253823 253823>

5.

20:26:01.645291 IP 192.168.172.128.53995> 192.168.172.128.8000: S 3824454212:3824454212(0) win 32792 <mss 16396,sackOK,timestamp 254826 0,nop,wscale 6>

3.

20:26:03.040319 IP 192.168.172.128.8000 > 192.168.172.128.53993: S 3833556338:3833556338(0) ack 3828629155 win 32768 <mss 16396,sackOK,timestamp 256221 252821,nop,wscale 6>

20:26:03.040332 IP 192.168.172.128.53993 > 192.168.172.128.8000: . ack 3833556339 win 513 <nop,nop,timestamp 256221 256221,nop,nop,sack 1 {3833556338:3833556339}>

4.

20:26:03.842281 IP 192.168.172.128.8000 > 192.168.172.128.53994: S 3831669364:3831669364(0) ack 3820886885 win 32768 <mss 16396,sackOK,timestamp 257023 253823,nop,wscale 6>

20:26:03.842295 IP 192.168.172.128.53994 > 192.168.172.128.8000: . ack 3831669365 win 513 <nop,nop,timestamp 257023 257023,nop,nop,sack 1 {3831669364:3831669365}>

5.

20:26:04.645946 IP 192.168.172.128.53995 > 192.168.172.128.8000: S 3824454212:3824454212(0) win 32792 <mss 16396,sackOK,timestamp 257826 0,nop,wscale 6>

20:26:04.645962 IP 192.168.172.128.8000 > 192.168.172.128.53995: S 3832652478:3832652478(0) ack 3824454213 win 32768 <mss 16396,sackOK,timestamp 257826 257826,nop,wscale 6>

20:26:04.645971 IP 192.168.172.128.53995 > 192.168.172.128.8000: . ack 3832652479 win 513 <nop,nop,timestamp 257826 257826>

20:26:08.846521 IP 192.168.172.128.8000 > 192.168.172.128.53995: S 3832652478:3832652478(0) ack 3824454213 win 32768 <mss 16396,sackOK,timestamp 262026 257826,nop,wscale 6>

20:26:08.846534 IP 192.168.172.128.53995 > 192.168.172.128.8000: . ack 3832652479 win 513 <nop,nop,timestamp 262026 262026,nop,nop,sack 1 {3832652478:3832652479}>

3.

20:26:09.246438 IP 192.168.172.128.8000 > 192.168.172.128.53993: S 3833556338:3833556338(0) ack 3828629155 win 32768 <mss 16396,sackOK,timestamp 262426 256221,nop,wscale 6>

20:26:09.246452 IP 192.168.172.128.53993 > 192.168.172.128.8000: . ack 3833556339 win 513 <nop,nop,timestamp 262426 262426,nop,nop,sack 1 {3833556338:3833556339}>

4.

20:26:09.853232 IP 192.168.172.128.8000 > 192.168.172.128.53994: S 3831669364:3831669364(0) ack 3820886885 win 32768 <mss 16396,sackOK,timestamp 263026 257023,nop,wscale 6>

20:26:09.853246 IP 192.168.172.128.53994 > 192.168.172.128.8000: . ack 3831669365 win 513 <nop,nop,timestamp 263026 263026,nop,nop,sack 1 {3831669364:3831669365}>

5.

20:26:15.055318 IP 192.168.172.128.8000 > 192.168.172.128.53995: S 3832652478:3832652478(0) ack 3824454213 win 32768 <mss 16396,sackOK,timestamp 268228 262026,nop,wscale 6>

20:26:15.055335 IP 192.168.172.128.53995 > 192.168.172.128.8000: . ack 3832652479 win 513 <nop,nop,timestamp 268228 268228,nop,nop,sack 1 {3832652478:3832652479}>

3.

20:26:21.260288 IP 192.168.172.128.8000 > 192.168.172.128.53993: S 3833556338:3833556338(0) ack 3828629155 win 32768 <mss 16396,sackOK,timestamp 274430 262426,nop,wscale 6>

20:26:21.260308 IP 192.168.172.128.53993 > 192.168.172.128.8000: . ack 3833556339 win 513 <nop,nop,timestamp 274430 274430,nop,nop,sack 1 {3833556338:3833556339}>

相关文章
相关标签/搜索