分析tcp协议原理
原理四个主要方面:一、tcp协议之连接建立、断开二、tcp协议之超时重传三、tcp协议之窗口管理四、tcp协议之拥塞控制TCP是一种面向有连接的协议,也就是说必须确认对方存在时才能发送数据而TCP通过检验和、序列号、确认应答、重发控制、连接管理、窗口控制等机制来实现可靠传输。1. 目的:TCP三次握手是客户端和服务器总共发三个数据包,通过三个数据包来确认主动发送能力和被动接收能力是否正常。2. 实质:通过指定的四元组(源地址、源端口、目标地址、目标端口)来建立TCP连接,同步双方各自发送序列号seq和确认号ACK,同时也会交换窗口大小信息三次握手过程的实现方式就是交换序列号seq。随便在网上找个地址,如果通过域名想看ip地址,可以ping下看连接。① 192.168.3.7发送[SYN]报文段至222.169.228.146,告知序列号x为0。② 222.169.228.146发送[SYN,ACK]报文段至192.168.3.7,告知序列号y为0,确认号ACK为x+1=1。③192.168.3.7发送[ACK]报文段至222.169.228.146,告知确认号ACK为y+1=1。报文段中的其他参数:MSS=1460:允许从对方接收到的最大报文段,图中为1460字节(指承载的数据,不包含报文段的头部)。win=8192:滑动窗口的大小为8192字节。SACK_PERM=1:开启选择确认。为什么会使用SACK:tcp确认方式不是一段报文段一确认,而是采用累积确认方式。服务器接收到的报文段无序所以序列号也是不连续,服务器的接收队列会出现空洞情况。为了解决空洞,提前了解当前空洞,应对丢失遗漏,采取重传。提前了解方式就是通过SACK选项信息,SACK信息包含接收方已经成功接收的数据块的序列号范围。而SACK_PERM字段为1表明,选择开启了SACK功能。网络层可能会出现丢失、重复、乱序的问题,tcp是提供可靠的数据传输服务的,为了保证数据的正确性,tcp协议会重传它认为的已经丢失的包。重传两种机制:一种基于时间重传,一种基于确认报文段提供的信息重传。RTT:数据完全发送完(完成最后一个比特推送到数据链路上)到收到确认信号的时间(往返时间)。RTO:重传超时时间(tcp发送数据时设置一个计时器,当计时器超时没有收到数据确认信息,引发超时而重传,判断的标准就是RTO)。思考:发送序列号为1、2、3、4这4个报文段,但是出现了序列号2报文段丢失,怎么办?发送端接收到seq1的确认报文(ACK=2)后,等待seq=2的确认报文。接收端当收到序列号为3的报文(2已丢失),发送ack为4的确认报文,发送端正等待ack为2的确认报文,面对跳跃的报文,那么发送端会一直等待,直到超出指定时间,重传报文2。为什么不跳跃确认呢?tcp是累积确认方式,如果确认报文3,那么意味着报文1和报文2都已经成功接收。超时处理方式:思考:上面计时器是以时间为标准重传,那么可以通过确认报文的次数来决定重传。发送端接收到seq1的确认报文(ACK=2)后,等待seq=2的确认报文。接收端收到报文3、4、5,但是没收到报文2,那么接收端发送三个ACK为2的确认报文,发送端收到这个三个确认报文,重传报文2。思考:如果快速重传中丢失包的地方很多(报文2,报文,7,报文9,报文30,报文300....),那么需要从头到尾都重传,这很蛋疼?思考:SACK重传对于接收到重复数据段怎样运作没有明确规定,通过DSACK重传可以让发送方知道哪些数据被重复接收了,而且明确是什么原因造成的。发送端没有收到100-199的ACK包,超过指定时间,重传报文。接收端都已经收到200-299的发送报文了,又来100-199是重复报文。再向发送端发送一个ACK报文,设置SACK 100-199,告知发送端,已经收到了100-199包,只是回应ACK包丢失。发送端发送包100-199,由于网络延迟,一直没有达到接收端。接收端连续发送三个ACK 200确认报文,触发快速重传,发送端收到了ACK 500的确认报文,表明之前的报文都已经交付成功。接收端又收到了延迟的报文100-199,再次向发送端发送一个SACK 100-199的ACK 500报文。发送端发现这是重复报文,判断为网络延迟造成的。计时器重传:根据超时,重传。快速重传:根据接收三次相同ACK报文,重传。选择确认重传:根据接收端提供的SACK信息,重传。DSACK重传:根据重复报文,明确丢失ACK报文还是网络延迟。Category1:已发送且已确认(已经收到ACK报文的数据)。Category2:已发送但未收到确认。Category3:即将发送。Category4:窗口移动前都不能发送。可用窗口:46-51字节。发送窗口:32-51字节。RCV.NXT:左边界RCV.WND:接收窗口RCV.NXT+RCV.WND:右边界接收端接收到序列号小于左边界,那么被认为重复数据而被丢弃。接收端接收到序列号大于右边界,那么被认为超出处理范围,丢弃。注意:tcp协议为累积ACK结构,只有当达到数据序列号等于左边界时,数据才不会被丢弃。如果窗口更新ACK丢失,对于发送端,窗口左边界右移,已发送数据得到ACK确认之后,左右边界距离减小,发送端窗口会减小,当左右边界相等时,称为零窗口。零窗口之后:接收端发送窗口更新能会发生窗口更新ACK丢失。<>解释:TCP是通过接收端的通告窗口来实现流量控制的,通告窗口指示了接收端可接收的数据量。当窗口值变为0时,可以有效阻止发送端继续发送,直到窗口大小恢复为非零值。当接收端重新获得可用空间时,会给发送端传输一个窗口更新告知其可继续发送数据。这样的窗口更新通常都不包含数据(纯ACK),接收端向发送端发送的窗口更新ACK可能丢失。结果双方处于等待状态,发生死锁。解决方案:发送端会采用一个持续计时器间歇性地查询接收端,看其窗口是否已增长。触发窗口探测,强制要求接收端返回ACK。发送几次探测,窗口大小还是0,那么断开连接。出现SWS的情况:① 接收端通告窗口太小。② 发送端发送的数据太小。解决方案:① 针对接收端:不应通告小窗口值[RFC1122]描述:在窗口可增至一个全长的报文段(接收端MSS)或者接收端缓存空间的一半(取两者中较小值)之前,不能通告比当前窗口更大的窗口值。标准:min(MSS , 缓存空间/2)。② 针对发送端:不应发送小的报文至少满足以下其一:(1)可以发送MSS字节的报文。window size >= MSS或者 数据大小>=MSS(2)数据段长度>=接收端通告过的最大窗口值的一半,才可以发送。收到之前发送的数据的ack回包,再发送数据,否则一直攒数据。(3) -1 没有未经确认的在传数据或者-2 连接禁用Nagle算法。tcp基于ACK数据包中的通告窗口大小字段实现了流量控制。当网络大规模通信负载而瘫痪,默认网络进入拥塞状态,减缓tcp的传输。发送方和接收方被要求承担超负荷的通信任务时,采取降低发送速率或者最终丢弃部分数据的方法。反映网络传输能力的变量称为拥塞窗口(cwnd)。通告窗口(awnd)。发送窗口swnd=min(cwnd,awnd)目的:tcp在用拥塞避免算法探寻更多可用带宽之前得到cwnd值,帮助tcp建立ACK时钟。[RFC5681] :在传输初始阶段,由于未知网络传输能力,需要缓慢探测可用传输资源,防止短时间内大量数据注入导致拥塞。慢启动算法针对这一问题而设计。在数据传输之初或者重传计时器检测到丢包后,需要执行慢启动。拥塞窗口值:每收到一个ACK值,cwnd扩充一倍。所以假设没有丢包且每个数据包都有相应ACK值,在k轮后swnd=,成指数增长。SMSS是发送方的最大段大小。慢启动阶段,cwnd会指数增长,很快,帮助确立一个慢启动阙值(ssthresh)。有了阙值,tcp会进入拥塞避免阶段,cwnd每次增长值近似于成功传输的数据段大小,成线性增长。实现公式:cwnd+=SMSS*SMSS/cwnd刚建立连接使用慢启动算法,初始窗口为4,收到一次ACK后,cwnd变为8,再收到一次ACK后,cwnd变为16,依次继续,32、64,达到阙值ssthresh为64。开始使用拥塞避免算法,设置ssthresh为ssthresh/2,值为32。重新从初始窗口4,线性递增到ssthresh=32。当cwnd < ssthresh时,使用慢启动算法当cwnd > ssthresh时,使用拥塞避免算法应用快速恢复算法时机:启动快速重传且正常未失序ACK段达到之前。启动快速恢复算法。实现过程:① 将ssthresh设置为1/2 cwnd,将cwnd设置为ssthresh+3*SMSS。② 每接收一个重复ACK,cwnd值暂时增加1 SMSS。③当接收到新数据ACK后,将cwnd设置为ssthresh。参考:<>

