相比传统 Java 读取文件通过网卡发送过程中,省略了内核缓冲区 copy 到用户缓冲区的过程。
直接把数据在内核空间进行拷贝,减少了上下文切换(内核空间切换到用户空间)。
由内核缓冲区将数据拷贝到 Socket 缓冲区,然后通过网卡发送数据。
Transclude of zero_copy_sendfile.excalidraw
具体执行过程:
改进
由内核缓冲区直接拷贝到网卡发送,少了一次内核缓冲区 copy 到 Socket 缓冲区的过程。Socket 缓冲区只需要接受文件描述符数据和数据长度
即可。
Transclude of zero_copy_sendfile_upgrade.excalidraw
具体执行过程:
缺点
sendfile 的实现中,文件的数据都没有拷贝到用户空间
,因此用户程序无法对读取的文件数据进行修改。
Java 中对应的实现
Java 中使用了 FileChannel.transferTo
的方法实现 sendFile。