2019独角兽企业重金招聘Python工程师标准>>>

Zero-copy概念

wiki上关于zero-copy的概念定义

"Zero-copy" describes computer operations in which the CPU does not perform the task of copying data from one memory area to another. This is frequently used to save CPU cycles and memory bandwidth when transmitting a file over a network.

从WIKI的定义中,我们看到“零拷贝”是指计算机操作的过程中,CPU不需要为数据在内存之间的拷贝消耗资源。而它通常是指计算机在网络上发送文件时,不需要将文件内容拷贝到用户空间(User Space)而直接在内核空间(Kernel Space)中传输到网络的方式。

Non-Zero Copy方式: 

Zero Copy方式: 

从上图中可以清楚的看到,Zero Copy的模式中,避免了数据在用户空间和内存空间之间的拷贝,从而提高了系统的整体性能。

程序访问方式

  1. The Linux kernel supports zero-copy through various system calls, such as sys/socket.h's sendfile, sendfile64, and splice. Some of them are specified in POSIX and thus also present in the BSD kernels or IBM AIX, some are unique to the Linux kernel API.
  2. Microsoft Windows supports zero-copy through the TransmitFile API.
  3. Java input streams can support zero-copy through the java.nio.channels.FileChannel's transferTo() method if the underlying operating system also supports zero copy

Netty支持的zero-copy有2种:

1 包装FileChannel.tranferTo方法实现zero-copy

Netty中通过在FileRegion中包装了NIO的FileChannel.transferTo()方法实现了零拷贝。

FileRegion是一个接口,默认的实现类是:DefaultFileRegion

2 复合缓冲类型中内置的透明的零拷贝实现。

Transparent Zero Copy 透明的零拷贝

举一个网络应用到极致的表现,你需要减少内存拷贝操作次数。你可能有一组缓冲区可以被组合以形成一个完整的消息。网络提供了一种复合缓冲,允许你从现有的任意数的缓冲区创建一个新的缓冲区而无需内存拷贝。例如,一个信息可以由两部分组成;header 和 body。在一个模块化的应用,当消息发送出去时,这两部分可以由不同的模块生产和装配。

+--------+----------+| header |   body   |+--------+----------+

如果你使用的是 ByteBuffer ,你必须要创建一个新的大缓存区用来拷贝这两部分到这个新缓存区中。或者,你可以在 NiO做一个收集写操作,但限制你将复合缓冲类型作为 ByteBuffer 的数组而不是一个单一的缓冲区,打破了抽象,并且引入了复杂的状态管理。此外,如果你不从 NIO channel 读或写,它是没有用的。

// 复合类型与组件类型不兼容。
ByteBuffer[] message = new ByteBuffer[] { header, body };

通过对比, ByteBuf 不会有警告,因为它是完全可扩展并有一个内置的复合缓冲区。

// 复合类型与组件类型是兼容的。
ByteBuf message = Unpooled.wrappedBuffer(header, body);// 因此,你甚至可以通过混合复合类型与普通缓冲区来创建一个复合类型。
ByteBuf messageWithFooter = Unpooled.wrappedBuffer(message, footer);// 由于复合类型仍是 ByteBuf,访问其内容很容易,
//并且访问方法的行为就像是访问一个单独的缓冲区,
//即使你想访问的区域是跨多个组件。
//这里的无符号整数读取位于 body 和 footer
messageWithFooter.getUnsignedInt(messageWithFooter.readableBytes() - footer.readableBytes() - 1);

Automatic Capacity Extension 自动容量扩展

许多协议定义可变长度的消息,这意味着没有办法确定消息的长度,直到你构建的消息。或者,在计算长度的精确值时,带来了困难和不便。这就像当你建立一个字符串。你经常估计得到的字符串的长度,让 StringBuffer 扩大了其本身的需求。

// 一种新的动态缓冲区被创建。在内部,实际缓冲区是被“懒”创建,从而避免潜在的浪费内存空间。
ByteBuf b = Unpooled.buffer(4);// 当第一个执行写尝试,内部指定初始容量 4 的缓冲区被创建
b.writeByte('1');b.writeByte('2');
b.writeByte('3');
b.writeByte('4');// 当写入的字节数超过初始容量 4 时,
//内部缓冲区自动分配具有较大的容量
b.writeByte('5');

Better Performance 更好的性能

最频繁使用的缓冲区 ByteBuf 的实现是一个非常薄的字节数组包装器(比如,一个字节)。与 ByteBuffer 不同,它没有复杂的边界和索引检查补偿,因此对于 JVM 优化缓冲区的访问更加简单。更多复杂的缓冲区实现是用于拆分或者组合缓存,并且比 ByteBuffer 拥有更好的性能。

ByteBuf 具有丰富的操作集,可以快速的实现协议的优化。例如,ByteBuf 提供各种操作用于访问无符号值和字符串,以及在缓冲区搜索一定的字节序列。你也可以扩展或包装现有的缓冲类型用来提供方便的访问。自定义缓冲仍然实现自 ByteBuf 接口,而不是引入一个不兼容的类型

与ByteBuffer相比,不再需要调用的flip()方法,并且正常情况下效率更高、响应更好。

