Hyppää sisältöön

Docs CSC now features an automatic Finnish translation. Click here for more information.

Warning!

Puhti and Mahti are being decommissioned in stages, and their storage areas will become fully unavailable from 15 October 2026. Clean up unnecessary files and move any data you need to keep by 31 August 2026. See the Roihu data migration guide for instructions on transferring your data to Roihu.

Puhti scratch is very full: keep only active data there and move or delete everything else. No new Puhti scratch quota will be granted.

GNU xargs ja rinnakkaiset työnkulut monille pienille, itsenäisille ajoille

Yleiskatsaus

Tämä opas esittelee yhden lähestymistavan suuren läpimenon laskentaan, jossa suuri määrä samankaltaisia, itsenäisiä tehtäviä pakataan pieneen määrään Slurm- töitä sen sijaan, että ne lähetettäisiin yksittäisinä töinä.

Sekä xargs että GNU Parallel ovat komentorivikäyttöliittymätyökaluja suuren tehtävämäärän rinnakkaiseen suorittamiseen, ja ne toimivat tässä tarkoituksessa melko samalla tavalla. Tässä oppaassa käytämme xargs-työkalua, koska se on yksinkertainen, kevyt ja yleensä käyttöjärjestelmän perusasennukseen kuuluva, mutta sama työnkulku voidaan toteuttaa myös GNU Parallelin parallel- komennolla. Tässä käytämme työkalua yhden Slurm-varauksen sisällä, jotta kaikki varatut ytimet pysyvät käytössä: syötetiedostojen nimet välitetään xargs- työkalulle, joka jatkaa tehtävien suorittamista, kunnes ne kaikki ovat valmiita, käynnistäen uuden tehtävän heti kun yksi ydin vapautuu.

xargs sopii tähän tarkoitukseen hyvin, koska se ei vaadi tietokantaa tai pysyvää hallintaprosessia, se käyttää ajastimen resursseja tehokkaasti ja skaalautuu helposti suureen määrään tehtäviä ja solmuja. Toisaalta se suorittaa vain sarjallisia alitehtäviä eikä tue tehtävien välisiä riippuvuuksia tai virheistä palautumista. Se myös edellyttää, että järjestät syöte- ja tulostiedostot huolellisesti, ja skaalauksen yhteydessä sinun on huomioitava järjestelmän I/O-suorituskyky. Bash-skriptauksen perusteiden tuntemus on suositeltavaa.

Jos tehtävilläsi on riippuvuuksia, tarvitset virheistä palautumista tai haluat tutustua työkaluihin, katso sivu suuren läpimenon laskenta ja työnkulut.

Esimerkki: 80000 itsenäisen yhden ytimen tehtävän suorittaminen

Yleisesti työnkulun suunnitteluun tarvitaan kolme syötettä:

  1. Kuinka monta ajoa on yhteensä?
  2. Kuinka kauan yksi ajo kestää?
  3. Kuinka monta tiedostoa luodaan?

Kaksi ensimmäistä määrittävät, miten ajot ryhmitellään eräajoiksi, ja viimeinen määrittää hakemistorakenteen.

Tarkastellaan esimerkkiä, jossa meillä on 80000 itsenäistä, ei-rinnakkaista yhden ytimen ajoa, joista kukin kestää 0–30 minuuttia, keskimäärin 15 minuuttia. Pahimmassa tapauksessa kaikki eräajon ajot kestävät enimmäisajan eli 30 minuuttia. Voimme nähdä, että yksi 40 tunnin eräajo riittää vähintään 80 ajolle yhdellä ytimellä ja 3200 ajolle kaikilla 40 ytimellä täydellä laskentasolmulla. Näin ollen kaikkien 80000 ajon pitäisi mahtua 25:een 40 tunnin eräajoon, joista kukin varaa yhden kokonaisen laskentasolmun.

Oletetaan, että sovelluksemme käyttää levyä erittäin paljon, ja yhden säilytettävän syötetiedoston ja yhden tulostiedoston lisäksi se luo myös 100 väliaikaistiedostoa nykyiseen hakemistoon. Yhdessä hakemistossa voi olla enintään noin 400 syöte- ja tulostiedostoa, ja väliaikaistiedostoille voidaan käyttää I/O-solmujen nopeaa paikallista levyä. Näin 80000 ajolle saadaan 200 hakemistoa, joissa kussakin on 400 ajoa.

many
    dir-001
        input-001
        input-002
        ...
        input-400
    dir-002
    ...
    dir-200

Lisähuomioita tarvitaan, jos yksittäiset ajot ovat rinnakkaisia tai niiden välillä on riippuvuuksia, mutta se on toinen tarina.

