Ошибка CUDA cudaMalloc после запуска ядра с огромными статическими массивами

0

У меня есть ядро, которое использует около 2 ГБ локальной памяти. Мой cudaMalloc который пытается выделить 2.5 ГБ памяти, сработает, если я запустил этот kernel_func раньше.

Я узнал, что память 2 ГБ по-прежнему занята после завершения работы kernel_func, которая оставляет только 1,5 ГБ для моего cudaMalloc. Кто-нибудь имеет решение или объяснение?

Я знаю, что использование глобальной памяти для kernel_func может решить проблему, но по какой-то причине мне нужно использовать локальную память для этого огромного локального статического массива.

__global__ kernel_func() {

    // The huge static array goes here
    short my_array[50000];

}

int main() {

    kernel_func<<<64, 128>>>();
    // my_array is still occupying memory are this point

    // This cudaMalloc will fail with insufficient memory
    cudaMalloc(/* 2.5GB data */);
}
  • 0
    Вы уверены, что ядро действительно работает? А что такое сообщение об ошибке во время выполнения, возвращаемое вызовом cudaMalloc?
Теги:
cuda

1 ответ

3
Лучший ответ

Если вы позволите завершить kernel_func (например, с помощью cudaDeviceSynchronize()), то я сомневаюсь, что my_array все еще "занимает память", как вы предлагаете, после завершения работы ядра, то есть в момент этого комментария:

    // my_array is still occupying memory are this point

Вы можете быть более уверенным с помощью вызова cudaMemGetInfo() в этот момент.

Тем не менее, вероятно, что вы испытываете какую-то фрагментацию памяти.

Единственный способ, которым я знаю, для "очистки листа" - это вызов cudaDeviceReset() в этот момент. Однако это уничтожит все операции, а также любые выделения на GPU, поэтому вы должны делать это только тогда, когда у вас нет никаких других действий с GPU, и вы должны перераспределять любые данные GPU, которые вам нужны после вызова cudaDeviceReset().

Конечно, если вы можете организовать распределение с помощью cudaMalloc, это может быть проще.

Обратите внимание, что одной функции cudaDeviceReset() недостаточно для восстановления надлежащего функционального поведения графического процессора. Для этого процесс "владения" также должен быть прекращен. Смотрите здесь

Ещё вопросы

Сообщество Overcoder
Наверх
Меню