专业网站设计力荐亿企邦,WordPress社区论坛,电商网站对比表,app推广代理文章目录 1. TCP报文的结构2. TCP的发送缓冲区和接收缓冲区3. 确保可靠性序列号和确认序列号确认应答超时重传连接管理1️⃣三次握手建立连接2️⃣四次挥手断开连接 4. 提高性能流量控制滑动窗口拥塞控制延迟应答捎带应答 5. 面向字节流6. TCP/UDP对比 概念#xff1a;TCPTCPTransmission Control Protocol是一种面向连接的、可靠的、面向字节流的传输层协议它用于在计算机网络中实现端到端的可靠数据传输。 1. TCP报文的结构 数据就是发送方发给接收方的资源应用层报文数据一个TCP报文也可以不携带数据而只有报头因此TCP报头Header比较重要。 各个Header字段的作用如下
源端口号与目的端口号表明报文是从哪个进程来到哪个进程去的序列号与确认序列号与TCP确认应答机制强相关后面详谈首部长度表示该TCP首部有多少个4字节该字段只有4个比特位即范围在0~15首部长度*4表示包括选项的整个报头长度因此报头长度范围在20~60字节窗口大小反映发送端目前的接收数据能力标志位6个不同的标志位标识TCP报文的类型置1标志位有效 URG当前报文为紧急报文搭配紧急指针使用ACK当前报文为确认应答报文搭配确认序列号使用PSH通知接收端应用层立即将该报文数据从缓冲区中取走“插队”RST复位报文段通知接收端重新建立连接SYN同步报文段请求与接收端建立连接FIN结束报文段通知接收端本端即将关闭需要断开连接 保留位暂未设置功能保留备用校验和发送端填充CRC校验。接收端校验不通过则认为数据有问题。此处的检验和不光包含TCP首部也包含TCP数据部分紧急指针一个偏移量通过紧急指针能够找到正文数据中的带外数据紧急数据选项用于在TCP连接的建立和维护过程中进行配置和协商报头前20字节是定长的选项是变长的范围在0~40字节。 2. TCP的发送缓冲区和接收缓冲区 在应用层用户建立以TCP协议为基础的socket套接字并使用系统调用write/send和read/recv进行数据的发送和接收。那么用户调用系统调用收发的数据是从网络的对端直接收发的吗不。实际上当一台主机建立了一个TCP连接其OS中会同时存在一个发送缓冲区和一个接收缓冲区由socket打开文件句柄维护当应用层调用write/send是向发送缓冲区中拷贝数据当应用层调用read/recv是从接收缓冲区拷贝数据。 OS负责将发送缓冲区中的数据送到网络中将网络中的数据收到接收缓冲区中。底层的网络传输是由传输层以下的网络层、数据链路层等负责的传输层只负责将数据发送给和接收到正确的端口进程。 补充 发送缓冲区和接收缓冲区中存储的都是一个个加了Header的TCP报文OS自动添加报头和解除报头而不是应用层的原始数据。 发送缓冲区和接收缓冲区都只用于缓存应用层数据一些TCP报文可以不进入缓冲区直接由OS负责发送和接收如不带数据的ACK,SYN,FIN报头。 因此TCP通信是全双工的可以同时发送数据和接收数据不会相互干扰。 3. 确保可靠性 要确保协议在网络传输中的可靠性就必须知道哪些情况是不可靠的再来解决这些不可靠的情况。网络传输中的不可靠情况有以下几种 丢包大量丢包和少量丢包乱序报文的发送顺序和接收顺序不一致重复接收端收到来自发送端的报文相同浪费额外成本 序列号和确认序列号 为了保证可靠性TCP引入了确认应答机制。确认应答机制需要与TCP报头中的序列号、确认序列号和标志位ACK搭配使用因此需要先了解序列号和确认序列号。 序列号Seq Number TCP中每一个字节都进行了编号TCP的数据存在于发送缓冲区和接收缓冲区中可以把这两个缓冲区看成是两个以字节为单位的数组字节编号就是数组下标。由于TCP传输面向字节流发送端发送的一个报文就是发送缓冲区中的一段以字节为单位的序列该报文的序号又称序列号就是这段字节中第一个字节的编号。 假设1001-2000字节是一个报文则该报文的序列号为1001 确认序列号ACK Number 每个ACK应答都会有一个有效的确认序列号以告知发送端下次期待接收的数据序列号。 确认序列号等于已成功接收到的数据的最后一个字节的序号加一。比如收到的报文是1001-2000字节序列号是1001大小由OS自动确认那么确认序列号就是2001告知发送端的信息是2001之前的字节都已经收到了下次请从2001号字节开始发送。注意只有ACK标志位被置为1确认序列号才有效。
确认应答
TCP发送端向接收端发送一个报文该报文如果在网络中丢包接收端就无法正确地收到完整的TCP报文了。因此为了解决丢包问题发送端必须先得知是否发生了丢包确认应答机制保证了发送端能够获知报文发送的状态 发送端向接收端发送一个报文若接收端成功收到报文则返回一个应答应答就是ACK标志位被置为1的TCP报文以告知发送端接收端已经成功收到报文了没有丢包或其它问题发生若接收端没有收到报文则不会返回应答。 站在接收端的角度已经告知了发送端它发送的报文是否被接收。而站在发送端的角度对于应答的接收有两种情况。
成功收到应答。表示发送端的报文成功被接收端收到发送端可以继续发送下一个报文。没有收到应答。这种情况还有两种子情况因为应答也是一个报文它也会丢包所以如果发送端没有收到应答一种情况是发送的报文接收端压根没收到那肯定也不会发回应答另一种情况是接收端收到了报文也发回应答但是应答丢包了此时发送端也收不到应答。后者虽然报文没有丢包但是发送端并无法确定。因此如果发送端没有收到应答统一认为是发送报文丢包则执行超时重传机制后面详谈。 序列号除了在确认应答中发挥作用还有其它两个重要的作用
保证报文的发送顺序与接受顺序相同。 报文在网络中传输会受到多种因素的影响发送路径、网络拥塞情况等这可能会导致报文从发送端发出的发送顺序与接收端接收到的顺序不同这是万万不可的。因为TCP是面向字节流传输在发送端一个完整的应用层报文可能会被组织在不同的TCP报文中发出然后在接收端重新将这些TCP报文拼接起来。只有保证报文按序到达才能成功完成拼接使接收端与发送端看到相同顺序的字节流数据。接收端的传输层会对一个连接收到的报文按序列号排列后再输入接收缓冲区。去除重复报文。 当发送端超时重传时并不能保证接收端曾经没有收到过重传的报文可能当前重传的报文已存在于接收端中因此接收端可能会受到很多重复的报文。为了防止空间浪费接收端会根据序列号进行比对去除重复的报文。
超时重传 ⏱发送端发出一个报文后会等待一段时间等待接收端的应答时间一到若未收到应答则表示确认应答失败此时发送端需重新发送该报文这就是超时重传机制RTO, Retransmission Timeout。 那么如何确定超时重传的时间呢 最理想的情况是找到一个最小时间保证正常情况下不出现丢包确认应答一定能在这段时间内到达。但是这个时间难以准确设定不同的网络环境注定了传输速度的不同时间也有长有短。若时间设置过长会导致重传效率降低 丢包早就发生了还一直不重传若时间设置过短可能会在发送报文或确认应答尚未到达目标端就触发重传导致频繁发送重复的报文。 因此TCP为了确保无论在任何网络环境下都保证较高的通信效率会不断动态更新这个最大超时时间。 在Linux中超时时间以500ms为单位初始时为500ms若第一次重传失败重传后仍没有收到应答则将超时时间改为2*500ms若第二次再次失败再变为4*500ms以此类推以指数形式递增。累计到一定的重传次数, TCP认为网络或者对端主机出现异常, 强制关闭连接这种情况是异常断开连接。 连接管理 TCP是面向连接的即两个网络进程在通信之前必须先建立连接。TCP采用三次握手的方式建立连接。 连接本质上就是在OS传输层中组织并管理的一种数据结构用于保存连接的本地ip和端口号、对端ip和端口号、协议、连接状态等信息netstat 指令可以查看网络状态即查看本地维护的连接。一个已建立的TCP连接与对应的套接字socket相关联。 netstat命令使用指南 语法netstat [选项] 常用选项 n 拒绝显示别名能显示数字的全部转化成数字l 仅列出有在 Listen (监听) 的服务状态p 显示建立相关链接的程序名t (tcp)仅显示tcp相关选项u (udp)仅显示udp相关选项a (all)显示所有选项默认不显示LISTEN相关 1️⃣三次握手建立连接
客户端与服务器通信前三次握手建立连接的过程图示 ⭕三次握手的过程
服务器端通过socket, bind, listen三板斧后获得一个LISTEN状态的连接用于监听Client端的连接请求。第一次握手 客户端向服务端发送同步报文段SYN标志位置1的报头此时客户端连接状态为SYN_SEND同步发送。服务端若成功收到同步报文段则创建一个连接状态为SYN_RCVD同步接收的半连接。此时双方都认为第一次握手完成。第二次握手 服务端向客户端发送同步和确认应答的报文确认客户端发来的同步报文已收到客户端若成功收到代表第二次握手完成此时客户端连接状态为ESTABLISHED可以进行数据读写。第三次握手 客户端建立连接完成后向服务器发送应答确认服务器发来的同步报文已收到服务端若成功收到应答代表三次握手完成则创建一个状态为ESTABLISHED的全连接可以进行数据读写。
什么是全连接和半连接 连接状态为SYN_SEND或SYN_RCVD的为半连接状态为ESTABLISHED的为全连接。服务端的TCP传输层内核维护着两个队列半连接队列和全连接队列这两个队列与服务端的listensocket相关联全连接队列的长度 listen的第二个参数backlog 1。 半连接队列中保存处于SYN_SEND或SYN_RCVD的连接请求半连接长时间未变为全连接会被清除。 连接队列即全连接队列用于存储尝试连接到该listensocket但尚未被服务器应用层accept函数接受的客户端连接请求。服务端应用层调用accpet就是获取全连接队列中的连接并建立新的文件fd供用户读写数据。 如果全连接队列满了多余的连接则无法进入ESTABLISHED状态始终处于同步接收状态即无法从半连接队列进入全连接队列过段时间会被OS自动删除。 设置backlog为1,全连接队列长度为2此时只能存储两个连接第三个连接到达服务端时状态为SYN_RECV无法进入全连接队列 过了一会服务端清除SYN_RECV连接客户端仍然维护着该连接
三次握手的优越性 三次握手建立连接时发送的报文也存在丢包问题。 如果第一次握手的SYN报文丢包客户端会触发超时重传机制即使超时重传也失败了对双方也并没有任何影响因为客户端和服务端都没有消耗维护连接的成本。如果第二次握手的SYNACK报文丢包同上也不会对双方超时影响。 问题在于第三次握手。第三次握手是客户端已经建立好连接向服务器发送应答此时客户端认为三次握手已完成连接建立成功。如果第三次握手的应答丢包了服务器没有收到应答不会创建ESTABLISHED连接。此时客户端和服务器对于连接的状态认知不一致连接失败。 三次握手保证了前两次握手都有应答来确认报文发送情况可无论如何都会有最新一次应答无法确认因此第三次握手的ACK应答无法确认是否发到服务器上。TCP协议采用的策略是不对第三次握手的ACK应答进行确认。客户端建立ESTABLISHED连接并将应答发出后默认三次握手已完成不管服务器是否收到应答它便直接通过已建立的连接向服务器发送报文了。服务器收到客户端的报文后如果发现本地没有与报文首部端口号相对应的连接则会向客户端发送连接重置报文RST标志位置1的报头。客户端收到RST报文重新触发三次握手建立连接。 因此三次握手的本质是在“赌”最后一次握手是否成功成功是大概率事件即使失败也能后续重连。 根据上一条目所述若三次握手的最后一次握手发送的应答丢包此时客户端已维护了一个连接而服务器没有此时连接失败的成本就在客户端无效的连接会占用客户端内存资源。在CS模式Client and Server中客户端是主动发起连接请求的一方而服务器端是等待接收连接请求的一方。因为服务器一般会同时维护多个连接处理来自不同客户端的数据如果连接失败的成本让服务端承担会导致服务器性能下降浪费服务器资源所以连接失败的成本最好嫁接到客户端上。而三次握手恰能满足这种需求。如果是两次握手呢见如下分析 两次握手如果第一次握手丢包没问题双方都没建立连接对象消耗成本。由于第二次握手即最后一次服务端发出SYNACK后就认为两次握手结束便建立了连接对象如果SYNACK丢包没有到达目标客户端则连接失败此时客户端并没有建立连接连接失败的成本在服务端上并不符号我们的预期。两次握手还有另外的问题客户端任意发送SYN请求服务器收到后没有其它确认机制直接在本地创建连接而客户端却可以不对服务端的应答进行处理也就不会消耗成本。这样一来服务端极易收到大量客户端的SYN请求造成严重的空间泄漏这种攻击称为SYN洪水。真正预防攻击的机制应该由应用层完成但是传输层TCP也绝不能有这种明显的漏洞出现。综上得两次握手的方案不可取。 综合三次握手和两次握手的过程得出结论最后一次应答报文由哪一方发出连接失败的成本就由哪一方承担。 又因为客户端是主动发起连接请求的一方服务器端是等待接收连接请求的一方由此推出奇数次握手——失败成本在客户端偶数次握手——失败成本在服务端。 因此必须采取奇数次握手的策略
既然要采取奇数次握手的策略为何TCP是三次握手而不是五次、七次握手呢事实上握手的功能除了建立连接还有验证双方通信信道的通畅情况。因为TCP传输是全双工的因此想要验证全双工信道通畅情况三次握手是最小成本且有助于建立连接尽快完成。
2️⃣四次挥手断开连接 TCP连接通信结束后要经过四次挥手断开连接。 通信双方任一方都可以调用close主动发起断开连接请求触发四次挥手下面以客户端向服务器主动发起断连请求为例。 断开连接必须双方达成共识后才能断即客户端调用一次close对应服务端也应调用一次close。不同于三次握手因为服务端收到断连请求FIN后必须由应用层调用close后才能再向客户端发送FIN请求因此不能像三次握手一样发送ACKSYN而是先发送确认应答后等待应用层close后才发送FIN请求。因此挥手规定是四次两次挥手无法保证让双方达成共识三次挥手更无法保证因此四次挥手是断开连接的最小成本。 ⭕四次挥手的状态变化
客户端close(fd)连接立即进入FIN_WAIT_1状态并向服务端发送FIN请求即告知服务端“我”已经关闭连接了等待应答。服务端收到FIN请求后连接立即进入CLOSE_WAIT状态并向客户端发送ACK应答。此时服务端并没有关闭连接而是保持CLOSE_WAIT状态等待应用层close。应用层可以通过read的返回值0得知客户端已关闭连接进而调用close关闭连接。客户端若成功收到ACK应答连接则进入FIN_WAIT_2状态等待服务端发送FIN请求“我”已经告知对端我要断连了当然也要获知对方也要断了以达成共识。若服务端一直没有发送FIN请求客户端也不会在FIN_WAIT_2状态一直等下去到达一定的时间直接断开连接清除连接数据。服务端在连接状态为CLOSE_WAIT时调用close则会进入LAST_ACK状态并向客户端发送FIN请求。客户端若成功收到服务端的FIN请求则会由FIN_WAIT_2状态进入TIME_WAIT状态并向服务端发送最后一次ACK应答。TIME_WAIT会等待一段时间结束后关闭连接。服务端若在LAST_ACK状态成功收到则关闭连接。至此四次挥手完成。 四次挥手过程中客户端会等待一次应答服务端也会等待一次应答。这里都存在超时重传机制若累积到一定重传次数认为连接异常强制关闭连接这样也关闭了连接。因此如果服务端在客户端FIN_WAIT_2状态等待时间结束自动关闭连接之后再调用close就会进入LAST_ACK状态并不断重发因为客户端已经关闭连接重发多少次都是无效的因此达到一定上限后服务端就异常断连了。 这种机制提醒程序员们在进行网络服务器开发时切记要在通信结束后close(fd)关闭连接否则连接的客户端一多服务器中就会残留非常多CLOSE_WAIT状态的连接这种连接会维持很长一段时间严重占用了服务器内存资源。这种情况称为文件描述符泄漏。 关于TIME_WAIT 为什么要有TIME_WAIT状态 主动发出断连请求的一方会进入TIME_WAIT状态主要目的是尽量保证对端能够收到最后一个ACK应答以完成正常的关闭连接过程。因为如果发出ACK后就直接关闭连接而不进入TIME_WAIT状态可能ACK还没到达对端连接异常无法发送过去即使对端想要重发也无济于事因为“我”已经关闭连接了。另一个目的是保证历史数据在通信信道中消失防止影响下一次通信。要知道通信双方进入四次挥手阶段可能还有一些尚未被接收或迟到的数据残留在信道中如果不让它们消失可能下次建立同客户端同服务端的连接时就会收到历史残留的数据产生意料之外的影响。 TIME_WAIT要等多久 TCP规定TIME_WAIT的时间是两个MSL(Maximum Segment Lifetime, TCP报文在网络中的最大存活时间)以保证全双工两个信道上的历史数据全部消失。MSL的值通常是2分钟120秒但在不同的TCP实现中它也可以有所不同。 Centos7默认配置为60s TIME_WAIT导致服务器无法立刻重启问题 若服务器端主动与客户端断开连接这种场景也是存在的比如服务器满载崩溃必定会进入TIME_WAIT状态此时再用相同的端口号重启服务器会bind失败因为本地还有该端口号的连接处于TIME_WAIT状态bind无法绑定已被使用的端口号。一般服务器的端口号是不能随意改变的所以要想以相同端口号重启服务器必须等待TIME_WAIT状态结束。但这是不可取的TIME_WAIT的等待时间较长一般大型服务器挂个几秒钟就会亏损很多更何况是一两分钟。 解决方案 setsockopt函数可以改变套接字状态使其可以重复绑定已被使用的端口号 // 函数原型int setsockopt(int sockfd, int level, int optname, const void *optval, socklen_t optlen);
// 用法int optval 1;setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, optval, sizeof(optval));⭕完整流程图 4. 提高性能 TCP协议为了实现可靠性设计十分复杂这势必会导致一些通信场景下的效率降低因此TCP在可靠性的基础上也采用了一些提高性能的机制。 流量控制 发送端的发送速度必须与接收端的接收能力相匹配否则会导致效率下降。 若发送速度过快接收端接收能力不足。这里的“接收能力”指的是接收端接收缓冲区的剩余容量比如发送端一次发送了1024个字节而此时接收端接收缓冲区剩余空间仅有512字节且应用层迟迟不read数据那么接收端就没能力接收数据溢出的512字节会被丢弃。根据确认应答机制发送端还会重传一部分数据影响了通信效率。若发送速度过慢接收端长时间空闲。好比现在接收端缓冲区还有1024字节的剩余空间而发送端每次只发送1字节数据接收端的应用层一次read的数据非常少处理数据的效率也大大降低。 流量控制是TCP协议中用于确保在数据传输期间发送方发送速度与接收方接收处理能力相匹配的一种机制。
TCP报头中的窗口大小字段是流量控制机制的核心。 接收端每次向发送端发出一个报文都会携带其目前接收缓冲区的剩余空间大小即窗口大小。发送端根据接收端的窗口大小控制发送数据的大小确保发送速度与接收端接收能力匹配这就是流量控制机制。 滑动窗口 前面我们讨论的情况都是假设通信是串行的即TCP发送端每次只发送一个报文然后再根据接收端应答的确认序列号发送下一个报文。这么做效率太低实际TCP中每次是同时发送多个报文一个报文的发送不用等待上一个报文的确认应答并发发送时间重叠提高效率。 TCP中的滑动窗口实际上是发送缓冲区中的一段区间这段区间中的数据是可以不用等待应答直接发送的数据。 滑动窗口控制每次发送的数据范围即每次发送应用层数据都是发送滑动窗口中的数据。 TCP初始滑动窗口大小一般在三次握手建立连接期间被确定滑动窗口的大小变化根据应答报文中的窗口大小决定。拥塞窗口也是决定因素之一后面讲
滑动窗口在发送缓冲区中的结构 滑动窗口之前的数据是已发送已确认应答的数据这部分数据已在发送缓冲区中无效可以被覆盖。 滑动窗口中前段部分是已发送但未确认应答的数据根据确认应答-超时重传机制这部分数据必须保留一段时间以支持重传后段部分是可以直接发送不用等待上个报文确认应答的数据。每次收到接收端的应答发送端都会根据该应答更新滑动窗口的大小。应答的确认序列号决定滑动窗口前半部分哪些数据已被确认应答的窗口大小影响滑动窗口这次能够发送多大数据。 滑动窗口之后的数据是尚不能发送的数据应用层wirte/send写入数据尾插到这一部分等待滑动窗口到达。
⭕滑动窗口工作过程 初始时假设发送端滑动窗口大小为5此时窗口内的5个报文可以同时发送但这5个报文的应答不一定同时到达发送端。 发送端收到最新一个ACK应答后会根据该应答调整滑动窗口的大小。假设滑动窗口的区间为[winBegin, winEnd] : winBegin 确认序列号 winEnd winBedin 窗口大小 发送端将已更新的滑动窗口中的数据包含前半部分的重传数据和后半部分首次传输的数据全部发出。 总而言之滑动窗口的工作过程就是不断向右滑动不能向左因为左边的数据已发送已应答发送窗口中的数据。值得注意的是由于TCP发送缓冲区设置为环状结构因此滑动窗口不会越界。 异常情况
若多个同时发出的报文部分确认应答丢包了。不要紧因为确认序列号X是接收端告知发送端X之前的数据已经收到了下次从X开始发送所以后续的应答也能够确认前面的报文。即使应答都丢了也还有重传机制兜底。 若是发出的数据报文丢包了 如图如果是第一个报文丢包了其它报文没丢接收端会收到2001~5000的三个报文并且后续每个报文的应答确认序列号都是1001因为1001~2000的报文没收到要告知发送端下次从1001开始发。随后发送端会收到三个重复的确认序列号。 原本报文丢包是超时重传机制解决的第一个报文没收到对应的确认应答会等待超时重传。而发送端在等待期间却收到了三个重复的确认序列号1001根据重复的确认序列号1001锁定最近的报文判断1001~2000已丢包不再等待超时重传直接补发1001~2000的数据。接收端成功收到空缺的数据后下次就发送确认序列号5001了。 这种机制称为“高速重传机制”又称快重传。 快重传与超时重传的区别 快重传规定发送端收到三个或三个以上两个可能是其它因素导致的重复ACK不可靠的重复确认应答立即补发以快速恢复丢失报文不等待超时。 超时重传是重传机制的下限快重传是重传机制的上限是在超时重传的基础上做效率优化。 拥塞控制 实际上在网络世界中通信双方进行数据传输时的效率不仅会受到彼此的影响还会受到网络的影响。网络中存在大量的主机可能当前的网络情况比较拥堵如果通信双方在不清楚当前网络状态下贸然向网络中发送大量数据可能会引发大量的丢包。而丢包又会触发重传重传又再次将大量数据发入网络又加剧了网络的拥堵情况这是一种恶性循环。 为了保证传输的可靠性提高传输效率通信双方必须清楚网络状态根据网络情况决定数据吞吐量TCP设计了拥塞控制机制。拥塞控制机制一般由慢启动和拥塞避免两部分构成。 慢启动 通信刚开始时双方并不清楚网络状态只能先以较慢速度传输数据以摸清网络状态。若传输数据正常收到应答则加快传输速度这里的传输速度指每次传输的数据量大小直到出现丢包问题这就是慢启动。慢启动的加快呈指数增长指数增长的特点是先慢后快符合刚开始不能向网络发送大量数据又想尽快摸清网络状况的需求。 拥塞避免 为了不增长的过快慢启动达到某个阈值后会由指数增长变为线性增长此后的过程称为拥塞避免。
拥塞窗口
为了量化网络重载通信传输的能力TCP中维护了一个拥塞窗口慢启动到拥塞避免的过程称为拥塞探测拥塞探测的本质就是在不断更新拥塞窗口的大小因为网络状况是不断变化的所以拥塞探测在通信过程中是持续进行的。
拥塞窗口是更新滑动窗口大小的另一指标发送端每次更新滑动窗口时滑动窗口大小 min(接收端窗口大小拥塞窗口大小)
⭕拥塞探测的状态变化 刚开始先是慢启动到达ssthresh阈值后TCP一般设置初始ssthresh为65535字节进入拥塞避免即线性增长每次传输拥塞窗口加1。探测时发生大量丢包则认为是网络拥塞此时将拥塞窗口reset为1以降低网络压力并重新开始拥塞探测先让网络缓一缓再慢慢试探它。 每次新的探测的ssthresh阈值是上一次的一半。 网络拥塞在探测全程都有可能出现不一定是在拥塞避免阶段。 延迟应答 通信双方发送数据希望每次发送的数据量尽量大一些这样可以减少发送次数因为过多的网络发送次数会降低效率。发送端发送的数据量取决于网络情况拥塞窗口cwnd和对端接受能力接收窗口大小rwnd网络情况不是通信双方能决定的因此TCP的策略是尽量加大每次发送端收到的rwnd。rwnd由接收端交付给发送端因此rwnd需在接收端计算。rwnd是接收缓冲区的窗口大小这不是TCP能随意扩大的而是要等TCP上层的应用程序read/recv读取缓冲区中的数据后rwnd才会变大。因此TCP能做的只有延缓应答的时间加大应用层读取数据的概率尽可能让rwnd更大再交付给发送端这就是延迟应答。 延迟应答除了延时应答还有隔包应答
延时应答超过一定时间再返回应答隔包应答每个N个包就应答一次
具体的数量和超时时间依操作系统不同也有差异一般N取2延时取200ms; 捎带应答 在确认应答机制里TCP报头中的起作用的只有ACK标志位和确认序列号。因此为了减少网络发送次数应答不一定独立成为一个报文而是搭乘其它数据报文的“顺风车”仅需将该报文中的ACK标志位置为1填上正确的确认序列号即可。 5. 面向字节流 TCP协议是面向字节流的发送端应用层调用write/send是先向TCP的发送缓冲区写入应用层报文数据数据怎么发发多少由TCP决定。 若TCP收到的数据过长则会拆分成多个TCP报文若收到的数据过短则会等待一段时间再打包一个TCP报文。 接收端应用层调用read/recv并无法保证一次就能提取一个完整的应用层报文因为TCP是面向字节流的TCP数据发送到接收端时是多个TCP报文这些TCP报文可能一个里面包含多个应用层报文也可能多个TCP报文才能组成一个应用层报文。TCP会根据报文序号自动拼接组成一段顺序与发送方数据一致的数据再交付给应用层。 应用层调用read/recv看到的永远都是一段字节流数据。由于缓冲区的存在TCP程序的读和写不需要一一匹配例如写100个字节数据时可以调用一次write写100个字节也可以调用100次write每次写一个字节;读100个字节数据时也完全不需要考虑写的时候是怎么写的既可以一次read 100个字节也可以一次read一个字节重复100次。 粘包问题 因为应用层调用read/recv看到是字节流数据无法直接区分报文与报文之间的间隔因此需要应用层自己定制协议规定如何提取报文明确两个应用层报文之间的边界。例如HTTP协议中采用的是Content-Length加空行的策略提取报文。 6. TCP/UDP对比
TCP/UDP对比
我们说了TCP是可靠连接那么是不是TCP一定就优于UDP呢TCP和UDP之间的优点和缺点绝对不能简单地进行比较
TCP用于可靠传输的情况应用于文件传输重要状态更新等场景UDP用于对高速传输和实时性要求较高的通信领域例如早期的QQ视频传输等。另外UDP还可以用于广播。
归根结底TCP和UDP都是程序员的工具什么时机用具体怎么用还是要根据具体的需求场景去判定。 ENDING… 文章转载自: http://www.morning.jsxrm.cn.gov.cn.jsxrm.cn http://www.morning.msbmp.cn.gov.cn.msbmp.cn http://www.morning.rrdch.cn.gov.cn.rrdch.cn http://www.morning.xgzwj.cn.gov.cn.xgzwj.cn http://www.morning.ftrpvh.cn.gov.cn.ftrpvh.cn http://www.morning.bntgy.cn.gov.cn.bntgy.cn http://www.morning.tssmk.cn.gov.cn.tssmk.cn http://www.morning.fxkgp.cn.gov.cn.fxkgp.cn http://www.morning.fldsb.cn.gov.cn.fldsb.cn http://www.morning.sqqhd.cn.gov.cn.sqqhd.cn http://www.morning.nkpls.cn.gov.cn.nkpls.cn http://www.morning.ggnrt.cn.gov.cn.ggnrt.cn http://www.morning.jfnbh.cn.gov.cn.jfnbh.cn http://www.morning.grpfj.cn.gov.cn.grpfj.cn http://www.morning.xsszn.cn.gov.cn.xsszn.cn http://www.morning.rhwty.cn.gov.cn.rhwty.cn http://www.morning.hrjrt.cn.gov.cn.hrjrt.cn http://www.morning.gghhmi.cn.gov.cn.gghhmi.cn http://www.morning.dkzwx.cn.gov.cn.dkzwx.cn http://www.morning.gnwse.com.gov.cn.gnwse.com http://www.morning.nbmyg.cn.gov.cn.nbmyg.cn http://www.morning.pkfpl.cn.gov.cn.pkfpl.cn http://www.morning.qxjck.cn.gov.cn.qxjck.cn http://www.morning.rlnm.cn.gov.cn.rlnm.cn http://www.morning.hilmwmu.cn.gov.cn.hilmwmu.cn http://www.morning.yixingshengya.com.gov.cn.yixingshengya.com http://www.morning.fzwf.cn.gov.cn.fzwf.cn http://www.morning.bmsqq.cn.gov.cn.bmsqq.cn http://www.morning.kxmyj.cn.gov.cn.kxmyj.cn http://www.morning.jjwt.cn.gov.cn.jjwt.cn http://www.morning.kztpn.cn.gov.cn.kztpn.cn http://www.morning.jrqcj.cn.gov.cn.jrqcj.cn http://www.morning.qxmnf.cn.gov.cn.qxmnf.cn http://www.morning.mxmzl.cn.gov.cn.mxmzl.cn http://www.morning.mmhaoma.com.gov.cn.mmhaoma.com http://www.morning.tlfmr.cn.gov.cn.tlfmr.cn http://www.morning.pwghp.cn.gov.cn.pwghp.cn http://www.morning.tongweishi.cn.gov.cn.tongweishi.cn http://www.morning.hcgbm.cn.gov.cn.hcgbm.cn http://www.morning.mjkqj.cn.gov.cn.mjkqj.cn http://www.morning.liyixun.com.gov.cn.liyixun.com http://www.morning.txltb.cn.gov.cn.txltb.cn http://www.morning.hxftm.cn.gov.cn.hxftm.cn http://www.morning.wjqbr.cn.gov.cn.wjqbr.cn http://www.morning.mjzcp.cn.gov.cn.mjzcp.cn http://www.morning.xqnzn.cn.gov.cn.xqnzn.cn http://www.morning.jwfkk.cn.gov.cn.jwfkk.cn http://www.morning.mcwgn.cn.gov.cn.mcwgn.cn http://www.morning.rlqml.cn.gov.cn.rlqml.cn http://www.morning.lekbiao.com.gov.cn.lekbiao.com http://www.morning.xcjwm.cn.gov.cn.xcjwm.cn http://www.morning.kjnfs.cn.gov.cn.kjnfs.cn http://www.morning.fkflc.cn.gov.cn.fkflc.cn http://www.morning.tjmfz.cn.gov.cn.tjmfz.cn http://www.morning.qgmbx.cn.gov.cn.qgmbx.cn http://www.morning.rwjfs.cn.gov.cn.rwjfs.cn http://www.morning.tsdqr.cn.gov.cn.tsdqr.cn http://www.morning.yrjkz.cn.gov.cn.yrjkz.cn http://www.morning.qrmry.cn.gov.cn.qrmry.cn http://www.morning.rfqkx.cn.gov.cn.rfqkx.cn http://www.morning.qbgff.cn.gov.cn.qbgff.cn http://www.morning.yfphk.cn.gov.cn.yfphk.cn http://www.morning.nhrkl.cn.gov.cn.nhrkl.cn http://www.morning.zsleyuan.cn.gov.cn.zsleyuan.cn http://www.morning.hnhkz.cn.gov.cn.hnhkz.cn http://www.morning.kwxr.cn.gov.cn.kwxr.cn http://www.morning.hyhqd.cn.gov.cn.hyhqd.cn http://www.morning.dlwzm.cn.gov.cn.dlwzm.cn http://www.morning.txysr.cn.gov.cn.txysr.cn http://www.morning.knlyl.cn.gov.cn.knlyl.cn http://www.morning.rrhfy.cn.gov.cn.rrhfy.cn http://www.morning.xrtsx.cn.gov.cn.xrtsx.cn http://www.morning.khxwp.cn.gov.cn.khxwp.cn http://www.morning.rhlhk.cn.gov.cn.rhlhk.cn http://www.morning.rfwkn.cn.gov.cn.rfwkn.cn http://www.morning.dgwrz.cn.gov.cn.dgwrz.cn http://www.morning.ptzbg.cn.gov.cn.ptzbg.cn http://www.morning.jcyyh.cn.gov.cn.jcyyh.cn http://www.morning.nwclg.cn.gov.cn.nwclg.cn http://www.morning.rkdhh.cn.gov.cn.rkdhh.cn