非阻塞mlock()

时间:2014-07-24 17:09:46

标签: c++ c linux file-io

是否存在非阻塞mlock()这样的事情?在交通繁忙的情况下,我不希望我的线程阻塞等待I / O.我宁愿告诉Linux内核我需要使用mlock()从mmap()文件中获取哪个区域,然后在获取页面时得到通知。 (据我所知,标准的mlock()调用是阻塞的。)

3 个答案:

答案 0 :(得分:2)

mlock界面似乎没有任何你想要的内置功能,所以我认为实现它的唯一方法是使用一个单独的线程来执行mlock并拥有当mlock返回时,该线程通知您(通过条件变量,信号量或其他机制)。显然这会产生一些开销,但如果你的目标是获得实时延迟保证而不是改善整体运行时间/平均延迟,那么它仍然是一个明显的胜利。

当然,除非您使用mlockall,否则很难做出任何实时假设,因为您的代码可能会被换出。因此,使用mlockall和POSIX AIO(或类似但更清洁的API系统自己在线程方面实现)进行读取而不是使用mmap可能更有意义。然后你有一个很难保证,一旦你的数据被提取,就无法换掉它。

答案 1 :(得分:2)

我认为您需要madvise()posix_madvise()mincore()的组合。

您将使用madvise调用向内核询问MADV_WILLNEED。然后,您必须使用mincore进行轮询,以检查页面是否已被读入内存。

如果系统负载过重,可能无法通过madvise调用读取页面,因此您需要超时并回退到阻塞读取模式。

答案 2 :(得分:0)

如果mmap()文件,则将文件视为内存,VM页面输入/输出文件块取决于您的使用情况,这可能会从预读中受益。

有多种方法可以进行非阻塞I / O(asyncio,poll,select,epoll),但mlock()是关于在RAM中保存一个内存区域,不允许它被分页到交换分区;虽然在严重的记忆压力下内核可能不会尊重它。

最有可能的是,mmap(2)就好像你正在使用内存页面一样,它们不会被选择用于页面输出,而是保留在内存中,所以考虑一下这个问题是否过早的验证,内核会努力提供(默认情况下)良好的表现。