【翻译】Linux 内核僵尸 cgroup 的清理

简介: 翻译自原文:https://lwn.net/Articles/787614/ Cgroup是linux内核中一种有效的资源管理机制,但是当cgroup本身成为一种资源问题时又会发生什么呢?在2019年的LSMM大会上,Roman Gushchin描述了一些他遇到的删除的cgroup会继续留在系统中的问题。其中有些已经被修复,但问题并没有被真正解决。 Cgroup是通过cgroup/cg

翻译自原文:https://lwn.net/Articles/787614/

Cgroup是linux内核中一种有效的资源管理机制,但是当cgroup本身成为一种资源问题时又会发生什么呢?在2019年的LSMM大会上,Roman Gushchin描述了一些他遇到的删除的cgroup会继续留在系统中的问题。其中有些已经被修复,但问题并没有被真正解决。

Cgroup是通过cgroup/cgroup2伪文件系统来管理的,可以通过删除伪文件系统中的文件目录来删除相应的cgroup。但事实上,Gushchin说到,当删除cgroup的目录后虽然用户态已经看不到它,但在内核中代表cgroup的结构体会一直存在直到所有对它的引用被释放。只要它依然存在,就会消耗相应的资源。

由于memory cgroup中的每个页都会引用该cgroup,使得该问题在memory cgroup上表现的尤为严重。只有当被删除的memory cgroup中的页都被回收掉,相应的引用都被释放,该memory cgroup才会彻底被删除,这可能会需要很长的时间,如果当中的一些页被活跃的使用,这些页可能永远不会被回收掉。另外,还有其他各种各样的问题,同样会导致删除的cgroup继续留在系统中。

僵尸cgroup虽然不会导致严重的后果,但依然是个问题。每个僵尸cgroup都会占用200KB的内存,随着僵尸cgroup的增加相应的内存消耗也会增加。同时这些僵尸cgroup会增加遍历cgroup树的开销。另外这些内存开销能够摆脱内存管理的统计。

有些导致僵尸cgroup产生的问题相对而言比较容易被处理,比如说在处理用户页的一个rounding错误会导致最后的页不会被回收掉。这个bug同时存在于cgroup v1和v2,已经被修复。另一个问题是有关内核栈的统计。该问题是在2016年转到使用vmalloced栈引入的。这些内核栈会统计到第一个分配它们的进程的所在cgroup中,当一个栈被一个新进程重新使用后,相应的统计并没有更新,这个问题也被修复了。

目前还没有被修复的一个问题是来自于slab对cgroup的引用,当从slab分配器中分配相应的slab对象时,相应的页会被统计到相应的cgroup上同时增加对该cgroup的引用,因此只有当上述slab对象的页被回收释放解除对该cgroup的引用,该cgroup才会最终被删除释放。但是在没有太大内存压力的情况下,这些slab 对象很难被回收释放。Gushchin写了个patch来施加一些额外的压力促使系统回收这些slab对象,但这个patch会导致XFS文件系统的性能回退,因此该patch也被回退了。目前他在进行另一个方案:当删除cgroup时把它的slab缓存移到到它的父组上。关于该方案的一组patch正在review过程中,希望这个问题在不久的将来能够得到解决。

还有一些潜在的问题如通过vmalloc分配的页以及per-cpu的页都容易产生对cgroup的潜在引用从而导致相应的cgroup无法被彻底删除。

在会议的最后,Michal Hocko提到问题的一部分是来自于memory cgroup结构体的大小,如果把这个结构体拆分成两部分并且当删除memory cgroup时只保留核心的那部分,可能会缓解该问题。但是Johannes Weiner回应说目前唯一可以彻底删除这些memory cgroup的是内存压力引起的回收,如果把它们变的更小,它们就会堆积的更深。看来尽管一些问题得到了解决,但是僵尸cgroup问题还会伴随我们一段时间。

目录
相关文章
|
9天前
|
Linux C语言
Linux内核队列queue.h
Linux内核队列queue.h
|
18天前
|
Linux Shell
Linux手动清理Linux脚本日志定时清理日志和log文件执行表达式
Linux手动清理Linux脚本日志定时清理日志和log文件执行表达式
72 1
|
28天前
|
存储 Shell Linux
【Shell 命令集合 系统设置 】Linux 生成并更新内核模块的依赖 depmod命令 使用指南
【Shell 命令集合 系统设置 】Linux 生成并更新内核模块的依赖 depmod命令 使用指南
30 0
|
28天前
|
Shell Linux C语言
【Shell 命令集合 系统设置 】⭐Linux 卸载已加载的内核模块rmmod命令 使用指南
【Shell 命令集合 系统设置 】⭐Linux 卸载已加载的内核模块rmmod命令 使用指南
29 1
|
2天前
|
算法 Linux 调度
深入理解Linux内核的进程调度机制
【4月更文挑战第17天】在多任务操作系统中,进程调度是核心功能之一,它决定了处理机资源的分配。本文旨在剖析Linux操作系统内核的进程调度机制,详细讨论其调度策略、调度算法及实现原理,并探讨了其对系统性能的影响。通过分析CFS(完全公平调度器)和实时调度策略,揭示了Linux如何在保证响应速度与公平性之间取得平衡。文章还将评估最新的调度技术趋势,如容器化和云计算环境下的调度优化。
|
7天前
|
算法 Linux 调度
深度解析:Linux内核的进程调度机制
【4月更文挑战第12天】 在多任务操作系统如Linux中,进程调度机制是系统的核心组成部分之一,它决定了处理器资源如何分配给多个竞争的进程。本文深入探讨了Linux内核中的进程调度策略和相关算法,包括其设计哲学、实现原理及对系统性能的影响。通过分析进程调度器的工作原理,我们能够理解操作系统如何平衡效率、公平性和响应性,进而优化系统表现和用户体验。
18 3
|
14天前
|
负载均衡 算法 Linux
深度解析:Linux内核调度器的演变与优化策略
【4月更文挑战第5天】 在本文中,我们将深入探讨Linux操作系统的核心组成部分——内核调度器。文章将首先回顾Linux内核调度器的发展历程,从早期的简单轮转调度(Round Robin)到现代的完全公平调度器(Completely Fair Scheduler, CFS)。接着,分析当前CFS面临的挑战以及社区提出的各种优化方案,最后提出未来可能的发展趋势和研究方向。通过本文,读者将对Linux调度器的原理、实现及其优化有一个全面的认识。
|
14天前
|
Ubuntu Linux
Linux查看内核版本
在Linux系统中查看内核版本有多种方法:1) 使用`uname -r`命令直接显示版本号;2) 通过`cat /proc/version`查看内核详细信息;3) 利用`dmesg | grep Linux`显示内核版本行;4) 如果支持,使用`lsb_release -a`查看发行版及内核版本。
36 6
|
17天前
|
Linux 内存技术
Linux内核读取spi-nor flash sn
Linux内核读取spi-nor flash sn
14 1
|
22天前
|
Linux Shell 调度
【Linux】进程排队的理解&&进程状态的表述&&僵尸进程和孤儿进程的理解
【Linux】进程排队的理解&&进程状态的表述&&僵尸进程和孤儿进程的理解