Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/linux/27.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 如何在mmaped内存中删除脏页并准备快速munmap?_C_Linux - Fatal编程技术网

C 如何在mmaped内存中删除脏页并准备快速munmap?

C 如何在mmaped内存中删除脏页并准备快速munmap?,c,linux,C,Linux,我正在尝试为无交换系统实现一个文件支持的内存分配器 对于每个新的分配,我使用mkstemp创建一个临时文件作为backstore,mmapit asMAP\u SHARED在系统内存压力较高时允许页面交换到backstore。我想我已经把这个部分做好了 然而,我在执行解除分配案例时遇到了困难 由于在解除分配时,后台存储的内容、常驻页或脏页的内容都不再重要,因此最快的方法是删除并释放所有常驻页,并保持后台存储不变。但是,我没有找到一个madvice标志可以这样做 MADV_DONTNEED似乎过多

我正在尝试为无交换系统实现一个文件支持的内存分配器

对于每个新的分配,我使用
mkstemp
创建一个临时文件作为backstore,
mmap
it as
MAP\u SHARED
在系统内存压力较高时允许页面交换到backstore。我想我已经把这个部分做好了

然而,我在执行解除分配案例时遇到了困难

由于在解除分配时,后台存储的内容、常驻页或脏页的内容都不再重要,因此最快的方法是删除并释放所有常驻页,并保持后台存储不变。但是,我没有找到一个
madvice
标志可以这样做

MADV_DONTNEED
似乎过多,因为它会将脏页提交到后台存储。(不正确,请参见下面的答案)

不需要

成功执行MADV_DONTNEED操作后,指定区域中内存访问的语义将发生更改:后续访问范围中的页面将成功,但将导致从基础映射文件的最新内容重新填充内存内容(用于共享文件映射、共享匿名映射和基于shmem的技术,如System V共享内存段)或用于匿名私有映射的按需零填充页面

MADV_REMOVE
似乎也太过分了,因为它不仅会删除常驻页面,还会删除后台存储本身

移动

释放给定范围的页及其关联的备份存储区。这相当于在备份存储区的相应字节范围内打孔(请参阅fallocate(2))。在指定地址范围内的后续访问将看到包含零的字节

那么,取消映射/关闭/删除
mmap
ed文件的最快路径是什么

也许
mmap
MAP\u PRIVATE
()相同的区域,然后
munmap
it?

根据
MADV\u DONTNEED
的操作就是:在不回写到后台存储的情况下删除页面

子句
从底层映射文件的最新内容重新填充内存内容
意味着
MADV_DONTNEED
之后的加载将从后台存储重新加载

在MADV_DONTNEED之前的所有脏页未提交到后台存储,因此将丢失

总之:
MADV_DONTNEED
删除所有映射页(包括未提交到后台存储的脏页),并保持后台存储不变


madvise MADV\u不需要脏页,不要放弃更改。
我刚刚使用mmap/madvise MADV_DONTNEED/munmap编写了一个5GB的文件,最后两个步骤在2-4MB的块中进行,创建该文件时没有一个错误。

然而,MADV_DONTNEED对脏页没有影响。munmap减少了进程的RSS,但编写仍由Linux自行决定。

我认为您可能误读了
msync
文档。它说“如果不使用此调用,就不能保证在调用munmap(2)之前写回更改。”,这意味着当调用
munmap
时,更改将被写回(这是有意义的;
msync
大致类似于
fsync
,而
munmap
类似于
close
,并且
close
不要求您先
fsync
)。