https://segmentfault.com/a/1190000007241437
在 Python 中使用 cgroup 对进程进行资源限制,需要结合 Python 的子进程管理和 cgroup 的命令行工具来实现。cgroup(Control Groups)是 Linux 内核的一项特性,用于限制、控制和隔离进程的资源使用(如 CPU、内存、磁盘 I/O 等)。
以下是一个示例,展示如何使用 cgroup 对某个子进程进行 CPU 和内存资源限制:
-
安装必要的工具:确保你的系统已经安装了
cgroup-tools。可以使用以下命令进行安装:sudo apt-get install cgroup-tools -
创建并配置 cgroup:使用 Python 脚本创建一个 cgroup,并配置其资源限制。
-
启动子进程,并将其添加到 cgroup 中。
下面是一个示例 Python 脚本,演示了如何实现上述步骤:
import os
import subprocess
# 创建一个新的 cgroup
cgroup_name = "my_cgroup"
subprocess.run(["sudo", "cgcreate", "-g", f"cpu,memory:/{cgroup_name}"])
# 设置 cgroup 的 CPU 限制,例如限制为 50% 的 CPU 使用率
cpu_quota = 50000 # 表示 50% 的 CPU 时间
cpu_period = 100000 # 表示周期为 100ms
subprocess.run(["sudo", "cgset", "-r", f"cpu.cfs_quota_us={cpu_quota}", cgroup_name])
subprocess.run(["sudo", "cgset", "-r", f"cpu.cfs_period_us={cpu_period}", cgroup_name])
# 设置 cgroup 的内存限制,例如限制为 100MB
memory_limit = 100 * 1024 * 1024 # 100MB
subprocess.run(["sudo", "cgset", "-r", f"memory.limit_in_bytes={memory_limit}", cgroup_name])
# 启动子进程,并将其添加到 cgroup 中
command = ["python3", "-c", "import time; time.sleep(30)"] # 示例命令
process = subprocess.Popen(command)
# 获取子进程的 PID
pid = process.pid
# 将子进程添加到 cgroup 中
subprocess.run(["sudo", "cgclassify", "-g", f"cpu,memory:/{cgroup_name}", str(pid)])
# 等待子进程完成
process.wait()
# 清理 cgroup
subprocess.run(["sudo", "cgdelete", "-g", f"cpu,memory:/{cgroup_name}"])
详细解释:
-
创建 cgroup:使用
cgcreate命令创建一个新的 cgroup,名字为my_cgroup,并指定控制资源为 CPU 和内存。 -
配置 CPU 限制:通过
cgset命令设置cpu.cfs_quota_us和cpu.cfs_period_us来限制 CPU 使用率。这里设置的值表示子进程只能使用 50% 的 CPU 时间。 -
配置内存限制:通过
cgset命令设置memory.limit_in_bytes来限制内存使用量为 100MB。 -
启动子进程:使用
subprocess.Popen启动一个子进程,这里示例子进程是一个简单的 Python 脚本,它会睡眠 30 秒。 -
将子进程添加到 cgroup 中:使用
cgclassify命令将子进程的 PID 添加到指定的 cgroup 中。 -
等待子进程完成:调用
process.wait()等待子进程完成。 -
清理 cgroup:使用
cgdelete命令删除创建的 cgroup。
这个示例展示了如何通过 Python 脚本结合 cgroup 命令行工具对进程进行资源限制。实际使用中,你可以根据需要调整 CPU 和内存的限制参数。
要查看已有的 cgroup 组,可以使用 cgget 命令。以下是具体步骤:
-
安装 cgroup-tools(如果尚未安装):
sudo apt-get install cgroup-tools -
列出所有 cgroup 组:
使用lscgroup命令来列出所有当前存在的 cgroup 组:lscgroup -
查看特定 cgroup 组的属性:
使用cgget命令来查看特定 cgroup 组的详细属性。例如,要查看名为test的 cgroup 组的属性,可以使用:cgget -r all /test
这些命令将帮助你管理和查看现有的 cgroup 组。如果有更多的需求或遇到问题,请随时告诉我。