4. 调度器参数全景:kernel.sched_* 关键参数列表与作用域(sysctl vs cgroup)

在 Linux 进程调度调优中,kernel.sched_* 参数是控制调度器行为的核心旋钮。这些参数分布在两个作用域:系统全局(sysctl) 和 控制组(cgroup)。理解它们的区别、层级关系以及适用场景,是精准调优 MySQL 查询延迟的前提。

核心原则:sysctl 参数设置全局默认值,cgroup 参数在子系统内覆盖或细化调度策略。对于数据库实例隔离场景,cgroup 级别的参数调整比全局修改更安全、更精准。

4.1 参数作用域对比:sysctl vs cgroup

下表从配置范围、生效时机、持久化方式、典型场景四个维度,对比两种作用域的核心差异:

对比维度 sysctl(全局) cgroup(局部)
配置范围 整个系统所有进程 仅作用于 cgroup 内的进程组
生效时机 立即生效,重启后需重新设置或写入 /etc/sysctl.conf 写入 cgroup 控制文件后即时生效,重启后随 cgroup 树重建
持久化方式 /etc/sysctl.conf 或 /etc/sysctl.d/*.conf cgroup 配置文件(如 /etc/cgconfig.conf)或 systemd 单元文件
典型场景 统一调整调度器基础行为(如唤醒抢占、带宽控制) 数据库容器/虚拟机隔离、延迟敏感型任务分组
调优提示:在 MySQL 专用主机上,优先使用 cgroup v2 的 cpu.weight 和 cpu.max 控制数据库进程组的 CPU 份额与上限,避免全局修改 kernel.sched_* 影响其他系统进程。

4.2 关键 kernel.sched_* 参数列表

以下参数是调度器调优的核心集合,按功能模块分组列出。每个参数均标注了作用域(G=全局 sysctl,C=cgroup 可覆盖)和典型值范围。

参数名 作用域 默认值 功能描述 MySQL 调优建议
kernel.sched_min_granularity_ns G 3000000 (3ms) CFS 调度器的最小执行粒度,控制进程被抢占前的最短运行时间 对延迟敏感型查询,可适当降低至 1-2ms,减少调度切换开销
kernel.sched_latency_ns G 18000000 (18ms) CFS 调度周期,决定每个进程在周期内至少获得一次调度的总时间窗口 高并发 MySQL 场景可增大至 24-36ms,提升吞吐稳定性
kernel.sched_wakeup_granularity_ns G 4000000 (4ms) 唤醒抢占阈值,新唤醒进程需比当前进程虚拟时间小多少才触发抢占 降低至 1-2ms 可加速短查询唤醒,但需注意增加上下文切换
kernel.sched_migration_cost_ns G 500000 (0.5ms) 进程迁移代价估算,影响负载均衡器判断是否值得迁移进程 NUMA 架构下可增大至 1-2ms,减少跨节点迁移导致的延迟抖动
kernel.sched_autogroup_enabled G 1 自动分组功能,将同一会话的进程自动分配到调度组 MySQL 专用主机建议关闭(设为 0),避免自动分组干扰手动调优
cpu.weight (cgroup v2) C 100 控制组内 CPU 权重,决定相对份额 MySQL 容器设为 200-500,确保数据库进程获得更高 CPU 比例
cpu.max (cgroup v2) C max 100000 控制组 CPU 使用上限(配额/周期),格式:$quota $period 设置 80000 100000 限制 MySQL 最多使用 80% CPU,防止突发占满
注意:kernel.sched_autogroup_enabled 在桌面环境或多用户服务器上有用,但在数据库专用节点上,自动分组可能掩盖手动设置的 cgroup 权重效果。建议在调优前确认其状态。

4.3 参数层级关系:从全局到 cgroup 的覆盖链

调度器参数的生效遵循明确的层级覆盖规则。下图展示了从 sysctl 全局默认值到 cgroup 局部覆盖的完整链路:

调度器参数层级覆盖链 sysctl 全局默认值 kernel.sched_* 参数 cgroup v2 控制器 cpu.weight / cpu.max / cpu.uclamp.latency_sensitive MySQL 进程组 高权重 + 延迟敏感标记 后台/批处理进程组 低权重 + 无延迟敏感标记 覆盖规则 cgroup 参数覆盖 sysctl 全局值;未设置的 cgroup 参数继承全局默认值

从图中可以看出:sysctl 全局参数 为整个系统提供基准配置;cgroup v2 控制器 在子系统层面提供更精细的覆盖能力;最终 进程组 根据其 cgroup 配置获得差异化的调度行为。MySQL 进程组通常配置高权重和延迟敏感标记,而后台任务组则使用低权重。

4.4 参数生效验证方法

修改参数后,必须验证其是否按预期生效。以下是针对两种作用域的验证命令:

# 查看 sysctl 全局参数当前值
sysctl kernel.sched_min_granularity_ns
sysctl kernel.sched_latency_ns
sysctl kernel.sched_wakeup_granularity_ns

# 查看 cgroup v2 参数(以 MySQL 容器为例)
cat /sys/fs/cgroup/system.slice/docker-<container_id>.scope/cpu.weight
cat /sys/fs/cgroup/system.slice/docker-<container_id>.scope/cpu.max

# 使用 perf 观察调度事件(验证参数效果)
perf stat -e sched:sched_switch,sched:sched_wakeup -p <mysql_pid> sleep 10
验证要点:修改 kernel.sched_wakeup_granularity_ns 后,使用 perf 观察 sched:sched_switch 事件频率。如果频率显著上升,说明抢占阈值降低生效,但需评估上下文切换开销是否在可接受范围内。

4.5 参数调优的典型组合模式

针对 MySQL 查询延迟优化,以下组合模式经过生产环境验证:

调优目标 sysctl 参数调整 cgroup 参数调整 适用场景
低延迟优先 sched_min_granularity_ns → 1ms
sched_wakeup_granularity_ns → 1ms
cpu.weight → 500
cpu.uclamp.latency_sensitive → 1
OLTP 在线交易,要求 P99 延迟 < 10ms
吞吐优先 sched_latency_ns → 24ms
sched_migration_cost_ns → 1ms
cpu.weight → 200
cpu.max → 90000 100000
OLAP 分析查询,追求 QPS 最大化
混合负载隔离 sched_autogroup_enabled → 0 MySQL 组:cpu.weight → 400
后台组:cpu.weight → 50
同一主机运行 MySQL + 监控/备份任务
风险提示:过度降低 sched_min_granularity_ns 和 sched_wakeup_granularity_ns 会导致上下文切换暴增(可能超过 10 万次/秒),反而增加调度延迟。建议每次调整后使用 vmstat 1 监控 cs(context switch)列,确保增幅在 20% 以内。

4.6 参数持久化配置示例

以下是一个完整的持久化配置示例,同时包含 sysctl 和 cgroup 设置:

# /etc/sysctl.d/99-mysql-sched.conf
# MySQL 专用调度器参数调优
kernel.sched_min_granularity_ns = 2000000
kernel.sched_latency_ns = 24000000
kernel.sched_wakeup_granularity_ns = 2000000
kernel.sched_migration_cost_ns = 1000000
kernel.sched_autogroup_enabled = 0

# 应用 sysctl 配置
sysctl --system
# cgroup v2 配置(使用 systemd 单元文件覆盖)
# /etc/systemd/system/mysql.service.d/override.conf
[Service]
# CPU 权重:相对份额
CPUWeight=400
# CPU 使用上限:最多使用 4 个核(400000/100000)
CPUQuota=400%
# 延迟敏感标记
AllowedCPUs=0-7

# 重新加载 systemd 并重启 MySQL
systemctl daemon-reload
systemctl restart mysql
最佳实践:在修改 sysctl 参数前,先使用 sysctl -a | grep sched_ 记录当前值,以便回滚。cgroup 参数建议通过 systemd 单元文件管理,避免手动写入 /sys/fs/cgroup 导致重启后丢失。