Linux环境下Python subprocess调用Maple时限制任务内存占用的实现方法
Linux环境下为subprocess子进程设置50MB内存上限的实现方法
方案1:使用Python标准库resource模块实现(推荐)
Linux系统自带的setrlimit系统调用可以对进程资源做强制限制,Python的resource标准库封装了该能力,结合subprocess.Popen的preexec_fn参数,可以在子进程启动前完成资源限制配置,不会影响主进程运行。
修改后的完整代码如下:
import subprocess import resource def limit_memory(): # 限制虚拟内存上限为50MB,单位为字节 mem_limit = 50 * 1024 * 1024 # soft limit和hard limit设置为相同值,硬限制普通进程无法自行修改 resource.setrlimit(resource.RLIMIT_AS, (mem_limit, mem_limit)) list_subprocess = ["maple"] + ["-i"] + [maple_file] task = subprocess.Popen( list_subprocess, stdout=subprocess.PIPE, preexec_fn=limit_memory # 子进程启动前先执行内存限制配置 ) task.communicate(timeout=30)
参数说明:
RLIMIT_AS限制的是进程的整个虚拟地址空间(包含物理内存、交换区、共享库占用等),是强制限制,进程超过该值后内存分配会直接失败,触发SIGSEGV信号终止,符合强限制需求- 如果要限制物理内存常驻集(RSS),可以替换为
resource.RLIMIT_RSS,但注意Linux 2.6及以上版本中该限制为建议性配置,不会强制终止超量进程
方案2:使用系统prlimit命令简化实现
如果不想额外编写回调函数,也可以直接调用Linux系统自带的prlimit工具包装Maple命令,直接在启动时指定内存限制,代码更简洁:
import subprocess # 用prlimit命令包装,直接指定虚拟内存上限为50MB list_subprocess = ["prlimit", "--as=50M", "maple", "-i", maple_file] task = subprocess.Popen( list_subprocess, stdout=subprocess.PIPE ) task.communicate(timeout=30)
注意事项
- 两种方案均仅对本次启动的Maple子进程生效,不会影响主进程和其他系统进程
- 需提前确认50MB的内存上限足够支撑你的Maple任务初始化和运行,内存不足会直接导致任务执行失败
- 如果Maple会自行启动子进程执行计算,以上方案仅限制一级子进程,如需限制所有后代进程的总内存,需要使用cgroup实现更复杂的资源管控
内容的提问来源于stack exchange,提问作者Tereso del Río Almajano
相关产品推荐
相关产品推荐

