程序员你了解零拷贝吗?

作者: 享学课堂 | 来源:发表于2019-07-17 18:22 被阅读51次

享学课堂特邀作者:老顾

转载请声明出处!

前言

老顾在接触大数据相关技术栈时,发现大数据相关的技术也是非常复杂,技术迭代也是很快的(我们搞技术的就是这么悲催啊,一直处于学习中.....)。很多更新的技术在宣传的时候,都会提到速度、性能这个指标,什么提升了10倍,100倍啊。其中有一个技术点叫做zero-copy,也叫做零拷贝,是很多中间件都用到的技术,今天老顾就来给大家讲讲什么是零拷贝

传统读操作

JAVA用传统方式进行读操作时整体流程如上图,具体如下:

1、应用程序发起读数据操作,JVM会发起read()系统调用。

2、这时操作系统OS会进行一次上下文切换(把用户空间切换到内核空间)

3、通过磁盘控制器把数据copy到内核缓冲区中,这里的就发生了一次DMACopy

4、然后内核将数据copy到用户空间的应用缓冲区中,发生了一次CPU Copy

5、read调用返回后,会再进行一次上下文切换(把内核空间切换到用户空间)

我们看一下一个读操作,发了2次上下文切换,和2次数据copy,一次是DMA Copy,一次是CPU Copy。

注意一点的是 内核从磁盘上面读取数据 是 不消耗CPU时间的,是通过磁盘控制器完成;称之为DMA Copy。

传统写操作

上图是JAVA传统的写操作,具体流程:

1、应用发起写操作,OS进行一次上下文切换(从用户空间切换为内核空间)

2、并且把数据copy到内核缓冲区Socket Buffer,做了一次CPU Copy

3、内核空间再把数据copy到磁盘或其他存储(网卡,进行网络传输),进行了DMA Copy

4、写入结束后返回,又从内核空间切换到用户空间

传统IO

我们可以看出传统的IO读写操作,总共进行了4次上下文切换,4次Copy动作。我们可以看到数据在内核空间和应用空间之间来回复制,其实他们什么都没有做,就是复制而已,这个机制太浪费时间了,而且是浪费的CPU的时间

那我们能不能让数据不要来回复制呢?零拷贝这个技术就是来解决这个问题。关于零拷贝提供了两种解决方式:mmap+write方式、sendfile方式

虚拟内存

所有现代操作系统都使用虚拟内存,使用虚拟地址取代物理地址,这样做的好处就是:

1、多个虚拟内存可以指向同一个物理地址

2、虚拟内存空间可以远远大于物理内存空间

我们利用第一条特性可以优化一下上面的设计思路,就是把内核空间和用户空间的虚拟地址映射到同一个物理地址,这样就不需要来回复制了,看图:

mmap+write方式

使用mmap+write方式替换原来的传统IO方式,就是利用了虚拟内存的特性,看图

整体流程的核心区别就是,把数据读取到内核缓冲区后,应用程序进行写入操作时,直接是把内核的Read Buffer的数据复制到 Socket Buffer 以便进行写入,这次内核之间的复制也是需要CPU参与的

注意:最后把Socket Buffer数据拷贝到很多地方,统称protocol engine(协议引擎)

这个流程就少了一个CPU Copy,提升了IO的速度。不过发现上下文的切换还是4次,没有减少,因为还是要应用程序发起write操作。那能不能减少上下文切换呢?

sendfile方式

这种方式可以替换上面的mmap+write方式,如:

mmap();
write();

替换为

sendfile();

这样就减少了一次上下文切换,因为少了一个应用程序发起write操作,直接发起sendfile操作。
到这里就只有3次Copy,其中只有1次CPU Copy;3次上下文切换。那能不能把CPU Copy减少到没有呢?

gather

Linux2.4内核进行了优化,提供了gather操作,这个操作可以把最后一次CPU Copy去除,什么原理呢?就是在内核空间Read Buffer和Socket Buffer不做数据复制,而是将Read Buffer的内存地址、偏移量记录到相应的Socket Buffer中,这样就不需要复制(其实本质就是和虚拟内存的解决方法思路一样,就是内存地址的记录),如图:

JAVA零拷贝

java nio实现零拷贝,JAVA提供了一下方法类:

1、MappedByteBuffer
2、DirectByteBuffer
3、FileChannel.transferTo

具体如何使用,小伙伴们上网自行查阅。

总结

零拷贝技术在很多中间件中,都有利用;如:Kafka,Spark、RocketMQ等,这个在网络传输数据时,能够提升速度,提升系统性能、吞吐量。小伙伴们不一定会编写,可以先了解基本原理就行。很多好的中间件产品都需要了解一些计算机原理方面的知识,才会更深入的理解。

好了,老顾今天就介绍到这里,谢谢!!!

持续关注我,分享更多干货。

相关文章

  • 程序员你了解零拷贝吗?

    享学课堂特邀作者:老顾转载请声明出处! 前言 老顾在接触大数据相关技术栈时,发现大数据相关的技术也是非常复杂,技术...

  • 转载:支撑百万并发的 “零拷贝” 技术,你了解吗?

    转载: 支撑百万并发的 “零拷贝” 技术,你了解吗? 零拷贝(Zero-copy)技术指在计算机执行操作时,CPU...

  • 常见的两种零拷贝技术

    什么是零拷贝? 在讲解零拷贝之前,我们先来了解一下为什么要引入零拷贝,以及零拷贝解决了什么问题。 内核态与用户态 ...

  • Netty之二NIO与零拷贝

    个人专题目录 1. Nio与零拷贝 零拷贝是服务器网络编程的关键,任何性能优化都离不开。在 Java 程序员的世界...

  • linux的零拷贝

    零拷贝主要是为了解决用户态与内核态之间数据的拷贝,减少cpu的负担。下面的图描述了常见的数据处理过程。 零拷贝的实...

  • 零拷贝

    前言 零拷贝这三个字,一直是服务器网络编程的关键字,任何性能优化都离不开。在 Java 程序员的世界,常用的零拷贝...

  • Netty分享之ByteBuf零拷贝

    gris 转载请注明原创出处,谢谢! 我们或多或少了解过一些零拷贝的概念,而零拷贝也正是netty能够实现高性能的...

  • ios 关于浅拷贝(copy)和深拷贝(mutableCopy)

    面试官: 1.浅拷贝和深拷贝你了解吗?详细说说?2.修改原对象的值,副本对象会变吗?3.copy 一个可变的数组,...

  • 共享空间与零拷贝,mmap与sendFile的区别

    零拷贝这三个字,一直是服务器网络编程的关键字,任何性能优化都离不开。在 Java 程序员的世界,常用的零拷贝有 m...

  • rocketMQ零拷贝、kafka零拷贝、netty零拷贝分析

    1.RocketMQ零拷贝?Netty零拷贝?kafka零拷贝?到底是个什么玩意儿!什么page cache?什么...

网友评论

    本文标题:程序员你了解零拷贝吗?

    本文链接:https://www.haomeiwen.com/subject/codokctx.html