C程序中的程序的最大堆大小是否固定,或者如果我保持malloc的大小,它会在某一时刻开始溢出?
码:
while(connectionOK) //connectionOK is the connection with server which might be forever { if(userlookup_IDNotFound(userID)) user_struct* newuser = malloc(getsize(user_struct)); setupUserAccount(newuser); }
如果有问题,我在ubuntu / linux中使用gcc。 我知道像getrlimit,但不知道它是否给堆大小。 尽pipe它确实为input参数中的某个选项提供了默认堆栈大小。 另外valgrind可能是一个好的工具,因为这里build议如何获得一个程序的堆大小,但我想dynamic打印一个错误消息,如果有一个堆溢出。 我的理解是进程地址空间是由操作系统分配的(如果需要的话,可以使用整个内存),但是我不确定一旦它请求的时候它是否dynamic的给予更多的物理内存额外的内存。
堆永远不会溢出它只是在一定的时间内耗尽内存(通常当malloc()
返回NULL
)所以要检测内存不足,只检查malloc()
调用的返回值。
if (newuser == NULL) { printf("OOM\n"); exit(1); /* exit if you want or can't handle being OOM */ }
malloc()
内部会从操作系统请求更多的内存,所以它动态地扩展,所以它不是真正的固定大小,因为它会将页面提供给不再需要的操作系统,以及在任何给定的时间请求更多的页面。
从技术上讲, malloc
在大多数系统上分配的内存不是内存,而是地址空间 。 在一个现代系统上,你可以很容易地用malloc分配几个PB的地址空间,而malloc可能总是返回一个非空的指针。 其原因是,大多数操作系统实际上只在一块地址空间被主动修改时才执行内存分配。 只要它不受影响,操作系统就会记下一个进程地址空间的某个区域已被有效保留以供将来使用。
这种行为被称为“内存过度使用”,在维护Linux系统时非常重要。 如果可能发生,那些分配的内存比可用的分配多一些,然后一些程序会实际写入一些过度的内存。 那么所发生的是,所谓的“内存不足的杀手”(OOM杀手)将会横行并杀死那些它认为最适合的进程; 不幸的是,它通常是那些在任何情况下都不想失去的进程。 数据库被认为是OOM杀手的主要目标之一。
因此,强烈建议在高可用性Linux机箱上切换内存过量使用。 禁用内存过量使用时,每个地址空间请求都必须由内存支持。 在这种情况下,如果请求无法满足,malloc实际上会返回0。
在某些时候,当系统将耗尽内存时, malloc()
将返回NULL
。 那么当你尝试解除引用时,你的程序将中止执行。
看看当你做malloc(SIZE_MAX)
几次会发生什么:-)