キューは、効果的なリソース管理と割り当て、最適化されたジョブスケジューリング、システム使用率の向上、および多様なジョブ要件への対応のためのタスクスケジューリングにおける重要な設定項目です。適切なキュー構成により、優先度の高いタスクが最初に必要なリソースを受け取り、リソース使用効率を最大化できます。このトピックでは、ジョブの送信時またはジョブの状態変更時にできるだけ多くのタスクを処理し、最適なパフォーマンスを実現するために、Slurm 環境で適切なキュー構成戦略を実装する方法について説明します。
1. Slurm のコア機能
リソース割り当て: 必要に応じて CPU/メモリ/GPU リソースを割り当て、競合と無駄を回避します。
ジョブスケジューリング: ジョブキューを動的にスケジュールし、優先順位に従って実行し、タスクの状態を全体的に監視します。
優先制御: 優先度の高いキュータスクが最初にスケジュールされます。
監視ツール:
scontrol/sacctを使用してリソース使用量とジョブの状態を監視します。カスタマイズサポート: 複数のキューがさまざまな要件(CPU 集約型/メモリ/GPU タスクなど)に適応します。
システムの最適化: リソース使用率を向上させ、アイドル時間を短縮し、計算効率を高めます。
このトピックは Slurm バージョン 24.05 に基づいています。他のバージョンでは違いがある場合があります。
2. Slurm キューの種類
Slurm タスクは優先順位に従って実行されます。パーティションにスケジュールできないタスクがある場合、後続のタスクは一時停止されます。優先度の高いタスクは、優先度の低いタスクのリソースをプリエンプトできます。プリエンプトされたタスクは、キャンセル、リセット、または一時停止できます。バックフィルスケジューリング(デフォルト)を有効にすると、システムは bf_interval サイクルに基づいて、優先度の低いタスクが優先度の高いタスクを遅延させることなく実行できるかどうかを計算します。これにはマシン全体の占有が必要であり、マシン全体のプリエンプションがトリガーされる場合があります。スケジューリング構成は、slurm.conf の SchedulerType(デフォルトの sched/backfill プラグイン)および詳細パラメータ SchedulerParameters を介して指定されます。特定のパラメータ構成については、公式ドキュメントをご参照ください。
スケジューリング中、すべてのタスクは単一のリストに統合され、それらの実行順序はさまざまな優先アルゴリズムによって決定されます。Slurm は、次の 2 つのキュータイプをサポートしています。
先入れ先出し(FIFO)キュー。タスクは送信時間の順序に基づいてソートされます。
MultiFactors キュー。これはデフォルトで有効になっている、より高度なタスクキューイングメカニズムです。複数の要因に基づいてジョブの優先順位を計算できます。
2.1 先入れ先出しキュー
デフォルトでは、Slurm は FIFO をジョブの優先順位を割り当てるための基準として使用します。優先スケジューリングの構成ファイルは、slurm.conf に保存されます。PriorityType パラメータを変更することで、優先順位を設定できます。
# 1. slurm.conf ファイルを見つけて編集します
sudo nano /etc/slurm-llnl/slurm.conf
# 2. プリエンプションモードを有効にし、先入れ先出しの優先順位に基づいてプリエンプション戦略を指定します
PriorityType=priority/basic 変更を加える前に、元の slurm.conf ファイルをバックアップすることをお勧めします。そうすれば、問題が発生した場合に復元できます。さらに、本番環境での大きな変更については、最初にテスト環境で徹底的にテストすることをお勧めします。
2.2 Multifactors ジョブキュー
Slurm マルチファクタースケジューリングは、ジョブの実行時間、リソースの差異(割り当て済みと消費済み)、ジョブサイズ、ユーザパラメータ、データパーティショニング、TRES(Total Resource Equivalents)タイプ、およびサービス品質(QoS)の加重計算によってタスクの優先順位を決定します。重み割り当てと特定の計算ロジックについては、マルチファクター優先構成手順をご参照ください。
Job_priority =
site_factor +
(PriorityWeightAge) * (age_factor) +
(PriorityWeightAssoc) * (assoc_factor) +
(PriorityWeightFairshare) * (fair-share_factor) +
(PriorityWeightJobSize) * (job_size_factor) +
(PriorityWeightPartition) * (priority_job_factor) +
(PriorityWeightQOS) * (QOS_factor) +
SUM(TRES_weight_cpu * TRES_factor_cpu,
TRES_weight_<type> * TRES_factor_<type>,
...)
- nice_factorSlurm ジョブの優先順位は、次の加重係数を使用して計算されます。
ベース値:
site_factor(カスタムスコア)。ジョブの待機時間ウェイト: ジョブの待機時間が長いほど、ウェイトは高くなります(
PriorityWeightAge × age_factor)。関連付けウェイト: ユーザーグループ/アカウントのリソース使用量の公平性(
PriorityWeightAssoc × assoc_factor)。フェアシェアウェイト: リソース使用率に基づいてスコアを調整します(
PriorityWeightFairshare × fair-share_factor)。ジョブサイズウェイト: 小/大ジョブの優先順位(
PriorityWeightJobSize × job_size_factor)。パーティションウェイト: パーティションの優先順位(
PriorityWeightPartition × priority_job_factor)。QoS ウェイト: サービス品質レベル(
PriorityWeightQOS × QOS_factor)。リソースウェイト: リソースタイプ(CPU/GPU など)の加重。
ナイスダウングレード:
- nice_factor(値が高いほど優先順位が低くなります)。
重みパラメータを動的に調整することで、公平で効率的なタスクスケジューリングを実現できます。
典型的なアプリケーション例。
小さなジョブをすばやく完了する:
PriorityWeightJobSize=-1を設定すると、大きなジョブの優先順位が下がり、小さなジョブがより速くスケジュールされます。重要なユーザー/グループを保証する:
PriorityWeightAssocとFair-share_factorを使用して、重要なチームからのジョブが最初に実行されるようにします。リソーススタベーション保護:
PriorityWeightFairshare=2000を構成すると、リソース使用量の少ないユーザーからのジョブの優先順位が大幅に向上します。
例: マルチファクタージョブの優先順位の設定
パーティションの優先順位のカスタマイズ
Slurm は、組織構造によってマシンを分割し、タスクが割り当てられたリソースプールでのみ実行されるように制限できます。タスクは、緊急(優先度の低いタスクをプリエンプトする)または非緊急(すぐに実行されるが、緊急のタスクをブロックしない)に分類されます。タスクが期限に近づき、緊急としてマークする必要がある場合、Slurm はこれを自動的に調整できません。優先度の高いキューへの手動移行が必要です。
同じノードプール(緊急/非緊急タスクを区別する)を指す 2 つのパーティションを作成し、タスクが属するパーティションを切り替えることによって優先順位を動的に調整できます。これにより、リソース使用率が向上し、操作が簡素化されます。動的ワークロードの柔軟なスケジューリングをサポートすると同時に、管理の複雑さを軽減します。これにより、システムが動的に変化するワークロード要件により適切に適応できるようになるだけでなく、複雑なジョブ環境での運用担当者の管理作業も簡素化されます。設定については、次の手順を参照できます。
まず、クラスタでプリエンプション機能スイッチを有効にし、プリエンプションタイプを
preempt/partition_prioに設定します。# 1. slurm.conf ファイルを見つけて編集します sudo nano /etc/slurm-llnl/slurm.conf # 2. プリエンプションモードを有効にし、パーティションの優先順位に基づいてプリエンプション戦略を指定します PreemptMode=preempt/partition_prio # 3. ジョブがプリエンプトされたときの動作。ジョブがプリエンプトされたときに何が起こるかを定義します。 # cancel はジョブの終了を意味します。suspend は、リソースが再び利用可能になるまでジョブを一時停止します。要件に基づいて選択します。 PreemptType=suspend # または "cancel"重要変更を加える前に、元の
slurm.confファイルをバックアップすることをお勧めします。そうすれば、問題が発生した場合に復元できます。さらに、本番環境での大きな変更については、最初にテスト環境で徹底的にテストすることをお勧めします。次のコマンドを使用するか、slurm.conf に新しいパーティションレコードを追加することで、クラスタに優先度の高いパーティションを追加できます。
scontrol create partition=hipri PriorityTier=2 nodes=ALLその後、hipriパーティションにジョブを送信するか、ジョブを優先度の高いパーティションに変更することで、ジョブのプリエンプションを実現できます。以下はジョブ送信の例です。# 1. Slurm クラスタに優先度の高いパーティションを追加します。 root@slurm-test-0:/# scontrol create partition=hipri PriorityTier=2 nodes=ALL # 2. 現在のクラスタパーティションを表示します。 root@slurm-test-0:/# scontrol show partition # 結果。 PartitionName=debug AllowGroups=ALL AllowAccounts=ALL AllowQos=ALL AllocNodes=ALL Default=YES QoS=N/A DefaultTime=NONE DisableRootJobs=NO ExclusiveUser=NO GraceTime=0 Hidden=NO MaxNodes=UNLIMITED MaxTime=UNLIMITED MinNodes=0 LLN=NO MaxCPUsPerNode=UNLIMITED MaxCPUsPerSocket=UNLIMITED Nodes=slurm-test-worker-cpu-0 PriorityJobFactor=1 PriorityTier=1 RootOnly=NO ReqResv=NO OverSubscribe=FORCE:1 OverTimeLimit=NONE PreemptMode=GANG,SUSPEND State=UP TotalCPUs=4 TotalNodes=1 SelectTypeParameters=NONE JobDefaults=(null) DefMemPerNode=UNLIMITED MaxMemPerNode=UNLIMITED TRES=cpu=4,mem=6401M,node=1,billing=4 ResumeTimeout=GLOBAL SuspendTimeout=GLOBAL SuspendTime=GLOBAL PowerDownOnIdle=NO PartitionName=hipri AllowGroups=ALL AllowAccounts=ALL AllowQos=ALL AllocNodes=ALL Default=NO QoS=N/A DefaultTime=NONE DisableRootJobs=NO ExclusiveUser=NO GraceTime=0 Hidden=NO MaxNodes=UNLIMITED MaxTime=UNLIMITED MinNodes=1 LLN=NO MaxCPUsPerNode=UNLIMITED MaxCPUsPerSocket=UNLIMITED Nodes=slurm-test-worker-cpu-0 PriorityJobFactor=1 PriorityTier=2 RootOnly=NO ReqResv=NO OverSubscribe=NO OverTimeLimit=NONE PreemptMode=GANG,SUSPEND State=UP TotalCPUs=0 TotalNodes=0 SelectTypeParameters=NONE JobDefaults=(null) DefMemPerNode=UNLIMITED MaxMemPerNode=UNLIMITED TRES=(null) ResumeTimeout=GLOBAL SuspendTimeout=GLOBAL SuspendTime=GLOBAL PowerDownOnIdle=NO # 4 つの連続したタスクを送信します。 root@slurm-test-0:/# srun sleep 1d & root@slurm-test-0:/# srun sleep 1d & root@slurm-test-0:/# srun sleep 1d & root@slurm-test-0:/# srun sleep 1d & # 現在のクラスタの状態を確認します。 root@slurm-test-0:/# squeue # クラスタには現在 4 つの実行中のタスクがあります。 JOBID PARTITION NAME USER ST TIME NODES NODELIST(REASON) 4 debug sleep root R 0:03 1 slurm-test-worker-cpu-0 2 debug sleep root R 0:04 1 slurm-test-worker-cpu-0 3 debug sleep root R 0:04 1 slurm-test-worker-cpu-0 1 debug sleep root R 0:05 1 slurm-test-worker-cpu-0 # 優先度の高いパーティションにタスクを送信します。 root@slurm-test-0:/# srun --partition=hipri sleep 1d & root@slurm-test-0:/# squeue # タスク 4 の ST(状態)は R から S に変更され、タスク 5 の状態は R に変更されました。これは、タスク 4 が一時停止されたことを示しています。 JOBID PARTITION NAME USER ST TIME NODES NODELIST(REASON) 2 debug sleep root R 1:06 1 slurm-test-worker-cpu-0 3 debug sleep root R 1:06 1 slurm-test-worker-cpu-0 1 debug sleep root R 1:07 1 slurm-test-worker-cpu-0 4 debug sleep root S 0:59 1 slurm-test-worker-cpu-0 5 hipri sleep root R 0:06 1 slurm-test-worker-cpu-0 # 優先度の低いタスクを送信します。 root@slurm-test-0:/# srun sleep 1d & # タスクを高い優先度に更新します。 root@slurm-test-0:/# scontrol update jobid=6 partition=hipri root@slurm-test-0:/# squeue # タスク 1 と 2 は一時停止されました。これは、同じパーティション内のタスクが実行時間を共有するため、1、2、3、4 が時分割方式で実行されるためです。 JOBID PARTITION NAME USER ST TIME NODES NODELIST(REASON) 4 debug sleep root R 3:21 1 slurm-test-worker-cpu-0 3 debug sleep root R 3:33 1 slurm-test-worker-cpu-0 2 debug sleep root S 3:41 1 slurm-test-worker-cpu-0 1 debug sleep root S 4:01 1 slurm-test-worker-cpu-0 6 hipri sleep root R 0:03 1 slurm-test-worker-cpu-0 5 hipri sleep root R 3:33 1 slurm-test-worker-cpu-0
QoS サービス品質の優先順位のカスタマイズ
Slurm は、高/低優先順位の QoS を設定する必要があります(デフォルトでは、優先順位 0 の normal がすでに存在します)。sacctmgr を使用して優先度の高い QoS を作成することでプリエンプションを有効にします。プリエンプション機能は、slurm.conf で有効にする必要があります(PreemptMode=priority など)。ただし、PreemptType=SUSPEND,GANG の場合、優先度の高いタスクがプリエンプトした後、優先度の低いタスクは優先度の高いタスクと時分割モードで共存することに注意してください(完全に中断されるわけではありません)。QoS を構成するには、sacctmgr ツールを使用する必要があります。以下は、優先度の高い QoS を作成するための一般的なコマンドです。
sacctmgr add qos high preempt=normal preemptmode=gang,suspend priority=10preempt=normal:highQoS がnormalQoS のタスクをプリエンプトできることを指定します。preemptmode=gang,suspend:ギャングモード: プリエンプトするタスクは、実行を開始する前にリソースを完全に取得する必要があります。
一時停止モード: プリエンプトされたタスクは終了するのではなく一時停止され、プリエンプタが使用するためのリソースを解放し、プリエンプトするタスクが終了すると実行を再開します。
priority=10:highQoS タスクのデフォルトの優先順位ベーススコアは 10 です(値が高いほど優先順位が高くなります)。
slurm.conf でプリエンプション関連のスイッチを有効にするには、次のパラメータが必要です。さらに、パーティションを構成するときは、構成の最後に OverSubscribe=FORCE:1 を追加する必要があります。
以下は、タスクプリエンプション管理に異なる QoS を使用した例です。
# 現在の QoS を表示します。
root@slurm-test-0:/# sacctmgr show qos format=name
Name
----------
normal
# 優先度の高い QoS を作成します。
root@slurm-test-0:/# sacctmgr add qos high preempt=normal preemptmode=gang,suspend priority=10
Adding QOS(s)
high
Settings
Description = high
Preempt = normal
PreemptMode = GANG,SUSPEND
Priority = 10
Would you like to commit changes? (You have 30 seconds to decide)
(N/y): y
# 現在の QoS を表示します。
root@slurm-test-0:/# sacctmgr show qos format=name,priority,preempt
Name Priority Preempt
---------- ---------- ----------
normal 0
high 10 normal
# test.sh の内容は次のとおりです。
# #!/bin/bash
# srun sleep 10m
# 5 つの連続したタスクを送信します。
root@slurm-test-0:/# sbatch test.sh
Submitted batch job 4
root@slurm-test-0:/# sbatch test.sh
Submitted batch job 5
root@slurm-test-0:/# sbatch test.sh
Submitted batch job 6
root@slurm-test-0:/# sbatch test.sh
Submitted batch job 7
root@slurm-test-0:/# sbatch test.sh
Submitted batch job 8
root@slurm-test-0:/# squeue # タスク 8 は Pending 状態です
JOBID PARTITION NAME USER ST TIME NODES NODELIST(REASON)
8 debug test.sh root PD 0:00 1 (Resources)
7 debug test.sh root R 0:03 1 slurm-test-worker-cpu-0
5 debug test.sh root R 0:15 1 slurm-test-worker-cpu-0
6 debug test.sh root R 0:15 1 slurm-test-worker-cpu-0
4 debug test.sh root R 0:18 1 slurm-test-worker-cpu-0
root@slurm-test-0:/# sbatch --qos=high test.sh # 優先度の高い QOS にタスクを送信します
Submitted batch job 9
root@slurm-test-0:/# squeue # 優先度の高い QoS が実行を開始し、他のタスクと時分割方式でリソースを共有します
JOBID PARTITION NAME USER ST TIME NODES NODELIST(REASON)
8 debug test.sh root PD 0:00 1 (Resources)
7 debug test.sh root R 0:26 1 slurm-test-worker-cpu-0
5 debug test.sh root R 0:38 1 slurm-test-worker-cpu-0
6 debug test.sh root R 0:38 1 slurm-test-worker-cpu-0
4 debug test.sh root R 0:41 1 slurm-test-worker-cpu-0
9 debug test.sh root S 0:00 1 slurm-test-worker-cpu-0
ジョブサイズ優先順位のカスタマイズ
ジョブサイズ優先順位は、PriorityWeightJobSize と PriorityWeightAge=1000 の両方によって決定されます。
ジョブサイズ係数
緊急ではないタスクは、(期限を超えることなく)クラスタリソースを効率的に使用する必要があります。タスクの実行時間が不明な場合、バックフィルスケジューリングは失敗します。この場合、小さなタスクを優先すると head-of-line ブロッキングが軽減されますが、キュー時間に基づいて大きなタスクの優先順位を上げると、スタベーションを防ぐことができます。期限が近づいている大きなタスクは、小さなタスクからリソースをプリエンプトできます(小さなタスクは完了するまで一時停止されます)。
緊急ではないタスクのクラスタ使用率を(期限を超えることなく)向上させるには、次の戦略を採用できます。
小さなタスクのスケジューリングを優先して、head-of-line ブロッキングを軽減します。
キューの長さに基づいて大きなタスクの優先順位を上げて、スタベーションを防ぎます。
期限が近づいている大きなタスクが小さなタスクからリソースをプリエンプトできるようにします(小さなタスクは完了するまで一時停止されます)。タスクの実行時間が不明な場合、バックフィルスケジューリングは失敗し、リソースを効率的に使用するには上記のメカニズムが必要になります。
これらの対策を実施することで、重要なタスクが時間どおりに完了することを保証しながら、クラスタリソースの使用率を最大化し、さまざまなタイプのタスクのバランスをとることができます。
slurm.conf で次の構成を行う必要があります(ここでは特別な構成のみが表示され、slurm.conf の他の構成は影響を受けません)。
PriorityFavorSmall=YES PriorityWeightAge=1000 PriorityWeightJobSize=1000 PriorityMaxAge=1-0ジョブ待機時間係数
ジョブサイズ優先順位を設定した後、送信待機時間は 2 番目の要因になります。Slurm は、リクエストされたリソースと合計クラスタリソースの比率に基づいてジョブサイズスコアを計算します。
PriorityFavorSmall=YESが有効になっている場合、スコアの式は次のとおりです。score = (1 - リソース比率) × PriorityWeightJobSize。たとえば、クラスタで使用可能な CPU コアが 4 つある場合:1 コアをリクエストするタスクのスコア:
(1 - 1/4) × weight = 0.75×weight → 例のスコア 0.375 (weight が 0.5 の場合)。4 コアをリクエストするタスクのスコアは 0 です(リソースを完全に占有)。
AgeFactor 優先順位の計算:
PriorityMaxAgeを超えるタスク:PriorityWeightAgeポイントを直接満点受け取ります。他のタスクは、送信時間の比率に基づいてスコアが付けられます。たとえば、
PriorityWeightAge=1000の場合、毎分約 0.69 ポイントが加算され、24 時間後に合計 1000 ポイントになります。
バックフィルスケジューリングの推奨事項: タスクの実行時間を推定できる場合は、デフォルトのバックフィルスケジューリングを有効にする(または手動で
SchedulerType=sched/backfillを構成する)ことをお勧めします。これにより、大きなタスクの前にアイドル期間を埋めるために小さなタスクをスケジュールできます。システムのデフォルトの大きなタスク優先メカニズムと期限が近づいているプリエンプション機能と組み合わせることで、リソース使用率と公平性のバランスをとることができます。