转载于:https://my.oschina.net/cloudcoder/blog/656778

理解Netty中的Zero-copy相关推荐

  1. 理解Netty中的零拷贝(Zero-Copy)机制

    理解Netty中的零拷贝(Zero-Copy)机制 发表于2年前(2014-01-13 15:11)   阅读(10209) | 评论(12) 164人收藏此文章,我要收藏 赞29 12月12日北京O ...

  2. Netty中ByteBuf的copy、duplicate、slice方法对比

    Jdk注释翻译 /** *返回ByteBuf的可读字节的拷贝.修改返回的ByteBuf内容与当前ByteBuf完全不会相互影响. *此方法不会修改当前ByteBuf的readerIndex或write ...

  3. 简单深入理解高性能网络编程(Netty)中的Reactor模型(图文+代码)

    文章目录 定义 传统网络交互方式 Reactor 模型组成 Netty中`Reactor`模型的实现 Reactor 单线程模式 非主从Reactor模式(单Reactor多线程模型) 主从React ...

  4. Netty中的那些坑

    Netty中的那些坑(上篇) 最近开发了一个纯异步的redis客户端,算是比较深入的使用了一把netty.在使用过程中一边优化,一边解决各种坑.儿这些坑大部分基本上是Netty4对Netty3的改进部 ...

  5. netty系列之:netty中的ByteBuf详解

    文章目录 简介 ByteBuf详解 创建一个Buff 随机访问Buff 序列读写 搜索 其他衍生buffer方法 和现有JDK类型的转换 总结 简介 netty中用于进行信息承载和交流的类叫做Byte ...

  6. TCP的粘包和拆包及Netty中的解决方案

    1.基本介绍 TCP 是面向连接的,面向流的,提供高可靠性服务.收发两端(客户端和服务器端)都要有一一成对的 socket, 因此,发送端为了将多个发给接收端的包,更有效的发给对方,使用了优化方法(N ...

  7. 深入理解PHP中赋值与引用

    原文:深入理解PHP中赋值与引用 先看下面的问题: <?php $a = 10;//将常量值赋给变量,会为a分配内存空间$b = $a;//变量赋值给变量,是不是copy了一份副本,b也分配了内 ...

  8. 深入理解Netty高性能网络框架

    大家好,今天我们来聊聊Netty的那些事儿,我们都知道Netty是一个高性能异步事件驱动的网络框架. 它的设计异常优雅简洁,扩展性高,稳定性强.拥有非常详细完整的用户文档. 同时内置了很多非常有用的模 ...

  9. netty系列之:netty中的Channel详解

    文章目录 简介 Channel详解 异步IO和ChannelFuture Channel的层级结构 释放资源 事件处理 总结 简介 Channel是连接ByteBuf和Event的桥梁,netty中的 ...

  10. 一文理解Netty模型架构

    转载自  一文理解Netty模型架构 本文基于Netty4.1展开介绍相关理论模型,使用场景,基本组件.整体架构,知其然且知其所以然,希望给读者提供学习实践参考. 1 Netty简介 Netty是 一 ...

最新文章

  1. 一次HP 阵列卡排障
  2. 介绍一个打怪升级练习 Python 的网站,寓教于乐~
  3. 各计算机语言之父,四大编程语言之父
  4. [hdu4333]Revolving Digits
  5. java readline 实现_基于自定义BufferedReader中的read和readLine方法
  6. 仔细看看_仔细看看,您会发现需要改进的地方
  7. 乔治敦大学计算机专业排名,2020USNEWS数据科学与分析专业综合排名(上)
  8. Android调用binder实现权限提升-android学习之旅(81)
  9. grunt打包压缩css、js方法
  10. java实现PDF转word,使用jacob插件
  11. latex中png、pdf和eps格式的图片文件转换
  12. linux 中文ssid 显示乱码,把中文SSID变成乱码!一切正常了?_网络设备-中关村在线...
  13. vray渲染不了 全白_3D VR渲染,怎么做到墙面白的很干净
  14. 手机连接电脑热点后,无法上网
  15. 用html做一个漂亮的网站,个人网页,css
  16. 软件外包交易平台排行
  17. Python之组合数据类型(列表、元组、集合、字典)
  18. SpringBoot整合Apollo配置中心快速使用
  19. Codeforces Round #545 (div 1.)
  20. Mock工具介绍,为什么使用Mock?

热门文章

  1. php 多个files 数量,php – 具有多个字段时$_FILES数组的奇怪格式
  2. tcp网络示例服务器端以及代码,演示
  3. 帆软高级函数应用之数(学)值函数
  4. linux光盘挂载加载过程,如何在Linux系统下挂载光盘
  5. matlab替换矩阵中元素的值,怎么修改矩阵中的某些元素 或者简单点说保留矩阵中的元素...
  6. java移位运算符_Java中的移位运算符(“”、“”、“”)
  7. 三菱fx编程手册_三菱FX串口PLC远程编程调试流程
  8. IDEA 不识别的MAVEN 项目应如何处理
  9. vm.$nextTick( [callback] )用法
  10. Spring的Bean有哪些作用域?