PPP协议的工作原理 - kummer话你知
我们知道,数据链路层协议运行在物理层之上,网络层之下。而底层的物理层,只能提供简单的bit流的物理信道,功能非常原始,如果直接使用物理层进行通讯,肯定是非常不方便的,所以数据链路层会在底层物理层提供的功能基础之上,提供一些增值服务,方便上面的网络层使用。所以可能认为数据链路层是对物理层功能的增强。如果您想用尽量少的词来记住数据链路层,那就是:“帧和介质访问控制”。典型的数据链路层功能包括:为了使传输中发生差错后只将有错的有限数据进行重发,同时,也为了上层使用起来更加方便,数据链路层将比特流组合成以帧为单位传送。每个帧除了要传送的数据外,还包括校验码,以使接收方能发现传输中的差错。帧的组织结构必须设计成使接收方能够 明确地从物理层收到的比特流中对其进行识别,也即能从比特流中区分出帧的起始与终止,这就所谓的报文成帧问题。当链路两端的节点要进行通信前,必须数据链路层的可靠性,包括两个子问题,第一个是差错控制,第二个是流量控制。PPP协议是一个数据链路层协议,所以它会解决标准数据链路层协议的所有问题,包括除此之外,PPP协议还提供了很多其他的附加功能,正是因为这些功能的提供,使得PPP协议称为一个使用非常广泛的链路层协议。PPP协议为串行链路上传输的数据报定义了一种封装方法,它基于高层数据链路控制(HDLC)标准。即使使用所有的帧头字段,PPP协议帧也只需要8个字节就可以形成封装。如果在低速链路上或者带宽需要付费的情况下,PPP协议允许只使用最基本的字段,将帧头的开销压缩到2或4个字节的长度,这就是所谓的PPP帧头压缩。PPP协议有两个重要部分组成:LCP和NCP,LCP就是其中用来进行链路层的通道建立、管理与维护的部分。一次完整的PPP会话过程包括四个阶段: 链路建立阶段、确定链路质量阶段、网络层控制协议阶段和链路终止阶段。LCP会进行一些链路层参数的协商,只有通过LCP协商之后,才会启动后续的认证和网络层参数协商过程一次LCP协商过程如下:至此,LCP两个状态完成,可以向下一个阶段Network Layer Protocol或者Autiontication跃迁在Link Establishment阶段,P2P双方至少发一个Config-Request报文,该报文中包含了发送方对于所有的配置参数的期望值。PPP相对其他协议的一个非常重要的功能特性是其内置了安全认证机制,这也是该协议在用户接入侧被广泛使用的一个重要原因。安全认证过程内置在协议规程中,并且在链路建立起来之前被执行。很好的保证了接入链路的安全性。验证过程在PPP协议中为可选项。在连接建立后进行连接者身份验证的目的是为了防止有人在未经授权的情况下成功连接,从而导致泄密。PPP协议支持两种验证协议:这两种验证机制共同的特点就是简单,比较适合于在低速率链路中应用。但简单的协议通常都有其他方面的不足,最突出的便是安全性较差。一方面,口令验证协议的用户名/口令以明文传送,很容易被窃取;另一方面,如果一次验证没有通过,PAP并不能阻止对端不断地发送验证信息,因此容易遭到强制攻击。挑战握手协议的优点在于密钥不在网络中传送,不会被窃听。由于使用三次握手的方法,发起连接的一方如果没有收到“挑战信息”就不能进行验证,因此在某种程度上挑战握手协议不容易被强制攻击。但是,CHAP中的密钥必须以明文形式存在,不允许被加密,安全性无法得到保障。密钥的保管和分发也是CHAP的一个难点,在大型网络中通常需要专门的服务器来管理密钥。在完成安全认证后,PPP还支持上层网络层协议一些参数的协商,这也是PPP非常有特点的一个设计。不同的上层网络层协议,可能会有不同的协商内容。PPP协议为上层网络层参数协商定义了一套标准的规程,同时又支持多种不同的上层协议进行协商。设计的可扩展性非常好。NCP协议主要包括IPCP、IPXCP等,但我们在实际当中最常遇见的也只有IPCP协议IPCP控制协议主要是负责完成IP网络层协议通信所需配置参数的选项协商,负责建立,使能和中止IP模块。IPCP在运行的过程当中,主要是完成点对点通信设备的两端动态的协商IP地址。IPCP包在PPP没有达到网络层协议阶段以前不能进行交换,如果有IPCP包在到达此阶段前到达会被抛弃。IPCP到底需要协商一些什么参数呢?最重要的是下面两项:IPCP控制协议协商有两种方式:静态和动态:PPP内置了的链路质量检测机制, PPP 通过定义链路质量报告包 (Link-Quality-Report Packet)和它的详细处理过程,为链路质量监控详细说明了监控机制。 PPP 没有具体说明链路质量监控策略――如何断定链路质量或者当链路不充分时该怎么 做。这个被留做一个实现决策,并且在链路的各端可能是有差别的。用各种各样的方法去实 现这一决策是被允许甚至鼓励的。链路质量监控机制说明书保证了使用不同策略的两个实现 可以实现通信和进行内部操作。Magic-Number:魔数字段用于辅助检测链路自环。这是在链路建立过程中比较重要的一个参数,这个参数是在Config-Request里面被协商的,主要的作用是防止环路,如果在双方不协商魔术字的情况下,某些LCP的数据报文需要使用魔术字时,那么只能是将魔术字的内容填充为全0;反之,则填充为配置参数选项协商后的结果魔术字在目前所有的设备当中都是需要进行协商的,它被放在Config-Request的配置选项参数中进行发送,而且需要由自身的通信设备独立产生,协议为了避免双方可能产生同样的魔术字,从而导致通信出现不必要的麻烦,因此要求由设备采用一些随机方法产生一个独一无二的魔术字。一般来说魔术字的选择会采用设备的系列号、网络硬件地址或时钟。双方产生相同魔术字的可能性不能说是没有的,但应尽量避免,通常这种情况是发产在相同厂商的设备进行互连时,因为一个厂商所生产的设备产生魔术字的方法是一样的。我们知道魔术字产生的作用是用来帮助检测链路是否存在环路,当接收端B收到一个Config-Request报文时,会将此报文与上一次所接收到(应该是上一次发送出)的Config-Request进行比较,如果两个报文中所含的魔术字不一致的话,表明链路不存在环路。但如果一致的话,接收端B认为链路可能存在环路,但不一定存在环路,还需进一步确认。此时接收端B将发送一个Config-Nak报文,并在该报文中携带一个重新产生的魔术字,而且此时在未接收到任何Config-Request或Config-Nak报文之前,接收端B也不会发送任何的Config-Request报文。这时我们假设可能会有以下两种情况发生:但在实际应用中根据不同设备实现PPP协议的方法,我们在链路环路检测时可采用两种方法。第一种机制就是如上面所述的,这个过程不断地重复,最终可能会给LCP状态机发一个Down事件,这时可能会使LCP的状态机又回到初始化阶段,又开始新一轮的协商。当然对于某些设备还会采用第二种机制,就是不产生任何事件去影响当前LCP的状态机,而是停留在请求发送状态。但这时认为链路有环路的一端设备需要不断的向链路上发送Echo-Request报文来检测链路环路是否被解除,当接收端收到Echo-Reply报文时,就认为链路环路被解除,从而就可能进行后续的PPP的过程。PPP在LCP和NCP协商期间,都可以对各自的报文或报文头协商是否需要启用压缩机制。比如PPP头的压缩,或者IP报文的压缩等。PPP是一个不可靠的二层协议,PPP并不提供关于流量控制,差错控制等可靠性机制,他把这些问题留给上层协议去解决。其实这是很明智的做法,OSI七层模型中,各个层次都有相应的差错控制协议,比如二层链路层的等停协议或滑动窗口协议,到了传输层(如TCP),又有自己的可靠性协议。这样反反复复的各个层面都在做同样的事情,浪费了资源,并且带来了额外的复杂度。PPP将可靠性问题留给上层去解决,自己则将更多的精力集中在上层没有解决的问题域上。最终取得了更好的效果。(PPP协议的广泛使用就是一个这种效果的一个很好的证明)https://wenku.baidu.com/view/7f7391fef9c75fbfc77da26925c52cc58bd690d1.htmlPPP协议详解及举例https://wenku.baidu.com/view/118ad274580216fc700afd5f.htmlPPP基本原理(HW)http://forum.huawei.com/enterprise/thread-364813.html

