关于mmapLinux系统中的实现,我有几个问题似乎没有太多记录:
使用时将文件映射到内存时mmap,如何处理预取此类文件中的数据?
也就是当你从mmaped区域读取数据时会发生什么?这些数据是否已移至L1/L2缓存?它是直接从磁盘缓存中读取的吗?prefetchnta相似的ASM指令是否适用于mmaped区域?
实际mmap通话的开销是多少?它是相对于映射数据量还是常量?
希望有人对此有所了解.提前致谢.
Wil*_*ung 29
mmap基本上是对虚拟内存子系统的编程访问.
当你有1G文件,并且你对它进行mmap时,你会得到一个指向"整个"文件的指针,就好像它在内存中一样.
但是,在此阶段没有发生任何事情,除了为VM中的文件保留页面的实际映射操作.(文件越大,映射操作的时间就越长.)
为了从文件中开始读取数据,您只需通过mmap调用中返回的指针访问它.
如果您希望"预加载"文件的某些部分,只需访问您要预加载的区域即可.确保您访问了要加载的所有页面,因为VM只会加载您访问的页面.例如,在你的1G文件中,你有一个10MB的"索引"区域,你想要映射.最简单的方法是"走你的索引",或者你拥有的任何数据结构,让VM页面必要时在数据中.或者,如果您"知道"它是文件的"前10MB",并且您的VM的页面大小是4K,那么您可以将mmap指针强制转换为char指针,然后只需遍历页面.
void load_mmap(char *mmapPtr) {
// We'll load 10MB of data from mmap
int offset = 0;
for(int offset = 0; offset < 10 * 1024 * 1024; offset += 4 * 1024) {
char *p = mmapPtr + offset;
// deref pointer to force mmap load
char c = *p;
}
}
Run Code Online (Sandbox Code Playgroud)
至于L1和L2缓存,mmap与此无关,这与你如何访问数据有关.
由于您正在使用底层VM系统,因此在mmap'd块中处理数据的任何内容都将起作用(从汇编开始).
如果您不更改任何mmap数据,VM将在需要新页面时自动清除旧页面如果您确实更改了它们,则VM将为您写回这些页面.