cgroups测试cpu bug

发布于:2025-07-31 ⋅ 阅读:(23) ⋅ 点赞:(0)

您遇到的 cgroup CPU 份额控制效果不明显 的问题,核心原因在于对 Linux 完全公平调度器 (CFS) 机制的理解偏差及实践场景的特殊性。以下是详细分析和解决方案:


一、关键认知纠偏

❌ 常见误解:“shares=200 vs 800 → 严格 20%:80% 硬性保障”

真实规则

  • cpu.shares 定义的是 相对优先级权重,而非绝对资源配额。
  • 当单一 cgroup 内有多个进程时,shares 决定它们之间的资源争夺比例;
  • 若整组仅一个进程,该进程可获得所在层级的全部可用 CPU 时间片(不受 shares 数值限制)。

👉 因此您的测试场景中:

  • lesscpu 组的 md5summorecpu 组的 sha1sum 各自独占自己所在层的全额 CPU 资源,二者本质上处于平等竞争地位!

二、实验设计缺陷拆解

环节 现存问题 影响程度
并发模型 单进程/单组 → 无组内竞争 ⭐⭐⭐⭐⭐
导致 shares 失效
观测工具 top 仅反映瞬时采样 ⭐⭐⭐
无法捕捉长期统计规律
负载特性 密码学计算非满负荷 ⭐⭐
未触发真正的 CPU 争抢
环境干扰 未隔离其他系统进程 ⭐⭐⭐⭐
后台进程稀释效果

三、科学验证方案 & 预期现象

🔧 修正版测试步骤
# 创建两组并设置份额
mkdir -p /sys/fs/cgroup/cpu/group1
echo 200 > /sys/fs/cgroup/cpu/group1/cpu.shares
mkdir -p /sys/fs/cgroup/cpu/group2
echo 800 > /sys/fs/cgroup/cpu/group2/cpu.shares

# 同时启动两个高负载进程(强制持续竞争)
cgexec -g cpu:group1 yes > /dev/null &   # PID_A
cgexec -g cpu:group2 yes > /dev/null &   # PID_B
📊 正确观测方式
工具 用法 预期结果
ps -o comm,pid,psr,ni -C 'yes' 实时查看进程亲和性+优先级 PID_B 的 ni 值应为 PID_A 的 4 倍
pidstat -u -h <PID_A> <PID_B> 1 每秒输出两进程的 CPU 占比 长期统计下 B : A ≈ 4:1
cat /proc/<PID>/schedstat 查看调度器原始数据 policy 字段显示 CFS
📌 关键原理说明
  • 只有当同一层级存在多个活跃进程时,CFS 才会依据 shares 进行动态调谐。
  • yes 命令通过死循环制造持续满负荷,迫使调度器频繁介入分配。
  • pidstat 的统计周期越长(如观察 60 秒),结果越趋近理论比例。

四、为何原始测试无效?

  1. 伪并行假象

    • 您先后执行两条独立命令,实质是串行操作而非真正并发。
    • md5sum /dev/zero 虽看似永续,实则单线程纯计算无阻塞,不会主动释放 CPU。
  2. top 命令局限性

    • 默认 3 秒刷新间隔 + 仅显示当前时刻快照 → 易受进程调度时机影响。
    • 缺乏历史累计数据支撑,难以发现微小差异。
  3. 算法轻量化

    • MD5/SHA1 属于轻量级加密算法,现代 CPU 可在很少时钟周期内完成单次运算。
    • 真实负载远低于 CPU 最大吞吐量,无法暴露调度器干预效果。

五、进阶验证建议

🚀 强化竞争压力测试
# 在每组启动多个同名进程加剧竞争
for i in {1..5}; do cgexec -g cpu:group1 sleep 100 & done
for i in {1..5}; do cgexec -g cpu:group2 sleep 100 & done

👉 此模式下,组内 5 个进程将严格按照 200:800 的比例分享 CPU 时间片。

🛠️ 可视化监控方案
# 安装图形化监控工具
yum install gnuplot htop -y

# 持续记录 CPU 使用率
while true; do 
    ps -o %cpu,comm -C 'yes' | grep -v PID | awk '{print strftime("%H:%M:%S") "\t" $1}' >> data.log; 
    sleep 1; 
done

# 生成趋势图
gnuplot <<EOF
set title "CPU Allocation Over Time"
set xlabel "Time"
set ylabel "CPU %"
plot "data.log" using 1:2 with lines title "Group1", \
     "data.log" using 1:3 with lines title "Group2"
EOF

六、结论与最佳实践

场景 推荐方案 备注
开发调试 使用 stress-ng --cpu 2 生成可控负载 精准模拟 CPU 压力
生产环境 结合 nice/ionice 调整优先级 配合 cgroup 实现三级管控
监控取证 perf record -ag + perf report 获取调度器事件明细

核心原则

CPU shares 只在 组内多进程共存 时生效,其本质是 相对权重而非绝对配额。若要实现严格资源隔离,需改用 quota 或转向更新的 cgroup v2 + controllers 体系。


网站公告

今日签到

点亮在社区的每一天
去签到