zero copy图解
原文链接:https://www.jianshu.com/p/8c6b056f73ce
1 传统的IO读写
传统的IO读写有两种方式:IO终端和DMA。他们各自的原理如下。
1.1 IO中断原理
整个流程如下:
- 1.用户进程调用read等系统调用向操作系统发出IO请求,请求读取数据到自己的内存缓冲区中。自己进入阻塞状态。
- 2.操作系统收到请求后,进一步将IO请求发送磁盘。
- 3.磁盘驱动器收到内核的IO请求,把数据从磁盘读取到驱动器的缓冲中。此时不占用CPU。当驱动器的缓冲区被读满后,向内核发起中断信号告知自己缓冲区已满。
- 4.内核收到中断,使用CPU时间将磁盘驱动器的缓存中的数据拷贝到内核缓冲区中。
- 5.如果内核缓冲区的数据少于用户申请的读的数据,重复步骤3跟步骤4,直到内核缓冲区的数据足够多为止。
- 6.将数据从内核缓冲区拷贝到用户缓冲区,同时从系统调用中返回。完成任务。
缺点:用户的每次IO请求,都需要CPU多次参与。
1.2 DMA原理
- 1.用户进程调用read等系统调用向操作系统发出IO请求,请求读取数据到自己的内存缓冲区中。自己进入阻塞状态。
- 2.操作系统收到请求后,进一步将IO请求发送DMA。然后让CPU干别的活去。
- 3.DMA进一步将IO请求发送给磁盘。
- 4.磁盘驱动器收到DMA的IO请求,把数据从磁盘读取到驱动器的缓冲中。当驱动器的缓冲区被读满后,向DMA发起中断信号告知自己缓冲区已满。
- 4.DMA收到磁盘驱动器的信号,将磁盘驱动器的缓存中的数据拷贝到内核缓冲区中。此时不占用CPU。这个时候只要内核缓冲区的数据少于用户申请的读的数据,内核就会一直重复步骤3跟步骤4,直到内核缓冲区的数据足够多为止。
- 5.当DMA读取了足够多的数据,就会发送中断信号给CPU。
- 6.CPU手动DMA的信号,知道数据已经准备好,于是将数据从内核拷贝到用户空间,系统调用返回。
跟IO中断模式相比,DMA模式下,DMA就是CPU的一个代理,它负责了一部分的拷贝工作,从而减轻了CPU的负担。
DMA的优点就是:中断少,CPU负担低。
2 文件到网络场景的zero copy技术
2.1 传统IO读写方式的问题
在读取文件数据然后发送到网络这个场景中,传统IO读写方式的过程如下。
由图可知,整个过程总共发生了四次拷贝和四次的用户态和内核态的切换。
用户态和内核态的切换如下。借个网上的图。
2.2 zero copy技术
zero copy技术就是减少不必要的内核缓冲区跟用户缓冲区间的拷贝,从而减少CPU的开销和内核态切换开销,达到性能的提升。
zero copy下,同样的读取文件然后通过网络发送出去,只需要拷贝三次,只发生两次内核态和用户态的切换。
再次盗用一下别人的图。
3 linux下的zero copy技术
linux下的用来实现zero copy的常见接口由如下几个:
- ssize_t sendfile(int out_fd, int in_fd, off_t *offset, size_t count)
- long splice(int fdin, int fdout, size_t len, unsigned int flags);
这两个接口都可以用来在两个文件描述符之间传输数据,实现所谓的zero copy。
splice接口则要求两个文件描述符中至少要有一个是pipe。
3.1 sendfile跟splice的局限性
上面提到的用来实现零拷贝的sendfile和splice接口,仅限于文件跟文件,文件跟sock之间传输数据,但是没法直接在两个socket之间传输数据的。这就是sendfile和splice接口的局限性。
如果要实现socket跟socket之间的数据直接拷贝,需要开辟一个pipe,然后调用两次splice。这样还是带来跟传统IO读写一样的问题。系能其实并没有什么大的提升。
zero copy图解的更多相关文章
- HEC-ResSim原文档
HEC-ResSim Reservoir System Simulation User's Manual Version 3.1 May 201 ...
- Java EE : 三、图解Session(会话)
目录 Java EE : 一.图解Http协议 Java EE : 二.图解 Cookie(小甜饼) Java EE : 三.图解Session(会话) 概述 一.Session由来 二.Sessio ...
- 黄聪:C#Winform程序如何发布并自动升级(图解)
有不少朋友问到C#Winform程序怎么样配置升级,怎么样打包,怎么样发布的,在这里我解释一下打包和发布关于打包的大家可以看我的文章C# winform程序怎么打包成安装项目(图解)其实打包是打包,发 ...
- 【转】C#Winform程序如何发布并自动升级(图解)
有不少朋友问到C#Winform程序怎么样配置升级,怎么样打包,怎么样发布的,在这里我解释一下打包和发布关于打包的大家可以看我的文章C# winform程序怎么打包成安装项目(图解)其实打包是打包,发 ...
- L#脚本语言,直接把DLL当脚本执行(图解说明)
L#是什么:Run DLL as a Script. A Pure C# IL Runner,直接解析执行IL的脚本引擎. 从原理上讲是模拟执行了CLR的工作,从表现上讲就是把DLL作为资源直接加载执 ...
- 图解 Java IO : 二、FilenameFilter源码
Writer :BYSocket(泥沙砖瓦浆木匠) 微 博:BYSocket 豆 瓣:BYSocket FaceBook:BYSocket Twitter ...
- 【转载】图解:二叉搜索树算法(BST)
原文:图解:二叉搜索树算法(BST) 摘要: 原创出处:www.bysocket.com 泥瓦匠BYSocket 希望转载,保留摘要,谢谢!“岁月极美,在于它必然的流逝”“春花 秋月 夏日 冬雪”— ...
- MAT Memory Analyzer Tool 插件安装(图解)
MAT Memory Analyzer Tool 插件安装(图解) 原文地址 @author YHC 前段时间做了一个项目,Exception in thread "main" j ...
- 最简单例子图解JVM内存分配和回收
一.简介 JVM采用分代垃圾回收.在JVM的内存空间中把堆空间分为年老代和年轻代.将大量(据说是90%以上)创建了没多久就会消亡的对象存储在年轻代,而年老代中存放生命周期长久的实例对象.年轻代中又被分 ...
随机推荐
- 【概率论】5-6:正态分布(The Normal Distributions Part III)
title: [概率论]5-6:正态分布(The Normal Distributions Part III) categories: - Mathematic - Probability keywo ...
- 13、SparkContext详解
一.SparkContext原理 1.图解 二.SparkContext源码 1.TaskScheduler创建 ###SparkContext.scala // Create and start t ...
- [golang][译]使用os/exec执行命令
[golang][译]使用os/exec执行命令 https://colobu.com/2017/06/19/advanced-command-execution-in-Go-with-os-exec ...
- Codeforces 1172D. Nauuo and Portals 构造
原文链接www.cnblogs.com/zhouzhendong/p/CF1172D.html 前言 明哥神仙打cf方式真潇洒.45分钟切D后就不打了? 我当场爆肝D想错方向不会做自闭了. 题解 考虑 ...
- [CTF]抓住那只猫(XCTF 4th-WHCTF-2017)
原作者:darkless 题目描述:抓住那只猫 思路: 打开页面,有个输入框输入域名,输入baidu.com进行测试 发现无任何回显,输入127.0.0.1进行测试. 发现已经执行成功,执行的是一个p ...
- ACL终极详解
- 利用Wireshark抓取并分析OpenFlow协议报文
OpenFlow 交换机与控制器交互步骤 1. 利用Mininet仿真平台构建如下图所示的网络拓扑,配置主机h1和h2的IP地址(h1:10.0.0.1,h2:10.0.0.2),测试两台主机之间的网 ...
- 美团Android自动化之旅—适配渠道包
http://tech.meituan.com/mt-apk-adaptation.html 概述 前一篇文章(美团Android自动化之旅-生成渠道包)介绍了Android中几种生成渠道包的方式,基 ...
- V语言 基本使用
新手必看-如何安装配置vlang运行环境(linux,macOS篇) 前置条件 发稿截止前只有Linux 或者 macOS系统能编译通过. 你需要安装clang或gcc 如果是macOS上需运行xco ...
- C图形化第一步
之前的贪吃蛇都是在cmd下实现,每次都要调用cls刷新屏幕,简直是闪瞎了我的狗眼. 度娘得知有一种方法可以避免闪烁,即:双缓冲.原理是先在内存中作图,然后将做好的图复制到前台,同时禁止背景刷新. 主要 ...