Должны ли мы использовать функцию cuda Event для определения времени (например, сортировку) или использовать таймеры процессора - PullRequest
1 голос
/ 20 января 2012

Я пытаюсь рассчитать время сортировки тяги. Представьте, я использую события CUDA. но мне было любопытно, если события Cuda дадут мне неправильное значение. Это связано с тем, что на моем компьютере Thrust сортирует 2 миллиона операций с плавающей запятой в графическом процессоре за 34 мс. Но это кажется слишком быстрым

Я пробовал оба раза процессор и графический процессор и получил следующее:

Процессор (занимает около 36 мс)

__int64 ctr1 = 0 , ctr2 = 0 , freq = 0 ;
    QueryPerformanceFrequency((LARGE_INTEGER *) &freq);
    QueryPerformanceCounter((LARGE_INTEGER *) &ctr1);
    thrust::sort(D.begin(),D.end());
    // transfer data back to host   
    thrust::copy(D.begin(), D.end(), H.begin());
    cudaThreadSynchronize(); // block until kernel is finished

   QueryPerformanceCounter((LARGE_INTEGER *)&ctr2);
    double ans = ((ctr2 - ctr1) * 1.0 / freq);
    printf("The time elapsed in milliseconds is %f\n",(ans*1000));

GPU

cudaEvent_t start, stop;
cudaEventCreate(&start);
cudaEventCreate(&stop);
cudaEventRecord(start, 0);
thrust::sort(D.begin(),D.end());

thrust::copy(D.begin(), D.end(), H.begin());
cudaEventRecord(stop, 0);
cudaEventSynchronize(stop);
float elapsedTime; 
cudaEventElapsedTime(&elapsedTime , start, stop);
printf("time is %f ms", elapsedTime);

Пожалуйста, дайте мне знать, какое время является правильным

Спасибо

Ответы [ 2 ]

10 голосов
/ 20 января 2012

Оба момента правильны с разных сторон. Время ЦП будет включать в себя служебную информацию, вызванную вызовами API и синхронизацией. Если вас интересуют эти издержки, вы должны использовать таймер процессора.

Синхронизация на основе событий изолирует синхронизацию на GPU и дает вам время выполнения GPU.

Другие различия между ЦП и синхронизацией событий заключаются в том, что если thrust :: sort () является первым вызовом графического процессора из текущего потока, то вызов, к которому потребуется, должен установить контекст CUDA и дать вам время, которое включает контекст настроить. Вы не получите эту проблему, если будете использовать синхронизацию на основе событий, потому что контекст будет настроен при вызове cudaEventCreate ().

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

cudaEvent_t start, stop;
cudaEventCreate(&start);
cudaEventCreate(&stop);
cudaEventRecord(start, 0);
for(int i=0; i < 100; i++){
thrust::sort(D.begin(),D.end());

thrust::copy(D.begin(), D.end(), H.begin());
}
cudaEventRecord(stop, 0);
cudaEventSynchronize(stop);
float elapsedTime; 
cudaEventElapsedTime(&elapsedTime , start, stop);
printf("Avg. time is %f ms", elapsedTime/100);
0 голосов
/ 20 января 2012

Ни. Я бы порекомендовал вам использовать NVIDIA Visual Profiler , который поставляется с CUDA SDK. Он скажет вам точное время для каждого процесса на GPU. Для получения дополнительной информации об инструменте посетите его Страница .

...