如何将 Linux 二进制文件限制在有限的 RAM 容量内?

如何将 Linux 二进制文件限制在有限的 RAM 容量内?

我希望能够限制已安装的二进制文件只能使用一定数量的 RAM。 我不希望它在超过该数量时被终止,只是希望这是它可以使用的最大数量。 我希望该进程在达到一定数量的 RAM 后终止,最好是在服务器开始大量交换之前。

我面临的问题是,我正在运行一个 Apache 2.2 服务器,其中包含 PHP 和开发人员为我们编写的一些自定义代码。问题是,在代码的某个地方,他们启动了一个 PHP exec 调用,该调用启动了 ImageMagick 的“转换”来创建已调整大小的图像文件。

我不太了解该项目或代码的很多细节,但需要找到一个解决方案来阻止他们关闭服务器,直到他们找到优化代码的方法。

我原本以为可以使用 /etc/security/limits.conf 来做到这一点,并对 apache 用户设置限制,但似乎没有效果。这是我使用的:

www-data 硬为 500

如果我理解正确的话,这应该会将任何 apache 用户进程的最大大小限制为 500kb,但是,当我运行一个会占用大量 RAM 的测试脚本时,在我将其关闭之前,它实际上已经占用了 1.5GB。以下是更改设置并重启系统后“ps auxf”的输出:

用户 PID %CPU %MEM VSZ RSS TTY STAT 开始时间命令
root 5268 0.0 0.0 401072 10264 ?Ss 15:28 0:00 /usr/sbin/apache2 -k 启动
www-数据 5274 0.0 0.0 402468 9484 ? S 15:28 0:00 \_ /usr/sbin/apache2 -k 启动
www-data 5285 102 9.4 1633500 1503452 ? Rl 15:29 0:58 | \_ /usr/bin/convert ../tours/28786/.….
www-数据 5275 0.0 0.0 401072 5812?S 15:28 0:00 \_ /usr/sbin/apache2 -k 启动

接下来,我认为我可以使用 Apache 的 RlimitMEM 设置来实现这一点,但结果却与限制相同。这是我的 apache.conf 文件中的内容:

限制内存 500000 512000

直到几个小时后我才明白,如果该进程实际上达到了这个数量,它就会因 OOM 错误而死亡。

很想知道如何设置此限制,以便其他东西可以在服务器上运行,并且它们都可以很好地协同运行。

答案1

创建一个新用户,仅用于 ImageMagick。为其设置所需的内存限制。设置 sudoers 文件,以便 Apache 可以以此用户身份调用 ImageMagick。将 PHP 代码中的 exec() 调用更改为通过 sudo 运行 convert,或用包装器脚本替换原始 convert 二进制文件。如果 ImageMagick 占用了所有内存,则让它死机并让 PHP 脚本抛出适当的错误消息。

或者完全替换 ImageMagick,它非常占用内存(尝试将小图片拼贴在一起。在某一时刻你会记得为什么你仍然有一个交换分区)。

答案2

有一个相当新的 (2.6.24) 内核接口,称为 cgroups,它允许您执行此操作。您可以将用户、组或 PID(及其子级)置于 cgroup 下,并为其提供 X 数量的 RAM、CPU、IO(磁盘、网络)等。它相当简洁,并且在与 KVM 虚拟机一起使用时非常强大。请参阅维基百科官方文档了解更多信息。

答案3

简单的答案是:你不能。如果程序无法分配更多内存,它就会崩溃。你可以通过设置工作程序等将服务器内存保持在一定范围内,但这会限制性能。

如果你需要更多的氧气,而又无法获得更多,你也会死。没有其他结果。

答案4

如果 Rlimitmeme 选项不起作用,那么似乎几乎没有机会将其限制在限制范围内。您能否至少在 pastebin 中向我展示 OOM killer 堆栈跟踪,以便我可以看到哪些区域正在耗尽或分配如何失败。这不是您遇到的问题的解决方案,而是我更愿意进行的一些更常见的调试。

但是,我真的想不出有什么办法可以限制二进制文件使用一定数量的 RAM。我想这几乎是不可能的。

相关内容