Я профилировал свою программу Cuda 4, и оказалось, что на каком-то этапе запущенный процесс использовал более 80 гигабайт виртуальной памяти. Это было намного больше, чем я ожидал. Изучив эволюцию карты памяти с течением времени и сравнивая, какую строку кода она выполняет, оказалось, что после этих простых инструкций использование виртуальной памяти увеличилось до 80 GiB:
int deviceCount;
cudaGetDeviceCount(&deviceCount);
if (deviceCount == 0) {
perror("No devices supporting CUDA");
}
Ясно, что это первый вызов Cuda, поэтому инициализируется среда выполнения. После этого карта памяти выглядит (усечена):
Address Kbytes RSS Dirty Mode Mapping
0000000000400000 89796 14716 0 r-x-- prg
0000000005db1000 12 12 8 rw--- prg
0000000005db4000 80 76 76 rw--- [ anon ]
0000000007343000 39192 37492 37492 rw--- [ anon ]
0000000200000000 4608 0 0 ----- [ anon ]
0000000200480000 1536 1536 1536 rw--- [ anon ]
0000000200600000 83879936 0 0 ----- [ anon ]
Теперь эта огромная область памяти отображается в пространство виртуальной памяти.
Хорошо, это, может быть, не большая проблема, поскольку резервирование/выделение памяти в Linux мало что делает, если вы на самом деле не пишете в эту память. Но это действительно раздражает, поскольку, например, задания MPI должны быть указаны с максимальным объемом vmem, который может быть использован при работе. И 80GiB, это только нижняя граница, то для рабочих мест Cuda - нужно также добавить все остальные вещи.
Я могу себе представить, что это связано с так называемым "царапин", которое поддерживает Куда. Вид пула памяти для кода ядра, который может динамически расти и сокращаться. Но это спекуляция. Также он выделяется в памяти устройства.
Любые идеи?