什么是 cgroup
📚️Reference:
control groups(控制组),通常被称为 cgroup,是 Linux 内核的一项性能。它容许将过程组织成分层的组,而后限度和监控各种资源的应用。内核的 cgroup 接口是通过一个叫做 cgroupfs 的伪文件系统提供的。分组是在外围的 cgroup 内核代码中实现的,而资源跟踪和限度是在一组每个资源类型的子系统中实现的(内存、CPU 等等)。
cgroup 是容器和云原生的底层技术栈. kubelet 和 CRI 都须要对接 cgroup 来强制执行为 Pod 和容器治理资源,即: requests/limits 和 cpu/memory。
Linux 中有两个 cgroup 版本:cgroup v1 和 cgroup v2。cgroup v2 是新一代的 cgroup API。
Kubernetes 自 v1.25 起 cgroup2 个性正式 stable.
cgroup v2 有哪些劣势
📚️Reference:
cgroup v2 提供了一个具备加强资源管理能力的对立控制系统。
cgroup v2 对 cgroup v1 进行了多项改良,例如:
- API 中单个对立的层次结构设计
- 更平安的子树委派给容器
- 更新的性能个性,例如压力阻塞信息(Pressure Stall Information,PSI)
跨多个资源的加强资源分配治理和隔离
- 对立核算不同类型的内存调配(网络内存、内核内存等)
- 思考非即时资源变动,例如页面缓存回写
一些 Kubernetes 个性专门应用 cgroup v2 来加强资源管理和隔离。例如,MemoryQoS 个性改良了内存 QoS 并依赖于 cgroup v2 原语。
应用 cgroup v2 前提
📚️Reference:
cgroup v2 具备以下要求:
操作系统发行版启用 cgroup v2
- Ubuntu(从 21.10 开始,举荐 22.04+)
- Debian GNU/Linux(从 Debian 11 Bullseye 开始)
- Fedora(从 31 开始)
- RHEL 和相似 RHEL 的发行版(从 9 开始)
- …
- Linux 内核为 5.8 或更高版本
容器运行时反对 cgroup v2。例如:
- containerd v1.4 和更高版本
- cri-o v1.20 和更高版本
- kubelet 和容器运行时被配置为应用 systemd cgroup 驱动
应用 cgroup v2
📝Notes:
这里以 Debian 11 Bullseye + containerd v1.4 为例.
启用并查看 Linux 节点的 cgroup v2
Debian 11 Bullseye 默认已启用 cgroup v2.
能够通过如下命令验证:
stat -fc %T /sys/fs/cgroup/
- 对于 cgroup v2,输入为
cgroup2fs
。 - 对于 cgroup v1,输入为
tmpfs
。
如果没有启用, 能够通过在 /etc/default/grub
下的 GRUB_CMDLINE_LINUX
中增加 systemd.unified_cgroup_hierarchy=1
,而后执行 sudo update-grub
📝Notes:
如果是树莓派, 规范 Raspberry Pi OS 装置时不会启用cgroups
。须要cgroups
来启动 systemd 服务。能够通过将cgroup_memory=1 cgroup_enable=memory systemd.unified_cgroup_hierarchy=1
附加到/boot/cmdline.txt
来启用cgroups
。
并重启失效
kubelet 应用 systemd cgroup 驱动
kubeadm 反对在执行 kubeadm init
时,传递一个 KubeletConfiguration
构造体。KubeletConfiguration
蕴含 cgroupDriver
字段,可用于管制 kubelet 的 cgroup 驱动。
阐明: 在版本 1.22 中,如果用户没有在 KubeletConfiguration
中设置 cgroupDriver
字段,kubeadm init
会将它设置为默认值 systemd
。
这是一个最小化的示例,其中显式的配置了此字段:
# kubeadm-config.yaml
kind: ClusterConfiguration
apiVersion: kubeadm.k8s.io/v1beta3
kubernetesVersion: v1.21.0
---
kind: KubeletConfiguration
apiVersion: kubelet.config.k8s.io/v1beta1
cgroupDriver: systemd
这样一个配置文件就能够传递给 kubeadm 命令了:
kubeadm init --config kubeadm-config.yaml
阐明:
Kubeadm 对集群所有的节点,应用雷同的 KubeletConfiguration
。KubeletConfiguration
寄存于 kube-system
命名空间下的某个 ConfigMap 对象中。
执行 init
、join
和 upgrade
等子命令会促使 kubeadm 将 KubeletConfiguration
写入到文件 /var/lib/kubelet/config.yaml
中,继而把它传递给本地节点的 kubelet。
containerd 应用 systemd cgroup 驱动
编辑 /etc/containerd/config.toml
:
[plugins.cri.containerd.runtimes.runc.options]
SystemdCgroup = true
降级监控组件以反对 cgroup v2 监控
📚️Reference:
cgroup v2 应用一个与 cgroup v1 不同的 API,因而如果有任何利用间接拜访 cgroup 文件系统,则须要将这些利用更新为反对 cgroup v2 的版本。例如:
- 一些第三方监控和平安代理可能依赖于 cgroup 文件系统。你要将这些代理更新到反对 cgroup v2 的版本。
- 如果以独立的 DaemonSet 的模式运行 cAdvisor 以监控 Pod 和容器,需将其更新到 v0.43.0 或更高版本。
- 如果你应用 JDK,举荐应用 JDK 11.0.16 及更高版本或 JDK 15 及更高版本,以便齐全反对 cgroup v2。
实现🎉🎉🎉
总结
Kubernetes 自 v1.25 起 cgroup2 个性正式 stable. cgroup2 相比 cgroup v1 有以下劣势:
- API 中单个对立的层次结构设计
- 更平安的子树委派给容器
- 更新的性能个性,例如压力阻塞信息(Pressure Stall Information,PSI)
-
跨多个资源的加强资源分配治理和隔离
- 对立核算不同类型的内存调配(网络内存、内核内存等)
- 思考非即时资源变动,例如页面缓存回写
举荐在应用 Kubernetes v1.25 及以上版本时, 应用反对 cgroup v2 的 linux 和 CRI. 并启用 Kubernetes 的 cgroup v2 性能.
📚️参考文档
- 对于 cgroup v2 | Kubernetes
- 配置 cgroup 驱动 | Kubernetes
- 容器运行时 | Kubernetes
本文由东风微鸣技术博客 EWhisper.cn 编写!