RPC框架如何选择网络IO模型

2,257 阅读3分钟

RPC是解决进程间通信的一种方式.一次RPC调用,本质就是服务消费者与服务提供者间的一次网络信息交换的过程.

网络通信是整个RPC调用流程的基础.

常见的网络IO模型

两台PC机之间的网络通信,世纪上就是两台PC机对网络IO的操作.

常见的网络IO模型分为四种:同步阻塞(BIO)\同步非阻塞(NIO)\IO多路复用和异步非阻塞(AIO)

最常用的是同步阻塞IO和IO多路复用

阻塞IO(blocking IO):

等待数据和拷贝数据

IO多路复用(IO multiplexing):

为什么说阻塞IO和IO多路复用最为常用?

网络IO应用都需要系统内核的支持以及编程语言的支持,阻塞IO和IO多路复用系统内核与编程语言支持最为完善.

RPC框架在网络通信上倾向选择哪种网络IO模型?

IO多路复用更是和高并发场景,可以用较少的进程(线程)处理较多的socket的IO请求,但是难度高

阻塞IO每处理一个socket的IO请求都会阻塞进程(线程),但难度低.

RPC调用是一个高并发场景,考虑内核\编程语言的支持以及IO模型本身特点,我们选择IO多路复用的方式

零拷贝(Zero-copy)

等待数据: 系统内核在等待网卡接收到数据后,把数据写到内核中

拷贝数据: 系统内核在获取到数据后,将数据拷贝到用户进程的空间中

应用进程的一次完整的读写操作,都需要在用户空间与内核空间中来回拷贝,并且每一次拷 贝,都需要 CPU 进行一次上下文切换(由用户进程切换到系统内核,或由系统内核切换到 : 用户进程)


取消用户空间与内核空间之间的数据拷贝操作,应用进程每一次的读写 操作,可以通过一种方式,直接将数据写入内核或从内核中读取数据,再通过 DMA 将内 核中的数据拷贝到网卡,或将网卡中的数据 copy 到内核.

实现:用户空间与内核空间都将数据写到同一个地方(虚拟内存)

零拷贝有两种解决方式,分别是 mmap+write 方式和 sendfile 方式


操作系统层面零拷贝,主要目标是避免用户空间与内核空间之间的数据拷贝操作,可以提升CPU的利用率.

Netty中的零拷贝

用户空间对数据的零拷贝,处理 TCP 传输中的拆包粘包问题有着重要的意义

Netty 的 ByteBuffer 可以采用 Direct Buffers,使用堆外直接内存进行 Socketd 的读写 操作,可以解决用户空间与内核空间间的数据拷贝.