TCP的三次握手四次挥手
一、三次握手
1.wireshark 抓包

2.TCP报文手部

注意标志位:
1).同步 SYN = 1 表示这是一个连接请求或连接接受报文。
2).只有当 ACK = 1 时确认号字段才有效。当 ACK = 0 时,确认号无效。
3).FIN = 1 表明此报文段的发送端的数据已发送完毕,并要求释放运输连接。
3.连接示意

二、四次挥手
1.知所以然
为什么建立连接协议是三次握手,而关闭连接却是四次握手呢?
这是因为服务端的LISTEN状态下的SOCKET当收到SYN报文的建连请求后,它可以把ACK和SYN(ACK起应答作用,而SYN起同步作用)
放在一个报文里来发送。但关闭连接时,当收到对方的FIN报文通知时,它仅仅表示对方没有数据发送给你了;但未必你所有的数据都全部
发送给对方了,所以你可以未必会马上会关闭SOCKET,也即你可能还需要发送一些数据给对方之后,再发送FIN报文给对方来表示你同意
现在可以关闭连接了,所以它这里的ACK报文和FIN报文多数情况下都是分开发送的。
更明了的回答:由于TCP连接是全双工的,因此每个方向都必须单独进行关闭。这个原则是当一方完成它的数据发送任务后就能发送一
个FIN来终止这个方向的连接。收到一个 FIN只意味着这一方向上没有数据流动,一个TCP连接在收到一个FIN后仍能发送数据。首先进行
关闭的一方将执行主动关闭,而另一方执行被动关闭。
2.图示

