linux `--oom-kill-disable`对Docker容器有什么作用?

x7rlezfr  于 12个月前  发布在  Linux
关注(0)|答案(3)|浏览(179)

我已经了解到docker run -m 256m --memory-swap 256m会限制一个容器最多使用256 MB内存,并且不允许交换。如果它分配更多内存,那么容器中的一个进程(不是“容器”)将被杀死。例如:

$ sudo docker run -it --rm -m 256m --memory-swap 256m \
        stress --vm 1 --vm-bytes 2000M --vm-hang 0
stress: info: [1] dispatching hogs: 0 cpu, 0 io, 1 vm, 0 hdd
stress: FAIL: [1] (415) <-- worker 7 got signal 9
stress: WARN: [1] (417) now reaping child worker processes
stress: FAIL: [1] (421) kill error: No such process
stress: FAIL: [1] (451) failed run completed in 1s

字符串
显然,其中一个工作进程分配的内存比允许的多,并收到SIGKILL。请注意,父进程保持活动状态。
现在,如果-m的效果是在一个进程分配了太多内存时调用OOM杀手,那么当指定-m * 和 * --oom-kill-disable时会发生什么?像上面这样尝试会有以下结果:

$ sudo docker run -it --rm -m 256m --memory-swap 256m --oom-kill-disable \
        stress --vm 1 --vm-bytes 2000M --vm-hang 0
stress: info: [1] dispatching hogs: 0 cpu, 0 io, 1 vm, 0 hdd
(waits here)


在不同的shell中:

$ docker stats
CONTAINER           CPU %               MEM USAGE / LIMIT       MEM %               NET I/O             BLOCK I/O           PIDS
f5e4c30d75c9        0.00%               256 MiB / 256 MiB       100.00%             0 B / 508 B         0 B / 0 B           2

$ top
  PID USER      PR  NI    VIRT    RES    SHR S  %CPU %MEM     TIME+ COMMAND                                           
19391 root      20   0 2055904 262352    340 D   0.0  0.1   0:00.05 stress


我看到docker stats显示了256 MB的内存消耗,top显示了256 MB的RES和2000 MB的VIRT。但是,这实际上意味着什么?容器内试图使用超过允许的内存的进程会发生什么?在什么意义上它受到-m的约束?

9jyewag0

9jyewag01#

据我所知,文档--oom-kill-disable不受-m的限制,但实际上需要它:
默认情况下,如果发生内存不足(OOM)错误,内核会杀死容器中的进程。要更改此行为,请使用--oom-kill-disable选项。仅在您还设置了-m/--memory选项的容器上禁用OOM杀手程序。如果未设置-m标志,则可能导致主机内存不足,并需要杀死主机的系统进程以释放内存。
一位开发商在2015年表示,
无论是否设置了-m标志,主机都可能会耗尽内存。但它也是无关紧要的,因为除非传递-m,否则--oom-kill-disable什么都不做。
关于你的更新,当OOM-killer被禁用而内存限制被达到时会发生什么?(intresting OOM article),id说对malloc的新调用将像here描述的那样失败,但这也取决于交换配置和主机的可用内存。如果您的-m限制高于实际可用内存,主机将开始杀死进程,其中之一可能是docker守护进程(他们试图通过改变其OOM优先级来避免)。
kernel docscgroup/memory.txt)表示
如果禁用了OOM-killer,cgroup下的任务在请求可解释内存时将挂起/休眠在内存cgroup的OOM-等待队列中
对于cgroups的实际实现(docker也使用),您必须使用check the sourcecode

5ktev3wc

5ktev3wc2#

在Linux中,“oom killer”的工作是牺牲一个或多个进程,以便在所有其他方法都失败时为系统释放内存。
--oom-kill-disable的设置将设置cgroup参数,以在满足-m指定的条件时禁用该特定容器的oom killer。如果没有-m标志,则oom killer将不相关。
-m标志并不意味着当进程使用超过xmb的内存时停止进程,只是确保Docker容器不会消耗所有的主机内存,这可能会迫使内核杀死它的进程。使用-m标志,容器不允许使用超过给定数量的用户或系统内存。
当容器遇到OOM时,它不会被杀死,但它可以挂起并保持在失效状态,因此容器内的进程无法响应,直到您手动干预并重新启动或杀死容器。希望这有助于解决您的问题。
有关内核如何处理OOM的更多详细信息,请查看Linux OOM管理和Docker内存限制页面。

7fyelxc5

7fyelxc53#

对于使用cgroups v2的新主机上的新Docker版本,--oom-kill-disable参数不再受支持。
要检查docker使用的Cgroup,请运行

> docker info | grep Cgroup
 Cgroup Driver: systemd
 Cgroup Version: 2

字符串
当尝试使用选项时,docker给出以下警告

WARNING: Your kernel does not support OomKillDisable. OomKillDisable discarded.


From:moby: Improve information about supported (cgroup) constraints
我还在想办法绕过他。

相关问题