Спестете време, необходимо за cudaHostAlloc

Опитвам се да разбера дали има смисъл да копирам данни в фиксирана памет, преди да ги прехвърля към устройството, тъй като нямам влияние върху разпределението на моите входни данни (това е библиотека).

std::vector<int> idata(WORK_SIZE);
int *idata_aligned = NULL;
int *d1 = NULL;
int *d2 = NULL;

for (int i = 0; i < WORK_SIZE; ++i)
    idata[i] = i;
CUDA_CHECK_RETURN(cudaMalloc((void**) &d1, sizeof(int) * WORK_SIZE));
CUDA_CHECK_RETURN(cudaMalloc((void**) &d2, sizeof(int) * WORK_SIZE));

printf("unpinned:\n");
{
    boost::timer::auto_cpu_timer t;
    CUDA_CHECK_RETURN(cudaMemcpy(d1, &idata[0], sizeof(int) * WORK_SIZE, cudaMemcpyHostToDevice));
}

printf("copy to pinned:\n");
{
    boost::timer::auto_cpu_timer t;
    CUDA_CHECK_RETURN(cudaHostAlloc((void**) &idata_aligned, sizeof(int) * WORK_SIZE,cudaHostAllocDefault));
    memcpy(idata_aligned, &idata[0], sizeof(int) * WORK_SIZE);
    CUDA_CHECK_RETURN(cudaMemcpy(d2, idata_aligned, sizeof(int) * WORK_SIZE, cudaMemcpyHostToDevice));
}

Изход за 10 000 000 елемента:

unpinned:
 0.018919s wall, 0.020000s user + 0.000000s system = 0.020000s CPU (105.7%)
copy to pinned:
 0.045428s wall, 0.020000s user + 0.020000s system = 0.040000s CPU (88.1%)

Основният проблем изглежда е cudaHostAlloc (дори без memcpy вторият подход е много по-бавен).

Направих ли нещо лошо? Има ли друг начин за използване на фиксирана памет за вече разпределена памет?


person Hannes    schedule 04.01.2013    source източник


Отговори (1)


Увеличаването на скоростта при използване на фиксирана памет също зависи от размера на трансфера и вашата система. Можете първо да изпълните примера CudaBandwidthTest, за да видите дали наистина има смисъл.

В противен случай бих измерил конкретните части от вашата програма, за да видя къде се губи времето. (разпределяне, memcpy, pcie-трансфер)

В зависимост от размера на паметта, която разпределяте със заключена страница, може също така да се случи системата ви да трябва да смени друга памет на диск, увеличавайки времето за изпълнение.

Както и да е, времената, които показвате, са доста кратки, така че предполагам, че размерите на трансфер също са малки. Трябва също така да можете да увеличите скоростта, като комбинирате няколко малки записа с едно по-голямо.

person rico    schedule 04.01.2013
comment
cudaMemcpy е почти два пъти по-бърз с фиксирана памет в моята система, memcpy отнема около 0,010 s в горния случай. Това е система без суап (но 24 GB RAM). Опитах и ​​с повече елементи: 100 000 000 отнема почти точно 10 пъти повече време и в двата случая; 640 MB трябва да са достатъчни, предполагам. - person Hannes; 04.01.2013
comment
Когато фиксираната памет беше добавена към CUDA, имаше около 2 пъти предимство в производителността на трансфера. С Nehalem (Intel i7) и други процесори, които интегрират контролера на паметта, честотната лента на трансферите е почти същата, така че основното предимство на фиксираната памет е, че тя може да участва в асинхронни memcpy и може да бъде картографирана в адресното пространство на CUDA и достъпна директно от ядра. - person ArchaeaSoftware; 05.01.2013