如何分配操作系统可以回收的内存缓冲区,以便在Mac OS X内核扩展中进行缓存?

时间:2011-01-21 18:05:15

标签: macos kernel iokit darwin xnu

根据我阅读的文档和xnu源代码,我了解到Mac OS X使用统一缓冲区缓存(UBC)缓存文件 I / O.根据可用的RAM,UBC的增长幅度最大,但是当内存变得更紧密时,UBC页面是首先被牺牲的页面。

在我的驱动程序中,我处理各种磁盘元数据。我希望能够使用UBC或类似的机制来保持MRU缓存这些数据以加快速度,同时让内核能够在需要时收回内存。但是,元数据不代表 file 数据,因此不会直接进入UBC的域。是否有我可以使用的低级机制,或者我可以以某种方式仅使用UBC中处理缓冲区本身的部分?

我正在寻找HFS +源代码,试图弄清楚它是否以及如何缓存文件系统元数据,尽管没有太大成功。

主要的替代方案当然是为缓存保留特定的内存区域并进行自己的LRU剔除。我可以选择一个固定的缓存大小或使用某种启发式方法,但是当RAM丰富时它总是会占用太少的内存,而当它没有时它会占用太多。

更新

在搜索了一些之后,我发现可以使用kIOMemoryPurgeable选项创建IOBufferMemoryDescriptor的实例。这使您可以在其上调用IOMemoryDescriptor::setPurgeable()来标记内存“公平游戏”以便丢弃。我会尝试并用结果更新问题。

1 个答案:

答案 0 :(得分:3)

你是对的。请求内存时,将kIOMemoryPurgeable设置为其中一个选项。它从非易失性开始,可以被分页,但不会被丢弃。

当你想让操作系统丢弃它时,请拨打setPurgeable(kIOMemoryPurgeableVolatile, &oldState );,操作系统会在必要时丢弃它,而不是将其分页到磁盘。

当您想要访问内存时,您必须调用setPurgeable(kIOMemoryPurgeableKeepCurrent, &oldState );并检查if(oldState != kIOMemoryPurgeableEmpty)如果内存仍然可用则为true,如果已被丢弃则为false。

如果您遇到任何捕获,我会很高兴听到。