我想使用mmap函数将文件映射到内存中,并想知道当前平台上的虚拟内存量是否足以映射一个巨大的文件。对于32位系统,我不能映射大于4 Gb的文件。
std::numeric_limits<size_t>::max()
是否会给我提供可寻址内存的大小,或者我是否应该测试其他类型(off_t或其他类型)?
正如Lie Ryan在他的评论中指出的那样,这里的“虚拟内存”被滥用了。然而,问题仍然存在:有一个与指针关联的类型,它具有最大值,该值定义了您可以在系统上访问的上限。这是什么类型?是size_t还是ptrdiff_t?
发布于 2010-11-18 21:53:28
size_t
只需要足够大来存储最大可能的单个连续对象。这可能与地址空间的大小不同(例如,在具有分段内存模型的系统上)
但是,在具有扁平内存空间的常见平台上,这两者是相等的,因此,如果您知道目标CPU,则可以在实践中使用size_t
。
无论如何,这并不能告诉你任何有用的东西。当然,32位的CPU有4 4GB的内存空间,所以size_t
是一个32位的无符号整数。但这并没有说明你能分配多少。内存空间的一部分由操作系统使用。而且有些部分已经被您自己的应用程序使用:用于将可执行文件映射到内存(以及它可能使用的任何动态库)、每个线程的堆栈、堆上分配的内存等等。
所以不会,像计算size_t
大小这样的技巧会告诉你一些关于你正在运行的地址空间的信息,但是没有什么非常有用的。您可以向操作系统询问您的进程和其他指标使用了多少内存,但同样,这对您没有多大帮助。有可能一个进程只使用几兆字节,但它分散在太多的小分配上,以至于不可能找到大于100MB的连续内存块。因此,在32位机器上,进程几乎不使用内存,您不太可能进行这样的分配。(即使操作系统有一个神奇的WhatIsTheLargestPossibleMemoryAllocationICanMake()
应用程序接口,也不会对你有任何帮助。它会告诉你刚才你需要什么。您不能保证在您尝试映射文件时答案仍然有效。
因此,实际上,您所能做的最好的事情就是尝试映射文件,看看是否失败。
发布于 2010-11-18 21:19:30
您好,如果您使用win32编码,则可以使用GlobalMemoryStatusEx和VirtualQueryEx
发布于 2010-11-19 00:22:11
问题是,指针的大小并不能告诉你实际有多少“地址空间”可用,也就是说,可以被映射为一个连续的块。
它受到以下因素的限制:
最后,不要混淆“可用内存”和“可用地址空间”。执行malloc(someBigSize)和mmap(...,someBigSize,...)是有区别的因为前者可能需要物理内存的可用性来容纳请求,而后者通常只需要足够大的空闲地址范围。
对于UNIX平台,部分答案是使用getrlimit(RLIMIT_AS),因为这给出了应用程序当前调用的上限-如上所述,用户和/或管理员可以对此进行配置。您可以保证,任何尝试mmap大于该值的区域都将失败。
https://stackoverflow.com/questions/4215127
复制相似问题