Cgroup

Cgroup

Posted by BlueFat on Saturday, November 9, 2019

cgroup

cgroups 是Linux内核提供的一种可以限制单个进程或者多个进程所使用资源的机制,可以对 cpu,内存等资源实现精确的控制,Docker 就使用了 cgroups 提供的资源限制能力来完成cpu,内存等部分的资源控制。

cgroups 的全称是control groups,cgroups为每种可以控制的资源定义了一个子系统。典型的子系统介绍如下:

cpu 子系统,主要限制进程的 cpu 使用率。
cpuacct 子系统,可以统计 cgroups 中的进程的 cpu 使用报告。
cpuset 子系统,可以为 cgroups 中的进程分配单独的 cpu 节点或者内存节点。
memory 子系统,可以限制进程的 memory 使用量。
blkio 子系统,可以限制进程的块设备 io。
devices 子系统,可以控制进程能够访问某些设备。
net_cls 子系统,可以标记 cgroups 中进程的网络数据包,然后可以使用 tc 模块(traffic control)对数据包进行控制。
net_prio 子系统, 限制任务中网络流量的优先级.
pids 子系统, 限制控制组中进程可以派生出的进程数量。
freezer 子系统,可以挂起或者恢复 cgroups 中的进程。 namespace。

cgroup和namespace类似,也是将进程进行分组,但它的目的和namespace不一样,namespace是为了隔离进程组之间的资源,而cgroup是为了对一组进程进行统一的资源监控和限制。

[root@gz cpu]# ls -l /sys/fs/cgroup/
total 0
dr-xr-xr-x 7 root root  0 Nov  9 15:30 blkio
lrwxrwxrwx 1 root root 11 Aug  2 16:16 cpu -> cpu,cpuacct
lrwxrwxrwx 1 root root 11 Aug  2 16:16 cpuacct -> cpu,cpuacct
dr-xr-xr-x 7 root root  0 Nov  9 15:30 cpu,cpuacct
dr-xr-xr-x 5 root root  0 Nov  9 14:39 cpuset
dr-xr-xr-x 7 root root  0 Nov  9 15:30 devices
dr-xr-xr-x 5 root root  0 Nov  9 14:39 freezer
dr-xr-xr-x 5 root root  0 Nov  9 14:39 hugetlb
dr-xr-xr-x 7 root root  0 Nov  9 15:30 memory
lrwxrwxrwx 1 root root 16 Aug  2 16:16 net_cls -> net_cls,net_prio
dr-xr-xr-x 5 root root  0 Nov  9 14:39 net_cls,net_prio
lrwxrwxrwx 1 root root 16 Aug  2 16:16 net_prio -> net_cls,net_prio
dr-xr-xr-x 5 root root  0 Nov  9 14:39 perf_event
dr-xr-xr-x 7 root root  0 Nov  9 15:30 pids
dr-xr-xr-x 5 root root  0 Nov  9 14:39 rdma
dr-xr-xr-x 7 root root  0 Nov  9 15:22 systemd

cgroups限制CPU

在/sys/fs/cgroup/cpu新建

[root@gz cpu]# mkdir /sys/fs/cgroup/cpu/stress_test
[root@gz cpu]# ls -l /sys/fs/cgroup/cpu/stress_test/
total 0
-rw-r--r-- 1 root root 0 Nov  9 17:06 cgroup.clone_children
-rw-r--r-- 1 root root 0 Nov  9 17:06 cgroup.procs
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.stat
-rw-r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage_all
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage_percpu
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage_percpu_sys
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage_percpu_user
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage_sys
-r--r--r-- 1 root root 0 Nov  9 17:06 cpuacct.usage_user
-rw-r--r-- 1 root root 0 Nov  9 17:06 cpu.cfs_period_us
-rw-r--r-- 1 root root 0 Nov  9 17:06 cpu.cfs_quota_us
-rw-r--r-- 1 root root 0 Nov  9 17:06 cpu.rt_period_us
-rw-r--r-- 1 root root 0 Nov  9 17:06 cpu.rt_runtime_us
-rw-r--r-- 1 root root 0 Nov  9 17:06 cpu.shares
-r--r--r-- 1 root root 0 Nov  9 17:06 cpu.stat
-rw-r--r-- 1 root root 0 Nov  9 17:06 notify_on_release
-rw-r--r-- 1 root root 0 Nov  9 17:06 tasks

开启压测,记录stress PID

[root@gz ~]# stress --cpu 1 --timeout 600

如果要限制CPU 使用5% ,cpu.cfs_quota_us 写入5000。

[root@gz stress_test]# echo 50000 > cpu.cfs_quota_us  # 限制50%CPU
[root@gz stress_test]# echo 20397 > tasks  # 限制PID,进程结束会自动清空

前后对比

cgroups限制内存

mkdir /sys/fs/cgroup/memory/stress_test
cgroup.procs: 使用该组配置的进程列表。
memory.limit_in_bytes:内存使用限制。
memory.memsw.limit_in_bytes:内存和交换分区总计限制。
memory.swappiness: 交换分区使用比例。
memory.usage_in_bytes: 当前进程内存使用量。
memory.stat: 内存使用统计信息。
memory.oom_control: OOM 控制参数。

假设有进程 pid 1234,希望设置内存限制为 10MB,我们可以这样操作: limit_in_bytes 设置为 10MB

echo "10*1024*1024" | bc > /sys/fs/cgroup/memory/stress_test/memory.limit_in_bytes

swappiness 设置为 0,表示禁用交换分区,实际生产中可以配置合适的比例。

echo 0 > /sys/fs/cgroup/memory/stress_test/memory.swappiness

添加控制进程pid,当进程 1234 使用内存超过 10MB 的时候,默认进程 1234 会触发 OOM,被系统 Kill 掉。

echo 1234 > /sys/fs/cgroup/memory/stress_test/cgroup.procs

systemd

systemctl set-property nginx.service CPUQuota=150% MemoryLimit=500M
systemctl set-property mysql.service BlockIOWeight=1000 # IO 权重
cat /sys/fs/cgroup/memory/system.slice/nginx.service/memory.limit_in_bytes 
524288000

默认即时生效

cat /etc/systemd/system/nginx.service.d/50-CPUQuota.conf 
[Service]
CPUQuota=150%

修改或删除

[root@gz ~]# rm -rf /etc/systemd/system/nginx.service.d/
[root@gz ~]# systemctl daemon-reload
[root@gz ~]# systemctl reload nginx
man systemd.resource-control

使用 systemd 限制系统资源的使用

https://access.redhat.com/documentation/zh-cn/red_hat_enterprise_linux/7/html/resource_management_guide/chap-introduction_to_control_groups