2015-10-13 4 views
1

У меня есть некоторые данные:Как повысить производительность памяти?

MyDataType *deviceData, *hostData; 

I выделено возлагал память для данных хостов и памяти для данных устройств:

cudaMallocHost(&hostData, dataSize * sizeof(MyDataType)); 
cudaMalloc(&deviceData, dataSize * (MyDataType)); 

Затем я работаю с этими данными. Каждый раз, когда шаг загружать данные CUDA, данные процесса и загружать данные с CUDA:

cudaMemcpy(deviceData, hostData, dataSize * sizeof(MyDataType), cudaMemcpyHostToDevice); 

//processing data 

cudaMemcpy(hostData, deviceData, dataSize * sizeof(MyDataType), cudaMemcpyDeviceToHost); 

Но этот процесс идет слишком медленно. Копирование данных в CUDA занимает около 3-5% всего рабочего времени. Копирование данных из CUDA занимает около 80-85% всего рабочего времени.

Как уменьшить время передачи данных?

+0

Для меня это было бы важно знать, с какими данными вы работаете. Вы можете создать собственную структуру для хранения ваших данных, вы можете использовать глобальную память для хранения ваших результатов, а когда у вас закончится нехватка памяти, вы сохраните результаты на hdd. Можете ли вы максимизировать графический процессор с вашими расчетами? – semm0

+0

@ semm0 Мой тип данных состоит из некоторых значений float3 и float. Я реализовал модель жидкости (например, SPH). Я использую результаты каждого шага расчета для рендеринга моих частиц. –

+1

Вы действительно уверены, что правильно настроили сроки своего кода? 'cudaMemcpy' является блокирующим вызовом, но запуска ядра запускаются асинхронно. Если вы делаете это неправильно, время, которое вы измеряете для копирования с GPU, может фактически включать время выполнения предыдущих ядер. – talonmies

ответ

0

Это оказалось проблемой времени и асинхронности запуска ядра, а не медленных скоростей передачи данных. Передача времени на перенос устройства включала выполнение предыдущих ядер, потому что вызов cudaMemcpy был первым блокирующим вызовом после запуска ядра. Мы не получили увидеть код любого вещества в вопросе, но решение меняется этот тип последовательности API вызовов:

cudaMemcpy(deviceData, hostData, dataSize * sizeof(MyDataType), cudaMemcpyHostToDevice); 

//processing data by launching kernels 

cudaMemcpy(hostData, deviceData, dataSize * sizeof(MyDataType), cudaMemcpyDeviceToHost); 

к этому:

cudaMemcpy(deviceData, hostData, dataSize * sizeof(MyDataType), cudaMemcpyHostToDevice); 

//processing data by launching kernels 

cudaDeviceSynchronize(); // host code blocks here instead 
cudaMemcpy(hostData, deviceData, dataSize * sizeof(MyDataType), cudaMemcpyDeviceToHost); 
Смежные вопросы