什么是TCP粘包,tcp粘包

什么是TCP粘包,tcp粘包

如何实现一个分布式RPC框架?

1.定义:明确下RPC是什么?PRC全称是Remote Procedure Call,是进程间的一种通信方式。2.解决的问题进程间调用就像本地调用函数一样简单,而业务层不需要去关心通信的细。3.组成在Nelson的论文Implementing Remote Procedurr Calls有论述,见图1User 调用方User-Stub 消息拼装,编解码RPCRuntime 发送,接受消息Service-Stub 消息拼装,编解码Server 服务方4.核心实现从图中可以看出我们需要实现Stub和RPCRuntime的功能。

Stub:主要功能是消息格式怎么定义和编解码。消息格式:一般需要设计消息头和消息体,当然越简洁越好,提高传输效率编解码:二进制最高效,可以使用Protocol Buffers,Thrift。当然也可以使用可读性比较好的JSON,XML。RPCRuntime主要负责通信,这里涉及到选择什么IO模型,BIO,NIO还是AIO,可以使用netty来实现NIO功能。

5.开源实现了解开源实现,更能促进自研的成熟稳定。当然看需求是否需要自研,一般开源就可以满足需求了。比较好的开源实现有Dubbo,brpc,grpc,Thrift,Hessian等6.小结虽然RPC说起来只是进程间的通信,但是RPC服务怎么注册,发现,路由这些都还是需要考虑的。再者毕竟是网络传输,就有可能出现延迟,丢包的情况,容错性也需要多考虑考虑。

这里再把RPC调用描述的全一点,见图2。图中的clinet,sever只和agent交互,agent就包含了Stub和RPCRuntime的功能,一般这里的agent实现为一个jar包,和应用程序部署在一起。现在Service Mesh也越来越成熟了,Service Mesh把agent独立为一个进程部署(必须和业务同一机器),这样降低了耦合性,同时业务和平台独立,开发迭代速度也更快。

怎么解决TCP网络传输「粘包」问题?

TCP粘包是指发送方发送的多个数据包到接收方后粘连在一起,导致数据包不能完整的提现发送的数据。 TCP协议TCP是一个面向连接的传输层协议,不属于ISO制定的协议集。TCP协议在商业界和工业界的成功应用,使它成为事实上的网络标准,广泛应用于各种网络主机间的通信。TCP目标是为用户提供可靠的端到端连接,保证信息有序无误的传输。

TCP为确保可靠性采用了数据编号、校验和计算、数据确认等一系列措施。TCP对传送的每个数据字节都进行编号,并请求接收方回传确认信息(ACK)。发送方如果在规定的时间内没有收到数据确认,就重传该数据。 数据编号使接收方能够处理数据的失序和重复问题。数据误码问题通过在每个传输的数据段中增加校验和予以解决,接收方在接收到数据后检查校验和,若校验和有误,则丢弃该有误码的数据段,并要求发送方重传。

流量控制也是保证可靠性的一个重要措施,若无流控,可能会因接收缓冲区溢出而丢失大量数据,导致许多重传,造成网络拥塞恶性循环。TCP采用可变窗口进行流量控制,由接收方控制发送方发送的数据量。这些可靠性保障措施为用户提供了高可靠性的网络传输服务,但也影响了传输效率。在实际工程应用中,只有关键数据的传输才采用TCP,而普通数据的传输一般采用高效率的UDP。

UDP不会出现粘包问题。UDP支持的是一对多的模式,不会使用块的合并优化算法,所以接收端的skbuff(套接字缓冲区)采用了链式结构来记录每一个到达的UDP包,在每个UDP包中就有了消息头(包含消息来源地址,端口等信息),接收端很容易就能进行区分处理了。粘包出现原因出现粘包现象的原因有很多方面,它既可能由发送方造成的,也可能是由接收方造成的。

发送方原因TCP需要尽可能高效和可靠,默认采用Nagle算法,发送方往往要收集到足够多的数据后合并相连的小数据包,才发送一包数据,这样接收方就收到了粘包数据。但接收方并不知晓发送方合并数据包,并数据包的合并在TCP协议中是没有分界线的,就会导致接收方不能还原其本来的数据包。接收方原因TCP是基于“流”的。

网络传输数据的速度可能会快过接收方处理数据的速度,这时候就会导致,接收方在读取缓冲区时,缓冲区存在多个数据包。在TCP协议中接收方是一次读取缓冲区中的所有内容,就不能反映原本的数据信息。粘包情况有两种:一种是粘在一起的包都是完整的数据包; 一种是粘在一起的包有不完整的包; 不是所有的粘包现象都需要处理如果传输的数据为不带结构的连续流数据(如文件传输),就不必把粘连的包分开(简称分包)。

