《网络协议》TCP 协议

概述

TCP 和 UDP 都使用相同的网络层 IP,但是与 UDP 不同的是,TCP 是面向连接的、可靠的字节流协议。因此,在传输数据之前通信双方必须建立一个 TCP 连接。TCP 通过检验和、序列号、确认应答、重发机制、连接管理以及窗口控制等机制实现可靠性传输。

TCP通过以下方式提供可靠性:

  1. 应用数据被分割成 TCP 认为最合适发送的数据块,即进行 TCP 分段。这点与 UDP 完全不同,应用程序产生的 UDP 数据报长度将保持不变,在 IP 层将 UDP 数据报加上IP 首部后,必要时对其进行 IP 分片。
  2. 当 TCP 发出一个报文段后,它会启动一个定时器,等待目的端确认收到这个报文段,如果没能及时收到该确认信息,则将重发这个报文段。即超时重传。
  3. 当 TCP 接收端收到发自连接另一端的 TCP 报文段时,它将发送一个确认,这个确认不是立即发送的,通常会推迟几分之一秒。即确认应答。
  4. TCP 将保持它首部和数据的校验和。这是一个端到端的校验和,目的是检查数据在传输过程中的任何变化。如果收到的报文段的校验和有差错,TCP 将丢弃该报文段,同时不发送确认收到的消息,从而使发送端超时重发。
  5. 由于 TCP 报文段作为 IP 数据报来传输,IP 数据报的到达可能会失序,因此 TCP 报文段的到达也可能失序,如果必要,TCP 将对收到的数据进行重排序,将收到的数据以正确的顺序交给应用层。
  6. 由于 IP 数据报有可能发生重复,TCP 的接收端必须丢弃重复的数据。
  7. TCP 能提供流量控制。TCP 连接的每一方都有固定大小的缓冲空间,TCP 的接受端只允许另一端发送接收端缓冲区所能接纳的数据,这将防止较快主机致使较慢主机的缓冲区溢出。即流量控制。

TCP 首部

TCP 首部如下图所示:

