Как узнать, какой процесс использует GPU?

Вопрос или проблема

Я заметил, что мой GPU использует много своих вычислительных ресурсов. Часто выше 70%, никогда не ниже 50% (измерено сразу после перезагрузки)

14:06:34 ~/  $ gpustat
laptop0                                       Ср Мар  9 14:09:11 2022  
[0] NVIDIA GeForce RTX 2060 с Max-Q Design | 56'C,  74 % |  1369 /  5934 MB 

Но это говорит только о загрузке GPU в целом. У меня нет представления, какой процесс использует GPU.

cpu-stat имеет опцию для отображения процессов, но это показывает только использование памяти:

14:10:38 ~/  $ gpustat -cp
laptop0                                       Ср Мар  9 14:10:44 2022  
[0] NVIDIA GeForce RTX 2060 с Max-Q Design | 54'C,  50 % |  1358 /  5934 MB |
Xorg/4904(843M) gnome-shell/5106(163M) mattermost-desktop/5640(55M) jetbrains-toolbox/6338(22M) 
brave/8888(269M)

Я пытался и не смог найти инструмент, который отображает использование GPU по процессам. Есть много программ для отображения использования GPU, но только в целом, а не по процессам.

Я пробовал:

  • glances
  • cpu-stat
  • nvidia-smi

Может быть, с другим параметром, который я пропустил? Может быть, это невозможно из-за проприетарного характера NVidia?

Инструмент nvidia-smi может получить доступ к GPU и запрашивать информацию. Например:

nvidia-smi --query-compute-apps=pid --format=csv,noheader

Это возвращает pid приложений, которые в настоящее время работают. Это работает, хотя могут быть некоторые оговорки, указанные ниже.

> nvidia-smi
Пт Ноя 11 02:08:18 2022
+-----------------------------------------------------------------------------+
| NVIDIA-SMI 520.61.05    Версия драйвера: 520.61.05    Версия CUDA: 11.8     |
|-------------------------------+----------------------+----------------------+
| Имя GPU        ПERSISTENCE-M| Bus-Id        Disp.A | Нестабильный некорр. ECC |
| Вентилятор  Темп  Perf  Потребление/Макс|         Использование памяти | Загрузка GPU  Вычисл. М. |
|                               |                      |               MIG M. |
|===============================+======================+======================|
|   0  NVIDIA GeForce ...  Вкл   | 00000000:01:00.0 Выкл |                  N/A |
| 50%   61C    P2   301W / 350W |  23683MiB / 24576MiB |     69%      По умолчанию |
|                               |                      |                  N/A |
+-------------------------------+----------------------+----------------------+

+-----------------------------------------------------------------------------+
| Процессы:                                                                  |
|  GPU   GI   CI        PID   Тип   Имя процесса                    Использование GPU памяти |
|        ID   ID                                                   Использование      |
|=============================================================================|
|    0   N/A  N/A   2747694      C   python                          23680MiB |
+-----------------------------------------------------------------------------+

> nvidia-smi --query-compute-apps pid --format=csv,noheader
2747694

Достаточно просто, потому что есть только один процесс. На машине с несколькими процессами это может быть неожиданно:

> nvidia-smi
Пт Ноя 11 11:10:38 2022
+-----------------------------------------------------------------------------+
| NVIDIA-SMI 510.85.02    Версия драйвера: 510.85.02    Версия CUDA: 11.6     |
|-------------------------------+----------------------+----------------------+
| Имя GPU        ПERSISTENCE-M| Bus-Id        Disp.A | Нестабильный некорр. ECC |
| Вентилятор  Темп  Perf  Потребление/Макс|         Использование памяти | Загрузка GPU  Вычисл. М. |
|                               |                      |               MIG M. |
|===============================+======================+======================|
|   0  NVIDIA GeForce ...  Вкл   | 00000000:01:00.0 Выкл |                  N/A |
| N/A   32C    P8    N/A /  N/A |   3546MiB /  4096MiB |      0%      По умолчанию |
|                               |                      |                  N/A |
+-------------------------------+----------------------+----------------------+

+-----------------------------------------------------------------------------+
| Процессы:                                                                  |
|  GPU   GI   CI        PID   Тип   Имя процесса                    Использование GPU памяти |
|        ID   ID                                                   Использование      |
|=============================================================================|
|    0   N/A  N/A      1515      G   /usr/lib/xorg/Xorg                 28MiB |
|    0   N/A  N/A      1724      G   /usr/bin/gnome-shell               67MiB |
|    0   N/A  N/A      2806      G   /usr/lib/xorg/Xorg                296MiB |
|    0   N/A  N/A      3025      G   /usr/bin/gnome-shell               22MiB |
|    0   N/A  N/A      3569      G   ...AAAAAAAAA= --shared-files       10MiB |
|    0   N/A  N/A     12329      G   /usr/lib/firefox/firefox           34MiB |
|    0   N/A  N/A     13708      G   ...oken=16615837409882897952        8MiB |
|    0   N/A  N/A     28690      C   ...abcdef/venv/bin/python3.7     3069MiB |
+-----------------------------------------------------------------------------+

