如何使 SLURM 作业步骤使用最少的节点数?

How to make SLURM job step use the minimum number of nodes?

我试图在一个大的多节点分配中 运行 许多较小的 SLURM 作业步骤,但我正在努力解决作业步骤的任务如何分配给不同节点的问题。一般来说,我希望将一个作业步骤的任务尽可能保持在本地(同一节点,同一套接字),并且仅当并非所有任务都可以放在单个节点上时才溢出到下一个节点。

以下示例展示了我分配 2 个节点,每个节点有 4 个任务并启动作业步骤要求 4 个任务的情况:

$ salloc -N 2 --ntasks-per-node=4 srun -l -n 4 hostname
salloc: Granted job allocation 9677936
0: compute-3-6.local
1: compute-3-6.local
2: compute-3-7.local
3: compute-3-7.local
salloc: Relinquishing job allocation 9677936

我希望这 4 个任务转到其中一个节点,以便第二个作业步骤可以声明另一个节点,但事实并非如此:第一个作业步骤在两个节点之间均匀分布。如果我启动包含 4 个任务的第二个作业步骤,它也会跨节点分布,导致很多不必要的节点间网络通信,这些通信很容易避免。

我已经发现我可以通过显式包含作业步骤启动的 -N 1 来强制我的作业步骤在单个节点上 运行:

$ salloc -N 2 --ntasks-per-node=4 srun -l -N 1 -n 4 hostname
salloc: Granted job allocation 9677939
0: compute-3-6.local
1: compute-3-6.local
2: compute-3-6.local
3: compute-3-6.local
salloc: Relinquishing job allocation 9677939

但是,启动的作业步骤数和每个作业步骤的任务数取决于我的用户输入,所以我不能只对所有这些强制执行 -N 1。可能有作业步骤的任务太多,无法放在单个节点上。

阅读 srun 联机帮助页时,我首先认为 --distribute=block:block 选项应该对我有用,但事实并非如此。似乎这个选项只有在决定了作业步骤要使用的节点数后才会起作用。

我的另一个想法是作业步骤可能只是从分配中继承 -N 2 参数,因此也被迫使用两个节点。我尝试为作业步骤设置 -N 1-2,以便至少允许 SLURM 将作业步骤分配给单个节点,但这对我没有任何影响,即使与 [=19= 结合使用时也是如此]旗帜。

$ salloc -N 2 --ntasks-per-node=4 srun -l -N 1-2 --use-min-nodes -n 4 hostname
salloc: Granted job allocation 9677947
0: compute-3-6.local
1: compute-3-6.local
2: compute-3-7.local
3: compute-3-7.local
salloc: Relinquishing job allocation 9677947

如何使 SLURM 作业步骤使用最少的节点数?

很遗憾,没有别的办法。你必须使用 -N.

即使您使用 -n 1(而不是 4)也会出现 警告:

salloc -N 2 --ntasks-per-node=4 srun -l -n 1 hostname
srun: Warning: can't run 1 processes on 2 nodes, setting nnodes to 1

但是如果你使用,

salloc -N 2 --ntasks-per-node=4 srun -l -N 1-2 --use-min-nodes -n 1 hostname

这里不会有任何警告,因为那时至少会使用一个节点。

原因:slurm 将尝试在节点数 allocated/requested 中至少启动一个 single task,除非使用 -N flag 另行指定(如以下输出)。

srun -l -N 1-2 --use-min-nodes -m plane=48 -n 4 hostname
0: compute-3-6.local
1: compute-3-6.local
2: compute-3-6.local
3: compute-3-7.local

您可以看到,一个任务在节点 2 中启动,而其余单独在另一个节点中。这是因为,您的分配请求了两个节点 (salloc)。如果你想在一个节点上 运行 你必须用 -N 变量指定它以强制它只使用单个节点。

我想您可以即时计算 -N 来解决您的问题。由于您知道节点中可能的最大任务数(假设它是同构系统),因此您可以使用 s运行.

计算应用程序在启动任务之前所需的节点数

However, the number of job steps launched and the number of tasks per job step depends on user input in my case, so I can not just force -N 1 for all of them. There may be job steps that have so many tasks that they can not be placed on a single node.