SYN和FIN都能携带数据吗?
SYN和FIN是TCP协议中三次握手和四次挥手的重要标志位。
第三次握手携带数据是常用,且在RFC 793中明确指出可行的。那SYN和FIN中我们能携带数据吗?
但在有些教材中,指出SYN不能携带,这是错误的。
早期的TCP 协议RFC 793并没有明确说SYN和FIN能不能带数据,它只限制了不能立刻交付数据给上层。(“this is perfectly legitimate, so long as the receiving TCP doesn’t deliver the data to the user until it is clear the data is valid (i.e., the data must be buffered at the receiver until the connection reaches the ESTABLISHED state)”——RFC 793 的第3.4节)。
所以它理论上是允许SYN携带数据的。为了SYN携带数据更方便,后续也有对应的TCP fast open。甚至说,在RFC 1379,在第一章举了一个合法但“畸形”的,把SYN、数据、FIN都放在一起的例子。
再后来,TCP协议 RFC 9293直接明确指出SYN携带数据是合法的,且不能带是一种误解。(“Note that it is legal to send and receive application data on SYN segments (this is the “text in the segment” mentioned above). There has been significant misinformation and misunderstanding of this topic historically.”——RFC 9293的第3.10.7.3节)
对于FIN能携带数据的肯定表述,并没有在网络上或相关协议上找到。只找到stackoverflow一个网友拿RFC 793中的“For sequence number purposes, the SYN is considered to occur before the first actual data octet of the segment in which it occurs, while the FIN is considered to occur after the last actual data octet in a segment in which it occurs.”来证明是能携带。用这句话来证明,这是不严谨的。
总之,个人觉得,SYN和FIN携带数据是“法无禁止即可为”。
题外话:我一直以为FIN和SYN携带数据都是不常用的,但是和B站UP主湖科大教书匠的讨论后,他说FTP有时候会出现携带FIN的数据包。由于我并无FTP服务器,对此并无验证。
但经我挂在电脑跑wireshark,只要时间长就能抓到了携带FIN。主要有两种,第一种是服务器向主机发出的最后的数据+FIN+ACK。第二种是主机发送FIN后,但收到服务器的RST报文。此后,主机会发送TCP Retransmission且携带数据+FIN+ACK。可见携带FIN的数据包并无想象中的那么少见。
参考资料:
[1] RFC 793
[2] RFC 9293
[3] RFC 1379