Exemples de soumission

Job standard

La soumission d’un job en ligne de commande se fait avec la syntaxe suivante :

% sbatch -t 0-00:30 -n 1 --mem 10G job.sh
sbatch: INFO: Account: ccin2p3
sbatch: INFO: Submission node: cca001
sbatch: INFO: Partition set to: htc
sbatch: INFO: Partition limited to one node per job.
sbatch: INFO: Time limit set to: 0-00:30:00 (30 minutes)
Submitted batch job 936607
-t <j-hh:mm>
spécifie la limite de temps evaluée. Tous les formats acceptés sont décrits dans le paragraphe Principales options de sbatch
-n <nombre>
spécifie le nombre de tâches demandés (dans cette syntaxe equivalent au nombre de cœurs). Pour un job multi-cœur, <nombre> sera plus grand de 1.
--mem <nombre>
spécifie la quantité de mémoire demandée.
job.sh
votre script de tâche executable.

Les trois paramètres indiqués ci-dessus doivent être toujours declarés lors d’une soumission. Le paramètre -c (nombre de CPU par tâche) peut substituer -n (voir Limites des paramètres obligatoires).

À la soumission, des informations vous sont retournées dans la sortie standard : le groupe de calcul (Account, ici ccin2p3), le nœud de soumission( ici cca001), la partition htc (par défaut) dans laquelle le job sera exécuté, ou encore l’identifiant du job 936607.

Si l’on souhaite accèder à une ressource nécessitant la déclaration, on utilisera l’option -L :

% sbatch -t 0-00:30 -n 4 --mem 10G -L sps,matlab job.sh

Scripts de soumission

Il est possible de spécifier des options de soumission directement dans un script utilisant la syntaxe suivante :

#!/bin/sh

# SLURM options:

#SBATCH --job-name=serial_job_test    # Nom du jobe
#SBATCH --output=serial_test_%j.log   # Standard output et error log

#SBATCH --partition=htc               # Choix de partition (htc par défaut)

#SBATCH --ntasks=1                    # Exécuter une seule tâche
#SBATCH --mem=2000                    # Mémoire en MB par défaut
#SBATCH --time=1-00:00:00             # Délai max = 7 jours

#SBATCH --mail-user=<email address>   # Où envoyer l'e-mail
#SBATCH --mail-type=END,FAIL          # Événements déclencheurs (NONE, BEGIN, END, FAIL, ALL)

# Commandes à soumettre :

module load python
python my_python_script.py

Dans cet exemple, on met en place un environnement Python via modules afin d’exécuter my_python_script.py. L’ensemble des options Slurm sont passées via des directives #SBATCH, et ce script pourra simplement être soumis comme suit :

% sbatch my_batch_script.sh

Script à tâches multiples

Des tâches de calcul en srun peuvent aussi être lancées de l’intérieur du script, pourvu que les ressources déclarées par les lignes #SBATCH se soient pas dépassées. Par exemple :

#!/bin/sh

#SBATCH --job-name=mulitple_jobs

#SBATCH --ntasks=2
#SBATCH --mem=5000
#SBATCH --time=1-00:00:00

#SBATCH --output=mulitple_jobs_%j.log
#SBATCH --licenses=sps

####################################
srun -n 1 --exclusive -L sps script_sps.sh &
srun -n 1 --exclusive script_software.sh &
srun -n 1 --cpus-per-task 2 script_software.sh
wait

L’option --exclusive permet à la tâche de ne pas partager la ressource. La syntaxe bash permet de:

  • & : lancer les tâches en parallèle; si une tâche ne trouve pas de ressource disponible, elle reste en attente et un message de warning est écrit sur le output,
  • wait : attendre que toutes les tâches soient terminées avant de sortir du script.

Dans le cas où la tâche soumise est un script exécutant des processus en paralèlle, alors il faut préciser le nombre de cpus par tâches :

#!/bin/bash

#SBATCH --time=1-00:00:00
#SBATCH --mem=6000

#SBATCH --ntasks=2 # Exécuter au maximum 2 tâches parallèles
#SBATCH --cpus-per-task=4 # Allouer 4 cœurs par tâche, soit 8 cœurs au total dans cet exemple (ntasks x cpus-per-task)

my_parallel_job.sh

sinon, tous les sous-processus lancés par my_parallel_job.sh ne s’exécuteront que sur un seul CPU.

Job interactif

La soumission d’un job interactif se fait via la commande srun. Dans le cas d’un job interactif GPU il faudra préciser la partition adéquate.

% srun -t 0-08:00 -n 4 --mem 10G --pty bash -i    # session interactive HTC

% srun -t 0-08:00 -n 4 --mem 10G job.sh           # lancement interactif d'un exécutable HTC

