热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

tcp与udp特点,三次握手四次挥手

一TCP、UDP区别1共同点:传输层协议,传输信息2区别:TCP传输控制协议UDP用户数据包协议可靠性可靠不可靠连接性面向连接无连接

一TCP、UDP区别

1共同点:传输层协议,传输信息

2区别:


TCP传输控制协议UDP用户数据包协议
可靠性可靠不可靠
 连接性 面向连接 无连接
 报文 面向字节流 面向报文
 效率 传输效率低 传输效率高
 双工性 全双工 一对一、一对多、多对一、多对多
 流量控制 有(滑动窗口) 无
 拥塞控制 有(慢开始、拥塞避免、快重传、快恢复) 无

tcp:面向连接,可靠,开销小,传输效率低,延时高,端到端传输

udp:无连接,不可靠,开销大,传输效率高,一对一、一对多、多对一、多对多

tcp有拥塞控制,可以慢开始,拥塞避免,快重传,快恢复。udp没有拥塞控制,不管网络是否拥塞,udp客户端都可以一直发送。

tcp适用于数据传输准确度要求度高的场合(电话)。udp适用于数据传输量大,实时性要求高的场合(短信)

tcp数据完整,按时,按序到达。udp尽最大努力交付数据。


二tcp如何保证可靠传输

TCP通过序列号、数据包检验、确认应答机制、超时重发、连接管理、流量控制、拥塞控制实现可靠性。


  • 校验和: TCP在发送报文之前,发送方要计算校验和,收到数据后,接收方也要计算校验和,如果校验和不相等则丢弃。

  • 序列号与确认应答:

    • 序列号:TCP传输时将每个字节的数据都进行了编号,这就是序列号。

    • 确认应答:TCP传输的过程中,每次接收方收到数据后,都会对传输方进行确认应答。也就是发送ACK报文。这个ACK报文当中带有对应的确认序列号,告诉发送方,接收到了哪些数据,下一次的数据从哪里发。

    • 序列号的作用不仅仅是应答的作用,有了序列号能够将接收到的数据根据序列号排序,并且去掉重复序列号的数据。这也是TCP传输可靠性的保证之一。

  • 超时重传: 在TCP传输过程中,我们在发送一部分数据后,都会等待对方的ACK确认报文,如果中间出现差错,没有收到ACK报文,这时候需要启动超时重传机制。这种超时重传机制保证了TCP在网络延迟或者报文丢失下的可靠传输。

    超时的原因:

    • 接收方没有收到TCP报文段:网络延迟或者丢包;

    • 发送方没有收到ACK报文段:网络延迟或者ACK报文丢失。

  • 连接管理:连接管理就是三次握手与四次挥手的过程(后面有详细解释)

  • 流量控制: 流量控制的目的是让接收方来得及接收数据。这样避免了数据丢包以及网络拥塞等情况。

  • 拥塞控制: 拥塞控制就是防止过多的数据注入到网络中,这样使网络中的路由器或者链路不至于过载。

  • 三拥塞控制详解

  • TCP通过慢启动、拥塞避免、快重传以及快恢复这四个算法来进行拥塞控制

    • 慢启动:一开始先设置一个比较小的拥塞窗口值cwnd(报文段的倍数),然后进行数据传输,每收到一个报文段的确认,我们就将cwnd+1,这样下来,cwnd总体上是乘以2^n的倍数增长。(慢启动非增长速度慢,只是增长的初始基数比较小)

    • 拥塞避免: 因为慢启动算法的增长比较快,当cwnd = ssthresh(预先设置好的门限值)时,我们启动拥塞避免算法,窗口值开始线性增长

    随着拥塞避免算法的进行,网络出现超时的情况(这时判断为拥塞出现)。这时将cwnd降为一开始的值,重新进行慢开始-拥塞避免,并且此时的门限值设为出现拥塞时的cwnd的一半。

    • 快重传: 快重传的目的是为了让发送方尽早知道某个报文段的丢失。如何知道呢?当我们重复收到某一个报文段的3次确认时,我们就可以判断,它的下一个报文段可能出现了丢失。这时我们启动快重传算法,立即重传丢失的报文段。

    • 快恢复: 上面快重传算法的启动只是因为个别报文段的丢失,我们这时并不判断为网络拥塞,而是启动快恢复算法。我们将cwnd=ssthresh=当前cwnd的一半,并且开始拥塞避免算法。

    当然,也有的快恢复算法是将当前拥塞窗口再增大3个报文段的值,因为既然收到了3个重复的ACK,则说明有三个分组已经离开了网络,不在占用网络资源而是停留在对方缓存当中,可以适当将窗口值增大。


