You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

NVMe磁盘4GB与32MB文件pread随机4K直读延迟差异原因问询

问题:NVMe磁盘上大文件与小文件Direct IO随机读延迟差异原因

我在NVMe磁盘上通过Direct IO(O_DIRECT)与pread接口,对4GB和32MB文件分别进行单4K页随机循环读取测试。结果显示4GB文件每页延迟约41微秒,32MB文件则约79微秒,请问该差异的合理原因是什么?

测试代码片段:

int b_fd = open("large.txt", O_RDONLY | O_DIRECT);
int s_fd = open("small.txt", O_RDONLY | O_DIRECT);

std::srand(std::time(nullptr));
  
void *buf;
int ps = getpagesize();
posix_memalign(&buf, ps, page_size);

long long nano_seconds = 0;

// 随机读取的页数
int iter = 256 * 100;

for (int i = 0; i < iter; i++) {
  int page_index = std::rand() % big_file_pages;

  auto start = std::chrono::steady_clock::now();
  pread(b_fd, buf, page_size, page_index * page_size);
  auto end = std::chrono::steady_clock::now();
  nano_seconds += std::chrono::duration_cast<std::chrono::nanoseconds>(end - start).count();
}

std::cout << "large file average random 1 page direct IO read in nanoseconds is:" << nano_seconds/iter << "\n";

分析与原因

这种延迟差异核心源于NVMe SSD的物理特性、文件系统分配策略以及控制器的调度机制,具体可以拆解为以下几点:

  • 多通道并行利用效率差异
    NVMe SSD依赖多闪存颗粒通道实现高并行性。4GB文件体积远大于SSD的最小连续分配单元(如块组、物理页块),文件系统会将其分散分配到多个独立通道的物理块上。随机读时,控制器可以同时调度多个通道的IO请求,分摊单IO的延迟;而32MB文件体积过小,大概率被限制在少数甚至单个通道的物理块中,无法充分利用NVMe的多通道并行优势,单IO延迟自然更高。

  • 物理块碎片化与GC干扰
    NVMe SSD的垃圾回收(GC)机制会定期回收包含无效页的物理块。小文件占用的物理块数量少,一旦其中某个块触发GC(比如有其他文件的无效页在同一块),随机读请求命中该块时会被GC操作阻塞,导致延迟陡增;而大文件占用的物理块数量多,单个块的GC操作对整体随机读的影响被稀释,且大文件通常被分配为连续块,GC触发频率更低。

  • LBA-PBA映射缓存命中率
    NVMe控制器会缓存逻辑块地址(LBA)到物理块地址(PBA)的映射表。4GB文件的LBA范围更广,随机读的分散性会让控制器的映射缓存更充分地被利用(缓存条目覆盖更多常用LBA);而小文件的LBA范围窄,若其物理块因多次分配/回收出现映射碎片化,缓存命中率反而更低,每次读都需要额外的地址转换开销。

  • 文件系统分配策略倾向
    主流文件系统(如ext4、XFS)对大文件会优先分配连续的物理块组,这些块组通常分布在不同的SSD通道上;而小文件常被分配到零散的空闲块,甚至与其他小文件共享块组,导致IO请求集中在局部通道,加剧竞争延迟。


内容的提问来源于stack exchange,提问作者Kenneth

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 22:40:29