> nvidia-smi --query-compute-apps=pid --format=csv,noheader
28690

Это возвращает только тот процесс, который меня интересует (повезло), типа C. Это может быть неожиданно, но имеет смысл, поскольку C обозначает вычисление, а фильтр запроса предназначен для вычислений (G обозначает графику).

Поскольку nvidia-smi не предоставляет --query-graphics-apps или --query-all-apps, альтернативой является просто разобрать необходимую информацию, используя экспорт в XML.

Вот однострочник на Python, который разбирает все процессы, запущенные на целевом GPU (указанном по адресу PCI/Bus-Id). При желании замените /pid на /process_name, /used_memory или /type для вычислений (C), графики (G) или C+G.

nvidia-smi -x -q | python -c "gpu_id = '0000:06:00.0'; import sys; import xml.etree.ElementTree as ET; root = ET.parse(sys.stdin).getroot(); processes = {gpu.get('id'): [pid.text for pid in gpu.findall('processes/process_info/pid')] for gpu in root.findall('gpu') if gpu_id in gpu.get('id')}; print('\n'.join(next(iter(processes.values()))))"

Ответ или решение

Чтобы определить, какие процессы используют графический процессор (GPU) на системе с NVIDIA, существует несколько инструментов и подходов. Прежде всего, вы уже пробовали некоторые базовые команды, такие как gpustat, glances, cpu-stat и nvidia-smi, но, как вы заметили, они не всегда предоставляют информацию о загрузке GPU по отдельным процессам. Давайте рассмотрим, как можно получить эти данные более детально.

1. Использование nvidia-smi

Команда nvidia-smi является основным инструментом для мониторинга GPU от NVIDIA. Она предоставляет информацию о текущих процессах и их использовании GPU. Вот несколько способов получить нужные вам данные:

1.1 Отображение всех процессов

Для просмотра всех процессов, использующих GPU, можно просто выполнить команду:

nvidia-smi

Эта команда выводит список всех процессов, использующих GPU, включая их PID, тип (графический или вычислительный) и объем используемой памяти. В этом выводе вы можете ознакомиться с теми процессами, которые используют ваш GPU.

1.2 Получение PID процессов, использующих GPU

Если вам нужно вывести только PID процессов, использующих GPU (например, для дальнейшего анализа), используйте следующую команду:

nvidia-smi --query-compute-apps=pid --format=csv,noheader

Однако стоит учитывать, что эта команда возвращает только PID процессов, относящихся к вычислительным приложениям (типа C). Если в вашей системе работают графические (типа G) приложения, их вы не увидите.

2. Использование XML-вывода

Поскольку nvidia-smi не предоставляет прямого способа для запроса всех типов приложений (графических и вычислительных), вы можете воспользоваться XML-выводом для более детального анализа. Ниже приведён пример однострочного Python-скрипта, который анализирует запущенные процессы на заданном GPU:

nvidia-smi -x -q | python -c "gpu_id = '0000:06:00.0'; import sys; import xml.etree.ElementTree as ET; root = ET.parse(sys.stdin).getroot(); processes = {gpu.get('id'): [pid.text for pid in gpu.findall('processes/process_info/pid')] for gpu in root.findall('gpu') if gpu_id in gpu.get('id')}; print('\n'.join(next(iter(processes.values()))))"

Замените '0000:06:00.0' на идентфикатор вашего GPU, если необходимо. В результате вы получите список PID всех процессов, использующих данный GPU.

3. Дополнительные инструменты

Кроме nvidia-smi, существуют и другие инструменты, которые позволяют отслеживать нагрузку на GPU по процессам:

  • htop и glances: Эти инструменты могут предоставить общую информацию о системе, включая некоторые сборки для мониторинга GPU, хотя они не всегда детализируют использование GPU по процессам.

  • gpu-top: Это утилита, которая может отображать загрузку GPU и процессы в реальном времени. Убедитесь, что она поддерживает ваш тип GPU.

Заключение

Определение того, какие процессы используют ваш GPU, может быть сложной задачей, но с помощью nvidia-smi и анализа XML-вывода, а также сторонних утилит, вы сможете получить необходимую информацию. Если у вас остаются вопросы или требуется дополнительная помощь, не стесняйтесь обращаться за советами на специализированные форумы или в техническую поддержку NVIDIA.

Оцените материал
Добавить комментарий

Капча загружается...