四udp的问题

丢包与无序

如何解决丢包问题:  增大接收端的缓冲区大小;       增大接收端的处理能力;

无序:修改协议,增加超时重发,确认机制


五三次握手
       

所谓三次握手(Three-Way Handshake)即建立TCP连接,就是指建立一个TCP连接时,需要客户端和服务端总共发送3个包以确认连接的建立。

1.TCP 为什么三次握手而不是两次握手

1.防止已失效的连接请求又传送到服务器端,因而产生错误。不太准确

  为了实现可靠数据传输, TCP 协议的通信双方, 都必须维护一个序列号, 以标识发送出去的数据包中, 哪些是已经被对方收到的。 三次握手的过程即是通信双方相互告知序列号起始值, 并确认对方已经收到了序列号起始值的必经步骤。如果只是两次握手, 至多只有连接发起方的起始序列号能被确认, 另一方选择的序列号则得不到确认。

在socket编程中,这一过程由客户端执行connect来触发,整个流程如下图所示:


                     图1 TCP三次握手

        (1)第一次握手:Client将标志位SYN置为1,随机产生一个值seq=J,并将该数据包发送给Server,Client进入SYN_SENT状态,等待Server确认。
        (2)第二次握手:Server收到数据包后由标志位SYN=1知道Client请求建立连接,Server将标志位SYN和ACK都置为1,ack=J+1(确认号码),随机产生一个值seq=K,并将该数据包发送给Client以确认连接请求,Server进入SYN_RCVD状态。
        (3)第三次握手:Client收到确认后,检查ack是否为J+1,ACK是否为1,如果正确则将标志位ACK置为1,ack=K+1,并将该数据包发送给Server,Server检查ack是否为K+1,ACK是否为1,如果正确则连接建立成功,Client和Server进入ESTABLISHED状态,完成三次握手,随后Client与Server之间可以开始传输数据了。
        
     ①   SYN攻击:
                在三次握手过程中,Server发送SYN-ACK之后,收到Client的ACK之前的TCP连接称为半连接(half-open connect),此时Server处于SYN_RCVD状态,当收到ACK后,Server转入ESTABLISHED状态。SYN攻击就是Client在短时间内伪造大量不存在的IP地址,并向Server不断地发送SYN包,Server回复确认包,并等待Client的确认,由于源地址是不存在的,因此,Server需要不断重发直至超时,这些伪造的SYN包将产生时间占用未连接队列,导致正常的SYN请求因为队列满而被丢弃,从而引起网络堵塞甚至系统瘫痪。SYN攻击时一种典型的DDOS攻击,检测SYN攻击的方式非常简单,即当Server上有大量半连接状态且源IP地址是随机的,则可以断定遭到SYN攻击了,使用如下命令可以让之现行:
                #netstat -nap | grep SYN_RECV
 


六 四次挥手


         所谓四次挥手(Four-Way Wavehand)即终止TCP连接,就是指断开一个TCP连接时,需要客户端和服务端总共发送4个包以确认连接的断开。在socket编程中,这一过程由客户端或服务端任一方执行close来触发,整个流程如下图所示:


                               图2 TCP四次挥手

        由于TCP连接时全双工的,因此,每个方向都必须要单独进行关闭,这一原则是当一方完成数据发送任务后,发送一个FIN来终止这一方向的连接,收到一个FIN只是意味着这一方向上没有数据流动了,即不会再收到数据了,但是在这个TCP连接上仍然能够发送数据,直到这一方向也发送了FIN。首先进行关闭的一方将执行主动关闭,而另一方则执行被动关闭,上图描述的即是如此。
        (1)第一次挥手:Client发送一个FIN,用来关闭Client到Server的数据传送,Client进入FIN_WAIT_1状态。
        (2)第二次挥手:Server收到FIN后,发送一个ACK给Client,确认序号为收到序号+1(与SYN相同,一个FIN占用一个序号),Server进入CLOSE_WAIT状态。
        (3)第三次挥手:Server发送一个FIN,用来关闭Server到Client的数据传送,Server进入LAST_ACK状态。
        (4)第四次挥手:Client收到FIN后,Client进入TIME_WAIT状态,接着发送一个ACK给Server,确认序号为收到序号+1,Server进入CLOSED状态,完成四次挥手。
        上面是一方主动关闭,另一方被动关闭的情况,实际中还会出现同时发起主动关闭的情况,具体流程如下图:

                                      图3 同时挥手

      

