Ви перезавантажуєте сервер, і ваш «той самий» GPU раптом працює повільніше, гарячіше, менш стабільно або просто… інакше.
Кремній не змінювався. Змінився драйвер. І драйвер — це частина, яка має власні погляди: щодо живлення,
частот, пам’яті, планування, обробки помилок, навіть щодо того, які функції є сьогодні порівняно з учора.
У продакшені оновлення драйвера — це не «просто патч». Це перепис поведінки пристрою, який ви вважаєте своїм.
Ставтеся до нього як до зміни контракту апаратного забезпечення. Тому що саме так воно і є.
Що означає, що програмне забезпечення «змiнює» GPU
Коли інженери кажуть «драйвер змінив мій GPU», вони не мають на увазі, що транзистори перепаяні.
Вони мають на увазі, що драйвер змінив спостережувану поведінку GPU — практичний контракт:
як швидко він працює, як відбувається планування, як використовується пам’ять, як обробляються помилки і як він тротлиться під нагрівом або обмеженням потужності.
Сучасний GPU — це результат узгодження між апаратним забезпеченням, прошивкою, ядровим модулем, бібліотеками в просторові користувача і, іноді, демоном,
що зберігає стан між процесами. Різні версії драйверів можуть:
- Змінювати стандартні ліміти потужності та поведінку бусту.
- Змінювати переходи P-state (простої vs обчислювальні частоти).
- Змінювати управління пам’яттю й поведінку виселення (особливо при перевищенні пам’яті).
- Змінювати справедливість планування між контекстами (MPS, MIG, тайм-шафлінг).
- Увімкнути або вимкнути функції (розмір BAR, SR-IOV, resizable BAR, доступ peer-to-peer).
- Змінювати відновлення після помилок: що стає відновлюваною помилкою, а що — «мертвим» GPU, що потребує скидання.
- Змінювати вибір ядер у бібліотеках (cuDNN, cuBLAS) та результати автотюнінгу.
Що болючіше: ви можете робити все «правильно» в коді й усе одно побачити коливання продуктивності на 20% тому, що драйвер змінив стандарт.
Друге, що болить: у драйвера є легітимні причини. Нові драйвери виправляють помилки коректності, проблеми безпеки та умови гонок.
Але вони також змінюють поведінку, а саме поведінка важлива в продакшені.
Примітка про те, що включає «драйвер»
Люди говорять «драйвер» у скороченні, але слід розділяти:
- Ядровий модуль (Linux:
nvidia.koта інші): володіє пристроєм, обробляє переривання, відображення пам’яті, логіку скидання. - Бібліотеки в просторові користувача (CUDA runtime, OpenCL ICD, стек GL/Vulkan): транслюють виклики API в роботу GPU.
- Прошивка (на карті): виконує завдання мікроконтролера як-от управління живленням і інколи примітиви планування.
- Менеджмент-стек (NVML, nvidia-smi, демони персистенції): встановлює частоти, ліміти потужності, режим обчислень, розкладку MIG.
Будь-хто з цих компонентів може змінитися між «версією A» і «версією B». Іноді оновлюють один, а інший залишається старим. Ось де починається веселість.
Факти та історія: як ми отримали GPU, сформовані драйверами
Ось кілька конкретних контекстних пунктів, які пояснюють, чому драйвери сьогодні мають таку вагу. Тримайте їх у голові; вони допомагають діагностувати реальність.
- Ранні GPU були з фіксованою функціональністю. Наприкінці 1990-х і на початку 2000-х GPU здебільшого виконували заздалегідь визначені графічні конвеєри. Драйвери були важливі, але «змінити GPU» означало виправлення помилок і оптимізації продуктивності, а не повністю нову поведінку обчислень.
- Програмовані шейдери перемістили складність у драйвери. Коли GPU стали програмованими (шейдери), драйвери почали виконувати агресивну компіляцію та приймати рішення про планування. Ви отримували продуктивність… і непередбачуваність.
- CUDA (2006) перетворила GPU на загальнопризначні обчислювачі. Це підвищило ставки: коректність і детермінізм почали конкурувати з максимальною пропускною здатністю. Політика драйвера стала частиною продуктивності застосунку.
- Boost-частоти перетворили частоту на регулятор політики програмного забезпечення. Динамічний буст означає, що дві «ідентичні» карти можуть працювати на різних частотах залежно від температури, потужності та евристик драйвера.
- ECC на деяких GPU ввів компроміс швидкість vs безпека. Увімкнення ECC може зменшити доступну пам’ять і іноді продуктивність; драйвери керують звітністю, скрабінгом і іноді стандартами за замовчуванням.
- MPS, а потім MIG змінили семантику спільного використання. Multi-process service і multi-instance GPU — це способи ділити пристрій. Вони також додають нові шляхи для шумних сусідів, трешу контекстів та заплутаної статистики використання.
- Resizable BAR і великі BAR-маппінги змінили шляхи передачі даних CPU↔GPU. Залежно від платформи і драйвера CPU може відобразити більше VRAM напряму, змінюючи поведінку трансферів і продуктивність деяких робочих навантажень.
- Безпека стала функцією драйвера, а не лише ОС. Ізоляція, захист пам’яті та міри пом’якшення живуть у стеку драйвера. Деякі міри коштують продуктивності; деякі виправляють серйозні ризики. Обирайте помірковано, а потім документуйте.
Драйвери як зброя: справжня поверхня атаки
«Зброя» не завжди означає «шкідливе ПЗ». В оперінгу «зброя» часто означає «важіль, що може мовчазно зруйнувати ваші SLO».
Драйвери — саме такий важіль, бо вони сидять під вашим застосунком і над апаратурою.
Зброя випадково: політики, що виглядають як дрейф апаратури
Оновлення драйверів часто приносять нові стандарти: інші криві бусту, інша політика вентиляторів, нові алокатори пам’яті, нове планування.
Ви не помічаєте, поки щось, що раніше працювало у P0, тепер не виходить із P2 під «тим самим» навантаженням,
або копії пам’яті регресують через зміну шляху IOMMU.
Найпростіший спосіб втратити тиждень — вважати, що «апарат стабільний». Апарат стабільний. Контракт — ні.
Зброя навмисно: штовхання в екосистему
Вендори не благодійні. Драйвери можуть спрямовувати вас до певних тулчейнів і відштовхувати від інших:
декомісії, фіч-ґейти, «підтримувані» версії, матриці сумісності, які непомітно карають за оновлення неправильного компонента.
Це не автоматично зло. Так еволюціонують комерційні стеки. Але у продакшені ви маєте ставитись до цього як до градієнта стимулів.
Вирішіть, чи йти за ним, чи ізолюватися фіксацією версій і контрольованими розгортаннями.
Зброя від ворогів: ланцюг постачання і привілеї
Драйвери GPU запускаються з високими привілеями. Вони торкаються простору ядра, DMA, відображення пам’яті. Якщо думати як атакувальник,
драйвер — відмінне місце для пошуку вразливостей.
Ваш відгук не повинен бути панікою. Він має бути: виміряною параноєю.
Підписані пакети, контрольовані репозиторії, secure boot де можливо і план відкату, який ви зможете виконати о 3 ранку.
Як драйвери змінюють продуктивність і надійність
1) Частоти: ваш «той самий» GPU на іншій частоті
Поведінка частот — це політика. Драйвер читає температуру, споживання потужності, тип навантаження і іноді налаштування «application clocks».
Якщо новий драйвер змінив агресивність бусту або інтерпретацію ліміту потужності, ви побачите зміну пропускної здатності без зміни коду.
Шукайте такі підказки: P-state застряг вище холостого, або ніколи не досягає P0 під навантаженням; частоти коливаються; обмеження потужності спрацьовують раніше.
2) Ліміти потужності та цілі по теплу
Ліміт потужності — це не лише «скільки тепла ви виділяєте». Це те, як часто GPU може утримувати буст.
Дата-центри люблять обмеження потужності. МL-тренування ненавидять несподіване обмеження потужності. Ваш драйвер може по-іншому застосовувати або інтерпретувати ці ліміти.
3) Управління пам’яттю та перевищення пам’яті
На папері у вашого GPU X GiB. На практиці алокації, фрагментація та поведінка міграції сторінок визначаються драйвером.
Unified memory, pinned memory і UVA додають шарів, де «вирішує драйвер».
Тому оновлення драйвера може перетворити роботу з «працює добре» на «випадковий OOM на кроці 8000».
Змінився аллокатор пам’яті. Або поріг виселення. Або драйвер тепер резервує більше пам’яті для себе.
4) Планування та конкурентність: MPS, MIG і тайм-шафлінг
Якщо ви ділите GPU, ви довіряєте планувальнику драйвера бути чесним і продуктивним.
Цей планувальник змінюється. Іноді він стає кращим. Іноді змінюється форма хвиль затримки.
MPS може покращити пропускну здатність для багатьох малих ядер. Він також може розмазати помилки між клієнтами і заплутати атрибуцію.
MIG дає сильнішу ізоляцію, але ви все ще можете натрапити на вузькі місця у спільних ресурсах і накладні витрати на рівні драйвера.
5) Обробка помилок і відновлення: різниця між «попередженням» і «мертвим вузлом»
Драйвер вирішує, що робити коли GPU поводиться погано: скинути канал, скинути пристрій або здатися.
Тут живе надійність.
У Linux ви побачите повідомлення NVRM Xid. Іноді вони нешкідливі й відновлювані. Іноді вони передбачають неминучу смерть.
Версії драйвера змінюють те, що вважається «відновлюваним».
6) Вибір ядер у бібліотеках: «оновлення драйвера», що не є тільки драйвером
Багато змін продуктивності, які звинувачують у «драйвері», насправді — зміни евристик у бібліотеках в просторові користувача:
cuDNN обирає інші алгоритми згортки; cuBLAS змінює вибір GEMM; результати автотюнінгу варіюються від незначних змін.
Якщо ви оновили драйвер і CUDA toolkit в одному вікні, ви отримали детективний роман. Розділяйте їх.
Одна цитата про надійність, щоб бути чесним із собою
Парафраз ідеї Вернера Вогельса: Все ламається весь час; будуйте системи, що очікують цього і автоматично відновлюються.
Швидкий план діагностики (перший/другий/третій)
Коли GPU-навантаження сповільнюється або стає нестабільним після зміни драйвера, не починайте з переписування моделі або звинувачення «PCIe».
Почніть із вузького циклу тріажу, який ізолює, де саме змінився контракт.
Перший: підтвердьте, що саме змінилося
- Версія драйвера, версія CUDA, версія ядра.
- Версія прошивки GPU, якщо доступна.
- Ліміт потужності, режим персистенції, режим обчислень, стан MIG/MPS.
- ECC увімкнено/вимкнено.
Другий: вирішіть, чи вузьке місце — у частотах, пам’яті чи плануванні
- Проблема з частотами/потужністю: P-state не досягає очікуваних рівнів, спрацьовує ліміт потужності, температура стрибає, продуктивність коливається.
- Проблема з пам’яттю: OOM, симптоми фрагментації, сплески сторінкування/міграції, раптове зниження ефективного розміру батчу.
- Проблема з плануванням: регресії в мультиорендному режимі, дивне використання, сплески хвостової затримки, ядра очікують інші контексти.
Третій: відтворіть мінімальним тестом і зафіксуйте змінні
- Запустіть стабільний мікробенчмарк або невеликий представницький крок inference/train з фіксованими seed.
- Використовуйте той самий образ контейнера і той самий хост-драйвер під час тестів (або навпаки — контролюйте одну сторону).
- Збирайте: частоти, потужність, температуру, використання, пам’ять, Xid-журнали.
Якщо ви не можете відтворити це в мінімальному тесті, це ймовірно проблема конкурентності або контенції, а не «сирий» GPU-швидкість.
Практичні завдання: команди, виводи, рішення (12+)
Це ті завдання, які я фактично виконую, коли хтось каже «драйвер змінив наші GPU».
Кожне завдання включає: команду, що означає вивід, і рішення, яке ви приймаєте.
Завдання 1: Визначити версію драйвера та інвентар GPU
cr0x@server:~$ nvidia-smi
Tue Jan 13 10:22:41 2026
+---------------------------------------------------------------------------------------+
| NVIDIA-SMI 550.54.14 Driver Version: 550.54.14 CUDA Version: 12.4 |
|-----------------------------------------+----------------------+----------------------|
| GPU Name Persistence-M | Bus-Id Disp.A | Volatile Uncorr. ECC |
| Fan Temp Perf Pwr:Usage/Cap | Memory-Usage | GPU-Util Compute M. |
| | | MIG M. |
|=========================================+======================+======================|
| 0 NVIDIA A100-SXM4-40GB On | 00000000:3B:00.0 Off | 0 |
| 36% 48C P0 210W / 400W| 1234MiB / 40960MiB | 12% Default |
+-----------------------------------------+----------------------+----------------------+
Значення: Підтверджує версію драйвера, сумісність CUDA, режим персистенції, ліміт потужності, perf state і базові лічильники здоров’я.
Рішення: Якщо версія драйвера відрізняється від вашого базового рівня, вважайте все інше підозрілим, поки не доведено стабільність. Зафіксуйте це у нотатках інциденту.
Завдання 2: Підтвердити версію ядрового модуля, що завантажено
cr0x@server:~$ modinfo nvidia | head -n 8
filename: /lib/modules/6.5.0-28-generic/updates/dkms/nvidia.ko
version: 550.54.14
license: NVIDIA
description: NVIDIA kernel module
author: NVIDIA Corporation
srcversion: 8F6C9C5B6B61A2D4E3B1B19
depends:
retpoline: Y
Значення: Переконується, що запущений ядровий модуль відповідає пакету, який ви вважали встановленим.
Рішення: Якщо nvidia-smi і modinfo не збігаються, у вас часткове оновлення або застарілий модуль. Виправте це перед бенчмаркінгом.
Завдання 3: Подивитися недавні помилки драйвера (Xid) і скидання GPU
cr0x@server:~$ sudo dmesg -T | egrep -i 'nvrm|xid|gpu has fallen off|reset' | tail -n 20
[Tue Jan 13 10:18:02 2026] NVRM: Xid (PCI:0000:3b:00): 31, pid=24811, name=python, Ch 0000002a
[Tue Jan 13 10:18:02 2026] NVRM: Xid (PCI:0000:3b:00): 31, pid=24811, name=python, MMU Fault: ENGINE GRAPHICS
[Tue Jan 13 10:18:04 2026] nvidia-modeset: WARNING: GPU:0: Corrected error detected
Значення: Коди Xid — це звіти про помилки на рівні драйвера. MMU-помилки можуть вказувати на багаті ядра, некоректний доступ до пам’яті або регресію драйвера.
Рішення: Якщо Xid з’явилися після оновлення і корелюють із падіннями завдань, перестаньте сперечатися про «продуктивність» і почніть трактувати це як регресію надійності. Розгляньте відкат або ізоляцію на канаркових вузлах.
Завдання 4: Перевірити, чи ліміт потужності було змінено мовчки
cr0x@server:~$ nvidia-smi -q -d POWER | egrep -i 'Power Limit|Default Power Limit|Enforced Power Limit'
Power Limit : 400.00 W
Default Power Limit : 400.00 W
Enforced Power Limit : 400.00 W
Значення: Показує поточну і стандартну політику потужності. Невідповідність між «Default» і «Enforced» — червоний прапор.
Рішення: Якщо enforced limit знизився (поширено у спільних стійках), вирішіть, чи піднімати його (якщо дозволено), чи переналаштувати розміри батчів і очікування. Не бенчмаркуйте з невідомими обмеженнями.
Завдання 5: Спостерігати реальний час частот і причини тротлінгу
cr0x@server:~$ nvidia-smi dmon -s pucvmt -d 1 -c 5
# gpu pwr u c v m t
# Idx W % MHz MHz % C
0 212 12 1410 12150 3 49
0 225 85 1410 12150 61 56
0 238 92 1410 12150 72 59
0 399 98 1170 12150 84 66
0 401 99 1140 12150 86 67
Значення: Ви бачите, як частоти падають, коли спрацьовує ліміт потужності. Використання лишається високим, частоти падають: це тротлінг по потужності.
Рішення: Якщо частоти колапсують при досягненні ліміту потужності, або підніміть ліміт (якщо політика дозволяє), покращіть охолодження/потік повітря, або прийміть нижчу пропускну здатність. Не звинувачуйте «модель».
Завдання 6: Підтвердити режим персистенції (щоб уникнути джиттера при холодному старті)
cr0x@server:~$ nvidia-smi -q | egrep -i 'Persistence Mode' | head -n 1
Persistence Mode : Enabled
Значення: Вимкнений persistence може спричиняти повторні витрати на ініціалізацію і затримки встановлення частот між завданнями.
Рішення: У спільних кластерах, де запускають короткі задачі, увімкніть persistence mode на обчислювальних вузлах, щоб зменшити варіативність — якщо у вашій організації немає причин проти.
Завдання 7: Перевірити режим ECC і лічильники помилок
cr0x@server:~$ nvidia-smi -q -d ECC | egrep -i 'ECC Mode|Volatile|Aggregate'
ECC Mode
Current : Enabled
Pending : Enabled
Volatile Uncorrectable ECC Errors : 0
Aggregate Uncorrectable ECC Errors : 0
Значення: ECC змінює поведінку пам’яті і може виявляти апаратні несправності. Volatile помилки — з моменту завантаження; aggregate — накопичується.
Рішення: Якщо aggregate uncorrectable errors ростуть, це тенденція до апаратного RMA, а не питання налаштування. Карантинуйте вузол.
Завдання 8: Перевірити стан і розкладку MIG (чи GPU справді розшаровано?)
cr0x@server:~$ nvidia-smi -L
GPU 0: NVIDIA A100-SXM4-40GB (UUID: GPU-0a1b2c3d-4e5f-6789-abcd-0123456789ef)
MIG 1g.5gb Device 0: (UUID: MIG-GPU-0a1b2c3d-4e5f-6789-abcd-0123456789ef/1/0)
MIG 1g.5gb Device 1: (UUID: MIG-GPU-0a1b2c3d-4e5f-6789-abcd-0123456789ef/2/0)
Значення: Якщо існують пристрої MIG, ваш «GPU 0» з точки зору завдання не є одним повним GPU.
Рішення: Якщо продуктивність погіршилася після оновлення драйвера і MIG увімкнено, переконайтеся, що ваш планувальник призначає очікуваний профіль MIG. Багато «регресій» — це насправді менші слайси.
Завдання 9: Перевірити ширину/швидкість PCIe (класичний тихий обмежувач)
cr0x@server:~$ sudo lspci -s 3b:00.0 -vv | egrep -i 'LnkCap|LnkSta'
LnkCap: Port #0, Speed 16GT/s, Width x16, ASPM L0s L1, Exit Latency L0s <1us, L1 <8us
LnkSta: Speed 8GT/s (downgraded), Width x8 (downgraded)
Значення: GPU працює на зниженій швидкості/ширині PCIe. Це може статися після змін прошивки, налаштувань BIOS або через проблеми з апаратурою.
Рішення: Якщо лінк понижено, ваш вузький пляшок може бути ввід/вивід хоста. Виправте платформу (пересидіти, BIOS, riser, налаштування ASPM) перед тим, як звинувачувати драйвер.
Завдання 10: Перевірити статус IOMMU (може впливати на продуктивність DMA і сумісність)
cr0x@server:~$ cat /proc/cmdline
BOOT_IMAGE=/vmlinuz-6.5.0-28-generic root=/dev/nvme0n1p2 ro quiet splash intel_iommu=on iommu=pt
Значення: Показує, чи увімкнено IOMMU і чи використовується passthrough. Деякі налаштування погіршуються, якщо IOMMU повністю транслює.
Рішення: Якщо ви бачите несподівані параметри IOMMU після оновлення ядра/драйвера, переоцініть продуктивність DMA і вимоги до ізоляції пристроїв. Не «оптимізуйте» це бездумно.
Завдання 11: Підтвердити, що контейнер бачить очікуване середовище CUDA
cr0x@server:~$ docker run --rm --gpus all nvidia/cuda:12.4.1-base-ubuntu22.04 nvidia-smi
Tue Jan 13 10:25:10 2026
+---------------------------------------------------------------------------------------+
| NVIDIA-SMI 550.54.14 Driver Version: 550.54.14 CUDA Version: 12.4 |
+---------------------------------------------------------------------------------------+
Значення: Підтверджує, що хост-драйвер експонується в контейнері і що інструменти всередині контейнера погоджуються.
Рішення: Якщо контейнер не може запустити nvidia-smi або повідомляє про невідповідні компоненти, виправте інтеграцію контейнерного рантайма (NVIDIA Container Toolkit) перед тим, як ганятися за «багом моделі».
Завдання 12: Виявити зсуви на рівні бібліотек (cuDNN / cuBLAS), що виглядають як регресія драйвера
cr0x@server:~$ python -c "import torch; print(torch.__version__); print(torch.version.cuda); print(torch.backends.cudnn.version())"
2.2.1
12.1
8902
Значення: Версії CUDA/cuDNN у вашому фреймворку важать так само, як і драйвер. Оновлення драйвера може співпасти з оновленням контейнера.
Рішення: Якщо версії змінилися, у вас немає чистого A/B. Перезапустіть тести, змінюючи лише одну змінну (тільки драйвер або тільки контейнер).
Завдання 13: Перевірити список процесів GPU і чи «utilization» вам бреше
cr0x@server:~$ nvidia-smi pmon -c 1
# gpu pid type sm mem enc dec jpg ofa command
# Idx # C/G % % % % % % name
0 24811 C 92 18 0 0 0 0 python
0 25102 C 5 2 0 0 0 0 python
Значення: Кілька обчислювальних процесів ділять пристрій. Ваш «сповільнення» може бути контенцією, а не регресією драйвера.
Рішення: Якщо є несподівані процеси, виправте планування/ізоляцію перш за все. Дебаг продуктивності без контролю за спільним використанням — це астрологія з кращими графіками.
Завдання 14: Захопити короткий трасувальний сніп продуктивності (високого рівня) для доказу регресії
cr0x@server:~$ nvidia-smi --query-gpu=timestamp,driver_version,pstate,clocks.sm,clocks.mem,power.draw,temperature.gpu,utilization.gpu,utilization.memory --format=csv -l 1 -c 5
timestamp, driver_version, pstate, clocks.sm [MHz], clocks.mem [MHz], power.draw [W], temperature.gpu, utilization.gpu [%], utilization.memory [%]
2026/01/13 10:26:31, 550.54.14, P0, 1410, 12150, 225.11, 56, 85, 61
2026/01/13 10:26:32, 550.54.14, P0, 1410, 12150, 238.42, 59, 92, 72
2026/01/13 10:26:33, 550.54.14, P0, 1170, 12150, 399.72, 66, 98, 84
2026/01/13 10:26:34, 550.54.14, P0, 1140, 12150, 401.03, 67, 99, 86
2026/01/13 10:26:35, 550.54.14, P0, 1140, 12150, 401.10, 67, 99, 86
Значення: Це найпростіший «чек» для прикріплення до інциденту: частоти, потужність, температура і використання в одному CSV.
Рішення: Якщо ви можете показати, що частоти падають саме тоді, коли спрацьовують обмеження потужності, ви припиняєте дебати і починаєте домовлятися про політику потужності або виправлення термічних умов.
Короткий жарт №1: Оновлення драйвера GPU — як «невелике прохання про зміну» від фінансів: технічно невелике, емоційно руйнівне.
Три корпоративні міні-історії з передової
Міні-історія 1: Інцидент через хибне припущення
Компанія експлуатувала змішаний парк GPU для тренування й inference. SRE-команда мала просте правило: оновлювати драйвери щомісяця, патчити ядра щокварталу.
Вони припускали, що ключова межа сумісності — це «версія CUDA всередині контейнера». Якщо контейнер запускався, вони були задоволені.
Одного місяця оновлення драйвера покотилося по половині inference-вузлів. Протягом кількох годин хвостова затримка почала поводитись дивно: не катастрофічно, але достатньо, щоб пропустити внутрішнє SLO.
Інженери бачили високий рівень завантаження GPU. Вони припустили, що модель стала «важчою». Це не так.
Справжня зміна була в політиці потужності. Новий драйвер по-іншому інтерпретував контролі ліміту потужності платформи. Під тривалим навантаженням GPU досягали капу і сильніше знижували частоти.
Те саме використання, менше ефективних циклів. Система виглядала «зайнятою», але виконувала менше роботи — класичний крах пропускної здатності, замаскований під продуктивність.
Помилкове припущення було в тому, що «оновлення драйвера не змінюють поведінку потужності». Вони змінюють. Виправлення було банальним: фіксувати й застосовувати ліміти потужності як частину провізії вузла
і зберігати базовий CSV-трейс (як наведено вище) з доведено добре роботи. Після цього «регресії продуктивності» стали доказовими подіями, а не інтуїтивними відчуттями.
Міні-історія 2: Оптимізація, що дала зворотній ефект
Інша організація ганялася за максимальною пропускною здатністю на мультиорендному кластері тренування. Вони ввімкнули фічу шарингу, щоб підвищити використання:
більше задач на GPU, менше простоїв, краща статистика на дашборді.
Спочатку це спрацювало. Потім прийшло оновлення драйвера. Раптом рідкісні тренувальні програми почали падати з помилками, пов’язаними з пам’яттю, і іноді з Xid драйвера.
Помилки не були рівномірними: деякі команди нещасні, інші були в порядку, що робило ситуацію політично смачною й технічно жахливою.
Оптимізація мала приховану ціну: нова версія драйвера змінила поведінку управління пам’яттю при перевищенні та збільшила накладні витрати на переключення контекстів
для їхнього набору ядер. Більша конкурентність означала більше фрагментації і більше часу в шляхах драйвера, а не на SM.
«Виправлення» не полягало в тому, щоб назавжди відмовитись від шарингу. Воно полягало в застосуванні з обмеженнями: встановити жорсткий запас по пам’яті на задачу, обмежити одночасні контексти на GPU
і затвердити оновлення драйвера лише після стрес-тестів, що провокують шлях фрагментації. Урок: використання ≠ пропускна здатність, а пропускна здатність ≠ надійність.
Короткий жарт №2: Ми намагались «оптимізувати шаринг GPU» і випадково винайшли генератор випадкових чисел з вентилятором.
Міні-історія 3: Нудна, але правильна практика, що врятувала день
Третя компанія зробила небойову річ: вони тримали «золотий вузол» на кожен клас GPU. Такий самий BIOS, те саме ядро, той самий драйвер,
ті самі образи контейнерів. На ньому щовечора запускали набори: мікробенчмарк, представницький batch inference і короткий цикл тренування.
Коли пропонувалося оновлення драйвера, воно спочатку потрапляло на золотий вузол і невеликий пул канарок. Набір запускався автоматично й порівнювався із зафіксованим базисом.
Команда не вимагала ідеалу; вони вимагали пояснення. Якщо продуктивність рухалась, вони хотіли причину: потужність, частоти, пам’ять, планування або зміни бібліотек.
Одне оновлення показало невелику регресію пропускної здатності, але також усунуло клас Xid-помилок, що раніше викликали рідкісні крахи вузлів.
Бізнес-ефект віддав перевагу надійності. Оскільки були докази, вони могли свідомо обрати компроміс, а не дізнаватися про нього раптово.
«Нудна практика» — це фіксація версій плюс контрольовані канарки плюс артефакти доказу регресій. Це не зробило нікого відомим.
Це зберегло кластер у каналі без інцидентів.
Поширені помилки: симптом → корінь → виправлення
Це патерни, які я регулярно бачу, коли команди ставляться до драйверів GPU як до нешкідливої залежності.
Використовуйте це як довідник режимів відмов.
1) Симптом: Велике використання GPU, але менша пропускна здатність, ніж минулого тижня
Корінь: Змінився ліміт потужності/тротлінг по теплу; частоти нижчі, хоча SM використовується високо.
Виправлення: Виміряйте частоти/потужність за допомогою nvidia-smi --query-gpu і dmon. Підтвердіть ліміт потужності. Покращіть охолодження або налаштуйте капи; переналаштуйте розміри батчів якщо капи — політика.
2) Симптом: Випадковий OOM після оновлення драйвера, той самий розмір батчу
Корінь: Драйвер тепер резервує більше VRAM; змінилася поведінка аллокатора; фрагментація зросла під конкурентністю.
Виправлення: Зменшіть пікове використання VRAM (батч/довжина послідовності), додайте запас, зменшіть одночасні контексти і порівняйте базові використання пам’яті між версіями.
3) Симптом: Тренувальні задачі зависають, вузол потребує перезавантаження
Корінь: Канал GPU завис; драйвер не може відновитися; шлях скидання змінився. Часто корелює з Xid-помилками.
Виправлення: Збирайте dmesg Xid, ізолюйте до версії драйвера, тестуйте відкат. Розгляньте вмикання health-check, що зливає вузол при патернах Xid до того, як він повністю зажене систему в зависання.
4) Симптом: Після оновлення деякі вузли повільні, інші в порядку
Корінь: Змішані версії драйверів, різні розкладки MIG або відмінності платформи (понижений PCIe, налаштування BIOS).
Виправлення: Забезпечте контроль дрейфу конфігурацій. Перевірте версії драйверів, стан MIG і статус PCIe. Не порівнюйте яблука з трохи пошкодженими яблуками.
5) Симптом: Контейнер каже версію CUDA X, але рантайм повідомляє про несумісний драйвер
Корінь: Драйвер хоста занадто старий для очікувань контейнера; або інтеграція контейнерного рантайма зламана.
Виправлення: Узгодьте драйвер хоста з необхідною сумісністю CUDA. Перевірте простим тестом docker run --gpus all ... nvidia-smi перед запуском реальних навантажень.
6) Симптом: Сплески затримки в мультиорендному inference після оновлення
Корінь: Зміни в справедливості планувальника; агресивніший тайм-шафлінг; відмінності в поведінці MPS; збільшені накладні витрати на переключення контекстів.
Виправлення: Зменшіть шаринг, використовуйте профілі MIG для сильної ізоляції, або виділіть GPU для сервісів із чутливою затримкою. Вимірюйте хвостову затримку під навантаженням, а не середню пропускну здатність у ізоляції.
7) Симптом: Продуктивність трансферу PCIe впала
Корінь: Лінк PCIe знижено в ширині/швидкості; змінився режим IOMMU; resizable BAR переключився BIOS/драйвером.
Виправлення: Перевірте lspci -vv LnkSta, підтвердіть налаштування BIOS, валідуйте параметри IOMMU. Якщо потрібно, пересадіть апарат або замініть riser перед налаштуванням софту.
Контрольні списки / покроковий план
Покроково: безпечне розгортання драйвера GPU в продакшні
- Інвентаризуйте та класифікуйте вузли за моделлю GPU, материнською платою, версією BIOS, версією ядра і типом навантаження (тренування vs inference).
- Зафіксуйте базис: збережіть версію драйвера, ліміти потужності, режим ECC, стан MIG/MPS і невеликий бенчмарк з трасою частот/потужності.
- Оновлюйте спочатку лише драйвер (не CUDA toolkit, не контейнери) на золотому вузлі. Збирайте ту саму трасу.
- Запустіть стрес-сьют, що включає довгі ядра, тиск на пам’ять і конкурентність, якщо ви використовуєте це в продакшені.
- Канаркуйте малий пул із репрезентативними навантаженнями. Слідкуйте за хвостовою затримкою й рівнем помилок, а не лише за пропускною здатністю.
- Встановіть явні політики: ліміти потужності, persistence mode, compute mode і розкладку MIG слід конфігурувати, а не покладатися на припущення.
- Розгортайте поступово з чіткою умовою відкату: певні патерни Xid, поріг регресії пропускної здатності або порушення SLO.
- Закріпіть конфігурацію після розгортання: забороніть випадкові автоновлення драйверів на вузлах. Дрейф — це причина, через яку «лише по вівторках повільно».
Передпольотний чекліст для повідомлень «GPU відчувається інакше»
- Чи маємо ми запис версії драйвера до/після?
- Чи порівнювані частоти/потужність/температури?
- Чи змінився стан MIG/MPS?
- Чи змінився режим ECC?
- Чи понижено лінк PCIe?
- Чи є Xid у
dmesg? - Чи змінилися версії CUDA/cuDNN у контейнері одночасно?
- Чи є несподіване мультиорендне використання на GPU?
Операційні запобіжники, які я рекомендую (моя думка)
- Ніколи не оновлюйте драйвер + CUDA toolkit + фреймворк в одному вікні змін, якщо вам важливо знайти корінь проблеми.
- Тримайте золотий вузол на кожен клас GPU з автоматизованим набором регресійних тестів.
- Робіть ліміти потужності явними. За замовчуванням — не контракт.
- Вимагайте план відкату, що включає відкат ядрового модуля і автоматизацію зливу вузла.
- Вимірюйте хвостову затримку для inference і стабільність кроків/с для тренування. Середні значення ховають політику драйвера.
Питання й відповіді
1) Чи може драйвер GPU справді змінити продуктивність без зміни коду?
Так. Драйвери встановлюють частоти, поведінку потужності, політику планування, стратегію алокації пам’яті і евристики вибору ядер у бібліотеках.
Ваш код може бути ідентичним, тоді як ефективний апаратний контракт зміниться.
2) Якщо nvidia-smi показує високе використання, хіба це не доводить, що GPU повністю задіяний?
Ні. Utilization — це «час зайнятості», а не «корисна виконана робота». Ви можете бути на 99% зайнятими при нижчих частотах через ліміт потужності і робити менше роботи.
Завжди дивіться на частоти й потужність разом з utilization.
3) Який найшвидший спосіб довести регресію по потужності/частотах?
Зберіть короткий CSV-трейс pstate, SM-частоти, споживання потужності, температуру й utilization під час навантаження.
Якщо частоти падають, коли потужність досягає капу, у вас є винуватець.
4) Чи стосуються оновлення драйверів здебільшого продуктивності?
Ні. Багато оновлень стосуються коректності, безпеки і стабільності між ядрами та платформами. Зміни продуктивності часто — побічний ефект зсувів політики.
У продакшені виправлення стабільності може коштувати невеликого уповільнення — якщо ви обрали це свідомо.
5) Чи завжди MIG краще для мультиорендності?
Це краща ізоляція, ніж простий тайм-шафлінг, але не чарівність. Ви все ще можете натрапити на вузькі місця у спільних ресурсах і накладні витрати драйвера.
MIG чудовий, коли потрібні передбачувані слайси; він може бути марнотратним, якщо навантаження імпульсні й не вкладаються у профілі.
6) Чому деякі оновлення драйверів збільшують використання пам’яті?
Драйвери можуть резервувати різні обсяги VRAM для внутрішньої звітності, таблиць сторінок або нових фіч.
Також змінюється поведінка бібліотек і аллокаторів. Те «відсутні 1–2 GiB» часто реальні, а не у вашій уяві.
7) Чи слід закріпити драйвери назавжди, коли все працює?
Ні. Постійна фіксація накопичує ризики безпеки і борг сумісності. Фіксуйте свідомо, оновлюйте свідомо.
Контрольований ритм з канарками краще і за хаос, і за застій.
8) У чому різниця між проблемами драйвера і апаратними проблемами?
Апаратні проблеми часто проявляються як стійка тенденція ECC-помилок, відтворювані збої незалежно від версій драйвера або фізичне пониження лінку.
Проблеми драйвера тісно корелюють зі змінами версій і часто впливають на багато вузлів однаково. Використовуйте Xid-журнали і лічильники ECC, щоб відділити їх.
9) Чому продуктивність відрізняється між «ідентичними» GPU?
Варіації кремнію, різниця охолодження, подача живлення та політики бусту мають значення. Драйвери підсилюють ці відмінності, змінюючи евристики бусту й тротлінгу.
Іншими словами: однакові артикульні номери — не однакова поведінка на виконанні.
10) Що зберігати в артефактах інциденту для регресії GPU?
Мінімум: версія драйвера, версія ядра, модель GPU, налаштування ліміту потужності, стан MIG/MPS/ECC, короткий трейc nvidia-smi --query-gpu
і відповідні витяги з dmesg з Xid.
Висновок: що робити наступного понеділка
Якщо ви експлуатуєте GPU в продакшені, перестаньте ставитися до драйверів як до фонової залежності і почніть ставитися до них як до прошивки з власними поглядами.
Драйвери не просто «вмикають пристрій». Вони визначають його поведінку під потужністю, теплом, контенцією і збоями.
Практичні кроки на наступний понеділок:
- Виберіть базовий драйвер для кожного класу GPU і явно зафіксуйте політики потужності/ECC/MIG/MPS.
- Побудуйте невеликий набір регресійних тестів і запускайте його на золотому вузлі та пулі канарок перед розгортаннями.
- Коли бачите регресії, спершу фіксуйте частоти/потужність/util трейс і Xid-журнали. Потім сперечайтесь.
- Розділяйте оновлення драйвера від оновлень CUDA/toolkit/framework, коли бажаєте чисту причину.
- Тримайте шляхи відкату відрепетированими, а не теоретичними.
Апарат старіє. Драйвери еволюціонують. Ваше завдання — зробити ці зміни видимими, перевірними і відворотними — щоб «GPU змінився» став діагнозом, а не забобоном.