但实际工程应用中一般为带结构的数据,这时就需要做分包处理。在处理定长结构数据的粘包问题时,分包算法比较简单;在处理不定长结构数据的粘包问题时,分包算法就比较复杂。特别是粘在一起的包有不完整的包的粘包情况,一包数据内容被分在了两个连续的接收包中,处理起来难度较大。实际工程应用中应尽量避免出现粘包现象。为了避免粘包现象,可采取以下几种措施:(1)发送方引起的粘包可通过编程设置来避免。

如:PUSH标志是TCP提供了强制数据立即传送的操作指令,TCP软件收到该操作指令后,就立即将本段数据发送出去,而不必等待发送缓冲区满。缺点:虽然可以避免发送方引起的粘包,但关闭了Negle优化算法,降低了网络发送效率,影响应用程序的性能,一般不建议使用。(2)接收方引起的粘包,可通过优化程序设计、精简接收进程工作量、提高接收进程优先级等措施来及时接收数据,尽量避免出现粘包现象。

缺点:只能减少出现粘包的可能性,但并不能完全避免粘包,当发送频率较高或某个时间段数据包到达接收方较快,接收方还是有可能来不及接收,导致粘包。(3)由接收方控制,将一包数据按结构字段,人为控制分多次接收,然后合并,通过这种手段来避免粘包。缺点:应用程序的效率较低,对实时应用的场合不适合。一种比较周全的对策是:接收方创建一预处理线程,对接收到的数据包进行预处理,将粘连的包分开。

微服务调用为什么用RPC框架,http不更简单吗?

简单点,HTTP是协议,RPC是概念!实现RPC可以基于HTTP协议(Feign),TCP协议(Netty),RMI协议(Soap),WebService(XML—RPC)框架。传输过程中,也因为序列化方式的不同,又有一些框架和协议,比如Dubbo中的Dubbo协议,gRpc—Protobuf序列化协议等等。

其实,都是基于远程调用的概念,何为远程调用?重点是,RPC就是远程调用,远程调用就是客户端把调用的接口,参数,参数类型,方法,返回值,返回值类型等(这些称为方法签名),通过如上的协议,发送给服务端,告知服务端需要调用的接口方法,这个过程就是RPC的实现过程!HTTP和RPC是不同层面的两个东西!性能方面,HTTP本身是基于TCP协议的,属于应用层协议,所以HTTP协议本身在实现过程中就会占用大量的资源(内存,带宽等),性能上肯定没有通过TCP直接实现RPC协议快,不管HTTP如何优化肯定的是不如TCP的!而TCP则是依靠字节码,现在普遍采用的是将客户端调用的接口信息,序列化的方式发送给服务端,序列化框架又包含很多(Hession,Protobuf,Kryo等等,序列化性能最高的是Kryo,序列化后字节码最小的是Protobuf),序列化后的字节码越小,占用带宽越少,序列化时间越短,线程IO等待时间就会越小。

为什么有很多出名开源的C/C 方面的高性能网络库,比如libevent,boost-asio,有些企业还要自己写?

到底是自己造轮子,还是直接使用开源库,我想很大程度上取决去部门老大的个人喜好。曾几何时,C 开发者都热衷于重复造轮子,那么为什么还有的企业要自己写呢?下面谈谈自己的看法:1)项目初期并不知道有这个库的存在,后面也懒得再引入。2)很多第三方库依赖的其他第三方库都比较多,为了引入A库,不得不引入B、C、D库,这无疑增加了部门成员的学习成本。

3)第三方开源库一般更新较频繁,明知有Bug了,你们要不要更新呢?基础库的更新无疑要花费更多的开发时间、测试时间。4)让项目整体可控性更强,一旦引入的开源库出现问题,而项目组有对它不熟悉,那么将是灾难性的。5)已有开源库过于复杂,学习成本高,组内成员水平参差不齐。最后附一张自己前段时间研读的书籍。本文为作者“一个程序员的奋斗史”悟空问答原创文章,未经允许转载、抄袭必究!。

  • 姓名:
  • 专业:
  • 层次:
  • 电话:
  • 微信:
  • 备注:
文章标题:什么是TCP粘包,tcp粘包
本文地址:http://www.55jiaoyu.com/show-732476.html
本文由合作方发布,不代表展全思梦立场,转载联系作者并注明出处:展全思梦

热门文档

推荐文档