LLM (Large Language Model)
- 사람처럼 문장을 생성하는 대규모 언어 모델
- GPT, LLaMA 같은 모델 전부 여기에 포함
추론(Inference)
- 이미 학습된 모델이 입력을 받아서 답을 생성하는 과정
- 학습(training)과 반대 개념
서빙(Serving)
- 모델을 여러 사람이 동시에 쓰도록 API 형태로 제공하는 것
- “모델 실행” + “요청 관리” + “운영”까지 포함
LLM(Large Language Model)은 대규모 텍스트 데이터를 학습해 문장을 생성하는 모델을 의미한다. GPT, LLaMA 계열 모델 모두 여기에 포함된다.
이 모델을 학습이 끝난 상태에서 실제로 문장을 생성하는 과정을 추론(inference)이라고 한다. 즉, “질문을 넣고 답을 받는 행위” 자체가 추론이다.
서빙(serving)은 여기서 한 단계 더 나아간 개념이다. 단순히 모델을 실행하는 것이 아니라, 여러 사용자가 동시에 모델을 사용할 수 있도록 API 형태로 제공하고, 요청 관리·지연 시간·장애 대응까지 포함한 운영 관점의 개념이다.
이 구분이 중요한 이유는,
llama.cpp
- 로컬 PC에서 LLM을 실행하기 위한 경량 추론 엔진
- CPU에서도 동작 가능
- 개인 실험용에 최적화
vLLM
- GPU 기반 LLM 서빙 프레임워크
- 여러 요청을 동시에 효율적으로 처리하는 데 초점
TGI (Text Generation Inference)
- HuggingFace에서 만든 프로덕션용 LLM 서빙 시스템
- Kubernetes, API 운영에 적합
FastAPI
- Python 기반 API 서버 프레임워크
- llama.cpp를 감싸서 간단한 서버를 만들 때 사용
CPU
- 일반적인 연산 장치
- 복잡하지만 병렬성이 낮음
GPU
- 단순한 연산을 대량 병렬 처리하는 장치
- LLM 추론에 매우 유리
RAM
- 일반 메모리
- CPU가 사용하는 작업 공간
VRAM
- GPU 전용 메모리
- 모델 가중치, KV cache가 올라감
- 부족하면 실행 자체가 안 됨
CPU는 복잡한 작업을 소수의 코어로 처리하는 범용 연산 장치다. 반면 GPU는 단순한 연산을 수천 개 코어로 동시에 처리하는 병렬 연산 장치다.
Transformer 기반 LLM은 행렬 곱 연산이 대부분이기 때문에 GPU 구조와 잘 맞는다. 이 때문에 LLM 추론은 GPU에서 훨씬 효율적이다.
여기서 메모리 개념이 나뉜다.
LLM 추론 시에는 다음이 VRAM에 올라간다.
따라서 VRAM이 부족하면, RAM이 아무리 많아도 모델은 실행되지 않는다.
7B / 13B / 70B
- 모델 파라미터 개수
- B = Billion (10억)
- 크다고 무조건 좋은 건 아님
context length (n_ctx)
- 모델이 한 번에 기억할 수 있는 토큰 길이
- 길수록 메모리 사용량 증가
딥러닝 모델의 가중치는 결국 숫자다.
이 숫자를 몇 비트로 표현하느냐가 메모리 사용량과 성능에 직접적인 영향을 준다.
대표적인 표현 방식은 다음과 같다.
FP32 (32비트): 정밀도 높음, 4바이트
FP16 (16비트): 정밀도 중간, 2바이트
INT8 (8비트): 정밀도 낮음, 1바이트
FP16은 FP32 대비 모델 크기를 정확히 절반으로 줄인다.
예를 들어 7B 모델 기준으로 보면,
이 차이로 인해 GPU VRAM에 더 큰 모델을 올릴 수 있게 된다.
중요한 점은, FP16은 “품질을 크게 희생한 옵션”이 아니라, 추론 환경에서 사실상 표준에 가까운 설정이라는 점이다.
대부분의 추론 프레임워크는 FP16 또는 BF16을 기준으로 성능과 안정성을 설계하며, 성능 손실은 일반적으로 1–2% 이내로 알려져 있다.
GGUF
- llama.cpp용 모델 포맷
- 가중치 + 토크나이저 + 메타데이터 포함
- 로컬 실행에 최적화
safetensors
- HuggingFace 표준 모델 포맷
- GPU 서빙 환경에 적합
- vLLM/TGI에서 주로 사용
Transformers weights
- HuggingFace Transformers 라이브러리에서 사용하는 모델 가중치
GGUF는 llama.cpp 개발자 Georgi Gerganov가 만든 모델 저장 포맷이다.
기존 GGML 포맷을 개선한 형태로, 로컬 LLM 실행을 전제로 설계되었다.
GGUF의 핵심 특징은 다음과 같다.
파일 이름만 봐도 설정을 유추할 수 있다.
llama-2-7b.Q4_K_M.gguf
양자화는 가중치를 더 적은 비트로 표현해 메모리 사용량을 극단적으로 줄이는 기법이다.
예를 들면,
이 덕분에 CPU 환경에서도 7B, 13B 모델 실행이 가능해졌다.
다만 GGUF 기반 양자화는 로컬 단일 요청 실행에 최적화된 구조이며,
GPU 서빙 환경에서는 AWQ, GPTQ 같은 다른 양자화 방식이 사용된다.
양자화(Quantization)
- 모델 가중치를 더 적은 비트로 표현해서 메모리를 줄이는 기법
Q4 / Q5 / Q8
- 가중치를 몇 비트로 저장하는지 의미
- 숫자 ↓ → 메모리 ↓ / 품질 손실 가능성 ↑
AWQ / GPTQ
- GPU 서빙 환경용 양자화 방식
- GGUF와는 다른 계열
앞선 두 글에서 자주 언급하긴 했지만... llama.cpp는 로컬 환경에서 LLM을 실행하기 위한 경량 추론 엔진이다.
단일 프로세스, 단일 요청을 빠르고 가볍게 처리하는 데 초점이 맞춰져 있다.
반면 vLLM과 TGI는 처음부터 다중 사용자 서빙을 전제로 설계되었다.
vLLM은 특히 continuous batching과 PagedAttention을 통해,
요청이 늘어날수록 GPU 효율이 오히려 좋아지는 구조를 만든다.
TGI는 여기에 더해 pipeline parallelism, Kubernetes 연계를 통한 운영 기능까지 포함한다.
Token
- 모델이 처리하는 최소 단위
- 단어보다 더 잘게 쪼개진 단위
Throughput
- 초당 처리 가능한 토큰 양
- 서버 성능 지표
Latency
- 요청 → 응답까지 걸리는 시간
- 사용자 체감 속도
KV Cache
- 이전 토큰 계산 결과를 저장하는 캐시
- 길어질수록 메모리 사용 증가
Continuous Batching
- 여러 사용자의 요청을 자동으로 묶어서 GPU에 한 번에 처리
- vLLM의 핵심 기술
PagedAttention
- KV cache를 효율적으로 쪼개 관리하는 방식
- vLLM 내부 최적화 기법
LLM은 문장을 토큰(token) 단위로 처리한다.
사용자가 입력한 문장과 모델이 생성하는 응답은 모두 토큰 단위로 쪼개진다.
이 과정에서 이전 토큰 계산 결과를 저장하는 것이 KV cache다.
Context가 길어질수록 KV cache가 커지고, VRAM 사용량도 함께 증가한다.
vLLM의 핵심은 이 KV cache를 요청 단위가 아니라 prefix 단위로 관리한다는 점이다.
이를 통해 여러 요청이 동일한 system prompt를 공유할 수 있고,
batching 효율이 극적으로 올라간다.
API
- 외부에서 모델을 호출하기 위한 인터페이스
SLA
- 서비스 품질 보장 기준
- 응답 시간, 가용성 등
동시 요청 (Concurrency)
- 여러 사용자가 동시에 요청을 보내는 상황
Queue
- 요청이 처리되기 전 대기하는 줄
Blocking
- 하나의 요청이 끝날 때까지 다른 요청이 기다리는 상태
Observability (관측성)
- 로그, 메트릭, 상태를 관찰할 수 있는 능력
Kubernetes (K8s)
- 컨테이너 기반 서버를 자동으로 배포·확장하는 시스템
- TGI와 자주 함께 사용
로컬 환경에서는 다음이 허용된다.
하지만 서빙 환경에서는 전부 장애다.
이 영역부터는 모델 성능이 아니라 시스템 설계 문제가 된다.
그래서 단순 실행 엔진인 llama.cpp와,
서빙 시스템인 vLLM/TGI는 같은 “LLM 도구”로 묶을 수 없다.