Что вызывает выделение 12 ГБ памяти и вызывает ошибку CUDA нехватки памяти? Модель, данные или что-то еще?

avatar
ashish.g
1 июля 2021 в 19:08
103
3
0

Я пытаюсь создать классификатор видео на основе 3D CNN, используя Pytorch. Когда я пытаюсь запустить одну точку данных, я сталкиваюсь с этой ошибкой:

CUDA out of memory. Tried to allocate 1.20 GiB (GPU 0; 14.76 GiB total capacity; 12.60 GiB already allocated; 1.09 GiB free; 12.61 GiB reserved in total by PyTorch)

Мои данные из 1000 видео имеют размер около 90 МБ на диске. Я думаю, что загружаю только модель и данные на GPU. Я не могу понять, что вызывает уже выделенные 12,6 ГБ памяти? моя модель слишком велика или это как-то связано с загруженными данными или с чем-то еще? Вот фрагмент моей модели. Он основан на C3D Tran et al, 2015.

    self.conv1 = nn.Conv3d(3, 64, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.pool1 = nn.MaxPool3d(kernel_size=(1, 2, 2), stride=(1, 2, 2))

    self.conv2 = nn.Conv3d(64, 128, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.pool2 = nn.MaxPool3d(kernel_size=(2, 2, 2), stride=(2, 2, 2))

    self.conv3a = nn.Conv3d(128, 256, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.conv3b = nn.Conv3d(256, 256, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.pool3 = nn.MaxPool3d(kernel_size=(2, 2, 2), stride=(2, 2, 2))

    self.conv4a = nn.Conv3d(256, 512, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.conv4b = nn.Conv3d(512, 512, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.pool4 = nn.MaxPool3d(kernel_size=(2, 2, 2), stride=(2, 2, 2))

    self.conv5a = nn.Conv3d(512, 512, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.conv5b = nn.Conv3d(512, 512, kernel_size=(3, 3, 3), padding=(1, 1, 1))
    self.pool5 = nn.MaxPool3d(kernel_size=(2, 2, 2), stride=(2, 2, 2), padding=(0, 1, 1))

    self.fc6 = nn.Linear(373248, 4096)
    self.fc7 = nn.Linear(4096, 128)
    self.fc8 = nn.Linear(128, 2)

    self.dropout = nn.Dropout(p=0.5)

    self.relu = nn.ReLU()
    self.softmax = nn.Softmax()

Кроме того, я использую Dataset, DataLoader и DeviceDataLoader для загрузки данных. Даже если они загружают все данные сразу, что приводит к раздуванию 90 МБ данных до 12,6 ГБ.

Источник
Sam Mason
1 июля 2021 в 19:48
0

высказывание «1000 видео имеют размер около 90 МБ на диске» не слишком полезно. важнее то, насколько они велики при декодировании. т. е. сколько кадров какого разрешения и какого типа данных вы используете для хранения на графическом процессоре

Ответы (3)

avatar
DerekG
1 июля 2021 в 23:41
2

Важно отметить, что реальная причина, по которой у вас в большинстве случаев возникают проблемы с нехваткой памяти, не обязательно связана с собственным размером самой модели (хотя это напрямую связано с этим). Даже 100 000 000 параметров с одинарной точностью с плавающей запятой занимают всего около 1 ГБ для хранения. (Теперь, в вашем случае, ваша модель на самом деле настолько велика, что только ваши параметры могут потреблять порядка 100 ГБ памяти, но в большинстве моделей это не так).

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

Как указано выше, ваши решения:

  1. уменьшить размер пакета
  2. понизить выборку данных (если возможно)
  3. уменьшить сложность вашей модели

(Кроме того, я не совсем уверен, как вы собираетесь обучать эту модель, но вы не можете, возможно<27355595012566>, надеяться на то, что в качестве входных данных вашей модели будет передано целое видео. Помимо проблем с памятью, модели было бы чрезвычайно трудно изучить временные отношения, необходимые для понимания данных.Обычные методы обработки видео, вероятно, будут передавать модели один кадр или несколько кадров за раз и использовать преобразователь, lstm или другие модель последовательности-вывода для изучения временного контекста.)

ashish.g
2 июля 2021 в 06:58
0

Я понятия не имел, что невинно выглядящая модель может быть причиной зла из-за большого количества параметров в FCN. Кроме того, градиент и другие параметры и вычисления могут вызвать взрыв в памяти. Я уменьшил параметры, уменьшив размерность. Теперь он работает нормально.

avatar
trialNerror
1 июля 2021 в 21:01
1

Первый линейный слой вашей модели (fc6) имеет 373248*4096=1 528 823 808 параметров, что далеко за пределами всего существующего и смехотворно массивно. Это делает саму модель чрезвычайно тяжелой, и из-за этого обработка каждого образца становится еще одной непосильной нагрузкой для вашего графического процессора.

Вам абсолютно необходимо уменьшить размер этого слоя. Один миллион параметров для одного линейного слоя уже весьма значителен, у вас в 1500 раз больше.

DerekG
1 июля 2021 в 23:29
1

Технически GPT-3 имеет около 100 миллиардов параметров, хотя, если честно, его нужно обучать на всем вычислительном кластере.

avatar
SarthakJain
1 июля 2021 в 19:36
0

Проблемы CUDA Out of Memory очень распространены и часто вызваны обработкой большего количества данных за раз, чем может обработать ваш графический процессор.

Самый распространенный способ решить эту проблему — уменьшить размер пакета загрузчика. Поскольку DataLoader является генератором, на самом деле не имеет значения, насколько велик ваш набор данных, но количество изображений, которые вы размещаете в CUDA и выполняете операции с за время или одну итерацию, очень важный. Таким образом, наиболее вероятная проблема заключается в том, что вы слишком много берете от этого генератора и, таким образом, вызываете проблемы с памятью.

Кроме того, модель, которую вы мне прислали, не выглядит слишком большой, чтобы сама по себе выдавать ошибку памяти CUDA. Примечание. На самом деле это может иметь место только в том случае, если вы используете общий сервер, а кто-то другой использует большую часть памяти графического процессора на этом общем ssh-сервере. Если это так, то я предлагаю запустить nvidia-smi или другую команду, чтобы узнать, сколько у вас памяти.

Сартхак