Katsotaanpa esimerkkitapauksemme työskriptiä:

#!/bin/bash
#SBATCH --partition=small
#SBATCH --account=<project>
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=40
#SBATCH --time=40:00:00
#SBATCH --mem=160G
#SBATCH --gres=nvme:3600
#SBATCH --array=0-24

cd /scratch/${SLURM_JOB_ACCOUNT}/many

(( from_dir_index = SLURM_ARRAY_TASK_ID * 8 + 1 ))
(( to_dir_index = SLURM_ARRAY_TASK_ID * 8 + 8 ))

job_dirs=$(printf "%dir-%03d " $(seq $from_dir_index $to_dir_index))

find $job_dirs -name 'input-*' | \
    xargs -n 1 -P $SLURM_CPUS_PER_TASK bash wrapper.sh {}

Eräajo varaa kokonaisen solmun 40 tunniksi. Solmussa käynnistyy yksi tehtävä, jolla on pääsy kaikkiin solmun 40 CPU-ytimeen. Koska varaamme kaikki ytimet, voimme samalla varata kaiken muistin ja kaiken paikallisen levyn, tässä ei tarvitse kitsastella. Viimeinen rivi, #SBATCH --array=0,24, kertoo eräajojärjestelmälle, että tästä työstä suoritetaan 25 kopiota, joista kukin yksilöidään ympäristömuuttujassa SLURM_ARRAY_TASK_ID olevalla numerolla. Jonotustilanteesta riippuen moni näistä töistä voi olla käynnissä rinnakkain.

xargs-komento kuuluu yleensä käyttöjärjestelmän perusasennukseen. HPC-järjestelmissä vastaavan GNU Parallelin parallel-komennon käyttö voi usein edellyttää moduulin lataamista. Käytämme xargs-komentoa (tai GNU Parallelia) solmun sisällä kaikkien 3200 ajon "ajastamiseen" työssä niin, että kaikki 40 ydintä ovat koko ajan käytössä, mutta eivät ylikuormitettuina.

Seuraavat rivit laskevat, mitkä hakemistot kuuluvat nykyiseen taulukkotyöhön, käyttäen SLURM_ARRAY_TASK_ID-ympäristömuuttujaa.

Skriptin pää-"silmukka" on toteutettu xargs-komennolla (tai GNU Parallelin parallel-komennolla). Valinnalla -P $SLURM_CPUS_PER_TASK kerromme xargs-työkalulle, että sen tulee pitää 40 komentoa (sovellusta) käynnissä rinnakkain. Koska meidän täytyy kopioida tiedostoja paikalliselle SSD-levylle ja sieltä pois jokaisessa ajossa, käärimme sovelluksemme pieneen komentotulkkiskriptiin wrapper.sh, joka ottaa syötetiedoston nimen argumenttina. Syötetiedostojen nimet välitetään xargs-työkalulle putken kautta, ja xargs jatkaa komennon bash wrapper.sh <syötetiedosto> suorittamista niin kauan kuin putkessa on argumentteja.

Kun wrapper-skripti erotetaan eräajon työskriptistä, kumpaakin voidaan kehittää ja testata erikseen. Yleisesti kannattaa käyttää pieniä testiaineistoja työnkulkua kehitettäessä eikä odottaa, että kaikki onnistuu täydellisesti ensimmäisellä yrittämällä. Voit tutkia ja testata esimerkkitapauksen pientä versiota seuraavasti:

export SBATCH_ACCOUNT=<your project>
wget -c https://a3s.fi/docs-files/support/tutorials/many.tar.gz -O - | tar xz
cd many
bash create_inputs.sh
tree /scratch/${SBATCH_ACCOUNT}/many
sbatch job.sh

Note

Useiden erillisten töiden suorittaminen suuremman varauksen sisällä voi johtaa käyttämättömiin resursseihin. Varmista, että tällaisessa työssä on paljon nopeasti suoritettavia töitä, jotta viimeisenä käynnissä oleva työ ei pidä koko varausta pitkään voimassa. Alityön keston tulisi siis olla paljon lyhyempi kuin varauksen kesto, ja alitöiden määrän paljon suurempi kuin yhdessä tehtävässä pyydettyjen ytimien määrä.

Voit käyttää seff -työkalua selvittääksesi, kuinka kauan aiemmat työt ovat kestäneet.

Suomenkielinen tekoälykäännös

Sisällössä voi esiintyä virheellistä tietoa tekoälykäännöksestä johtuen.

Klikkaa tästä antaaksesi palautetta