Migrating from LSF to Slurm
A guide for users transitioning from LSF to Slurm.
Command Mapping
Most LSF commands have direct Slurm equivalents:
| Task | LSF | Slurm |
|---|---|---|
| Submit batch job | bsub < script.sh | sbatch script.sh |
| Interactive session | bsub -Is bash | salloc or srun --pty bash |
| View your jobs | bjobs | squeue -u $USER |
| View job details | bjobs -l JOBID | squeue -j JOBID -l or scontrol show job JOBID |
| Cancel job | bkill JOBID | scancel JOBID |
| Cancel all your jobs | bkill 0 | scancel -u $USER |
| View queues/partitions | bqueues | sinfo |
| View node status | bhosts | sinfo -N |
| Modify pending job | bmod | scontrol update job JOBID |
| Job history | bhist | sacct |
| Run parallel tasks | mpirun | srun |
Batch Script Directive Translation
LSF uses #BSUB directives; Slurm uses #SBATCH:
| Purpose | LSF (#BSUB) | Slurm (#SBATCH) |
|---|---|---|
| Job name | -J jobname | --job-name=jobname |
| Standard output | -o file.%J | --output=file.%j |
| Standard error | -e file.%J | --error=file.%j |
| Wall time | -W 120 (minutes) or -W 2:00 | --time=02:00:00 |
| Number of tasks | -n 4 | --ntasks=4 |
| Tasks per node | -R "span[ptile=4]" | --ntasks-per-node=4 |
| All tasks on one node | -R "span[hosts=1]" | --nodes=1 |
| Exclusive node | -x | --exclusive |
| Memory limit | -M 16000 (KB) or -R "rusage[mem=16000]" | --mem=16G |
| Queue/Partition | -q queuename | --partition=partname--qos=qosname |
| GPU request | -gpu "num=1" | --gres=gpu:a100:1 |
| Node feature | -R "select[avx2]" | --constraint=avx2 |
| Processor model | -R "select[model==Gold6226R]" | --constraint=cascadelake |
Environment Variable Translation
| Purpose | LSF | Slurm |
|---|---|---|
| Job ID | $LSB_JOBID | $SLURM_JOB_ID |
| Job name | $LSB_JOBNAME | $SLURM_JOB_NAME |
| Number of tasks | $LSB_DJOB_NUMPROC | $SLURM_NTASKS |
| Node list | $LSB_HOSTS | $SLURM_JOB_NODELIST |
| Submit directory | $LS_SUBCWD | $SLURM_SUBMIT_DIR |
| Array index | $LSB_JOBINDEX | $SLURM_ARRAY_TASK_ID |
| CPUs per task | (not directly available) | $SLURM_CPUS_PER_TASK |
Example: Before (LSF)
#!/bin/bash #BSUB -J myanalysis #BSUB -o output.%J #BSUB -e error.%J #BSUB -n 8 #BSUB -R "span[hosts=1]" #BSUB -W 4:00 #BSUB -q standard #BSUB -R "rusage[mem=32000]" module load PrgEnv-intel mpirun ./myprogram
Example: After (Slurm)
#!/bin/bash #SBATCH --job-name=myanalysis #SBATCH --output=output.%j #SBATCH --error=error.%j #SBATCH --ntasks=8 #SBATCH --nodes=1 #SBATCH --time=04:00:00 #SBATCH --partition=compute #SBATCH --mem=32G module load PrgEnv-intel srun ./myprogram
GPU Example: Before (LSF)
#!/bin/bash #BSUB -J gpujob #BSUB -o gpu.%J #BSUB -n 1 #BSUB -W 2:00 #BSUB -q gpu #BSUB -gpu "num=2:mode=shared" module load cuda ./my_gpu_code
GPU Example: After (Slurm)
#!/bin/bash #SBATCH --job-name=gpujob #SBATCH --output=gpu.%j #SBATCH --ntasks=1 #SBATCH --time=02:00:00 #SBATCH --partition=gpu #SBATCH --gres=gpu:a100:2 module load cuda ./my_gpu_code
Key Differences
Job Submission
- LSF: bsub < script.sh (requires redirect)
- Slurm: sbatch script.sh (no redirect needed)
Time Format
- LSF: Minutes (-W 120) or HH:MM (-W 2:00)
- Slurm: HH:MM:SS (--time=02:00:00) or D-HH:MM:SS (--time=1-00:00:00)
Memory Units
- LSF: Gigabytes by default (-M 16 = 16 GB)
- Slurm: Supports suffixes (--mem=16G, --mem=16000M)
MPI Launching
- LSF: mpirun reads LSF environment
- Slurm: Use srun for best integration (mpirun also works)
Job Output
- LSF: %J for job ID in filenames
- Slurm: %j for job ID (lowercase)