一. Cgroups介紹
默認cgroups配置文件在/etc/cgconfig.conf中,具體的掛載目錄請參見配置文件。
重新啟動:/etc/init.d/cgconfigrestart
安裝包:yum install libcgroup libcgroup-tools
二. Cgroups基本概念
1. 控制組(controlgroup)。
控制組就是一組按照某種標准划分的進程。Cgroups中的資源控制都是以控制組為單位實現。一個進程可以加入到某個控制組,也從一個進程組遷移到另一個控制組。一個進程組的進程可以使用cgroups以控制組為單位分配的資源,同時受到cgroups以控制組為單位設定的限制。
2. 層級(hierarchy)。
控制組可以組織成hierarchical的形式,既一顆控制組樹。控制組樹上的子節點控制組是父節點控制組的孩子,繼承父控制組的特定的屬性。
3. 子系統(subsytem)。
一個子系統就是一個資源控制器,比如cpu子系統就是控制cpu時間分配的一個控制器。子系統必須附加(attach)到一個層級上才能起作用,一個子系統附加到某個層級以后,這個層級上的所有控制族群都受到這個子系統的控制。可用子系統:
· blkio--這個子系統為塊設備設定輸入/輸出限制,比如物理設備(磁盤,固態硬盤,USB等等)。
· cpu--這個子系統使用調度程序提供對CPU的cgroup任務訪問。
· cpuacct--這個子系統自動生成cgroup中任務所使用的CPU報告。
· cpuset--這個子系統為cgroup中的任務分配獨立CPU(在多核系統)和內存節點。
· devices--這個子系統可允許或者拒絕cgroup中的任務訪問設備。
· freezer--這個子系統掛起或者恢復cgroup中的任務。
· memory--這個子系統設定cgroup中任務使用的內存限制,並自動生成由那些任務使用的內存資源報告。
· net_cls--這個子系統使用等級識別符(classid)標記網絡數據包,可允許Linux流量控制程序(tc)識別從具體cgroup中生成的數據包。
· ns--名稱空間子系統。
三. 幾個常用示例
1. CPU使用時間(使用率)限制
mkdir /cgroup/cpu/limit#創建CPU控制組limit,或cgcreate -g cpu:/limit
echo 50000> /cgroup/cpu/limit/cpu.cfs_quota_us #將cpu.cfs_quota_us設置為50000,相當於cpu.cfs_period_us值100000的50%,或cgset-r cpu.cfs_quota_us=50000 limit
echo $pid> /cgroup/cpu/limit/tasks #將需要限制CPU使用率的的進程ID寫到tasks中,或cgclassify -g cpu:limit $pid
echo ‘’ >/cgroup/cpu/limit/tasks #取消限制
rmdir/cgroup/cpu/limit #刪除CPU控制組limit,或cgdelete cpu:/limit
2. CPU資源綁定
mkdir/cgroup/cpuset/limit #創建CPU設置控制組limit,或cgcreate -g cpuset:/limit
echo ‘0-2,16’/cgroup/cpuset/limit/cpuset.cpus #將所綁定的CPU核ID寫入到cpuset.cpus中,或cgset -r cpuset.cpus=‘0-2,16’ limit
echo $pid> /cgroup/cpuset/limit/ tasks #將需要綁定CPU核心的進程ID寫入到tasks中,或cgclassify -g cpuset:limit $pid
3. 內存資源限制
mkdir/cgroup/memory/limit #創建內存控制組limit
echo 104857600> /cgroup/memory/limit/memory.limit_in_bytes #分配100M內存給這個控制組
echo $pid> /cgroup/memory/limit/tasks #將需要限制內存使用的進程ID寫到tasks中,一旦進程內存超過配置的值,將發生OOM killer(Out-Of-Memory killer)
4. IO資源限制
mkdir /cgroup/blkio/limit#創建IO控制組limit
echo '252:2 1048576' > /cgroup/blkio/limit/blkio.throttle.read_bps_device #限制設置252:2讀速度為1M/s,252:2為對應的主設備號和副設備號,可能通過ls -l /dev/vda2 查看,后面的數字為限制帶寬
echo $pid> /cgroup/blkio/limit/tasks #將需要限制IO的進程ID寫入到tasks中
四. 常用cgroups參數
通過上面,可以看到調整某個組里面的參數,並且將進程ID加入到該組中,就可以對進程進行資源控制,以下是可能用到的相關子系統的參數:
1. blkio
1.1. blkio.weight
指定cgroup默認可用訪問塊I/O的相對比例(加權),范圍在100到1000。這個值可由具體設備的blkio.weight_device參數覆蓋。例如:如果將cgroup訪問塊設備的默認加權設定為500,請運行:
echo 500 > blkio.weight
1.2. blkio.weight_device
指定對cgroup中可用的具體設備I/O訪問的相對比例(加權),范圍是100到1000。這個值可由為設備指定的blkio.weight參數覆蓋。例如:如果為訪問/dev/sda的cgroup分配加權500,請運行:
echo "8:0 500" > blkio.weight_device
1.3. blkio.throttle.read_bps_device
此參數用於設定設備執行“讀”操作字節的上限。“讀”的操作率以每秒的字節數來限定。bytes_per_second是“讀”操作可被執行的上限率。例如,讓/dev/sda設備運行“讀”操作的最大速率是10MBps,請運行:
echo "8:0 10485760" >/cgroup/blkio/test/blkio.throttle.read_bps_device
1.4. blkio.throttle.write_bps_devicev
此參數用於設定設備執行“寫”操作次數的上限。“寫”的操作率用“字節/秒”來表示。bytes_per_second是“寫”操作可被執行的上限率。例如,讓/dev/sda設備執行“寫”操作的最大比率為10MBps,請運行:
echo "8:0 10485760"> /cgroup/blkio/test/blkio.throttle.write_bps_device
1.5. blkio.throttle.read_iops_device
此參數用於設定設備執行“讀”操作次數的上限。“讀”的操作率以每秒的操作次數來表示。operations_per_second是“讀”可被執行的上限率。例如:如要設定/dev/sda設備執行“讀”的最大比率為10次/秒,請運行:
echo "8:0 10"> /cgroup/blkio/test/blkio.throttle.read_iops_device
1.6. blkio.throttle.write_iops_device
此參數用於設定設備執行“寫”操作次數的上限。“寫”的操作率以每秒的操作次數來表示。operations_per_second是“寫”操作可被執行的上限率。例如:如要讓/dev/sda設備執行“寫”操作的最大比率為10次/秒,請運行:
echo "8:0 10">/cgroup/blkio/test/blkio.throttle.write_iops_device
2. cpu
2.1. cpu.shares
包含用來指定在cgroup中的任務可用的相對共享CPU時間的整數值。例如:在兩個cgroup中都將cpu.shares設定為1的任務將有相同的CPU時間,但在cgroup中將cpu.shares設定為2的任務可使用的CPU時間是在cgroup中將cpu.shares設定為1的任務可使用的CPU時間的兩倍。
2.2. cpu.cfs_period_us
此參數可以設定重新分配cgroup可用CPU資源的時間間隔,單位為微秒(μs,這里以“us”表示)。如果一個cgroup中的任務在每1秒鍾內有0.2秒的時間可存取一個單獨的CPU,則請將cpu.rt_runtime_us設定為2000000,並將cpu.rt_period_us設定為1000000。cpu.cfs_quota_us參數的上限為1秒,下限為1000微秒。
2.3. cpu.cfs_quota_us
此參數可以設定在某一階段(由cpu.cfs_period_us規定)某個cgroup中所有任務可運行的時間總量,單位為微秒(μs,這里以"us"代表)。一旦cgroup中任務用完按配額分得的時間,它們就會被在此階段的時間提醒限制流量,並在進入下階段前禁止運行。如果cgroup中任務在每1秒內有0.2秒,可對單獨CPU進行存取,請將cpu.cfs_quota_us設定為200000,cpu.cfs_period_us設定為1000000。請注意,配額和時間段參數都根據CPU來操作。例如,如要讓一個進程完全利用兩個CPU,請將cpu.cfs_quota_us設定為200000,cpu.cfs_period_us設定為100000。如將cpu.cfs_quota_us的值設定為-1,這表示cgroup不需要遵循任何CPU時間限制。這也是每個cgroup的默認值(rootcgroup除外)。
3. cpuset
3.1. cpuset.cpus(強制)
設定該cgroup任務可以訪問的CPU。這是一個逗號分隔列表,格式為ASCII,小橫線("-")代表范圍。例如:
0-2,16 表示CPU0、1、2和16。
3.2. cpuset.mems(強制)
設定該cgroup中任務可以訪問的內存節點。這是一個逗號分隔列表,格式為ASCII,小橫線("-")代表范圍。例如:
0-2,16 表示內存節點0、1、2和16。
4. memory
4.1. memory.limit_in_bytes
設定用戶內存(包括文件緩存)的最大用量。如果沒有指定單位,則該數值將被解讀為字節。但是可以使用后綴代表更大的單位——k或者K代表千字節,m或者M代表兆字節,g或者G代表千兆字節。您不能使用memory.limit_in_bytes限制rootcgroup;您只能對層級中較低的群組應用這些值。在memory.limit_in_bytes中寫入-1可以移除全部已有限制。
4.2. memory.memsw.limit_in_bytes
設定內存與swap用量之和的最大值。如果沒有指定單位,則該值將被解讀為字節。但是可以使用后綴代表更大的單位——k或者K代表千字節,m或者M代表兆字節,g或者G代表千兆字節。您不能使用memory.memsw.limit_in_bytes來限制rootcgroup;您只能對層級中較低的群組應用這些值。在memory.memsw.limit_in_bytes中寫入-1可以刪除已有限制。
4.3. memory.force_empty
當設定為0時,該cgroup中任務所用的所有頁面內存都將被清空。這個接口只可在cgroup沒有任務時使用。如果無法清空內存,請在可能的情況下將其移動到父cgroup中。移除cgroup前請使用memory.force_empty參數以免將廢棄的頁面緩存移動到它的父cgroup中。
4.4. memory.swappiness
將kernel傾向設定為換出該cgroup中任務所使用的進程內存,而不是從頁高速緩沖中再生頁面。這與/proc/sys/vm/swappiness為整體系統設定的傾向、計算方法相同。默認值為60。低於60會降低kernel換出進程內存的傾向;高於0會增加kernel換出進程內存的傾向。高於100時,kernel將開始換出作為該cgroup中進程地址空間一部分的頁面。請注意:值0不會阻止進程內存被換出;系統內存不足時,換出仍可能發生,因為全局虛擬內存管理邏輯不讀取該cgroup值。要完全鎖定頁面,請使用mlock()而不是cgroup。您不能更改以下群組的swappiness:
rootcgroup,它使用/proc/sys/vm/swappiness設定的swappiness;
有子群組的cgroup。
4.5. memory.oom_control
包含標簽(0或者1),它可以為cgroup啟用或者禁用“內存不足”(OutofMemory,OOM)終止程序。如果啟用(0),嘗試消耗超過其允許內存的任務會被OOM終止程序立即終止。默認情況下,所有使用memory子系統的cgroup都會啟用OOM終止程序。要禁用它,請在memory.oom_control文件中寫入1:
echo 1 > /cgroup/memory/lab1/memory.oom_control
禁用OOM殺手程序后,嘗試使用超過其允許內存的任務會被暫停,直到有額外內存可用。memory.oom_control文件也在under_oom條目下報告當前cgroup的OOM狀態。如果該cgroup缺少內存,則會暫停它里面的任務。under_oom條目報告值為1。memory.oom_control文件可以使用API通知來報告OOM情況的出現。
5. net_cls
net_cls子系統使用等級識別符(classid)標記網絡數據包,這讓Linux流量管控器(tc)可以識別從特定cgroup中生成的數據包。可配置流量管控器,讓其為不同cgroup中的數據包設定不同的優先級。
5.1. net_cls.classid
net_cls.classid包含表示流量控制handle的單一數值。從net_cls.classid文件中讀取的classid值是十進制格式,但寫入該文件的值則為十六進制格式。例如:0x100001表示控制點通常寫為iproute2所用的10:1格式。在net_cls.classid文件中,將以數字1048577表示。這些控制點的格式為:0xAAAABBBB,其中AAAA是十六進制主設備號,BBBB是十六進制副設備號。您可以忽略前面的零;0x10001與0x00010001一樣,代表1:1。以下是在net_cls.classid文件中設定10:1控制點的示例:
echo 0x100001 > /cgroup/net_cls/red/net_cls.classid
6. net_prio
網絡優先權(net_prio)子系統可以為各個cgroup中的應用程序動態配置每個網絡接口的流量優先級。網絡優先級是一個分配給網絡流量的數值,可在系統內部和網絡設備間使用。網絡優先級用來區分發送、排隊以net_prio.prioidx只讀文件。它包含一個特有整數值,kernel使用該整數值作為這個cgroup的內部代表。net_prio.ifpriomap包含優先級圖譜,這些優先級被分配給源於此群組進程的流量以及通過不同接口離開系統的流量。
echo "eth0 5"> /cgroup/net_prio/iscsi/net_prio.ifpriomap
上述指令將強制設定任何源於iscsinet_priocgroup進程的流量和eth0網絡接口傳出的流量的優先級為5。父cgroup也有可寫入的net_prio.ifpriomap文件,可以設定系統默認優先級。