connection reset by peer 发生了什么?
一. 概述
在后台应用开发过程中,许多组件会打出日志,connection timeout, connection reset by peer,让人一头雾水。timeout 通常比较好理解,可能是网络不通。那么connection reset by peer 呢?
二. 预备知识
为了理解这个问题,我们需要一些tcp连接的基础知识,一个典型的tcp连接如下。
tcp 的握手挥手过程不再赘述,我们需要注意的是tcp是双向连接的,即我们常说的客户端和服务端
1.都有自己的监听端口
在linux中执行netstat命令,可以查看本机端口和另一端的端口
➜ / netstat
Active Internet connections
Proto Recv-Q Send-Q Local Address Foreign Address (state)
tcp4 0 0 192.168.0.102.59451 111.6.87.16.47798 ESTABLISHED
tcp4 0 0 localhost.cplscrambler localhost.59450 ESTABLISHED
tcp4 0 0 localhost.59450 localhost.cplscrambler ESTABLISHED
tcp4 0 0 192.168.0.102.59441 111.6.87.16.47798 ESTABLISHED
tcp4 0 0 localhost.cplscrambler localhost.59440 ESTABLISHED
tcp4 0 0 localhost.59440 localhost.cplscrambler ESTABLISHED
tcp4 0 0 192.168.0.102.59413 49.7.21.45.http ESTABLISHED
如果是服务器,监听的端口范围更广泛,如果有客户端连接,会单独创建一条tcp连接
tcp46 0 0 *.6666 *.* LISTEN
2.都可以主动发起连接,发送数据和返回ack,断开连接。
3.都有自己的发送窗口和接受窗口,用来缓存数据报文
三. 常见原因
一般connection reset by peer 对应tcp RST 报文。
1. 针对不存在端口的连接请求,比如服务器端口为localhost:8080,访问的却是 localhost:8081
2.主机终止一条连接,客户端或者服务端在tcp连接的过程中主动发送RST报文段,断开连接
3.半开连接(half-open),通常出现在某一段的异常关机(比如电源切断),正常工作的一端将不会检测出另一端已经崩溃,发送数据报文会得到RST 报文。
4.时间等待错误,在TIME_WAIT 期间收到的消息也会返回RST 报文。
四.模拟
我们这里来模拟第三种情况
1.机器准备
客户端使用时我的mac机器,服务端使用的云服务器
云服务器上安装sock程序 (http://www.icir.org/christian/sock.html),该程序需要进行编译
2.在云服务器上启动sock 服务
服务端口号为6666
[root@iZbp1hh62zkt10csxrr34uZ ~]# sock -i -s -v 6666
3.在本机使用telnet连接
➜ / telnet 120.26.97.171 6666
Trying 120.26.97.171...
Connected to 120.26.97.171.
Escape character is '^]'.
aaa
bbb
发送一些数据后,在服务端能看到变化
[root@iZbp1hh62zkt10csxrr34uZ ~]# sock -i -s -v 6666
connection on 172.24.249.245.6666 from 171.113.24.170.8810
TCP_MAXSEG = 1400
received 5 bytes
received 5 bytes
4.然后强制关闭mac上的进程, 云服务器会提示 connection reset by peer
[root@iZbp1hh62zkt10csxrr34uZ ~]# sock -i -s -v 6666
connection on 172.24.249.245.6666 from 171.113.24.170.5287
TCP_MAXSEG = 1400
received 5 bytes
received 5 bytes
received 1 bytes
received 63 bytes
connection closed by peer
[root@iZbp1hh62zkt10csxrr34uZ ~]#
客户端使用wireshark抓包如下
前三条报文用于建立tcp连接,后四条报文用于发送数据
五.参考
《tcp/ip详解》卷一