11 KiB
ADR-001: Необязательная CUDA и загрузка cuBLAS из окружения
Статус: Принято; пересмотр обязательной cuBLAS от 2026-03-18 Дата: 2026-03-18 Обновлено: 2026-09-21, задача #2
Контекст
CTranslate2 загружает cuBLAS динамически и не поставляет её в своём wheel.
Прежняя обязательная зависимость добавляла около 581 MB скачивания на Linux
x86_64, даже если пользователь работал только через ONNX CPU.
Наличие nvidia-smi доказывает наличие утилиты драйвера, но не совместимость GPU
с runtime. Автоматический выбор CUDA мог приводить к ошибке на старом GPU.
Прежнее утверждение о недоступности Windows wheel nvidia-cublas-cu12 было
ошибочным: такой wheel есть и для закреплённой версии 12.9.1.4. Следовательно,
системный CUDA Toolkit не должен быть обязательным способом подключения Windows.
Решение
CUDA подключается через extra cuda на Linux/WSL x86_64 и Windows x64.
Драйвер NVIDIA остаётся внешним требованием; Windows также требует Visual C++
Runtime x64. Установка extra не включает CUDA: пользователь выбирает её через
CLI или TOML. auto всегда выбирает ONNX CPU, ASR и VAD получают явный
CPUExecutionProvider. Команды установки и обновления — в
README.
CTranslate2 4.8.1 и cuBLAS 12.9.1.4 закреплены в pyproject.toml, чтобы
установка через uv tool и из клона использовала проверенное сочетание.
В cuBLAS 12.9.2.10 появилась дополнительная зависимость NVRTC. Обновление
версий требует повторной проверки библиотек и bootstrap; одного обновления
lock-файла недостаточно.
Linux: preload по полному пути
_cuda_bootstrap.py загружает libcublas.so.12 через ctypes.CDLL с
RTLD_GLOBAL. Линкер затем разрешает запрос CTranslate2 по soname.
Изменение LD_LIBRARY_PATH внутри процесса не решает задачу: glibc кеширует
пути поиска. Путь optional-пакета определяется через nvidia.cublas.__path__,
что поддерживает namespace package без __file__.
Windows: регистрация каталога и preload DLL
Bootstrap регистрирует nvidia/cublas/bin через os.add_dll_directory, затем
загружает по абсолютным путям сначала cublasLt64_12.dll, затем
cublas64_12.dll. Handles библиотек и регистрации каталога хранятся до
завершения процесса. Повторный вызов не загружает их заново. Это обеспечивает
доступность уже загруженных DLL для динамического загрузчика CTranslate2 и
не требует изменения системного PATH.
Bootstrap вызывается только при создании CUDA-модели, до локального импорта
WhisperModel. Если CTranslate2 ранее импортирован для декодирования аудио,
preload всё равно выполняется до создания CUDA-модели. CPU-путь bootstrap не
вызывает. Отсутствие optional-пакета безопасно: системная cuBLAS всё ещё может
обслужить явно выбранную CUDA. Ошибка загрузки найденной Windows DLL сохраняется.
Ошибки и явный выбор
Явный device из CLI или TOML передаёт strict_device=True при загрузке и
транскрипции. CUDA не заменяется молча на CPU. Подсказки различают отсутствие
библиотек, проблемы драйвера, несовместимость GPU/runtime и нехватку памяти;
отказ по неподдерживаемому типу вычислений учитывает устройство, чтобы
одинаковая ошибка CTranslate2 на CPU не получала CUDA-подсказку. Исходное
сообщение сохраняется. Неизвестная ошибка не получает произвольный
совет установить Toolkit. Это одинаково для одного файла и батча.
Прежний механизм fallback оркестратора при strict_device=False сохранён
для существующих программных callers. Автоматический CLI-путь теперь ONNX,
поэтому он не попадает в CUDA fallback.
Проверка зависимостей Windows
Статическая проверка 2026-09-21: скачаны wheels из PyPI, проверены SHA-256,
для DLL/PYD прочитаны PE imports через objdump -p и строки динамической
загрузки. Модели распознавания не скачивались.
ctranslate2-4.8.1-cp313-cp313-win_amd64.whl, SHA-256d52499f05a60a791aeadee28d609efa130142f376d1ea76b2b1c593bb01f8827.ctranslate2.dllсодержит именаcublas64_12.dllиnvcuda.dll; ссылок на cuDNN и динамическую cudart в этой DLL не обнаружено. В wheel естьcudnn64_9.dll, но её наличие не означает использование cuDNN проверенной рабочей DLL. OpenMP DLL поставляется внутри wheel; импорты MSVCP/VCRUNTIME требуют Visual C++ Runtime.nvidia_cublas_cu12-12.9.1.4-py3-none-win_amd64.whl, SHA-2561e5fee10662e6e52bd71dec533fbbd4971bb70a5f24f3bc3793e5c2e9dc640bf. DLL находятся вnvidia/cublas/bin. cuBLAS импортирует cuBLAS Lt и KERNEL32; cuBLAS Lt импортирует KERNEL32. В строках cuBLAS Lt также найдена динамическая ссылка наnvrtc64_120_0.dll, которой нет в PE imports. Обязательность NVRTC для Whisper этим статическим анализом не установлена; первый реальный Windows-прогон должен проверить и этот путь загрузки.nvblas64_12.dllне требуется проверенному пути CTranslate2.
Основания: CTranslate2 4.8.1 на PyPI, cuBLAS 12.9.1.4 на PyPI, загрузчик CTranslate2, метаданные cuBLAS 12.9.2.10.
Это обоснование состава extra для конкретных wheels, а не подтверждение транскрипции на Windows GPU. Реальный прогон Windows x64 с драйвером и extra, без Toolkit и ручной правки PATH, не выполнен. Linux-тесты с подменой Windows API не заменяют такую проверку.
Проверка поставки и поведения
На Linux выполнены uv run pytest: 524 passed, 2 skipped. Пропуски —
Windows-only кодировка OEM и интеграционный bootstrap без optional-пакета.
До удаления cuBLAS интеграционный тест Linux bootstrap проходил.
Обычный uv sync --locked удаляет прежнюю обязательную cuBLAS;
uv sync --extra cuda --locked --dry-run возвращает её в план установки.
Метаданные собранного wheel проверены для 12 сочетаний платформы, архитектуры
и extra. Полное разрешение зависимостей wheel через uv pip compile для Linux
и Windows, с extra и без, подтверждает отсутствие NVIDIA-пакетов в обычной
установке и наличие только cuBLAS 12.9.1.4 при выборе extra.
Формы uv tool install для клона, клона с extra и именованной Git-зависимости
с extra проверены в отдельном временном каталоге tools. Для проверки самой
команды зависимости были исключены; их разрешение проверено отдельно выше.
Git-транспорт проверялся через локальный репозиторий и ветку реализации,
а не через ещё не опубликованную ветку на сервере. Версия uv — 0.12.17.
Последствия и альтернативы
- Обычная установка не требует NVIDIA-пакетов. FasterWhisper CPU сохраняется.
- Дополнительные библиотеки скачиваются только по выбору пользователя.
- Единый extra заменяет требование установить полный Toolkit на Windows; существующая системная установка библиотек остаётся допустимой.
- Отклонено сохранение обязательной cuBLAS ради готовности CUDA сразу после установки: это увеличивает CPU-установку и не решает несовместимость GPU.
- Отклонено автоматическое включение CUDA по драйверу или extra: установка библиотек не должна менять движок и модель по умолчанию.
- Перезапуск процесса с
LD_LIBRARY_PATHне нужен; явная загрузка библиотек решает проблему без изменения обработки сигналов и файловых дескрипторов. - CUDA extra на Windows ARM64, Linux ARM и macOS в эту задачу не входит.