①第四次挥手客服端为什么要等待2MSL时间?

去向ACK消息最大存活时间(MSL) + 来向FIN消息的最大存活时间(MSL)。

这恰恰就是2MSL( Maximum Segment Life)。

      1.  当客户端的最后一次确认连接的报文丢失(第四次挥手发送的),服务器会再次发送FIN报文,等待客户端的确认,客户端在2MSL内收到服务器重传的报文再次确认(防止此时客户端已经关闭)。安心的释放tcp占用的资源,端口

      2.  2MSL 的时间可以使所有已失效的报文都消失(防止对新建的连接造成影响),若在不等待2MSL,马上建立新的连接,那么在关闭连接前发送的失效报文段很可能影响本次连接如果不等,释放的端口可能会重连刚断开的服务器端口,这样依然存活在网络里的老的TCP报文可能与新TCP连接报文冲突,造成数据冲突

   然而,TCP规定处于2MSL状态的的插口对(客户端IP/端口和服务器IP和端口)不能再次被使用。 若在2MSL状态下新建连接可以使用这个插口对,当已失效的数据包再次到达这个新连接,判断插口一致就会接受这个报文,但实际上这不是新建连接交互的数据,因此不能使用此无效数据包。



七    为什么建立连接是三次握手,而关闭连接却是四次挥手呢?


        这是因为服务端在LISTEN状态下,收到建立连接请求的SYN报文后,把ACK和SYN放在一个报文里发送给客户端。而关闭连接时,当收到对方的FIN报文时,仅仅表示对方不再发送数据了但是还能接收数据,己方也未必全部数据都发送给对方了,所以己方可以立即close,也可以发送一些数据给对方后,再发送FIN报文给对方来表示同意现在关闭连接,因此,己方ACK和FIN一般都会分开发送。

TCP传输信息

客户端:①创建socket,链接远端地址

②连接后发送数据和接收数据

③传输完毕,关闭socket

