zoukankan      html  css  js  c++  java
  • 计算机网络之传输层

    传输层

    1、传输层服务

    1.1 传输层与网络层的关系

    网络层只把分组发送到目的主机,但是真正通信的并不是主机而是主机中的进程。传输层与网络层的区别在于:传输层提供了不同主机的应用进程间的逻辑通信,而网络层提供了主机之间的逻辑通信。传输层向高层用户屏蔽了下面网络层的核心细节,使应用程序看起来像是在两个传输层实体之间有一条端到端的逻辑通信信道。

    传输层协议只工作在端系统中。在端系统中,运输层协议将应用进程的报文移动到网络层边缘。

    传输层协议能够提供的服务常常受限于底层网络层协议的服务模型。如果网络层协议不能为传输层报文提供时延和带宽保证的话,传输层协议也不能为进程间发送的应用程序报文提供时延和带宽保证。

    1.2 多路复用和多路分解

    在接收主机的传输层并不是直接将数据交付给进程,而是将数据交付给该进程相应的套接字,这一过程称为多路分解。相应的源主机从不同套接字中收集数据块,并为每个数据块封装上首部信息从而生成报文段,然后将报文段传送给网络层,这一过程称为多路复用

    端口(port):软件端口是应用层的各种协议进程与运输实体进行层间交互的一个地址。TCP/IP的运输层用一个 16 位的端口号来标志一个端口。

    2、用户数据协议UDP

    2.1 UDP概述

    用户数据协议UDP只在 IP 的数据报服务上增加复用、分用以及差错检测的功能。主要特点如下:

    1. UDP 是无连接的。发送数据之前不需要建立连接,减少了开销和发送数据之前的时延;再发送报文段前,发送方和接受放的运输层实体没有建立握手连接;
    2. UDP 使用尽最大努力交付。不保证可靠交付,主机不需要维持复杂的连接状态表;
    3. UDP 是面向报文的。发送方的 UDP 对应从程序交下来的报文,在添加首部后就向下交付给 IP 层,在接收方的 UDP 对 IP 层交上来的 UDP 用户数据报,去除首部后就交付给上层的应用进程;
    4. UDP 没有拥塞控制。网络出现拥塞不会使源主机的发送速率变低;
    5. UDP 支持一对一、一对多、多对一和多对多的交互通信

    2.2 UDP的首部格式

    用户数据报 UDP 有两个字段:数据字段和首部字段。首部字段只有 8 个字节,由 4 个字段组成,每个字段的长度都是两个字节

    • 源端口:源端口号。在需要对方回信时选用,不需要是可用全0
    • 目的端口:目的端口号。在终点交付报文时必须使用
    • 长度:UDP 用户数据报的长度。其最小值是8
    • 校验和:检测 UDP 用户数据报在传输中是否出错,有错就丢弃。
    • 伪首部:不是 TCP/UDP 数据报中的有效成分,既不向下传送也不向上递交,只是为了计算校验和。

    2.3 UDP的检验和

    UDP检验和提供了差错检测功能。用于确定当UDP报文段从源到达目的地移动时,其中的比特是否发生了改变。

    其原因是不能保证源和目的之间的所有链路都提供了差错检测;又无法确保报文段存储在某台路由器中不会引发比特差错。如果端到端数据传输服务要提供差错检测,UDP可就必须在端到端基础上在传输层提供差错检测。

    端到端原则:与在较高级别提供这些功能的代价相比,在较低级别上设置的功能可能是冗余的或几乎没有价值的。

    3、 传输控制协议TCP

    3.1 TCP概述

    传输控制协议TCP的主要特点如下:

    1. TCP 是面向连接的运输层协议。应用程序在使用 TCP 协议之前,必须先建立 TCP 连接。在传送数据完毕后,必须释放以建立的 TCP 连接。
    2. 每一条 TCP 连接只能有两个端点(endpoint),每一条 TCP 连接只能是点对点的(一对一)。
    3. TCP 提供可靠交付的服务。通过 TCP 连接传送的数据,无差错、不丢失、不重复,并且按序到达。
    4. TCP 提供全双工通信。TCP 允许应用程序在任何时候都能发送数据。TCP 连接的两端都设有发送缓存和接收缓存,用来临时存放双向通信的数据。
    5. 面向字节流。把应用层传下来的报文看成字节流,把字节流组织成大小不等的数据块。

    TCP 协议与 UDP 协议的区别:

    • TCP面向连接,UDP是无连接的,即发送数据之前不需要建立连接。
    • TCP提供可靠的服务。也就是说,通过TCP连接传送的数据,无差错,不丢失,不重复,且按序到达;而UDP尽最大努力交付,即不保证可靠交付
    • TCP通过校验和、拥塞控制、序号标识、滑动窗口、应答确认、超时重传等机制实现可靠传输。
    • UDP具有较好的实时性,工作效率比TCP高,适用于对高速传输和实时性有较高的通信或广播通信。
    • 每一条TCP连接只能是点到点的,而UDP支持一对一,一对多,多对一和多对多的交互通信
    • TCP对系统资源要求较多,UDP对系统资源要求较少。

    3.2 TCP的连接

    套接字(Socket)就是应用层与TCP/IP协议族通信的中间软件抽象层,它是一组接口,端口号拼接到 IP 地址即构成了套接字。

    套接字 socket=(IP地址:端口号)

    每一条 TCP 连接唯一的被通信两端的两个端点(即两个套接字)所确定,即:TCP连接 ::= { socket_1, socket_2 } = { (IP_1:port_1), (IP_2:port_2) }

    IP_1 和 IP_2 分别是两个端点主机的 IP 地址,port_1 和 port_2 分别是两个端点主机中的端口号。

    3.3 TCP的发送缓存

    客户进程通过套接字传递数据流。数据一旦通过套接字,它就由客户中运行的TCP控制了。TCP将这些数据引导到该连接的发送缓存,发送缓存是发起三次握手期间设置的缓存之一。

    TCP可从缓存中取出并放入报文段中的数据数量受限于最大报文段长度(MSS)。MSS通常根据最初确定的由本地发送主机发送的最大链路层帧长度(MTU)。以太网和PPP链路层协议都有1500字节的MTU,因此MSS的典型值设置为1460。MSS是指在报文段中应用层数据的最大长度,而不是值包括首部的TCP报文段的最大长度。


    3.4 TCP报文段首部格式

    一个 TCP 报文段可以分为首部和数据部分,而 TCP 的全部功能都体现在首部中各字段的作用。TCP 报文段首部的前 20 个字节是固定的。


    • 源端口和目的端口:各占 2 个字节,分别写入源端口号和目的端口号。
    • 序号:占 4 个字节。用于对字节流进行编号,例如序号为 301,表示第一个字节的编号为 301,如果携带的数据长度为 100 字节,那么下一个报文段的序号应为 401。
    • 确认号:占 4 个字节。期望收到的下一个报文段的序号。例如 B 正确收到 A 发送来的一个报文段,序号为 501,携带的数据长度为 200 字节,因此 B 期望下一个报文段的序号为 701,B 发送给 A 的确认报文段中确认号就为 701。
    • 数据偏移:占 4 比特。指的是数据部分距离报文段起始处的偏移量,实际上指的是首部的长度。注意数据偏移的单位是“32位”即 4 字节。最大可以表示 60 字节。
    • 紧急URG(URGent):当 URG=1 时表示紧急指针字段有效。告诉系统此报文段有紧急数据,应尽快传送。
    • 确认ACK(ACKnowledgment):仅当 ACK=1 时确认号字段有效,否则无效。TCP 规定,在连接建立后所有传送的报文段都必须把 ACK 置 1
    • 推送PSH(PuSH):PSH=1,发送方立即创建一个报文段发送出去,接收方尽快交付给应用进程。
    • 复位RST(ReSeT):当 RST=1 时表明 TCP 连接中出现严重差错,必须释放连接,然后重新建立运输连接。
    • 同步SYN(SYNcronization):在连接建立时用来同步序号。当 SYN=1,ACK=0 时表示这是一个连接请求报文段。若对方同意建立连接,则响应报文中 SYN=1,ACK=1。
    • 终止FIN(FINis):用来释放一个连接,当 FIN=1 时,表示此报文段的发送方的数据已发送完毕,并要求释放连接
    • 窗口:占 2 个字节。发送本报文段的一方的接收窗口,窗口值告诉对方从本报文段首部的确认号算起,接收方目前允许对方发送的数据量。窗口值作为接收方让发送方设置其发送窗口的依据。之所以要有这个限制,是因为接收方的数据缓存空间是有限的。
    • 检验和:占 2 个字节。
    • 紧急指针:占 2 个字节。仅在 URG=1 时有意义,指出本报文段中紧急数据的字节数。
    • 选项:最大报文段长度MSS、窗口扩大选项、时间戳选项等。

    3.5 TCP运输连接管理

    TCP 是面向连接的协议,运输连接是用来传送 TCP 报文的。运输连接有是那个阶段:连接建立、数据传送和连接释放
    TCP 连接的建立采用客户服务器方式,主动发起连接建立的应用程序叫客户(client),被动等待连接建立的应用程序称为服务器(sever)。

    3.6 TCP的连接建立

    TCP 建立连接的过程称为握手,握手需要在客户和服务器之间交换三个 TCP 报文段,连接建立的过程称为三次握手


    假设 A 为客户端,B 为服务器端。最初两端的 TCP 进程都处在CLOSED(关闭)状态。

    • 首先 B 的 TCP 服务器进程先创建传输控制块TCB,准备接受客户进程连接请求,然后服务器进程处于 LISTEN(监听)状态,等待客户的连接请求
    • 然后 A 的 TCP 服务器进程创建传输控制块TCB,A 向 B 发送连接请求报文段,同步位 SYN=1,ACK=0,选择一个初始的序号 seq=x。
    • B 收到连接请求报文,如果同意建立连接,则向 A 发送连接确认报文,SYN=1,ACK=1,确认号为 ack=x+1,同时也选择一个初始的序号 seq=y。此时 B 进入 SYN-RCVD(同步收到)状态
    • TCP 客户进程 A 收到 B 的连接确认报文后,还要向 B 发出确认,确认报文段的 ACK=1,确认号为 ack=y+1,序号为 x+1。这时,TCP 连接建立,A 进入ESTABLISHED(连接)状态
    • B 收到 A 的确认后,连接建立,B 也进入 ESTABLISHED 状态。

    三次握手的原因

    第三次握手是为了防止失效的连接请求到达服务器,让服务器错误打开连接
    客户端发送的连接请求如果在网络中滞留,那么就会隔很长一段时间才能收到服务器端发回的连接确认。客户端等待一个超时重传时间之后,就会重新请求连接。但是这个滞留的连接请求最后还是会到达服务器,如果不进行三次握手,那么服务器就会打开两个连接。如果有第三次握手,客户端会忽略服务器之后发送的对滞留连接请求的连接确认,不进行第三次握手,因此就不会再次打开连接。

    3.7 TCP的连接释放

    数据传输结束后,通信双方都可释放连接。现在 A 和 B 都处于 ESTABLISHED 状态。TCP 的连接释放过程称为四次挥手


    • A 的应用进程向其 TCP 发送连接释放报文,并停止发送数据,终止控制位 FIN=1,其序号 seq=u 等于前面以传送数据的最后一个字节的序号加1。A 进入 FIN-WAIT-FIN-WAIT-1(终止等待1)状态,等待 B 的确认。
    • B 收到连接释放报文之后发出确认,确认号是 ack=u+1。此时 TCP 属于半关闭(half-close)状态,B 能向 A 发送数据但是 A 不能向 B 发送数据。A 收到 B的确认后,就进入 TIME-WAIT-2(终止等待2)状态,等待 B 发出的释放连接报文。
    • 当 B 不再需要连接时,发送连接释放报文,FIN=1。此时 B 进入 LASTLAST-ACK(最后确认)状态,等待 A 的确认。
    • A 收到来自 B 发出的连接释放报文后对此作出确认,确认报文段中 ACK=1,确认号 ack=w+1w+1,而自己的序号 seq=u+1。然后进入 TIME-WAIT(时间等待)状态,等待 时间等待计时器设置的时间 2MSL(最大报文存活时间)后释放连接。
    • B 收到 A 的确认后释放连接。

    四次挥手的原因

    客户端发送了 FIN 连接释放报文之后,服务器收到了这个报文,就进入了 CLOSE-WAIT 状态。这个状态是为了让服务器端发送还未传送完毕的数据,传送完毕之后,服务器会发送 FIN 连接释放报文。
    确保数据能够完成传输,但关闭连接时,当收到对方的 FIN 报文通知时,它仅仅表示对方没有数据发送给你了;但未必你所有的数据都全部发送给对方了,所以你可以未必会马上会关闭 SOCKET,也即你可能还需要发送一些数据给对方之后,再发送 FIN 报文给对方来表示你同意现在可以关闭连接了,所以它这里的 ACK 报文和 FIN 报文多数情况下都是分开发送的。

    TIME_WAIT

    客户端接收到服务器端的 FIN 报文后进入此状态,此时并不是直接进入 CLOSED 状态,还需要等待一个时间计时器设置的时间 2MSL。这么做有两个理由:

    • 确保客户端发送的最后一个确认(ACK)报文能够到达服务器。如果 B 没收到 A 发送来的确认报文,那么就会重新发送连接释放请求报文,A 等待一段时间就是为了处理这种情况的发生。
    • 等待一段时间是为了让本连接持续时间内所产生的所有报文都从网络中消失,使得下一个新的连接不会出现旧的连接请求报文。

    3.8 TCP可靠传输的实现

    3.8.1 滑动窗口

    TCP 的滑动窗口是以字节为单位的。窗口是缓存的一部分,用来暂时存放字节流。发送方和接收方各有一个窗口,接收方通过 TCP 报文段中的窗口字段告诉发送方自己的窗口大小,发送方根据这个值和其它信息设置自己的窗口大小。

    发送窗口内的字节都允许被发送,接收窗口内的字节都允许被接收。如果发送窗口左部的字节已经发送并且收到了确认,那么就将发送窗口向右滑动一定距离,直到左部第一个字节不是已发送并且已确认的状态;接收窗口的滑动类似,接收窗口左部字节已经发送确认并交付主机,就向右滑动接收窗口。

    接收窗口只会对窗口内最后一个按序到达的字节进行确认,例如接收窗口已经收到的字节为 {31, 34, 35},其中 {31} 按序到达,而 {34, 35} 就不是,因此只对字节 31 进行确认。发送方得到一个字节的确认之后,就知道这个字节之前的所有字节都已经被接收。


    3.8.2 超时重传

    TCP 使用超时重传来实现可靠传输:如果一个已经发送的报文段在超时时间内没有收到确认,那么就重传这个报文段。
    一个报文段从发送再到接收到确认所经过的时间称为报文段的往返时间 RTT,加权平均往返时间 RTTs 计算如下:
    $$新的RTTs=(1-alpha) imes(旧的RTTs)+alpha imes(新的RTT样本)$$
    其中,$0<=alpha<=1$。若$alpha$很接近零,表示新的 RTTs 和旧的 RTTs 值相比变化不大。RTTs 随着 a 的增加更容易受到 RTT 的影响。

    超时计时器设置的超时重传时间RTO(RetransmissionTime-Out)应该略大于 RTTs,TCP 使用的超时时间计算如下:
    $$RTO=RTTs+4 imes RTTd$$
    其中 RTTd 为偏差的加权平均值

    3.9 TCP的流量控制

    流量控制是为了控制发送方发送速率,保证接收方来得及接收

    接收方发送的确认报文中的窗口字段可以用来控制发送方窗口大小,从而影响发送方的发送速率。将窗口字段设置为0,则发送方不能发送数据。

    4. 拥塞控制

    在某段时间内,若对网络中某一资源的需求超过该资源所能提供的可用部分,网络的性能就变差,这种情况称为拥塞(congestion)
    如果网络出现拥塞,分组将会丢失,此时发送方会继续重传,从而导致网络拥塞程度更高。因此当出现拥塞时,应当控制发送方的速率。这一点和流量控制很像,但是出发点不同。

    流量控制和拥塞控制的区别

    • 流量控制是为了让接收方能来得及接收,而拥塞控制是为了降低整个网络的拥塞程度
    • 流量控制往往是指点对点通信量的控制,是端到端的问题。拥塞控制是为了防止过多的数据注入到网络中,使网路中的路由和链路不致过载,是一个全局性的问题。

    当提供的负载达到某一数值,网络的吞吐量反而随提供负载的增大而下降,网络进入了拥塞状态。当提供的负载继续增大到某一数值,网络的吞吐量下降到零,就是所谓的死锁(deadlock)。

    4.1 拥塞控制方法

    端到端拥塞控制

    TCP采用端到端的方法解决拥塞控制,因为IP层不会向端系统提供有关于网络拥塞的反馈信息。TCP报文段的丢失(通过超时或3次冗余确认得知)被认为是网络拥塞的一个迹象,TCP会相应地减少其窗口长度;还可以使用增加的往返时延值作为网络拥塞程度增加的指示。

    网络辅助的拥塞控制

    在网络辅助的拥塞控制中,路由器向发送方提供关于网络中拥塞状态的显示反馈信息。

    4.2 TCP拥塞控制

    TCP必须使用端到端拥塞控制而不是使用网络辅助的拥塞控制,因为IP层不向端系统提供显式的网络拥塞控制。

    TCP所采用的方法是让每一个发送方根据所感知到的网络拥塞程度来限制其能向连接发送流量的速率。

    TCP 主要通过四个算法来进行拥塞控制:慢开始(slow-start)、拥塞避免(congestion avoidance)、快重传(fast retransmit)、快恢复(fast recovery)。

    发送方需要维护一个叫做拥塞窗口(cwnd)的状态变量,注意拥塞窗口与发送方窗口的区别:拥塞窗口只是一个状态变量,实际决定发送方能发送多少数据的是发送方窗口
    为了便于讨论,做如下假设:

    • 接收方有足够大的接收缓存,因此不会发生流量控制;
    • 虽然 TCP 的窗口基于字节,但是这里设窗口的大小单位为报文段。
    4.3 慢开始和拥塞避免

    慢开始算法的思路:主机开始发送数据时,并不清楚当前网络的负荷情况,所以立即把大量数据注入到网络可能引发网络的拥塞。最好的方法是先探测一下,即由小到大逐渐增大发送窗口,也就是说由小到大逐渐增大拥塞窗口数值

    发送的最初执行慢开始,令初始拥塞窗口 cwnd 不超过 2 至 4 个发送方最大报文段 SMSS 的数值,发送方只能发送 1 个报文段;在每收到一个新的报文段的确认后,将拥塞窗口 cwnd 最多增加一个 SMSS 的数值,具体为:
    $$拥塞窗口 cwnd 每次的增加量=min(N,SMSS)$$

    其中$N$为原先未确认的、但现在被刚收到的确认报文段所确认的字节数。

    注意到慢开始每个轮次都将 cwnd 加倍,这样会让 cwnd 增长速度非常快,从而使得发送方发送的速度增长速度过快,网络拥塞的可能性也就更高。设置一个慢开始门限 ssthresh,当 cwnd >= ssthresh 时,进入拥塞避免,每个轮次只将 cwnd 加 1。

    拥塞避免算法的思路:让拥塞窗口 cwnd 缓慢增大,即每经过一个往返时间 RTT 就把发送方的拥塞窗口 cwnd 增加 1,而不是像慢开始阶段一样成倍增加


    如果出现了超时,则令 ssthresh = cwnd / 2,然后重新执行慢开始。

    4.4 快重传和快恢复

    个别报文段在网络中丢失,但实际网络并没有发生拥塞。如果发送方迟迟收不到确认,就会产生超时。导致发送方错误的启动慢开始,降低了传输效率。

    采用快重传算法就是让发送方尽早知道发生了个别报文丢失

    • 在接收方,要求每次接收到报文段都应该对最后一个已收到的有序报文段进行确认。例如已经接收到 M1 和 M2,此时收到 M4,应当发送对 M2 的确认。
    • 在发送方,如果收到三个重复确认,那么可以知道下一个报文段丢失,此时执行快重传,立即重传下一个报文段。例如收到三个 M2,则 M3 丢失,立即重传 M3。

    在这种情况下,只是丢失个别报文段,而不是网络拥塞。因此执行快恢复,令 ssthresh = cwnd / 2 ,cwnd = ssthresh,注意到此时直接进入拥塞避免。
    慢开始和快恢复的快慢指的是 cwnd 的设定值,而不是 cwnd 的增长速率。慢开始 cwnd 设定为 1,而快恢复 cwnd 设定为 ssthresh。

  • 相关阅读:
    Collections之sort、reverse
    网页小实验——在平面空间建立大量“可思考的”对象
    3D网页小实验——将txt配置文本转化为3D陈列室
    原生JavaScript实现一种日历
    JavaScript实现竖向滚动条的一种思路
    一个原生JavaScript动画库原型
    html小工具——文章注释编辑器
    基于Babylon.js编写宇宙飞船模拟程序1——程序基础结构、物理引擎使用、三维罗盘
    WebGL场景的两种地面构造方法
    基于Babylon.js编写简单的骨骼动画生成器
  • 原文地址:https://www.cnblogs.com/njuptzheng/p/13374953.html
Copyright © 2011-2022 走看看