LWN: cgroup 新增 kill 功能!
關(guān)注了就能看到更多這么棒的文章哦~
A "kill" button for control groups
By Jonathan Corbet
May 3, 2021
DeepL assisted translation
https://lwn.net/Articles/855049/
內(nèi)核的 cgroup 機(jī)制(control group)是用來(lái)劃分進(jìn)程并為每個(gè)進(jìn)程提供資源保證(和限制)而存在的。在一個(gè)正確配置好的 cgroup 中運(yùn)行的進(jìn)程不能剝奪在其他 group 中運(yùn)行的進(jìn)程所預(yù)留的資源(CPU 時(shí)間、內(nèi)存、I/O 帶寬等),并且同樣不受其他進(jìn)程的干擾。除了少數(shù)例外情況以外,cgroup 不會(huì)直接對(duì)進(jìn)程采取行動(dòng),而 Christian Brauner 的 cgroup.kill 這組 patch set 就為了成為這些例外之一。
在目前的內(nèi)核中,對(duì) cgroup 內(nèi)的進(jìn)程采取行動(dòng)的一種方式是通過(guò) "freezer",也就是用來(lái)暫停(或恢復(fù))這個(gè) cgroup 中所包含的進(jìn)程。不過(guò),除此之外,很少有 cgroup 的開(kāi)關(guān)會(huì)直接影響到進(jìn)程的狀態(tài)。Brauner 的 patch set 在每個(gè) non-root 的 cgroup 中增加了一個(gè)控制文件,名為 "kill"。它的效果正如它的名字那樣。向該文件寫(xiě)入 "1" 會(huì)將導(dǎo)致該 group 中的所有進(jìn)程立即死亡(更正確的說(shuō)法是它會(huì)立即觸發(fā)向每個(gè)進(jìn)程發(fā)送一個(gè) SIGKILL 信號(hào))。如果 cgroup 里包含了其他的 cgroup,那也會(huì)一起被消滅。等操作完成,該組通常會(huì)處于一個(gè)完全被清除干凈的狀態(tài)。
當(dāng)然,這種行為也有幾個(gè)例外。kill 操作的定義,是對(duì)一個(gè)進(jìn)程起作用。如果該進(jìn)程包含許多線程,那么它們都將被 kill。但是,如果相關(guān)的 cgroup 是在thread mode下,也就是允許一個(gè)進(jìn)程的多個(gè)線程分布在多個(gè) cgroup 中,這就可能導(dǎo)致不在目標(biāo) cgroup 中的線程也會(huì)被意外殺死。因此,如果試圖對(duì)以 thread mode 運(yùn)行的 cgroup 進(jìn)行 kill 操作,將會(huì)直接失敗。
同樣,kill 操作也不會(huì)殺死內(nèi)核線程,因?yàn)檫@可能導(dǎo)致一些不好的結(jié)果。對(duì)一個(gè)包含內(nèi)核線程的 cgroup 中可以寫(xiě)入 kill,但內(nèi)核線程本身繼續(xù)保持存活。因此在這種情況下,這個(gè) cgroup 在調(diào)用結(jié)束時(shí)不會(huì)是空的。
Brauner 列舉了這個(gè)功能的一些潛在用途。最明顯的用途之一是容器(container)管理。如果決定關(guān)閉一個(gè)容器,那么這個(gè) kill 操作是一種快速而直接的方式。Systemd 已經(jīng)將各個(gè) service 都按照 cgroup 來(lái)劃分管理了起來(lái),在需要時(shí),它可以使用這個(gè)操作作為一種更簡(jiǎn)單的方式來(lái)停止一項(xiàng) service。同樣地,用戶空間的 out-of-memory 管理也可以使用這個(gè)操作,在需要時(shí)直接讓整個(gè) cgroup 消失。kill 操作也可以是抵御 fork-bomb 的一種有效的手段,當(dāng)調(diào)用了 kill 操作時(shí),在 cgroup 里設(shè)置一個(gè)標(biāo)志,防止創(chuàng)建新的進(jìn)程,這樣就能有效組織正在進(jìn)行 fork 的進(jìn)程。
另一方面,這個(gè)功能可以被認(rèn)為是給系統(tǒng)中的每個(gè) cgroup 配備了一個(gè)大大的紅色按鈕,上面寫(xiě)著 "DO NOT PUSH THIS"。如果錯(cuò)誤寫(xiě)入 kill 節(jié)點(diǎn)有可能會(huì)對(duì)運(yùn)行中的系統(tǒng)造成巨大的損害。對(duì)于人們的這種擔(dān)憂,簡(jiǎn)單的回答就是:"那就別這么做",但不難想象,會(huì)有一些人希望在對(duì)這個(gè)文件加一些防護(hù)。
目前的 patch 是通過(guò)向目標(biāo) cgroup 中的每個(gè)進(jìn)程發(fā)送 SIGKILL 信號(hào)來(lái)生效的。沒(méi)有任何關(guān)于不能發(fā)送其他信號(hào)的限制,這個(gè)功能今后似乎也可能在有些情況下會(huì)有好處。kill() 系統(tǒng)調(diào)用可以發(fā)送任何信號(hào),最終可能也有需要讓 cgroup.kill 文件也允許其他信號(hào)。
到目前為止,對(duì)這組 patch 還沒(méi)有很多評(píng)論,也許部分原因是它還沒(méi)有傳播到 cgroup 郵件列表之外。對(duì)于代碼實(shí)現(xiàn)來(lái)說(shuō),可能沒(méi)有什么可以挑毛病的,因?yàn)榇a實(shí)現(xiàn)相當(dāng)直接,所以如果要說(shuō)有什么會(huì)導(dǎo)致這項(xiàng)工作暫時(shí)無(wú)法合入的話,那也一定是跟這個(gè)功能本身有關(guān)。不過(guò),似乎使用場(chǎng)景非常明顯,所以這個(gè) kill 開(kāi)關(guān)在不久的將來(lái)確實(shí)可能成為 cgroup 的一個(gè)功能。
全文完
LWN 文章遵循 CC BY-SA 4.0 許可協(xié)議。
長(zhǎng)按下面二維碼關(guān)注,關(guān)注 LWN 深度文章以及開(kāi)源社區(qū)的各種新近言論~
