Обслуживание Llama 3.3 70B на одном узле.
От машины, полученной пять минут назад, до OpenAI-совместимого эндпоинта, отвечающего на запросы — с двумя флагами, которые незаметно вдвое снижают пропускную способность, и одним, из-за которого вас взломают.
Коротко
- Требуется памяти
- 43 GB на 4-bit, 82 GB на FP8, 164 GB на BF16 — всё при контексте 8k
- Самая простая машина
- Одна карта на 80 GB. Без шардинга, без интерконнекта, без синхронизации
- Время до первого токена
- Меньше пятнадцати минут с момента получения, большая часть — загрузка весов
- Единственная ошибка
- Публикация порта 8000 на публичном адресе. У него нет аутентификации
Что вам нужно
70 миллиардов параметров. В 4-bit это 35 GB весов; KV-кэш добавляет ещё 2.5 GB при контексте 8k для одного запроса, а накладные расходы времени выполнения — около 15 %. Всё остальное следует из этих трёх чисел — руководство по расчёту VRAM показывает, откуда они берутся.
| Точность | Веса | Всего при 8k | Всего при 32k | Всего при 128k |
|---|---|---|---|---|
| BF16 / FP16 | 140 GB | 164 GB | 173 GB | 207 GB |
| FP8 | 70 GB | 82 GB | 86 GB | 103 GB |
| 4-bit (AWQ, GPTQ) | 35 GB | 43 GB | 52 GB | 86 GB |
Обратите внимание на строку 4-bit при 128k: веса сжимаются до 35 GB, а кэш не сжимается вовсе, потому что AWQ и GPTQ квантуют только веса. Именно этот факт определяет большую часть выбора машины ниже.
Выбор узла
Самые дешёвые машины в нашем каталоге, где эта модель помещается на одну карту — конфигурация, которая нужна вам, если она доступна: без шардинга не нужна синхронизация, и на одну проблему для отладки меньше.
| Узел | Точность, которая помещается | Память карты | Расчётный tok/s | В месяц |
|---|---|---|---|---|
| NVIDIA RTX A6000 | 4-bit (AWQ, GPTQ) | 48 GB | ~10 | $286/мес |
| 2 × NVIDIA RTX A6000 | 4-bit (AWQ, GPTQ) | 48 GB | ~10 | $597/мес |
| NVIDIA L40S | 4-bit (AWQ, GPTQ) | 48 GB | ~11 | $714/мес |
| NVIDIA A100 PCIe | 4-bit (AWQ, GPTQ) | 80 GB | ~25 | $1,091/мес |
Пропускная способность — это генерация в один поток, ограниченная пропускной способностью памяти, и намеренно консервативная оценка. При непрерывном батчинге суммарная пропускная способность по всем параллельным запросам в разы выше — в этом весь смысл vLLM.
Десять минут настройки
Здесь нет ничего специфичного именно для нас, кроме адреса. Docker, NVIDIA container toolkit и рабочий стек драйверов уже установлены на машине.
$ ssh root@203.0.113.42
$ nvidia-smi --query-gpu=name,memory.total --format=csv
# Weights on the fast local NVMe, not the system volume.
$ mkdir -p /scratch/models
$ df -h /scratch
# A gated model needs a token. Skip if yours is open.
$ export HF_TOKEN=hf_xxxxxxxxxxxxxxxxxxxx
Запуск сервера
Один контейнер. При первом запуске скачивается около 40 GB квантованных весов, что на порту 1 Gbit/s занимает несколько минут; каждый следующий перезапуск — секунды.
$ docker run -d --name vllm --restart unless-stopped \
--gpus all --ipc=host \
-v /scratch/models:/root/.cache/huggingface \
-e HF_TOKEN="$HF_TOKEN" \
-p 127.0.0.1:8000:8000 \
vllm/vllm-openai:latest \
--model casperhansen/llama-3.3-70b-instruct-awq \
--quantization awq_marlin \
--max-model-len 8192 \
--gpu-memory-utilization 0.92
# Watch it load. "Application startup complete" is the signal.
$ docker logs -f vllm
$ curl -s http://127.0.0.1:8000/v1/models | head
$ curl -s http://127.0.0.1:8000/v1/chat/completions \
-H 'Content-Type: application/json' \
-d '{"model":"casperhansen/llama-3.3-70b-instruct-awq",
"messages":[{"role":"user","content":"In one sentence: what is a KV cache?"}],
"max_tokens":80}'
Флаги, которые имеют значение
Не открывать его всему миру
0.0.0.0 на публичном адресе, это открытый сервер инференса, и сканеры находят такие за часы. Обратите внимание на -p 127.0.0.1:8000:8000 в команде выше — именно этот начальный адрес защищает от интернета, и это тот единственный символ, который чаще всего теряется при копировании команды откуда-то ещё.
Обращайтесь к нему со своей машины через SSH-туннель — ни одного открытого порта, ни сертификата для управления, нечего настроить неправильно:
$ ssh -N -L 8000:127.0.0.1:8000 root@203.0.113.42
# Now http://127.0.0.1:8000 on your laptop is the server.
Если ему действительно нужно быть публичным, поставьте перед ним reverse proxy с TLS и API-ключом, а также ограничьте адреса источника в файрволе. В документации есть минимальный набор правил. Для эндпоинта, который отвечает всем подряд, двойная защита — это правильный подход.
Повышение пропускной способности
В порядке, в котором стоит пробовать. Первые два — бесплатны и обычно дают наибольший выигрыш.
- Снизьте
--max-model-lenдо реального контекста. Почти всегда это даёт наибольший выигрыш и не отнимает ничего, чем вы пользовались. - Повысьте
--gpu-memory-utilizationдо 0.95. Это выделенная машина: оставлять место больше не для кого. - Включите FP8 KV-кэш, если карта это поддерживает. Удваивает то, что помещается.
- Батчинг на стороне клиента. Непрерывный батчинг помогает только при одновременном поступлении запросов. Запросы по одному оставляют большую часть карты простаивать, что бы вы ни настроили.
- И только затем — более быстрая карта. Генерация ограничена пропускной способностью памяти, поэтому H200 при 4 800 GB/s примерно в 2,4× быстрее, чем H100 PCIe при 2 000 для той же модели — реальный выигрыш, и самый дорогой пункт в этом списке.
$ docker exec vllm python -m vllm.entrypoints.openai.api_server --help | head -1
$ docker exec vllm vllm bench serve \
--model casperhansen/llama-3.3-70b-instruct-awq \
--num-prompts 200 --request-rate 8
# And watch the card while it runs: if utilisation sits below 90%,
# the bottleneck is your client, not the GPU.
$ nvidia-smi dmon -s um
Поддержание работы
Три вещи, которые стоит сделать в первый день, потому что все три неприятно обнаружить на четырнадцатый.
Политика перезапуска
--restart unless-stopped есть в команде выше. После перезагрузки контейнер возвращается, а веса уже лежат на /scratch, так что всё поднимается меньше чем за минуту.
Следите за картой, а не за процессом
GPU, отвалившийся от шины, оставляет контейнер на вид здоровым. nvidia-smi -q -d PERFORMANCE в проверке состояния это обнаружит; проверка порта — нет.
Веса не резервируются
Они находятся на вашем локальном NVMe и больше нигде. Это нормально — их можно скачать заново. А вот ваши файнтюнинговые адаптеры — нет, так что храните их где-то вне машины.
А когда срок заканчивается, диски стираются в течение часа без льготного периода. Всё на /scratch исчезает вместе с ними. Это сделано намеренно — то же самое обещание гарантирует, что на полученной вами машине не было чужих данных, — но это значит, что последний день срока не подходит для того, чтобы начинать копировать данные.
Проверьте эту модель на каждом узле, который мы сдаём.
Конфигуратор показывает, какие конфигурации помещают её на одну карту, какие вынуждены делить, и сколько стоит каждая.
Другие руководства
- Практика · 10 мин
Файнтюнинг модели 70B на одной карте
QLoRA на одной GPU с 48 GB: что помещается, сколько это стоит в месяц и почему полный файнтюнинг — машина совсем другого уровня.
Читать руководство - Оплата · 8 мин
Оплата сервера криптовалютой
Что на самом деле происходит между нажатием «оплатить» и получением root, какую монету выбрать и четыре ошибки, которые теряют деньги при первом платеже.
Читать руководство - Расчёт · 9 мин
Сколько VRAM реально нужно модели
Арифметика вопроса «поместится ли модель»: веса, KV-кэш и два места, где эмпирическое правило ошибается сразу втрое.
Читать руководство