文件io - 操纵文件空间 - fallocate

说明

  • 用户层程序以普通方式(缓存io)写文件时,数据实际上是写入系统缓存(内存)中,一段时间后系统进程再将缓存脏页写入磁盘,如果缓存内存页没有对应的磁盘空间(磁盘块),系统会触发中断,向存储器申请分配一块,再将数据写入存储器中。
  • 由上可知:
  1. 普通方式下文件磁盘空间的分配和释放是由操作系统管理的,用户是无法感知和干涉的。
  2. 由于无法预知文件的最终size(即所需磁盘块个数),操作系统申请磁盘只能按需分配,多次分配。
  • 因此普通方式写文件会有些局限性以及性能影响,为了处理这些问题,linux设计了fallocate接口来操纵文件空间(主要是提供接口给用户操作磁盘空间的申请和释放)。

使用场景

  • 录像文件预分配功能:创建固定大小的预分配文件,文件按照设置提前分配好磁盘空间,以加快录像存储的速度。

加速原理

  1. 减少查找可用块的时间损耗
  • 按需分配磁盘块时,每次申请一块磁盘块,申请时存储器需要查找可用磁盘块,需要耗费一定的时长,sd卡或固态硬盘的查找时间相对于机械硬盘会更少点,磁盘碎片较多时查找时长也会变长,而预分配将多次申请合并成一次,查找时间也会相应减少,特别是格式化存储器后立即预分配,申请磁盘块会快很多。
  1. 减少磁盘碎片化
  • 按需分配磁盘块时,文件的创建删除会导致磁盘块的申请释放,可能会导致磁盘块的碎片化,连续的磁盘块较少,可用块的查找耗时变得越来越长,特别是需要申请大块磁盘空间时,这也是存储器越用越慢的元凶。
  1. 减少读写分配时的块跳转时长
  • 预分配的磁盘块会尽可能的连续(因为预分配算法,当连续的磁盘块都是空闲的,就不用去其它地方找可用块),对块进行读写以及查找需要跳转到别的块时,速度更快,因为块是连续,对于sd卡和固态硬盘影响不明显,但是对于机械硬盘会更明显(机械硬盘磁头需要移动,耗时更长)。

优化措施

  1. 存储器格式化后将所有磁盘空间都预分配好
  • 如果使用一段时间后再进行磁盘预分配,磁盘或多或少会有些碎片,预分配申请磁盘空间可能会不连续,性能达不到最优。

fallocate

  • 以下描述都来源于man描述,描述不清晰的地方可以查看原文。
  • manipulate file space - 操纵文件空间

定义

#define _GNU_SOURCE             /* See feature_test_macros(7) */
#include <fcntl.h>

int fallocate(int fd, int mode, off_t offset, off_t len);

描述

  • fallocate是不可移植的linux平台磁盘空间预分配接口,用户可以通过该接口的参数偏移(offset)以及空间长度(len)直接操作参数(fd)文件描述符打开的文件的磁盘空间,该接口拥有以下行为(模式控制):
  • 磁盘块由文件系统管理,所以该接口需要文件系统的支持。
  1. 分配磁盘空间(Allocating disk space)
  • fallocate的默认行为(此时mode为0)就是通过offset和len扩张磁盘空间,stat看到的文件size将会变大,扩张的磁盘空间中的数据将会被置空,如果执行成功,向扩张的空间中写数据不会出现磁盘空间不足的错误。
  • 如果在模式中指定了FALLOC_FL_KEEP_SIZE标志,则行为和默认模式类似,不同的是即使offset+len更大,stat看到的文件大小也不会变大,而是实际的数据size,这种方式预先分配文件末尾以外的零块对于优化追加写的工作负载非常有用。
  • 如果在模式中指定了“FALLOC_FL_UNSHARE”标志,则共享文件数据块将成为文件的专用数据块,以确保后续写入不会发生由于缺少空间而失败,通常,这将通过对文件中的所有共享数据执行写时复制操作来完成。
  1. 释放文件空间(Deallocating file space)
  • 如果在模式中指定FALLOC_FL_PUNCH_HOLE标志(自Linux 2.6.38起支持,并且FALLOC_FL_PUNCH_HOLE标志必须与FALLOC_FL_KEEP_SIZE进行OR运算)将释放从偏移量开始len长度的字节范围中的空间块(即创建一个孔),释放的磁盘块将从文件中删除,执行成功后,读取该范围内的数据将返回零,并且stat看到的文件大小不会发生变化。
  • 不是所有的文件系统支持FALLOC_FL_PUNCH_HOLE该标志,不支持将会返回一个错误,以下文件系统支持的linux版本
