【发布时间】:2013-11-21 00:36:26
【问题描述】:
这个网站上有很多关于内存分配的问题,但是我 找不到一个专门解决我的问题的。 This question 似乎最接近,它引导我到this article,所以......我比较了 它包含在(虚拟)桌面 x86 上的三个演示程序的行为 Linux 系统和基于 ARM 的系统。
我的发现很详细here,但是
快速总结是:在我的桌面系统上,demo3 程序来自
文章似乎表明malloc() 总是 谎报内存量
分配——即使交换被禁用。例如,它愉快地“分配” 3
GB 的 RAM,然后在程序开始实际运行时调用 OOM 杀手
写入所有的内存。禁用交换后,将调用 OOM 杀手
在写入仅 610 MB 的 3 GB malloc() 之后
可用。
演示程序的目的是为了展示这个有据可查的 Linux '特性',所以这一切都不足为奇。
但是我们基于 i.MX6 的嵌入式目标在工作中的行为是不同的,
malloc() 似乎在说关于它有多少 RAM 的真相
allocates(?) 下面的程序(从文章中逐字复制)总是
在i == n 时在第二个循环中被 OOM 杀死:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define N 10000
int main (void) {
int i, n = 0;
char *pp[N];
for (n = 0; n < N; n++) {
pp[n] = malloc(1<<20);
if (pp[n] == NULL)
break;
}
printf("malloc failure after %d MiB\n", n);
for (i = 0; i < n; i++) {
memset (pp[i], 0, (1<<20));
printf("%d\n", i+1);
}
return 0;
}
所以简而言之,我的问题是:为什么demo3 程序或其他一些程序
不幸的 OOM 杀手受害者——总是早在我的 i == n 之前就被杀死了
桌面系统(暗示malloc() 是骗子),但它只会被杀死
当i == n 在我们的 i.MX6 ARM 目标上时(暗示malloc() 可能会告诉
真相)?这种差异是 libc 和/或内核版本的功能,还是
别的东西?我可以得出结论malloc() 将总是返回 NULL 如果
在这个目标上分配失败?
注意:每个系统的一些细节(请注意overcommit_memory 和overcommit_ratio 的值相同):
# Desktop system
% uname -a
Linux ubuntu 3.8.0-33-generic #48-Ubuntu SMP Wed Oct 23 17:26:34 UTC 2013 i686 i686 i686 GNU/Linux
% /lib/i386-linux-gnu/libc.so.6
GNU C Library (Ubuntu EGLIBC 2.17-0ubuntu5.1) stable release version 2.17, by Roland McGrath et al.
Copyright (C) 2012 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.
There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE.
Compiled by GNU CC version 4.7.3.
Compiled on a Linux 3.8.13 system on 2013-09-30.
Available extensions:
crypt add-on version 2.1 by Michael Glad and others
GNU Libidn by Simon Josefsson
Native POSIX Threads Library by Ulrich Drepper et al
BIND-8.2.3-T5B
libc ABIs: UNIQUE IFUNC
For bug reporting instructions, please see:
<https://bugs.launchpad.net/ubuntu/+source/eglibc/+bugs>.
% cat /proc/sys/vm/overcommit_memory
0
% cat /proc/sys/vm/overcommit_ratio
50
# i.MX6 ARM system
# uname -a
Linux acmewidgets 3.0.35-ts-armv7l #2 SMP PREEMPT Mon Aug 12 19:27:25 CST 2013 armv7l GNU/Linux
# /lib/libc.so.6
GNU C Library (GNU libc) stable release version 2.17, by Roland McGrath et al.
Copyright (C) 2012 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.
There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A
PARTICULAR PURPOSE.
Compiled by GNU CC version 4.7.3.
Compiled on a Linux 3.0.35 system on 2013-08-14.
Available extensions:
crypt add-on version 2.1 by Michael Glad and others
Native POSIX Threads Library by Ulrich Drepper et al
BIND-8.2.3-T5B
libc ABIs: UNIQUE
For bug reporting instructions, please see:
<http://www.gnu.org/software/libc/bugs.html>.
# cat /proc/sys/vm/overcommit_memory
0
% cat /proc/sys/vm/overcommit_ratio
50
BACKGROUND:我们正在尝试决定如何处理我们的内存不足的情况
面向媒体的嵌入式应用程序,并且想知道我们是否可以——对于这个特定目标——信任malloc(),以便在分配失败时提醒我们。我对桌面 Linux 的体验
应用程序让我认为答案肯定是不是,但现在我不太确定。
【问题讨论】:
-
你应该禁用memory overcommit
-
@BasileStarynkevitch,我们很可能会选择这样做,但我们想了解为什么在两个系统的设置相似时,该程序的行为会有所不同。
-
您将Ubuntu eglibc 与ARM glibc 进行比较。该软件可能会做一些不同的事情。同样,您的内核版本也完全不同。通常,ARM 在几个版本的功能上落后于 x86。你在比较完全不同的东西。 ARM 内部没有任何东西可以阻止这种情况。但所涉及的软件堆栈很大,差异很大。
-
我知道,这是问题的症结所在:具体来说有什么不同?您链接到的
malloc.c文件(感谢那些!)是相同的,所以它不是那个文件。 ARM 实现是否以某种方式绕过了内核过度使用设置(如果这甚至可能的话),还是demo3程序没有比承诺的其他原因更早触发 OOM 杀手?