第一阶段
- 首先client会发送一个FIN包给server(同时还有ack和seq包),这是要告诉server,我已经没有数据要发给你了,此时client处于FIN_WAIT_1状态。接收到FIN包的server处于CLOSE_WAIT的状态。
- server发回一个ACK(值为client传过来的seq+1)和seq(值为client传过来的ack的值)给client。client收到server发过来的包后确认关闭连接,此时client处于FIN_WAIT_2。
第二阶段
- server在接收到client的FIN后,得知client要断开tcp连接了,于是在发送完ack和seq给client后,自己发送一个FIN包给client(也带有ack和seq包),告诉client我也要断开连接了,此时server处于LAST_ACK状态。
- client接收到server的FIN信息后,会回复server一个ack包,并且会进入TIME_WAIT状态,持续2个MSL(Max Segment Lifetime)。而server接收到client ack后便关闭连接。client在指定时间过后仍然没有接收到server的数据,确认server已经没有数据过来,也关闭了连接。
(1)、CLOSE_WAIT的解释。
在以上事例,我们知道server在接收到FIN后,发送ACK之前会进入CLOSE_WAIT,如果长期处于这个状态,或者说服务器出现大量CLOSE_WAIT,说明ACK包一直没有发出,这时候就应该检查代码了。
(2)、TIME_WAIT注意事项
从事例我们知道,主动关闭连接的一方会经历TIME_WAIT状态,在该状态下的socket是不会被回收的。而如果是服务器端主动关闭连接,则可能会面临处于大量TIME_WAIT的情况(因为连接很多嘛),会严重影响服务器的处理能力。
怎么解决呢,那就减少服务器端TIME_WAIT的时间咯。
(3)2MSL(Maximum Segment Lifetime)存在的理由
TCP的TIME_WAIT状态也称为2MSL等待状态
(4)2MSL状态为什么设计在主动关闭这一方
(1)发最后ack的是主动关闭一方
(2)只要有一方保持TIME_WAIT状态,就能起到避免incarnation connection在2MSL内的重新建立,不需要两方都有
三、TCP连接出现大量TIME_WAIT的解决办法
主动关闭TCP/IP连接,会通过TIME_WAIT的状态保留一段时间,时间过了才会释放这个端口,当端口接受的频繁请求数量过多的时候,
就会产生大量的TIME_WAIT状态的连接,这些连接占着端口,会消耗大量的资源。
这个TIME_WAIT的作用是什么?
原因有二:
一、保证TCP协议的全双工连接能够可靠关闭
如果Client直接CLOSED了,那么由于IP协议的不可靠性或者是其它网络原因,导致Server没有收到Client最后回复的ACK。那么Server就会在超时之后继续发送FIN。 此时由于Client已经CLOSED了,就找不到与重发的FIN对应的连接,最后Server就会收到RST而不是ACK,Server就会以为是连接错误把问题报告给高层。 这样的情况虽然不会造成数据丢失,但是却导致TCP协议不符合可靠连接的要求。 所以,Client不是直接进入CLOSED,而是要保持TIME_WAIT,当再次收到FIN的时候,能够保证对方收到ACK,最后正确的关闭连接。
二、保证这次连接的重复数据段从网络中消失
如果Client直接CLOSED,然后又再向Server发起一个新连接,我们不能保证这个新连接与刚关闭的连接的端口号是不同的。也就是说有可能新连接和老连接的端口号是相同的。
一般来说不会发生什么问题,但是还是有特殊情况出现:假设新连接和已经关闭的老连接端口号是一样的,如果前一次连接的某些数据仍然滞留在网络中,这些延迟数据在建立新连接之后才到达Server,由于新连接和老连接的端口号是一样的,又因为TCP协议判断不同连接的依据是socket pair。
于是,TCP协议就认为那个延迟的数据是属于新连接的,这样就和真正的新连接的数据包发生混淆了。
vi /etc/sysctl.conf
#当出现SYN等待队列溢出时,启用cookies来处理,可防范少量SYN攻击
net.ipv4.tcp_syncookies = 1 #允许将TIME-WAIT sockets重新用于新的TCP连接,默认为0
net.ipv4.tcp_tw_reuse = 1 #开启TCP连接中TIME-WAIT sockets的快速回收,默认为0,表示关闭
net.ipv4.tcp_tw_recycle = 1 # 默认60
net.ipv4.tcp_fin_timeout = 30 /sbin/sysctl -p
此外,如果你的连接数本身就很多,我们可以再优化一下TCP/IP的可使用端口范围,进一步提升服务器的并发能力。
net.ipv4.tcp_keepalive_time = 1200
表示当keepalive起用的时候,TCP发送keepalive消息的频度。缺省是2小时,改为20分钟。
net.ipv4.ip_local_port_range = 10000 65000
表示用于向外连接的端口范围。缺省情况下很小:32768到61000,改为10000到65000。设的太低,否则可能会占用掉正常的端口
net.ipv4.tcp_max_syn_backlog = 8192
表示SYN队列的长度,默认为1024,加大队列长度为8192,可以容纳更多等待连接的网络连接数。
net.ipv4.tcp_max_tw_buckets = 5000
表示系统同时保持TIME_WAIT的最大数量,如果超过这个数字,TIME_WAIT将立刻被清除并打印警告信息。默认为180000,改为5000。对于Apache、Nginx等服务器,上几行的参数可以很好地减少TIME_WAIT套接字数量。
参考:TCP连接的建立和释放
TCP的三次握手四次挥手的更多相关文章
- 在深谈TCP/IP三步握手&四步挥手原理及衍生问题—长文解剖IP
如果对网络工程基础不牢,建议通读<细说OSI七层协议模型及OSI参考模型中的数据封装过程?> 下面就是TCP/IP(Transmission Control Protoco/Interne ...
- [na]TCP的三次握手四次挥手/SYN泛洪
1.TCP报文格式 上图中有几个字段需要重点介绍下: (1)序号:Seq序号,占32位,用来标识从TCP源端向目的端发送的字节流,发起方发送数据时对此进行标记. (2)确认序号:Ack序号,占32位, ...
- TCP/IP三次握手四次挥手
本文通过图来梳理TCP-IP协议相关知识.TCP通信过程包括三个步骤:建立TCP连接通道,传输数据,断开TCP连接通道.如图所示,给出了TCP通信过程的示意图. TCP 三次握手四次挥手 主要包括三部 ...
- TCP协议—三次握手四次挥手的原理<转>
三次握手四次挥手的原理 TCP是面向连接的,无论哪一方向另一方发送数据之前,都必须先在双方之间建立一条连接.在TCP/IP协议中,TCP 协议提供可靠的连接服务,连接是通过三次握手进行初始化的.三 ...
- 救救孩子吧,到现在还搞不懂TCP的三次握手四次挥手
本文在个人技术博客同步发布,详情可用力戳 亦可扫描屏幕右侧二维码关注个人公众号,公众号内有个人联系方式,等你来撩... 前几天发了一个朋友圈,发现暗恋已久的女生给我点了个赞,于是我当晚辗转反侧.彻 ...
- 通俗了解TCP/IP三次握手四次挥手
前言: tcp/ip通信机制是计算机中很重要的一个知识点,不是一句两句就能解释清楚的,需要反复推敲其中的玄妙. 通俗理解: 但是为什么一定要进行三次握手来保证连接是双工的呢,一次不行么?两次不行么?我 ...
- TCP的三次握手四次挥手理解及面试题
一.TCP概述 每一条TCP连接都有两个端点,这种端点我们叫作套接字(socket),它的定义为端口号拼接到IP地址即构成了套接字, 例如,若IP地址为192.0.0.1 而端口号为8000,那么得到 ...
- 详解 TCP的三次握手四次挥手
本文转载来自https://blog.csdn.net/qzcsu/article/details/72861891 背景描述 通过上一篇中网络模型中的IP层的介绍,我们知道网络层,可以实现两个主机之 ...
- TCP/IP 三次握手-四次挥手
TCP的建立需要三次握手,断开需要四次挥手. 首先三次握手: 首先,客户机向服务器发送请求报文,服务器回复ACK,并分配资源,而客户端接受到ACK后回复确认报文,并分配资源,此时三次握手完成. 四次挥 ...
随机推荐
- libyuv 编译for ios
这里有编译好的库 https://bintray.com/yarr/ios/libyuv-ios# lipo -info libyuv.a Architectures in the fat file ...
- js:语言精髓笔记6----作用域
js基础语法:由语句.表达式和变量构成: 语句是主要表达方式:单语句->复合语句(代码块)->程序片段(函数):js中没有单元和程序的概念: 作用域: 语法作用域与变量作用域的区别:前 ...
- 算法教程(1)zz
Introduction Many TopCoders seem to be mortally afraid of geometry problems. I think it's safe to sa ...
- 折线分割平面[HDU2050]
折线分割平面 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Subm ...
- 【wikioi】1217 借教室
题目链接http://www.wikioi.com/problem/1217/ 算法:二分答案(线段树可过wikioi数据) 二分:http://www.wikioi.com/solution/lis ...
- java中的sleep()和wait()的区别
对于sleep()方法,我们首先要知道该方法是属于Thread类中的.而wait()方法,则是属于Object类中的. sleep()方法导致了程序暂停执行指定的时间,让出cpu该其他线程,但是他的监 ...
- NSMakeRange,substringWithRange,substringToIndex,substringFromIndex区别和联系
typedef NSRange *NSRangePointer; NS_INLINE NSRange NSMakeRange(NSUInteger loc, NSUInteger len) { ...
- php 版本的indexof —— strpos坑爹
如果没有找到则会返回false,如果是在第一位,那么会返回0.那么在if判断的时候会非常麻烦. 我的方法是转化为string,当返回0的时候则是"0",如果返回的是false,则会 ...
- OS | 读写锁【摘】
读写锁是用来解决读者写者问题的,读操作可以共享,写操作是排他的,读可以有多个在读,写只有唯一个在写,同时写的时候不允许读. 互斥锁与读写锁的区别: 当访问临界区资源时(访问的含义包括所有的操作:读和写 ...
- Excel 2003 中如何用VBA 代码访问单元格里的值及操作单元格 - 唐诗宋词的专栏 - 博客频道 - CSDN.NET
在Excel 中编写VBA 代码,最常做的事可能就是操作表单中单元格里的数据. 我这里总结一下如何从VBA 代码中操作单元格的数据. 在VBA 代码中操作单元格需要用到Range 对象,Range 是 ...