% srun -p gpu_interactive -t 0-08:00 --mem 10G --gres=gpu:[type]:1 --pty bash -i   # session interactive GPU
-p
sélectionne la partition
--gres=
permet de spécifier l’utilisation d’une ressource GPU, et de la définir.
--pty
autorise l’interactivité avec la session ouverte.

Afin de quitter sa session interactive, faire :

% exit

Job parallèle (MPI)

Il s’agit de jobs qui exécutent des opérations en parallèle, possiblement sur des serveurs de calcul différents, en utilisant une interface de type MPI à travers une connectique InfiniBand. Il faut préciser la partition hpc :

% sbatch -p hpc -t 0-02:00 -n 8 --mem 10G -N 2 job.sh
-N <nombre>
spécifie le nombre de serveurs de calcul (nœuds) requis

Note

Dans le cas où le nombre de serveurs de calcul (option -N) est 1, il n’est pas nécessaire de l’indiquer, ni de spécifier la partition.

Job GPU

Ce sont des jobs qui s’exécutent sur des serveurs de calcul équipés de GPUs. Deux types de syntaxes sont permises :

% sbatch -t 0-01:00 -n <N> --mem 10G --gpus 1 job.sh

% sbatch -t 0-01:00 -n <N> --mem 10G --gres=gpu:v100:1 job.sh # demande spécifique du type de GPU

Ici, on demande l’allocation d’un seul GPU, mais il est possible d’en utiliser plusieurs, jusqu’à la limite de GPUs dans le nœud correspondant. La limite du nombre de taches <N> est expliquée dans Limites des paramètres obligatoires.

Un seul type de GPUs est disponible actuellement au CC-IN2P3 : Nvidia V100, identifié par le mot clé v100.

Utiliser CUDA

Si vous devez utiliser des bibliothèques CUDA spécifiques, précisez dans votre script:

  • bash

    if !echo ${LD_LIBRARY_PATH} | /bin/grep -q /usr/local/cuda-11.3/lib64 ; then
           LD_LIBRARY_PATH=/usr/local/cuda-11.3/lib64:${LD_LIBRARY_PATH}
    fi
    
  • csh

    if ($?LD_LIBRARY_PATH) then
           setenv LD_LIBRARY_PATH /usr/local/cuda-11.3/lib64:${LD_LIBRARY_PATH}
    else
           setenv LD_LIBRARY_PATH /usr/local/cuda-11.3/lib64
    endif
    

Important

Plusieurs environnements CUDA sont disponibles, et sont régulièrement mis-à-jour. La version courante des pilotes Nvidia est 465.19.01 ; la version CUDA par défaut est 11.3 et cudnn est 8.2.0.

Pour compiler votre code CUDA, vous devriez vous connecter sur un serveur GPU interactif et utiliser le compilateur nvcc :

% /usr/local/cuda-11.3/bin/nvcc

Une fois le code compilé, nous vous conseillons de sortir du serveur interactif et soumettre vos jobs avec sbatch.

Note

Pour le profilage des jobs GPU, CUPTI (CUDA Profiling Tools Interface) est installé sur nos machines de calcul. CUPTI étant directement lié à CUDA, la version installée est la même.

Job daemon et récursivité

Pour les jobs de longue durée à petite consommation de ressources (motoring ou orchestration d’autres jobs) privilegiez la partition htc_daemon (voir Limites des paramètres obligatoires) :

% sbatch -p htc_daemon -t 90-00:00 -n 1 --mem 1G job.sh

Plus généralement, la limite de temps de calcul peut être contournée avec un script de job récursif qui se re-soumet lui-même et reste en queue tant que le premier job ne disparait pas. La ligne de commande ci-dessous doit être écrite à l’intérieur du script lui-même, de préférence au début du script.

sbatch --dependency=afterany:$SLURM_JOBID my_batch_script.sh

$SLURM_JOBID étant l’identifiant du job en cours depuis lequel le job est lancé.

Enchaînement de jobs

Il est possible d’utiliser la notion de dépendance de Slurm pour bâtir un enchaînement (pipeline) de jobs basé sur la réalisation de conditions spécifiques :

% sbatch --dependency=<type:job_id[:job_id][,type:job_id[:job_id]]> -t 0-01:00 -n 2 --mem 10G job.sh

Avec les types de dépendances suivants :

after:jobid[:jobid...]
exécution possible après qu’un ou plusieurs jobs donnés (identifiés par leurs identifiants) aient été démarrés
afterany:jobid[:jobid...]
exécution possible après qu’un ou plusieurs jobs donnés soient terminés
afternotok:jobid[:jobid...]
exécution possible après qu’un ou plusieurs jobs donnés aient échoués
afterok:jobid[:jobid...]
exécution possible après qu’un ou plusieurs jobs donnés se soient terminés avec succès (code retour de 0)
singleton
exécution possible après que tous les jobs d’un même nom appartenant au même utilisateur se soient terminés.

Un exemple de construction d’un tel enchaînement est donné sur cette page.