TCP 首部比 UDP 首部复杂很多,并且没有表示包长度和数据长度的字段,可由 IP 层获取 TCP 的包长度,并由 TCP 包长度可知数据的长度。下面对 TCP 首部的个字段进行简单介绍:

  • 源端口号:表示发送端端口号,字段长 16 位;
  • 目标端口号:表示接收端端口号,字段长 16 位;
  • 序列号:字段长 32 位,是指发送数据的位置,即标识从发送端向接收端发送的字节流。每发送一次数据,就累加一次该数据字节数的大小。序列号不会从 0 或 1 开始,而是在建立连接时由计算机生成的随机数作为其初始值,通过 SYN 包传给接收端主机。然后再将每转发过去的字节数累加到初始值上表示数据的位置。此外,在建立连接和断开连接时发送的 SYN 包和 FIN 包虽然并不携带数据,但是也会作为一个字节增加对应的序列号。由此可知,建立 TCP 连接是为了初始化序列号;
  • 确认应答:字段长 32 位,是指下一次应该收到的数据的序列号。实际上,它是指已收到确认应答号减一为止的数据。发送端收到确认应答后可以认为在这个序列号以前的数据都已经被正常接收;
  • 首部长度(数据偏移):该字段表示 TCP 所传输的数据部分应该从 TCP 包的哪个位置开始计算,可以把它看作是 TCP 首部的长度。该字段长 4 位,单位是 4 字节(即 32 位)。不包括选项字段的话,TCP 首部长度为 20 个字节,因此,数据偏移字段可设置为 5。反之,若该字段值为 5,那么说明从 TCP 包的一开始到 20 字节为止都是 TCP 首部,余下的部分为 TCP 数据;
  • 保留:该字段主要是为了以后扩展时使用,其长度为 4 位,一般设置为 0,但即使收到的包在该字段不为 0,此包也不会被丢弃;
  • 控制位:字段长为 8 位,每一位从左到右分别为 CWR、ECE、URG、ACK、PSH、RST、SYN、FIN。这些控制标志也叫做控制位。当他们的对应位上值为 1 时,具体含义如下:
    • CWR:CWR 标志与后面的 ECE 标志都用于 IP 首部的 ECN 字段,ECE 标志为 1 时,则通知对方已将拥塞窗口缩小;
    • ECE:若其值为 1 则会通知对方,从对方到这边的网络有阻塞。在收到数据包的 IP 首部中 ECN 为 1 时将 TCP 首部中的 ECE 设为 1.;
    • URG:该位设为 1,表示包中有需要紧急处理的数据,对于需要紧急处理的数据,与后面的紧急指针有关;
    • ACK:该位设为 1,确认应答的字段有效,TCP 规定除了最初建立连接时的 SYN 包之外该位必须设为 1;
    • PSH:该位设为 1,表示需要将收到的数据立刻传给上层应用协议,若设为 0,则先将数据进行缓存;
    • RST:该位设为 1,表示 TCP 连接出现异常必须强制断开连接;
    • SYN:用于建立连接,该位设为 1,表示希望建立连接,并在其序列号的字段进行序列号初值设定;
    • FIN:该位设为 1,表示今后不再有数据发送,希望断开连接。当通信结束希望断开连接时,通信双方的主机之间就可以相互交换 FIN 位置为 1 的 TCP 段。每个主机又对对方的 FIN 包进行确认应答之后可以断开连接。不过,主机收到 FIN 设置为 1 的 TCP 段之后不必马上回复一个 FIN 包,而是可以等到缓冲区中的所有数据都因为已成功发送而被自动删除之后再发 FIN 包;
  • 窗口大小:该字段长 16 位,用于通知从相同 TCP 首部的确认应答号所指位置开始能够接收的数据大小(8 位字节)。TCP 不允许发送超过该窗口大小的数据。若窗口为 0,则表示可以发送窗口探测,以了解最新的窗口大小,但这个数据必须是 1 个字节;
  • 检验和:TCP 的检验和与 UDP 检验和一样,也是采用伪首部,但是 TCP 的检验和无法关闭。TCP 伪首部的信息和 UDP 一样,包括:源 IP 地址、目的 IP 地址、填充、协议号以及 TCP 包长度;
  • 紧急指针:该字段为 16 位。只有在 URG 控制位为 1 时有效。该字段的数值表示本报文段中紧急数据的指针。从数据部分的首位到紧急指针所在的位置为止是紧急数据。因此,紧急指针是指出了紧急数据的末尾在报文段中的位置;

序列号与确认应答

在 TCP 中,当发送端的数据到达接收端主机时,接收端主机会返回一个已收到消息通知,该消息就是确认应答(ACK)。TCP 通过确认应答和序列号实现可靠的数据传输,若发送端发出数据之后得到接收端的确认应答,则表示该数据已成功到达接收端,否则可能丢失数据。

超时重传

超时重传是指在重发数据之前,等待确认应答到来的那个特定的时间间隔。若发送端将数据发送出去之后,在特定的时间内没有收到接收端的确认应答,则发送端会重新发送该数据,这就是超时重传机制。

连接管理

TCP 协议是提供面向连接的通信传输,面向连接是指双方在进行传输数据之前必须建立连接。有关 TCP 的建立连接和释放连接放在后面讲解,这里只是提到 TCP 存在知识。

窗口控制

TCP 传输数据是以 1 个段为单位,每发送一个段进行一次确认应答的处理,这样使通信时包的往返时间很长导致降低通信性能。为了解决这个问题,TCP 引入了窗口控制,确认应答不再是以每个分段,而是以更大的单位进行确认,这样缩短转发时间,也就是说,发送端主机在发送了一个段之后不必要一直等待确认应答,而是继续发送数据段。窗口大小是指无需等待确认应答而可以发送数据的最大值。

                         