TCP三次握手与四次挥手
传输控制协议(TCP,Transmission Control Protocol)是一种面向连接的、可靠的、基于字节流的传输层通信协议,由IETF的RFC 793定义。 TCP旨在适应支持多网络应用的分层协议层次结构。 连接到不同但互连的计算机通信网络的主计算机中的成对进程之间依靠TCP提供可靠的通信服务。TCP假设它可以从较低级别的协议获得简单的,可能不可靠的数据报服务。 原则上,TCP应该能够在从硬线连接到分组交换或电路交换网络的各种通信系统之上操作。传输控制协议(TCP,Transmission Control Protocol)是为了在不可靠的互联网络上提供可靠的端到端字节流而专门设计的一个传输协议。互联网络与单个网络有很大的不同,因为互联网络的不同部分可能有截然不同的拓扑结构、带宽、延迟、数据包大小和其他参数。TCP的设计目标是能够动态地适应互联网络的这些特性,而且具备面对各种故障时的健壮性。三次握手过程理解第一次握手:建立连接时,客户端发送syn包(syn=x)到服务器,并进入SYN_SENT状态,等待服务器确认;SYN:同步序列编号(Synchronize Sequence Numbers)。第二次握手:服务器收到syn包,必须确认客户的SYN(ack=x+1),同时自己也发送一个SYN包(syn=y),即SYN+ACK包,此时服务器进入SYN_RECV状态;第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=y+1),此包发送完毕,客户端和服务器进入ESTABLISHED(TCP连接成功)状态,完成三次握手。举个例子一对情侣准备周天去看电影。第一次握手 男孩发送:周天去看电影吧。第二次握手 女孩回应:好的。第三次握手 男孩回应:那说好了。1、为什么不能用两次握手进行连接?3次握手完成两个重要的功能,既要双方做好发送数据的准备工作(双方都知道彼此已准备好),也要允许双方就初始序列号进行协商,这个序列号在握手过程中被发送和确认。两次握手出现意外时,将会出现资源的浪费。握手分为Server s,Client c。两次握手,当C想要建立连接时发送一个SYN,然后等待ACK,结果这个SYN因为网络问题没有及时到达S,所以C在一段时间内没收到ACK后,再发送一个SYN,这次S顺利收到,接着C也收到ACK,这时C发送的第一个SYN终于到了S,对于S来说这是一个新连接请求,然后S又为这个连接申请资源,返回ACK,然而这个SYN是个无效的请求,C收到这个SYN的ACK后也并不会理会它,而S却不知道,S会一直为这个连接维持着资源,造成资源的浪费。三次握手出现错误时的应对措施第一次握手A发送SYN传输失败,A,B都不会申请资源,连接失败。如果一段时间内发出多个SYN连接请求,那么A只会接受它最后发送的那个SYN的SYN+ACK回应,忽略其他回应全部回应,B中多申请的资源也会释放第二次握手B发送SYN+ACK传输失败,A不会申请资源,B申请了资源,但收不到A的ACK,过一段时间释放资源。如果是收到了多个A的SYN请求,B都会回复SYN+ACK,但A只会承认其中它最早发送的那个SYN的回应,并回复最后一次握手的ACK第三次握手ACK传输失败,B没有收到ACK,释放资源,对于后序的A的传输数据返回RST。实际上B会因为没有收到A的ACK会多次发送SYN+ACK,次数是可以设置的,如果最后还是没有收到A的ACK,则释放资源,对A的数据传输返回RST。TCP的四次挥手(1)首先客户端想要释放连接,向服务器端发送一段TCP报文,其中:标记位为FIN,表示“请求释放连接“;序号为Seq=U;随后客户端进入FIN-WAIT-1阶段,即半关闭阶段。并且停止在客户端到服务器端方向上发送数据,但是客户端仍然能接收从服务器端传输过来的数据。注意:这里不发送的是正常连接时传输的数据(非确认报文),而不是一切数据,所以客户端仍然能发送ACK确认报文。(2)服务器端接收到从客户端发出的TCP报文之后,确认了客户端想要释放连接,随后服务器端结束ESTABLISHED阶段,进入CLOSE-WAIT阶段(半关闭状态)并返回一段TCP报文。前"两次挥手"既让服务器端知道了客户端想要释放连接,也让客户端知道了服务器端了解了自己想要释放连接的请求。于是,可以确认关闭客户端到服务器端方向上的连接了(3)服务器端自从发出ACK确认报文之后,经过CLOSED-WAIT阶段,做好了释放服务器端到客户端方向上的连接准备,再次向客户端发出一段TCP报文,其中:标记位为FIN,ACK,表示“已经准备好释放连接了”。注意:这里的ACK并不是确认收到服务器端报文的确认报文。序号为Seq=W;确认号为Ack=U+1;表示是在收到客户端报文的基础上,将其序号Seq值加1作为本段报文确认号Ack的值。随后服务器端结束CLOSE-WAIT阶段,进入LAST-ACK阶段。并且停止在服务器端到客户端的方向上发送数据,但是服务器端仍然能够接收从客户端传输过来的数据。(4)客户端收到从服务器端发出的TCP报文,确认了服务器端已做好释放连接的准备,结束FIN-WAIT-2阶段,进入TIME-WAIT阶段,并向服务器端发送一段报文,其中:标记位为ACK,表示“接收到服务器准备好释放连接的信号”。序号为Seq=U+1;表示是在收到了服务器端报文的基础上,将其确认号Ack值作为本段报文序号的值。确认号为Ack=W+1;表示是在收到了服务器端报文的基础上,将其序号Seq值作为本段报文确认号的值。随后客户端开始在TIME-WAIT阶段等待2MSL服务器端收到从客户端发出的TCP报文之后结束LAST-ACK阶段,进入CLOSED阶段。由此正式确认关闭服务器端到客户端方向上的连接。客户端等待完2MSL之后,结束TIME-WAIT阶段,进入CLOSED阶段,由此完成“四次挥手”。后“两次挥手”既让客户端知道了服务器端准备好释放连接了,也让服务器端知道了客户端了解了自己准备好释放连接了。于是,可以确认关闭服务器端到客户端方向上的连接了,由此完成“四次挥手”。与“三次挥手”一样,在客户端与服务器端传输的TCP报文中,双方的确认号Ack和序号Seq的值,都是在彼此Ack和Seq值的基础上进行计算的,这样做保证了TCP报文传输的连贯性,一旦出现某一方发出的TCP报文丢失,便无法继续"挥手",以此确保了"四次挥手"的顺利完成。为何要四次分手呢?我们在此之前先说说TCP异常断开的情况TCP异常断开1、如果已经建立了连接,但是一方突然出现故障了怎么办?TCP还设有一个保活计时器,显然,客户端如果出现故障,服务器不能一直等下去,白白浪费资源。服务器每收到一次客户端的请求后都会重新复位这个计时器,时间通常是设置为2小时,若两小时还没有收到客户端的任何数据,服务器就会发送一个探测报文段,以后每隔75秒钟发送一次。若一连发送10个探测报文仍然没反应,服务器就认为客户端出了故障,接着就关闭连接。心跳检测机制在TCP网络通信中,经常会出现客户端和服务器之间的非正常断开,需要实时检测查询链接状态。常用的解决方法就是在程序中加入心跳机制。此外,还有Heart-Beat线程、设置TCP属性等机制。通俗理解断电、死机、这意味着所有状态信息的失,如同-个失忆的人,对外界的一-切是陌生的,即使重新启动、程序征常运行也是如此。另一方肯定还是有正常记忆的,但双方状态(记忆)不对称已经无法完成正常意义的沟通,所以最好的方法,就是让好的一方检测到记忆的不对称,然后把自己的记忆也释放( reset) ,双方再重新谈-场恋爰(TCP重连)。好的一方如何检测呢?TCP Keepalive默认情况下, TCP 120分钟会发送检测信号,如果对方没有回复, 会重试几次到放弃,然后宣布对方翘辫子,发送Reset释放连接。对方收到会莫名其妙,会默默地忽视,因为压根没有这个连接(掉电释放掉了)。2个小时是一个漫长的等待 ,滞留的TCP会话会-直站用资源, 这是一种浪费!Application Keepalive为了更快地检测对方已经Dead的事实,应用程序层面可以发送检测信号,比如5 -10分钟检测一次。通过以上两种常用方法,可以克服好的一方永久驻留在内存里的现状,释放是唯一正确的方法 !实, Application Keepalive除了检测对方是否在线,大的作用是为了避免存在于通信双方之间的NAT设备表超时删除,需要周期性地刷新保活。所以四次挥手也是为了能实时的断开连接,释放资源这也是为了应对意外情况比如客户端在发送一次断开报文后直接自行断开了连接。而这个连接服务器端却没有收到。此时服务器并不知道客户端已经断开了连接。在此期间会一直发送请求判断客户端是否连接。直到最后还没有回应,才会断开连接。TCP协议是一种面向连接的、可靠的、基于字节流的运输层通信协议。TCP是全双工模式,这就意味着,当主机1发出FIN报文段时,只是表示主机1已经没有数据要发送了,主机1告诉主机2,它的数据已经全部发送完毕了;但是,这个时候主机1还是可以接受来自主机2的数据;当主机2返回ACK报文段时,表示它已经知道主机1没有数据发送了,但是主机2还是可以发送数据到主机1的;当主机2也发送了FIN报文段时,这个时候就表示主机2也没有数据要发送了,就会告诉主机1,我也没有数据要发送了,之后彼此就会愉快的中断这次TCP连接。如果要正确的理解四次分手的原理,就需要了解四次分手过程中的状态变化。举个例子本来一对情侣约好周天去看电影如果是一次挥手即一方发送断开请求之后立即关闭连接。女孩不想去了,就发送:周天不去了,手机就关掉了(关闭连接),如果这个消息没有发送成功。男孩认为约会还是算数的。就一直等待,等待超时的时候询问:还在不在?此时女孩已经关机了,所以接受不到这个信息。男孩可能会等待两个小时之后才选择回去。如果是两次挥手。女孩不想去了,就发送:周天不去了。然后手机没有关机,想确认男孩有没有收到。因为是两次挥手。男孩接到信息后回应:好的。 就选择关机(断开连接,这里先看成男孩已经没有其他数据要发送,因为是两次挥手)。但是回应没有发送到。此时女孩就会一直等,并反复发送消息。但此时男孩已经关机了。女孩可能会反复发送很长时间才选择断开连接。或者男孩回复好的之后,女孩也接受到了,但男孩还有话没说完,想继续聊一聊之前的那个话题,这个话题还很重要。但是因为对面关闭连接也接收不到了。(这就可能出现传输过程中数据的不完整,不满足数据可靠)所以要等双方数据都传输完毕的四次挥手。 可以实时的关闭掉连接。