XFS (since Linux 2.6.38)
ext4 (since Linux 3.0)
Btrfs (since Linux 3.7)
tmpfs(5) (since Linux 3.5)
  1. 折叠文件空间(Collapsing file space)
  • 如果在模式中指定FALLOC_FL_COLLAPSE_RANGE标志(自Linux 3.15起提供)将释放该范围内的磁盘空间,并且不会留下空洞,后面的数据将会附加到offset偏移处,并且文件size将会减少len字节。
  • 文件系统为了确保实现的高效性,可能会对该操作的范围进行判断,即释放的磁盘空间必须是文件系统磁盘块大小的倍数,磁盘块大小由文件系统类型和配置决定,如果不是磁盘块大小的倍数,fallocate将会返回参数错误(EINVAL)
  • 如果指定了FALLOC_FL_COLLAPSE_RANGE模式则不能或上其它模式。
  • 如果offset+len指定的磁盘空间是文件末尾,该操作将会报错,你可以使用ftruncate来实现该操作。
  • 在Linux 3.15上,ext4(仅适用于基于扩展的文件)和XFS支持FALLOC_FL_COLLAPSE_RANGE 模式。
  1. 清空文件空间(Zeroing file space)
  • 如果在模式中指定FALLOC_FL_ZERO_RANGE标志(从Linux 3.15开始提供)会将offset到offset+len字节范围中的空间清零,在该范围内,如果有文件空洞将会预先分配块,从该范围进行后续读取将返回零。
  • 使用该模式性能最好的情况是清空文件还未使用的磁盘空间,这样就不需要真正的清空磁盘空间,只需要更改文件系统该文件的meta数据即可。
  • 如果在模式中另外指定了FALLOC_FL_KEEP_SIZE标志,则调用的行为类似,即使是offset+len大于当前文件大小,文件大小也不会更改,该行为与单独使用FALLOC_FL_KEEP_SIZE预分配空间时相同。
  • 不是所有文件系统都支持该模式,不支持将会报错,以下文件系统支持的条件限制如下:
XFS (since Linux 3.15)
ext4, for extent-based files (since Linux 3.15)
SMB3 (since Linux 3.17)
  1. 增加文件空间(Increasing file space)
  • 如果在模式中指定FALLOC_FL_INSERT_RANGE标志(自Linux 4.1起提供),将会在文件offset到offset+len范围内插入一个磁盘空洞,并且不需要写入任何数据,该范围内的文件内容将会向上偏移,文件大小也会增加该范围大小。
  • 该模式具有和FALLOC_FL_COLLAPSE_RANGE模式相同的限制,如果不满足该限制将会执行失败并且返回参数错误(EINVAL),该模式也不适用于offset等于或者大于文件size的情况(这种情况需要使用ftruncate)。
  • 该模式只能单独使用,不能OR上其它模式,并且该模式需要文件系统支持,当前支持该模式的文件系统有XFS (since Linux 4.1) 和 ext4 (since Linux 4.2)。

注意

  • 容易造成混淆和困惑的函数:ftruncate
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
Mac Rust io-uring是一种在Mac操作系统上使用Rust语言进行开发的io-uring库。 io-uring是Linux内核中的一个新特性,它为应用程序提供了一种高性能、高效率的异步I/O操作方式。它通过使用事件驱动和无锁技术,实现了在高并发环境下进行文件操作的优化。io-uring提供了更低的系统开销和更高的吞吐量,特别适用于需要大量I/O操作的应用程序。 虽然io-uring最初是为Linux内核设计的,但由于其高性能的特性,一些开发者试图将其移植到其他操作系统上。其中,Mac Rust io-uring就是一个在Mac操作系统上使用Rust语言实现io-uring的库。 使用Mac Rust io-uring,开发者可以在Mac环境下利用io-uring的特性来提高文件操作的性能。这对于需要进行大量I/O操作的应用程序来说,是一个很有价值的工具。例如,对于数据库、Web服务器或文件传输等应用,通过使用Mac Rust io-uring,可以显著提高其性能和吞吐量。 Mac Rust io-uring不仅提供了对io-uring的封装,还提供了一些更高级别的功能和接口,以方便开发者使用。开发者可以使用Mac Rust io-uring来实现一些高级的文件操作,例如批量读取或写入文件,提高数据处理的效率。 总之,Mac Rust io-uring是一个在Mac操作系统上使用Rust语言开发的io-uring库,它能够为开发者提供高性能的异步I/O操作方式,从而提高应用程序的性能和吞吐量。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值