Slurm(Simple Linux Utility for Resource Management)是当今 HPC 领域最主流的集群资源调度与作业管理系统。它管理着全球 Top500 超算中超过半数以上的系统资源,从几节点的小型实验室集群到数万个节点的大型超算中心,Slurm 都提供了稳定、可扩展的调度能力。
Slurm 核心架构
+-----------------+ +-----------------+ +-----------------+
| slurmctld | <-> | slurmdbd | <-> | slurmd |
| (控制器) | | (记账数据库) | | (计算节点) |
| | | | | |
| 作业分配/调度 | | 作业历史/用量 | | 作业执行/监控 |
+-----------------+ +-----------------+ +-----------------+
^ ^ ^
| | |
sbatch/srun sacct/sreport ssh/mpi
- slurmctld:中央控制器,负责任务队列管理、节点状态监控、作业调度决策。通常以主备模式部署。
- slurmd:运行在每个计算节点上的守护进程,负责接收 slurmctld 指令、启停作业步(step)、收集资源使用数据。
- slurmdbd:可选的记账数据库守护进程,将作业历史、资源用量记录至 MySQL/MariaDB,支撑
sacct和sreport。
作业提交方式
Slurm 提供三种核心提交方式,满足不同使用场景:
| 命令 | 模式 | 适用场景 | 终端阻断 |
|---|---|---|---|
sbatch | 批处理 | 长时间运行、无需交互 | 否(后台) |
srun | 实时运行 | MPI 并行程序、调试 | 是(前台) |
salloc | 交互式分配 | 交互式调试、GPU 开发 | 是(分配后进入 shell) |
典型 sbatch 脚本示例:
#!/bin/bash
#SBATCH --job-name=mpi_stencil
#SBATCH --partition=cpu-std
#SBATCH --nodes=4
#SBATCH --ntasks-per-node=32
#SBATCH --cpus-per-task=1
#SBATCH --time=02:00:00
#SBATCH --output=%x-%j.out
module load openmpi/5.0
srun ./stencil_3d --grid 4096 --iter 10000
sbatch 支持参数覆盖:sbatch --nodelist=node[01-04] job.sh。srun 是 MPI 作业的首选启动器,可自动处理 PMI/PMIx 进程映射。
分区与队列配置
slurm.conf 中的 Partition 定义了资源分组策略,类比云平台的队列概念:
PartitionName=cpu-std Nodes=cpu[001-128] Default=YES MaxTime=48:00:00 State=UP
PartitionName=cpu-long Nodes=cpu[129-160] MaxTime=168:00:00 Priority=10
PartitionName=gpu-a100 Nodes=gpu[001-032] MaxTime=24:00:00 Gres=gpu:a100:8
PartitionName=debug Nodes=cpu[001-004] MaxTime=00:30:00 MaxNodes=2 PriorityTier=100
关键配置项说明:
| 配置项 | 作用 |
|---|---|
Default | 用户未指定分区时的默认队列 |
Priority / PriorityTier | 数值越高,该分区获得调度优先权 |
MaxTime / MaxNodes | 防止单个作业过度占用资源 |
Gres | 声明通用资源(GPU、FPGA、NVMe 等) |
OverSubscribe | 控制节点/CPU 是否允许超配 |
调度策略详解
Slurm 调度器(sched/backfill 或 sched/builtin)的核心目标是在满足资源约束的前提下最大化吞吐量与利用率。
Backfill 回填调度
Backfill 是生产环境最常用的策略。其工作逻辑如下:
队列状态: [J1: 需 100 节点, 2 小时] [J2: 需 10 节点, 1 小时] [J3: 需 50 节点, 0.5 小时]
当前空闲: 60 节点
步骤 1: J1 优先级最高,预留未来 100 节点,预计开始时间 T+2h
步骤 2: Backfill 扫描 J2、J3...
J3 运行 0.5h 后释放,不影响 J1 预留 => 允许 J3 立即运行
J2 运行 1h 后释放,仍不影响 J1 预留 => 允许 J2 立即运行
结果: J2 和 J3 被"回填",在 J1 等待期间充分利用空闲资源
配置开启 Backfill:
SchedulerType=sched/backfill
SelectType=select/cons_tres
SelectTypeParameters=CR_Core_MEMORY
CR_Core_MEMORY 表示按 Core 和 Memory 作为可分配资源粒度,避免整节点浪费。
Gang Scheduling 分时调度
当资源不足但作业要求低延迟响应时,Gang Scheduling 允许多个作业共享同一组 CPU/GPU 时间片。Slurm 通过 PreemptMode=SUSPEND,GANG 配合 OverSubscribe=FORCE 实现。
⚠️ 注意:Gang 调度对 MPI 同步密集型应用可能造成性能抖动,推荐仅用于开发调试或 I/O 密集型负载。
QoS 与优先级系统
QoS(Quality of Service)为不同用户/项目提供差异化的资源承诺:
# 创建 QoS
sacctmgr add qos gold flags=OverPartQOS priority=100 \
MaxWall=72:00:00 MaxTRESPU=cpu=256,gres/gpu=8 \
GrpTRES=cpu=2048 GrpJobs=50
# 绑定用户至 QoS
sacctmgr modify user where name=alice set qos=gold
优先级计算公式(PriorityType=priority/multifactor):
Priority = (Age_weight * Job_Age / Max_Age)
+ (JobSize_weight * Job_Size / Max_Size)
+ (Partition_weight * Partition_Factor)
+ (QOS_weight * QOS_Factor)
+ (FairShare_weight * FairShare_Factor)
Fair-Share 避免单一用户长期垄断资源,其衰减窗口可用 PriorityDecayHalfLife 调节。
资源预留与抢占
对于 deadline 敏感型作业,可提前锁定资源:
# 预留 64 节点未来 2 小时,供用户 bob 使用
scontrol create reservation=urgent_res \
starttime=now+2hours duration=4hours \
nodes=64 flags=maint,ignore_jobs users=bob
# 查看预留
scontrol show reservation=urgent_res
抢占策略(PreemptMode=CANCEL 或 REQUEUE)允许高优先级作业踢走低优先级正在运行的作业。REQUEUE 模式会重新排队被抢占作业,适合容错良好的 checkpoint/restart 应用。
常用命令速查表
| 操作 | 命令 |
|---|---|
| 提交批处理作业 | sbatch job.sh |
| 交互式运行命令 | srun --pty /bin/bash |
| 查看队列 | squeue -u $USER --format="%.18i %.9P %.8j %.8u %.2t %.10M %.6D %R" |
| 取消作业 | scancel <jobid> |
| 查看作业详情 | scontrol show job <jobid> |
| 查看节点状态 | sinfo -N -o "%N %.6D %.10T %.4c %.8z %.6m %.10G %E" |
| 查看历史作业 | sacct -j <jobid> --format=JobID,JobName,Partition,State,Elapsed,MaxRSS |
| 查看用量报告 | sreport cluster utilization |
| 调整作业时间 | scontrol update job <jobid> timelimit=04:00:00 |
| 挂起/恢复作业 | scontrol hold <jobid> / scontrol release <jobid> |
生产环境最佳实践
- 合理设置
DefMemPerCPU:避免作业因内存 OOM 被 Kill,同时防止用户申请整节点却只用一个核心。 - 启用
Prolog/Epilog脚本:在作业启动前后执行健康检查、环境准备、日志归档。 - 配置
JobAcctGatherType=jobacct_gather/cgroup:使用 cgroup 精确采集 CPU、内存、I/O 用量。 - 定期
slurmctldcheckpoint:SlurmctldParameters=archive_jobs确保控制器故障时可快速恢复状态。 - Gres 资源绑定:GPU 作业务必使用
--gpus-per-task或--gres=gpu:4,防止进程漂移导致数据局部性丧失。
Slurm 的灵活配置使其既能服务国家级超算中心,也能适配企业内部的 AI 训练集群。理解其核心调度机制,是 HPC 系统管理员和重度用户的必修课。
继续阅读
探索更多技术文章
浏览归档,发现更多关于系统设计、工具链和工程实践的内容。