import socket
s=socket.socket()
host=10.0.0.0
port=123
s.connect(host,port)
print(s.recv(1024)
s.close()

服务端:①创建socket,绑定socket到本地ip与端口

②开始监听连接

③进入循环不断接收客户端的连接请求

④接受传来的数据,发送数据给对方

⑤传输完毕,关闭socket

import socket
s=socket.socket()
host=10.0.0.0
port=123
s.bind(host,port)s.listen(5)
while True:c,addr=s.accept()print(addr)c.send("hello")c.close()

 

UDP传输信息

客户端:①创建socket,链接远端地址

②发送数据和接收数据

③传输完毕,关闭socket

import socket
s=socket.socket()
host=10.0.0.0
port=123
addr=(host,port)
data=input("the data you need to send:")
s.sendto(data.encode(),addr)
s.close()

服务端:①创建socket,绑定socket到本地ip与端口

②开始监听连接

③进入循环不断接收客户端的连接请求

④等待对方发送数据,接受传来的数据,

⑤传输完毕,关闭socket

import socket
s=socket.socket()
host=10.0.0.0
port=123
s.bind(host,port)
data=input("data:")
s.sendto(data.encode(),addr)
receive_data=s.recvfrom(1024)
s.close()


推荐阅读
  • 本文详细介绍了在Linux虚拟化部署中进行VLAN配置的方法。首先要确认Linux系统内核是否已经支持VLAN功能,然后配置物理网卡、子网卡和虚拟VLAN网卡的关系。接着介绍了在Linux配置VLAN Trunk的步骤,包括将物理网卡添加到VLAN、检查添加的VLAN虚拟网卡信息以及重启网络服务等。最后,通过验证连通性来确认配置是否成功。 ... [详细]
  • 本文介绍了计算机网络的定义和通信流程,包括客户端编译文件、二进制转换、三层路由设备等。同时,还介绍了计算机网络中常用的关键词,如MAC地址和IP地址。 ... [详细]
  • 浅解XXE与Portswigger Web Sec
    XXE与PortswiggerWebSec​相关链接:​博客园​安全脉搏​FreeBuf​XML的全称为XML外部实体注入,在学习的过程中发现有回显的XXE并不多,而 ... [详细]
  • 本文分享了一个关于在C#中使用异步代码的问题,作者在控制台中运行时代码正常工作,但在Windows窗体中却无法正常工作。作者尝试搜索局域网上的主机,但在窗体中计数器没有减少。文章提供了相关的代码和解决思路。 ... [详细]
  • 本文介绍了为什么要使用多进程处理TCP服务端,多进程的好处包括可靠性高和处理大量数据时速度快。然而,多进程不能共享进程空间,因此有一些变量不能共享。文章还提供了使用多进程实现TCP服务端的代码,并对代码进行了详细注释。 ... [详细]
  • centos安装Mysql的方法及步骤详解
    本文介绍了centos安装Mysql的两种方式:rpm方式和绿色方式安装,详细介绍了安装所需的软件包以及安装过程中的注意事项,包括检查是否安装成功的方法。通过本文,读者可以了解到在centos系统上如何正确安装Mysql。 ... [详细]
  • HSRP热备份路由器协议的应用及配置
    本文介绍了HSRP热备份路由器协议的应用及配置方法,包括设计目标、工作原理、配置命令等。通过HSRP协议,可以实现在主动路由器故障时自动切换到备份路由器,保证网络连通性。此外,还介绍了R1和R2路由器的配置方法以及Sw1和Sw2交换机的配置方法,最后还介绍了测试连通性和路由追踪的方法。 ... [详细]
  • 利用Visual Basic开发SAP接口程序初探的方法与原理
    本文介绍了利用Visual Basic开发SAP接口程序的方法与原理,以及SAP R/3系统的特点和二次开发平台ABAP的使用。通过程序接口自动读取SAP R/3的数据表或视图,在外部进行处理和利用水晶报表等工具生成符合中国人习惯的报表样式。具体介绍了RFC调用的原理和模型,并强调本文主要不讨论SAP R/3函数的开发,而是针对使用SAP的公司的非ABAP开发人员提供了初步的接口程序开发指导。 ... [详细]
  • 移动端常用单位——rem的使用方法和注意事项
    本文介绍了移动端常用的单位rem的使用方法和注意事项,包括px、%、em、vw、vh等其他常用单位的比较。同时还介绍了如何通过JS获取视口宽度并动态调整rem的值,以适应不同设备的屏幕大小。此外,还提到了rem目前在移动端的主流地位。 ... [详细]
  • Redis API
    安装启动最简启动命令行输入验证动态参数启动配置文件启动常用配置通用命令keysbdsize计算key的总数exists判断是否存在delkeyvalue删除指定的keyvalue成 ... [详细]
  • 本文介绍了使用readlink命令获取文件的完整路径的简单方法,并提供了一个示例命令来打印文件的完整路径。共有28种解决方案可供选择。 ... [详细]
  • 面试经验分享:华为面试四轮电话面试、一轮笔试、一轮主管视频面试、一轮hr视频面试
    最近有朋友去华为面试,面试经历包括四轮电话面试、一轮笔试、一轮主管视频面试、一轮hr视频面试。80%的人都在第一轮电话面试中失败,因为缺乏基础知识。面试问题涉及 ... [详细]
  •   1、确认自己的线路是否连接正确腾达a9设置。 ... [详细]
  • [翻译]微服务设计模式5. 服务发现服务端服务发现
    服务之间需要互相调用,在单体架构中,服务之间的互相调用直接通过编程语言层面的方法调用就搞定了。在传统的分布式应用的部署中,服务地 ... [详细]
  • 解决浏览器打开网页后提示“dns_probe_possible 怎么解决”的方法
    在使用浏览器进行网上冲浪的时候遇到故障是一件很常见的事情,很多用户都遇到过系统提示:dns_probe_possible。从提示中可以看出和DNS是有一定的关系的,经过小编测试之后 ... [详细]
author-avatar
cecilysun
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有