采用窗口控制机制必须实现缓冲区,在图 4 中,窗口内的数据即便是没有收到确认应答也可以发送出去。此外从该窗口中能看到的数据是因其某种数据已在传输中丢失,所以发送端才能接收到确认应答,这种情况下需要进行重发。为此,发送端主机在等到确认应答返回之前,必须在缓冲区中保留这部分的数据。在滑动窗口以外的部分包括尚未发送的数据已经已经确认对端已经收到的数据。当数据发出后若如期收到确认应答就可以不用进行重发,此时数据可以从缓冲区中删除。收到确认应答后,将窗口滑到确认应答中的序列号的位置,这样可以顺序地将多个段同时发送提供通信性能。这种机制也称为滑动窗口机制。

流量控制

流量控制可以让发送端根据接收端的实际接受能力控制发送的数据量。它的具体操作是,接收端主机向发送端主机通知自己可以接收数据的大小,于是发送端会发送不会超过该大小的数据,该限制大小即为窗口大小,即窗口大小由接收端主机决定。TCP 首部中,专门有一个字段来通知窗口大小,接收主机将自己可以接收的缓冲区大小放在该字段中通知发送端。当接收端的缓冲区面临数据溢出时,窗口大小的值也是随之改变,设置为一个更小的值通知发送端,从而控制数据的发送量,这样达到流量的控制。

拥塞控制

为了防止网络拥塞,TCP 采用了一种慢启动算法,对发送数据量进行控制。为了调节发送端的数据发送量,引入了拥塞窗口,在慢启动时,将这个拥塞窗口设为 1 个数据段发送数据,之后每收到一次确认应答,拥塞窗口的值就加 1。在发送数据包时,将拥塞窗口的大小与接收端主机通知的窗口大小进行比较,然后选择较小的值来控制数据量的发送。

参考资料:

《TCP/IP 详解》

《图解 TCP/IP》

时间: 2024-07-31 07:49:40

《网络协议》TCP 协议的相关文章

可靠的传输层协议——TCP协议

TCP协议 TCP协议工作在传输层,虽然它与UDP的下一层都是IP但是它却和UDP的效果完全不同,它是一种可靠的传输层协议 一.TCP协议封装 TCP数据段头部共有20个字节,包括16位的源端口号,16位的目的端口号,端口号与前面各层中的协议类型相似,都指的是上层将要交给谁,这个端口号就是主机上一个进程所绑定的一个入口,所以通过端口号和IP就能找到唯一主机的唯一进程. 32位序号:用来标识从TCP发端向TCP收端发送的数据字节流,它表示在这个报文段中的的第一个数据字节.如果将字节流看作在两个应用

网络 基于TCP协议socket编程

一.socket编程         1.socket编程        socket这个词可以表示很多概念: 在TCP/IP协议中,"IP地址+TCP或UDP端号"唯一标识网络通讯中的一个进程,"IP地址+端口号"就称为socket.在TCP协议中,建立连接的两个进程各自有一个socket来标识,那么这两个socket组成 的socket pair就唯一标识一个连接. socket本义有"插座"的意思,因此用来描述网络连接的一对一关系.    

【网络】TCP协议

TCP协议:对于网络协议而言.TCP在传输层中是一个十分钟要的协议,那么什么是TCP协议呢? TCP协议概念: 传输控制协议(英语:Transmission Control Protocol,缩写为 TCP)是一种面向连接的.可靠的.基于字节流的传输层通信协议,由IETF的RFC 793定义.在简化的计算机网络OSI模型中,它完成第四层传输层所指定的功能,用户数据报协议(UDP)是同一层内另一个重要的传输协议. 在因特网协议族(Internet protocol suite)中,TCP层是位于I

数据通讯与网络 第五版第24章 传输层协议-TCP协议部分要点

