如何使用 Linux hugetlbfs 进行文件的共享内存映射?

我有一个使用 mmap() 和共享内存来有效访问大型数据库文件的程序。我想尝试使用大页面,看看它是否可以加快速度。

我认为一种快速简便的方法是将数据库文件复制到 Linux 的 hugetlbfs 目录并在旧位置创建一个 symlink

但是,这不起作用,因为 cp 命令无法写入文件。我怀疑只能通过调用 ftrunc()mmap() 系统调用来写入文件来创建文件。我可能会尝试编写一个复制工具来执行此操作,除非我得到描述现有工具的答案。

我正在寻找在 Linux 中使用大页面进行共享内存映射的任何其他好方法。

stack overflow How to use Linux hugetlbfs for shared memory maps of files?
原文答案

答案:

作者头像

现在是一个老问题。但是看到没有人回答,我实际上也想尝试使用大页面支持(出于不同的原因)。我会提供一个答案。

尽管大页面现在在现代内核中是透明的,但您仍然可以获得更多控制权。

这些功能可能就是您正在寻找的。

get_huge_pages() , free_huge_pages() , get_hugepage_region() , free_hugepage_region()

您需要安装 libhugetlbfs ,它是 hugetlbfs 的包装器。

这是一篇 Linux Weekly 文章,您可能会发现它有帮助。 Huge pages - part 1 (Introduction)

作者头像

大页面是一种通过将几个连续的物理内存页面(例如 4KB 长)映射到一个大页面(例如 2MB、1GB...)来避免 TLB 未命中的方法。 Linux 提出了两种机制:

  • 透明大页面 (THP) 在内核内部透明管理;
  • 由用户空间应用程序管理的用户控制大页面。

除此之外,一个名为 libhugetlbfs 的可选用户空间库可用于提供用户友好的 API 和工具,以将大页面用于堆、静态链接程序的代码和数据段。这个库隐藏了内核提供的“原始”接口。根据应用程序,这可能有用或不够灵活。

对于问题的数据库示例问题,想法是在 hugetlbfs 文件系统中创建文件(它实际上是一种基于巨大内存页的 RAM 文件系统),扩展文件(使用 {JXM= }) 到大页面大小的倍数,将文件 mmap 到内存中,并将这些内存区域用作缓冲区来读/写数据库文件。由于访问内存页面所需的 TLB 条目较少,因此性能得到提高。

ftrunc() 提供了有关使用 Linux“原始”接口映射大页面的方法的详细信息。