如果从同一个客户端应用程序收到 2 个 SYN 数据包,服务器端会发生什么?

网络工程 路由 tcp linux
2022-02-15 02:50:09

一旦服务器从客户端应用程序获得 SYN 数据包,它就会进入 SYN_RECV 状态。

如果从同一个客户端应用程序收到 2 个 SYN 数据包,服务器端会发生什么?

2个回答

基本上,接收重复 SYN 的 TCP 将 SYN,ACK 它们,但它会收到重复的 RST。

RFC 793,传输控制协议,第 3.4 节。建立连接正好解释了这种情况:

3.4. 建立连接

“三次握手”是用于建立连接的过程。这个过程通常由一个 TCP 发起并由另一个 TCP 响应。如果两个 TCP 同时启动该过程,该过程也可以工作。当同时尝试发生时,每个 TCP 都会收到一个“SYN”段,该段在发送“SYN”后不携带确认。当然,旧的重复“SYN”段的到来可能会使接收者觉得同时启动连接正在进行中。正确使用“重置”段可以消除这些情况的歧义。

在本节的后面,它会更详细地介绍:

三次握手的主要原因是为了防止旧的重复连接启动造成混乱。为了解决这个问题,已经设计了一个特殊的控制消息,reset。如果接收 TCP 处于非同步状态(即 SYN-SENT、SYN-RECEIVED),它会在接收到可接受的复位后返回 LISTEN。如果 TCP 处于同步状态之一(ESTABLISHED、FIN-WAIT-1、FIN-WAIT-2、CLOSE-WAIT、CLOSING、LAST-ACK、TIME-WAIT),它会中止连接并通知其用户。我们在下面的“半开”连接下讨论后一种情况。

    TCP A                                                TCP B

1.  CLOSED                                               LISTEN

2.  SYN-SENT    --> <SEQ=100><CTL=SYN>               ...

3.  (duplicate) ... <SEQ=90><CTL=SYN>               --> SYN-RECEIVED

4.  SYN-SENT    <-- <SEQ=300><ACK=91><CTL=SYN,ACK>  <-- SYN-RECEIVED

5.  SYN-SENT    --> <SEQ=91><CTL=RST>               --> LISTEN

6.              ... <SEQ=100><CTL=SYN>               --> SYN-RECEIVED

7.  SYN-SENT    <-- <SEQ=400><ACK=101><CTL=SYN,ACK>  <-- SYN-RECEIVED

8.  ESTABLISHED --> <SEQ=101><ACK=401><CTL=ACK>      --> ESTABLISHED

                  Recovery from Old Duplicate SYN

                             Figure 9.

作为从旧副本恢复的简单示例,请考虑图 9。在第 3 行,旧副本 SYN 到达 TCP B。TCP B 无法判断这是旧副本,因此它正常响应(第 4 行)。TCP A 检测到 ACK 字段不正确,并返回一个 RST(重置),并选择其 SEQ 字段以使该段可信。TCP B 在收到 RST 后,返回 LISTEN 状态。当原始的 SYN(双关语)最终到达第 6 行时,同步正常进行。如果第 6 行的 SYN 在 RST 之前到达,则在双向发送 RST 时可能会发生更复杂的交换。

RFC 是 TCP 的定义,你应该参考它。还有后来的 RFC 对其进行了更新(RFC 1122、3168、6093、6528)。

服务器将简单地重置客户端重新发送的同步数据包,并将其视为重复数据包。

基本上,由于 TCP 是可靠的协议,因此 TCP 握手成功后只有实际应用程序数据被传输。

  Client --------------- Server 
  1. .. 客户端发送同步数据包
  2. 服务器返回 SYN-ACK 3) 再次从客户端收到 SYN-ACK。客户端向服务器发送 Ack 消息。

在此期间,任何数据包被丢弃的主机都会重新传输数据包。但如果它被认为是重复数据包,请重置连接。