TCP/IP三次握手具体过程是什么?
端口扫描,这种入侵检测方法大家想必都经常用到,但是你对这些方法的基本原理又了解多少呢? 首先,你可以选择都种工具,本人喜欢nmap for linux,但不是常在linux下混,毕竟还是windows方便点,呵呵,高手别笑我哦!下面谈下端口扫描方式!大体可以分为两种,TCP扫描和秘密扫描TCP扫描最常见的有两种全扫描、半扫描说到TCP,就一定要谈3次握手客户端——SYN——>服务器客户端<——SYN+ACK——服务器客户端——ACK——〉服务器这就是3次握手,也就是全扫描的全过程,但是,由于这种方式要与目标建立连接,所以一定会被记录下来,所以,这种扫描方式是不隐密的,容易暴露身份。所以,就有了半扫描这种扫描方式,会发送一个SYN包给目标服务器,然后如果对方在特定端口监听,就会回复一个ACK+SYN,如果主机在活动,但没有监听特定端口,就会回一个RST包。这种方法并没有完成3次握手,所以一般不会被主机记录。下面,我们就抛开TCP协议,看看有没有办法通过其他方式扫描!说到文件传送,大家最先想到的就应该是FTP协议了,那么,能不能通过FTP扫描呢?答案是可以,出于设计上的需要,当FTP客户端要以主动模式请求传送数据时,服务器必须要建立一个返回到客户机端口上的连接客户端发出PORT命令,以IP和端口作为参数,如果参数中有另一台主机的IP数据,服务器将与这台主机相连。我们就利用FTP的这种特点来执行代理端口扫描。 还有FIN,ident,XMAS扫描等等,由于时间关系和其他种种原因,我现在就不讲了,lz有兴趣,可以加我大家一起探讨~
TCP需要三次握手才能建立连接,那么为什么需要三次握手呢?

