LabHub

LLM 서빙 · 배칭(연속 배칭)과 큐잉 · 실습

연속 배칭 스케줄러 시뮬레이션

LabHub 에서 이어서 보기

목표

정적 배칭과 연속 배칭을 각각 시뮬레이션으로 구현해 처리량 차이를 숫자로 확인하고, TTFT SLO 를 만족하는 최대 동시성을 탐색하는 방법을 익힌다.

왜 중요한가

LLM 생성은 요청마다 출력 길이가 제각각입니다. 어떤 요청은 10토큰, 어떤 요청은 1,000토큰입니다. 정적 배칭으로 32개를 묶으면 31개가 일찍 끝나도 가장 긴 하나가 끝날 때까지 그 슬롯들이 비어 있습니다. GPU 는 32개 분량의 자원을 잡고 1개를 처리합니다. 연속 배칭은 매 디코딩 반복마다 끝난 슬롯을 대기 큐의 요청으로 채웁니다. 코드로는 한 줄 차이인데 처리량은 2~5배 달라집니다. 이 실습은 GPU 없이 그 메커니즘만 시뮬레이션으로 재현합니다. 마지막 8번 스텝의 순서가 실무의 핵심입니다 — 처리량부터 최대화하고 지연을 나중에 보면 대개 SLO 를 못 지킵니다. TTFT 목표를 먼저 정하고 그것을 만족하는 최대 동시성을 찾는 것이 올바른 순서입니다.

단계

1. /root/lb2/static.py 로 정적 배칭을 시뮬레이션한다. 요청은 /opt/fixtures/llms/requests.json(100건, 각각 prompt_tokens 와 output_tokens 를 가짐)을 쓰고 배치 크기는 16 이다.
2. /root/lb2/static.txttotal_steps=<n> throughput_tps=<수> slot_util=<0~1 소수> 를 적는다. slot_util 은 0.7 미만이어야 한다.
3. /root/lb2/continuous.py 로 연속 배칭을 시뮬레이션한다. 매 반복마다 끝난 시퀀스를 빼고 대기 큐에서 채운다.
4. /root/lb2/compare.txtstatic_tps=<수> continuous_tps=<수> speedup=<수> 를 적는다. speedup 은 1.8 이상이어야 한다.
5. max_num_seqs=32 상한을 적용한다. /root/lb2/maxseqs.txtmax_num_seqs=32 peak_running=<n> 을 적고 peak_running 은 32 이하여야 한다.
6. 유입률을 초당 5, 10, 20, 40건으로 바꿔 가며 /root/lb2/queue.csvrps,avg_queue,p99_wait_ms 헤더와 4행을 적는다. rps 가 오를수록 p99_wait_ms 가 단조 증가해야 한다.
7. /root/lb2/cost.pyprefill_ms = prompt_tokens * 0.05decode_ms = output_tokens * 8.0 으로 비용을 분리한다. /root/lb2/cost.txttotal_prefill_ms=<수> total_decode_ms=<수> decode_share=<0~1 소수> 를 적는다.
8. /root/lb2/tune.txttarget_ttft_ms=200 max_concurrency=<n> throughput_at_target=<수> 를 적는다. 그 동시성에서 p99 TTFT 가 200 이하여야 한다.

참고

단계 8개

  1. 정적 배칭 시뮬레이터 만들기
  2. 정적 배칭 지표 재기
  3. 연속 배칭 스케줄러 만들기
  4. 두 방식 처리량 비교하기
  5. 동시성 상한 적용하기
  6. 큐 깊이와 p99 대기의 관계 보기
  7. prefill 과 decode 비용 분리 모델링하기
  8. TTFT 목표를 만족하는 최대 동시성 찾기