上一博客记录了UDP协议的关键要点,这部分记录TCP协议的关键要点. 24.3 传输控制协议(TRANSMISSION CONTROL PROTOCOL) TCP(Transmission Control Procotol )协议是一个面向连接,可靠的协议.TCP为了提供面向连接的服务,专门定义了连接创建,数据传输.连接终止阶段.TCP使用GBN和SR协议来提供可靠性.为了实现可靠性这个目标,TCP使用检验和来进行误差控制.重传来处理数据包丢失和冲突.同时还利用了应答和计数机制.在本节,首先讨论

java 网络编程-TCP协议基本步骤

TCP:TCP协议基于请求-响应模式利用io流实现数据的传输 创建服务器1.指定端口 使用ServerSocket创建服务器2.阻塞式等待连接accept,有一个accept就建立了一个客户端3.操作:io流4.释放资源 public class tcp { public static void main(String[]args) throws IOException { System.out.println("-----Server-----"); // 1.指定端口 使用Serv

网络编程 TCP协议:三次握手,四次回收,反馈机制 socket套接字通信 粘包问题与解决方法

TCP协议:三次握手,四次挥手 TCP协议建立双向通道. 三次握手, 建连接: 1:客户端向服务端发送建立连接的请求 2:服务端返回收到请求的信息给客户端,并且发送往客户端建立连接的请求 3:客户端接收到服务端发来的请求,返回接成功给服务端,完成双向连接 第一客戶向服务端发送请求,请求建立连接 服务端同客户端的请求,并同时向客户端发送建立 连接的请求,最后客户端同意后建立 双向连接. C ----> S C <---- S - 反馈机制: 客户端往服务端发送请求,服务端必须返回响应, 告诉客户

Http与协议TCP协议简单易懂

于C#编写代码,很多时候会遇到Http协议或TCP合约,这里做一个简单的了解. TCP对应于该传送层协议,和HTTP对应于应用层协议,从本质上讲,两者是没有可比性.Http该协议是基于TCP之上的,当浏览器须要从server获取网页数据的时候,会发出一次Http请求. Http会通过TCP建立起一个到server的连接通道.当本次请求须要的数据完成后,Http会马上将TCP连接断开,这个过程是非常短的.所以Http连接是一种短连接.是一种无状态的连接.所谓的无状态,是指浏览器每次向server发

UDP协议&amp;TCP协议

域名: DN (Domain name)是由一串由点分隔的名字组成的Internet上某一台计算机或计算机组的名称. 域名服务系统:DNS:它可以作为将域名和IP地址相互映射的一个分布式数据库. 协议: 应用层常见协议: http协议:超文本传输语言. ftp协议:文件传输协议 smtp协议:简单邮件传输协议 传输层的协议: UDP协议:用户数据报协议,面向无连接的,简单不可靠的传输层协议. 面向无连接 通过数据报包来进行传输,每个数据报包大小不会超过64k. 不可靠的传输. 传输速度快. TC

python网络编程-TCP协议中的三次握手和四次挥手(图解)

建立TCP需要三次握手才能建立,而断开连接则需要四次握手.整个过程如下图所示: 先来看看如何建立连接的. 首先Client端发送连接请求报文,Server段接受连接后回复ACK报文,并为这次连接分配资源.Client端接收到ACK报文后也向Server段发生ACK报文,并分配资源,这样TCP连接就建立了. 那如何断开连接呢?简单的过程如下: [注意]中断连接端可以是Client端,也可以是Server端. 假设Client端发起中断连接请求,也就是发送FIN报文.Server端接到FIN报文后,

java 网络编程 TCP协议 java 服务器和客户端 java socket编程

一个 HelloWord 级别的 Java Socket 通信的例子.通讯过程:        先启动 Server 端,进入一个死循环以便一直监听某端口是否有连接请求.然后运行 Client 端,客户端发出连接请求,服务端监听到这次请求后向客户端发回接受消息,连接建立,启动一个线程去处理这次请求,然后继续死循环监听其他请求.客户端输入字符串后按回车键,向服务器发送数据.服务器读取数据后回复客户端数据.这次请求处理完毕,启动的线程消亡.如果客户端接收到 "OK" 之外的返回数据,会再次