TCP中三个函数与三次握手的关系?
TCP是属于网络分层中的传输层,因为OSI分为7层,感觉太麻烦了,所以分为四层就好了,简单。 分层以及每层的协议,TCP是属于传输层,如下两张图:TCP三次握手会涉及到状态转换所以这里贴出TCP的状态转换图如下:TCP三次握手简述TCP三次握手如图:第一次握手客户主动(active open)去connect服务器,并且发送SYN 假设序列号为J,服务器是被动打开(passive open)第二次握手服务器在收到SYN后,它会发送一个SYN以及一个ACK(应答)给客户,ACK的序列号是 J+1表示是给SYN J的应答,新发送的SYN K 序列号是K第三次握手客户在收到新SYN K, ACK J+1 后,也回应ACK K+1 以表示收到了,然后两边就可以开始数据发送数据了使用tcpdump观察如下:因为都是在本机同时运行client和server所以命令为:tcpdump -i lo port 5555, 只能监听回路lo接口,结果如下如图用红色圈起来的就是3次握手,但是为什么最后一次握手,为什么ack = 1,而不是369535922 呢,这是因为这里的第三次握手tcpdump显示的是相对的顺序号。但是为了便于观察我们需要把tcpdump的顺序号变为绝对的顺序号。命令只需要加-S(大写)便可,即:tcpdump -i lo port 5555 -S加上之后结果就正常了如下图:从tcpdump的数据,可以明显的看到三次握手的过程是:第一次握手:client syn 2322326583 —> server第二次握手:server syn 3573692787, ack 2322326583 + 1 —> client第三次握手:client ack 3573692787 + 1 -->serverTCP三次握手详细解析过程:第一次握手客户在socket() connect()后主动(active open)连接上服务器, 发送SYN ,这时客户端的状态是SYN_SENT服务器在进行socket(),bind(),listen()后等待客户的连接,收到客户端的 SYN 后,1.半连接队列(syn queue)未满服务器将该连接的状态变为SYN_RCVD, 服务器把连接信息放到半连接队列(syn queue)里面。2.半连接队列(syn queue)已满服务器不会将该连接的状态变为SYN_RCVD,且将该连接丢弃(SYN flood攻击就是利用这个原理,对于SYN foold攻击,应对方法之一是使syncookies生效,将其值置1即可,路径/proc/sys/net/ipv4/tcp_syncookies,即使是半连接队列syn queue已经满了,也可以接收正常的非恶意攻击的客户端的请求,但是这种方法只在无计可施的情况下使用,man tcp里面的解析是这样说的,但是我不知道为什么Centos6.9默认是置为1,所以这让我很疑惑)。半连接队列(syn queue)最大值 /proc/sys/net/ipv4/tcp_max_syn_backlogSYN flood攻击攻击方的客户端只发送SYN分节给服务器,然后对服务器发回来的SYN+ACK什么也不做,直接忽略掉,不发送ACK给服务器;这样就可以占据着服务器的半连接队列的资源,导致正常的客户端连接无法连接上服务器。-----[维基百科](SYN flood攻击的方式其实也分两种,第一种,攻击方的客户端一直发送SYN,对于服务器回应的SYN+ACK什么也不做,不回应ACK, 第二种,攻击方的客户端发送SYN时,将源IP改为一个虚假的IP, 然后服务器将SYN+ACK发送到虚假的IP, 这样当然永远也得不到ACK的回应。)第二次握手服务器返回SYN+ACK给到客户端,客户端收到SYN+ACK后,状态从SYN_SENT变为ESTABLISHED,也即是connect()函数的返回。第三次握手全连接队列(accept queue)的最大值 /proc/sys/net/core/somaxconn (默认128)全连接队列值 = min(backlog, somaxconn)这里的backlog是listen(int sockfd, int backlog)函数里面的那个参数backlog1.全连接队列(accept queue)未满服务器收到客户端发来的ACK, 服务端该连接的状态从SYN_RCVD变为ESTABLISHED,然后服务器将该连接从半连接队列(syn queue)里面移除,且将该连接的信息放到全连接队列(accept queue)里面。2.全连接队列(accept queue)已满服务器收到客户端发来的ACK, 不会将该连接的状态从SYN_RCVD变为ESTABLISHED。当然全连接队列(accept queue)已满时,则根据 tcp_abort_on_overflow 的值来执行相应动作/proc/sys/net/ipv4/tcp_abort_on_overflow 查看参数值2.1 tcp_abort_on_overflow = 0则服务器建立该连接的定时器,这个定时器是一个服务器的规则是从新发送syn+ack的时间间隔成倍的增加,比如从新了第二次握手,进行了5次,这五次的时间分别是 1s, 2s,4s,8s,16s,这种倍数规则叫“二进制指数退让”(binary exponential backoff)给客户端定时从新发回SYN+ACK即从新进行第二次握手,(如果客户端设定的超时时间比较短就很容易出现异常)服务器从新进行第二次握手的次数/proc/sys/net/ipv4/tcp_synack_retries2.2 tcp_abort_on_overflow = 1关于tcp_abort_on_overflow的解析如下:意思应该是,当 tcp_abort_on_overflow 等于1 时,重置连接(一般是发送RST给客户端),至于怎么重置连接是系统的事情了。不过我在查资料的过程发现,阿里中间件团队博客说并不是发送RST, —[阿里中间件团队博客]这个博客跑的实例观察到的是服务器会忽略client传过来的包,然后client重传,一定次数后client认为异常,然后断开连接。当然,我们写代码的都知道代码是第一手的注释,实践是检验真理的唯一标准,最好还是自己以自己实践为准,因为可能你的环境跟别人的不一样。)查看全连接队列(accept queue)的使用情况如上图,第二列Recv-Q是,全连接队列接收到达的连接,第三列是Send-Q全连接队列的所能容纳最大值,如果,Recv-Q 大于 Send-Q 那么大于的那部分,是要溢出的即要被丢弃overflow掉的。感想:1.本来想写TCP连接的建立和终止的,没想到要讲清楚TCP连接的建立已经很大的篇幅了,就只讲TCP连接的建立而已。2.以前看书的时候,没有解决一个问题的来的深刻或者说脉络清晰,这个就是主题阅读的好处吧。3.以前没有养成一个遇到问题深入解析,解决问题的习惯,今后慢慢养成。下面的参考1有实例,会比较详细一点,清晰一些。参考:http://jm.taobao.org/2017/05/25/525-1/https://coolshell.cn/articles/11564.htmlhttps://zh.wikipedia.org/wiki/SYN_cookiehttps://zh.wikipedia.org/wiki/SYN_floodhttps://www.cnblogs.com/menghuanbiao/p/5212131.html————————————————版权声明:本文为CSDN博主「jun2016425」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。原文链接:https://blog.csdn.net/jun2016425/article/details/81506353
这是你创建的套接字类型决定的,常用的套接字是数据流类型(TCP)和数据报文类型(UDP),创建这些类型的套接字的时候就已经带上了相应的协议栈,这些握手信息在协议栈内部就已经实现了,不需要上层应用去实现 如果你想自己去控制握手信息,需要创建原始套接字,这种类型的套接字是基于IP层的,很多抓包工具就是通过这种类型的套接字来实现的,在这一层上你就可以自己定义处理握手信息,但这样相当于你要自己来实现TCP协议栈了,这难度太高,而且一般情况下也没必要 如果只是对握手的过程感兴趣,安装一个抓包工具观察一下连接的时候C/S之间的通信数据包就可以了
TCP需要三次握手才能建立连接,那么为什么需要三次握手呢?

本文由 在线网速测试 整理编辑,转载请注明出处,原文链接:https://www.wangsu123.cn/news/46618.html。