一.cgroup的简介
cgroups概念
- cgroups(Control groups)是linux内核提供的一种机制,这种机制可以根据需求把一系列的系统任务以及子系统任务整合(或者分隔)到资源划分等级的不同的组内,从而为系统资源管理提供了一个统一的框架。
- 简单来说,cgroups可以限制、记录任务组所使用的物理资源,本质上来说,cgroups是内核附加在程序上的一系列钩子(hook),通过程序运行时对资源的调度触发相应的钩子以达到资源追踪和限制的目的。
- 在以容器技术为代表的虚拟化技术大行其道的时代下,了解cgroups技术是很有必要的!比如我们可以很方便的限制某个容器可以使用的cpu、内存等资源。
cgroups的作用
- 实现cgroups的主要目的是为了不同用户层面的资源管理提供一个统一化的接口。
- 从单个任务资源控制到操作系统层面的虚拟化,cgroups提供了四大功能:
资源限制:cgroups可以对任务要的资源总额进行限制。比如设定任务运行时使用的内存上限,一旦超出就发OOM。
优先级分配:通过分配的cpu时间片数量和磁盘IO带宽,实际上就等同于控制了任务运行的优先级。
资源统计:cgroups可以统计系统的资源使用量,比如cpu的使用时长,内存用量等。这个功能非常合适当前云端产品按使用量计费的方式。
任务控制:cgroups可以对任务执行挂起、恢复等操作
相关概念
- Task(任务):在linux系统中,内核本身的调度和管理并不对进程和线程进行区分,只是根据clone时传入的参数的不同来从概念上区分进程和线程。
- Cgroups(控制组):cgroups中的资源控制以cgroup为单位实现。cgroup表示按照某种资源控制标准划分而成的任务组,包含一个或者多个子系统。一个任务可以加入某个cgroup,也可以从某个cgroup迁移到另外一个cgroup。
- Subsystem(子系统):cgroups中的子系统就是一个资源调度控制器(又叫作controllers)。比如cpu子系统可以控制cpu的时间分配,内存子系统可以限制内存的使用量
[root@cloud ~]# cat /proc/cgroups
#subsys_name hierarchy num_cgroups enabled
cpuset 8 2 1 ##给cgroup中的任务分配独立的cpu资源报告,与cpu挂载在同一目录
cpu 4 52 1 ##cpu限制cpu时间片的分配,与cpuset挂载在同一目录
cpuacct 4 52 1 ##生成cgroup中的任务占用cpu资源的报告,与cpu挂载在同一个目录
memory 3 52 1 ##对cgroup中任务的可用内存进行限制,并且自动生成资源占用报告
devices 6 52 1 ##允许或者禁止cgroup中的任务访问设备
freezer 10 2 1 ##暂停/恢复cgroup中的任务
net_cls 5 2 1 ##使用等级识别符(classid)标记网络数据包,这让Linux流量控制器(tc指令)可以识别来自特定cgroup任务的数据包,并且进行网络限制
blkio 9 52 1 ##对块设备的IO进行限制
perf_event 11 2 1 ##允许使用perf工具来监控cgroup
hugetlb 2 2 1
pids 7 52 1 ##限制任务的数量
net_prio 5 2 1
[root@cloud ~]#
-
Hierachy(层级):层级有一系列的cgroup以一个树状结构排列而成,每个层级通过绑定对应的子系统进行资源控制。层级中的cgroup节点可以包含0个或者多个子节点,子节点继承父节点挂载的子系统。一个操作系统中可以有多个层级
cgroups的文件系统接口
- cgroups以文件的方式提供应用接口,我们可以通过mount命令来查看cgroups默认的挂载点
[root@cloud ~]# mount | grep cgroup
tmpfs on /sys/fs/cgroup type tmpfs (ro,nosuid,nodev,noexec,mode=755)
cgroup on /sys/fs/cgroup/systemd type cgroup (rw,nosuid,nodev,noexec,relatime,xattr,release_agent=/usr/lib/systemd/systemd-cgroups-agent,name=systemd)
cgroup on /sys/fs/cgroup/hugetlb type cgroup (rw,nosuid,nodev,noexec,relatime,hugetlb)
cgroup on /sys/fs/cgroup/memory type cgroup (rw,nosuid,nodev,noexec,relatime,memory)
cgroup on /sys/fs/cgroup/cpu,cpuacct type cgroup (rw,nosuid,nodev,noexec,relatime,cpuacct,cpu)
cgroup on /sys/fs/cgroup/net_cls,net_prio type cgroup (rw,nosuid,nodev,noexec,relatime,net_prio,net_cls)
cgroup on /sys/fs/cgroup/devices type cgroup (rw,nosuid,nodev,noexec,relatime,devices)
cgroup on /sys/fs/cgroup/pids type cgroup (rw,nosuid,nodev,noexec,relatime,pids)
cgroup on /sys/fs/cgroup/cpuset type cgroup (rw,nosuid,nodev,noexec,relatime,cpuset)
cgroup on /sys/fs/cgroup/blkio type cgroup (rw,nosuid,nodev,noexec,relatime,blkio)
cgroup on /sys/fs/cgroup/freezer type cgroup (rw,nosuid,nodev,noexec,relatime,freezer)
cgroup on /sys/fs/cgroup/perf_event type cgroup (rw,nosuid,nodev,noexec,relatime,perf_event)
[root@cloud ~]#
//第一行的tmpfs说明/sys/fs/cgroup 目录下的文件都是存在于内存中的临时文件。
//第二行的挂载点/sys/fscgroup/systemd用于systemd系统对cgroups的支持
//其余挂载点则是内核支持的各个子系统的根级层级结构
systemd依赖于cgroups:要理解systemd与cgroups的关系,我们需要先区分cgroups的两个方面:层级结构(A)和资源控制(B)。首先cgroups是以层级结构组织并且标识进程的一种方式,同时它也是在该层级结构上执行资源限制的一种方式。我们简单的把cgroups的层级结构称为A,把cgroups的资源控制能力称为B。
对于systemd来说,层级结构是必须的,如果没有层级结构,systemd将不能很好的工作。而资源限制则是可选的,如果你不需要对资源进行控制,那么在编译Linux内核时完全可以去掉B相关的编译选项。
以下都是对cgroup的资源限制的相关操作。
二.stress工具测试容器cpu和内存
- stress是用来测试cpu内存的负载,通过在两个容器分别执行stress -c 1,这将会给系统一个随机负载,产生一个进程,这个进程会反复不停地计算由rand()产生地随机数的平方根,直到资源耗尽。
- 首先使用Dockerfile创建一个基于centos的stress的工具镜像
[root@cloud ~]# ls
stress
[root@cloud ~]# cd stress/
[root@cloud stress]# cat Dockerfile
FROM centos
MAINTAINER this is stress images
RUN yum install -y wget
RUN wget -O /etc/yum.repos.d/epel.repo http://mirrors.aliyun.com/repo/epel-7.repo
RUN yum install -y stress
[root@cloud stress]# docker build -t centos:stress .
Successfully built f188ad991193
Successfully tagged centos:stress
[root@cloud stress]#
[ro