LabHub
배우기 러닝패스 코스

HPCとSlurm

GPUを口約束で分け合うと起きること

LabHub 에서 이어서 보기

한국어 원문으로 표시합니다.

한 줄 요약

배치 스케줄러는 "누가 언제 무엇을 쓸지"를 사람의 합의가 아니라 정책으로 결정하는 시스템이다.

概念マップ: "누가 언제 무엇을 쓸지"를 사람의 합의가 아니라 정책으로 결정하는 시스템・OOM 으로 둘 다 죽는다・자원 할당이 상태로 관리되지 않는다・노드 간 인증

왜 이게 필요했나

GPU 서버가 한 대일 때는 이렇게 한다. "지금 쓰시나요?" "아뇨 쓰세요." 잘 돌아간다.

두 대가 되고 사용자가 다섯이 되면 슬랙에 예약 스레드가 생긴다. 세 대가 되고 사용자가 열이 되면 이런 일이 벌어진다.

이 문제들의 공통점은 자원 할당이 상태로 관리되지 않는다는 것이다. 스케줄러는 그것을 큐와 정책으로 바꾼다.

어떻게 동작하나

Slurm 의 구성요소

구성요소 역할 어디서 도나
slurmctld 중앙 컨트롤러. 큐 관리, 스케줄링 결정 관리 노드 1대(HA 시 2대)
slurmd 각 계산 노드의 에이전트. 작업 실행 모든 계산 노드
slurmdbd 계정·사용량 데이터베이스(선택) 관리 노드
munge 노드 간 인증 모든 노드

munge 가 이 그림에서 가장 자주 문제를 일으킨다. 클러스터의 모든 노드가 같은 munge 키를 갖고 있어야 하고, 시계도 맞아야 한다(기본 허용 오차는 수 분). 키가 다르거나 시계가 어긋나면 Munge decode failed 가 나고 노드가 통신하지 못한다.

ls -l /etc/munge/munge.key      # 0400, munge:munge 여야 한다

권한이 조금이라도 느슨하면 munged 가 아예 뜨지 않는다.

스케줄링의 기본 개념

백필(backfill)

기본 스케줄러는 우선순위 순으로 작업을 배치한다. 그런데 큰 작업이 자원을 기다리는 동안 노드가 놀 수 있다. 백필은 "앞 작업의 시작 시각을 늦추지 않는 범위에서" 뒤의 작은 작업을 먼저 채워 넣는다.

백필이 잘 동작하려면 사용자가 --time 을 정직하게 적어야 한다. 모두가 최대값을 적으면 스케줄러는 빈틈을 계산할 수 없다. 그래서 성숙한 클러스터는 "짧게 적으면 빨리 돈다" 는 인센티브를 정책으로 만든다.

자원 요청의 의미

sbatch --nodes=1 --ntasks=1 --cpus-per-task=8 --mem=64G --gres=gpu:a100:2 --time=04:00:00 train.sh

요청하지 않은 자원은 쓸 수 없다. cgroup 으로 강제되므로, --gres=gpu:1 로 받고 코드에서 2장을 쓰려 하면 두 번째 장이 아예 보이지 않는다.

큐가 안 도는 이유를 읽는 법

배치 스케줄러를 붙이고 나면 가장 자주 듣는 말이 "내 작업이 안 돌아간다" 다. 슬럼은 그 이유를 상태 문자열로 알려 주므로, 표만 알면 대부분 스스로 해결된다.

squeue -u $USER -o "%.10i %.9P %.20j %.8T %.10M %R"
scontrol show job <작업번호> | grep -E 'JobState|Reason|NodeList'
사유 대개의 해결
Resources 요청한 자원이 지금 비어 있지 않다 기다린다. 요청을 줄이면 빨라진다
Priority 앞에 우선순위가 높은 작업이 있다 공정 공유 정책의 문제
QOSMaxJobsPerUserLimit 그 QoS 의 동시 실행 상한 배열 작업으로 묶는다
AssocGrpCPUMinutesLimit 계정의 할당량을 다 썼다 관리자에게
ReqNodeNotAvail 그 노드가 예약·정지 중 노드 지정을 푼다
PartitionTimeLimit 요청한 시간이 파티션 상한보다 길다 --time 을 줄인다

요청을 크게 잡을수록 더 오래 기다린다. 노드 4대를 8시간 요청하면 그만큼의 빈 창이 생길 때까지 기다린다. 백필(backfill) 스케줄러는 짧고 작은 작업을 빈틈에 끼워 넣으므로, --time 을 정직하게(넉넉하지만 과하지 않게) 적으면 훨씬 빨리 시작된다. 상한을 최대로 적어 두는 습관이 스스로를 뒤로 미룬다.

노드가 drain 이면 이유가 적혀 있다.

sinfo -R          # drain 사유 목록
scontrol show node <노드> | grep -E 'State|Reason'

디스크 부족, GPU 오류, 헬스체크 실패가 대부분이다. 사유를 안 지우고 노드만 되살리면 다음 검사에서 다시 빠진다.

작업이 죽었는데 이유를 모를 때는 회계 기록을 본다. 표준 출력에 아무것도 안 남고 사라지는 경우, sacct 가 종료 코드와 함께 OUT_OF_MEMORYTIMEOUT 을 알려 준다.

sacct -j <작업번호> --format=JobID,State,ExitCode,MaxRSS,Elapsed,ReqMem

MaxRSSReqMem 에 붙어 있으면 메모리가 원인이다.

현장에서 만나는 모습

홈랩에서도 의미가 있다. GPU 두 장짜리 서버라도 여러 실험을 순차로 돌려야 한다면 스케줄러가 낫다. 밤새 큐에 넣어 두면 자동으로 이어서 돈다. 그리고 그 경험이 그대로 대규모 클러스터로 이어진다.

노드가 DRAIN 으로 빠지는 것. 하드웨어 오류나 GRES 불일치가 감지되면 Slurm 은 그 노드를 자동으로 뺀다. 원인을 고친 뒤 scontrol update NodeName=... State=RESUME 으로 복귀시켜야 한다. 자동으로 돌아오지 않는다 — 이것을 모르면 노드 하나가 며칠씩 놀고 있게 된다.

다음 확인에서 볼 것

이어지는 퀴즈에서는 파티션·백필·자원 요청이 각각 어떤 스케줄링 결정을 만드는지 먼저 확인한다. 그 기준을 통과한 뒤 다음 모듈부터 slurm.conf 작성, GPU GRES 정의, sbatch 스크립트와 깨진 설정 진단을 순서대로 실습한다.