Fak*_*ame 2 memory out-of-memory
我有一个存在内存问题的虚拟机。我想在其中运行的任务之一是因内存不足错误而崩溃。
然而,当它崩溃时,系统仍然保持内存不足。我不确定这是否只是我遗漏的一个进程,还是一个实际的错误(这是在 hyper-v 中,具有允许 linux 主机内存膨胀的新内核扩展,因此它很可能是一个真正的内核错误)。
durr@sqlbox:~$ free -h
total used free shared buffers cached
Mem: 3.1G 2.6G 541M 88K 7.4M 39M
-/+ buffers/cache: 2.5G 588M
Swap: 1.0G 6.2M 1.0G
Run Code Online (Sandbox Code Playgroud)
Free 告诉我,它不只是缓存,实际上有一些东西似乎正在占用 2.6G 内存。
但是,查看按虚拟大小排序的 PS 输出并不具有启发性:
durr@sqlbox:~$ ps -e ax -o pid,vsz,comm | sort --numeric-sort --key=2
[ ... snip ... ]
PID VSZ COMMAND
96 0 rcuob/23
97 0 rcuob/24
98 0 rcuob/25
99 0 rcuob/26
1124 4368 acpid
59863 10016 ps
1031 15668 upstart-file-br
1047 15820 getty
1050 15820 getty
1055 15820 getty
1056 15820 getty
1058 15820 getty
1167 15820 getty
1023 15920 upstart-socket-
1076 19140 atd
1099 19188 irqbalance
428 19476 upstart-udev-br
59864 21860 sort
59267 22644 bash
59234 22664 bash
59280 22808 bash
1075 23656 cron
59261 26928 screen
59279 27380 htop
59262 28472 screen
1 33776 init
749 39240 dbus-daemon
816 43452 systemd-logind
432 51348 systemd-udevd
1090 61364 sshd
871 255844 rsyslogd
59184 269028 sshd
59233 269028 sshd
Run Code Online (Sandbox Code Playgroud)
所以最大的内存消耗者是sshd
,它使用..... 269K?我所有的记忆都去哪儿了?
看/proc/meminfo
节目:
durr@sqlbox:~$ cat /proc/meminfo
MemTotal: 3266904 kB
MemFree: 554228 kB
Buffers: 7596 kB
Cached: 41104 kB
SwapCached: 3032 kB
Active: 32552 kB
Inactive: 34292 kB
Active(anon): 13224 kB
Inactive(anon): 5008 kB
Active(file): 19328 kB
Inactive(file): 29284 kB
Unevictable: 0 kB
Mlocked: 0 kB
SwapTotal: 1044476 kB
SwapFree: 1038084 kB
Dirty: 0 kB
Writeback: 0 kB
AnonPages: 15656 kB
Mapped: 9196 kB
Shmem: 88 kB
Slab: 33488 kB
SReclaimable: 14532 kB
SUnreclaim: 18956 kB
KernelStack: 2352 kB
PageTables: 2748 kB
NFS_Unstable: 0 kB
Bounce: 0 kB
WritebackTmp: 0 kB
CommitLimit: 2677928 kB
Committed_AS: 56148 kB
VmallocTotal: 34359738367 kB
VmallocUsed: 34360 kB
VmallocChunk: 34359695660 kB
HardwareCorrupted: 0 kB
AnonHugePages: 0 kB
HugePages_Total: 0
HugePages_Free: 0
HugePages_Rsvd: 0
HugePages_Surp: 0
Hugepagesize: 2048 kB
DirectMap4k: 44456 kB
DirectMap2M: 3491840 kB
Run Code Online (Sandbox Code Playgroud)
显然,似乎有些东西Vmalloc
占用了大量内存,但我不确定这是否相关。
您的程序可能使用了共享内存并且没有清理它。
linux上共享内存的三种变体:
1.)POSIX共享存储器(一个由glibc的实现)是经由上的文件访问的tmpfs
伪文件系统,通常被安装在系统上的地方,如/dev/shm
,/run
,/run/shm
或/run/lock
。确定的最佳方法是在 shell 中输入mount | grep -E '^tmpfs'
(更便携)或grep -E '^tmpfs' /proc/mounts
(最适合 linux)。
请注意,进程可能会调用共享内存中unlink()
的mmap()
'ed 文件,从而无法通过文件名访问该文件(例如,需要先前分配的文件句柄才能继续访问它)。然而,unlink()
ed 文件通常在退出所有被 ed 的进程时被删除open()
——也许如果你的程序完成了,还有另一个进程仍然持有它的句柄。
2.) SysV IPC 共享内存,无法通过tmpfs
伪文件系统看到,而是通过/proc/sysvipc/shm
, linux 系统调用(仅当您是黑客时)、其 libc 包装器或最近通过ipcs -m -p -[tclu]
. 您需要在任何这些列表中找到匹配的进程 ID,然后进一步检查该进程。
3.) 匿名映射共享内存,在这种情况下,内存不受任何文件支持,而是最初在进程及其所有子进程之间共享内存。AFAIK 这样的匿名映射共享内存在处理mmap()
它exit()
的进程时被释放。因此,如果您的程序终止并且它的所有子进程也终止了,它们不应该进一步占用任何内存。