2015-08-20 3 views
1

Я пытаюсь использовать кеш $ acc для определенного цикла внутри 2D-решателя Laplace. Когда я анализирую код с -Mcuda = ptxinfo, он не использует разделяемую память (smem), но код работает медленнее базового условия ?!Использование кеша с OpenACC

Вот часть кода:

!$acc parallel loop reduction(max:error) num_gangs(n/THREADS) vector_length(THREADS) 
    do j=2,m-1 
    do i=2,n-1 
     #ifdef SHARED 
     !$acc cache(A(i-1:i+1,j),A(i,j-1:j+1)) 
     #endif 
     Anew(i,j) = 0.25 * (A(i+1,j) + A(i-1,j) + A(i,j-1) + A(i,j+1)) 
     error = max(error, abs(Anew(i,j) - A(i,j))) 
    end do 
    end do 
!$acc end parallel 

Это выход с помощью $ AcC кэш

ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_20' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 28 registers, 96 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_20' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 12 registers, 96 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_20' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 20 registers, 64 bytes cmem[0] 
ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_30' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 37 registers, 384 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_30' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 14 registers, 384 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_30' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 20 registers, 352 bytes cmem[0] 
ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_35' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 38 registers, 384 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_35' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 14 registers, 384 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_35' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 39 registers, 352 bytes cmem[0] 
ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_50' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 37 registers, 384 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_50' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 12 registers, 384 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_50' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 30 registers, 352 bytes cmem[0] 

Это выход без кэша:

ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_20' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 23 registers, 88 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_20' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 12 registers, 88 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_20' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 20 registers, 64 bytes cmem[0] 
ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_30' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 29 registers, 376 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_30' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 14 registers, 376 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_30' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 20 registers, 352 bytes cmem[0] 
ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_35' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 36 registers, 376 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_35' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 14 registers, 376 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_35' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 39 registers, 352 bytes cmem[0] 
ptxas info : 0 bytes gmem 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu' for 'sm_50' 
ptxas info : Function properties for acc_lap2d_39_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 38 registers, 376 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_39_gpu_red' for 'sm_50' 
ptxas info : Function properties for acc_lap2d_39_gpu_red 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 12 registers, 376 bytes cmem[0] 
ptxas info : Compiling entry function 'acc_lap2d_58_gpu' for 'sm_50' 
ptxas info : Function properties for acc_lap2d_58_gpu 
    0 bytes stack frame, 0 bytes spill stores, 0 bytes spill loads 
ptxas info : Used 30 registers, 352 bytes cmem[0] 

Также он показывает с помощью -Minfo = accel, что кешируется некоторый объем памяти:

acc_lap2d: 
    17, Generating copy(a(:4096,:4096)) 
     Generating create(anew(:4096,:4096)) 
    39, Accelerator kernel generated 
     Generating Tesla code 
     39, Max reduction generated for error 
     40, !$acc loop gang(256) ! blockidx%x 
     41, !$acc loop vector(16) ! threadidx%x 
      Cached references to size [(x)x3] block of a 
     Loop is parallelizable 
    58, Accelerator kernel generated 
     Generating Tesla code 
     59, !$acc loop gang ! blockidx%x 
     60, !$acc loop vector(128) ! threadidx%x 
     Loop is parallelizable 

Мне интересно, как эффективно использовать кеш (разделяемую память в смысле CUDA) в OpenACC?

Большое вам спасибо за помощь.

Бехзад

+1

версии инструментов PGI вы используете? –

+0

Я использую PGI 15.7 –

ответ

3

Компилятор должен быть маркировки это как ошибку. Вы не можете иметь одну и ту же переменную, указанную дважды в одной и той же директиве кэша. Поскольку я работаю в PGI, я добавил технический отчет о проблеме (TPR # 21898) с просьбой об обнаружении этой ошибки. Хотя это не является специально незаконным в текущей спецификации OpenACC, мы подберем его с комитетом по стандартам. Проблема заключается в том, что компилятор не сможет определить, какой из двух кэшированных массивов использовать в этом случае.

Исправление было бы объединить две ссылки:

!$acc cache(A(i-1:i+1,j-1:j+1)) 

Обратите внимание, что информация PTX обыкновения показывать разделяемую память, так как это показывает только общую память фиксированного размера. Мы динамически настраиваем размер общей памяти при запуске ядра CUDA. При просмотре сгенерированного кода CUDA C (-ta = tesla: nollvm, keep) я вижу, что ссылки на разделяемую память генерируются.

Также обратите внимание, что использование общей памяти не гарантирует лучшую производительность. При заполнении общего массива возникают накладные расходы, и сгенерированное ядро ​​должно будет синхронизировать потоки. Если не будет много повторного использования, «кеш» может оказаться нецелесообразным.

Если компилятор PGI может определить, что массив «доступен только для чтения», либо через анализ, либо когда объявлено с помощью «INTENT (IN)», и мы нацеливаем устройство с вычислительной способностью 3.5 или выше, тогда мы будет пытаться использовать текстурированную память. В этом случае добавление «A» в текстурированную память может быть более выгодным.

Надеется, что это помогает, Mat

+0

Большое спасибо за ваш ответ Матем. Это мне очень помогло. Итак, поскольку нет синтаксиса для явного управления общей памятью в openacc (syncthreads() и т. Д.), Как я могу понять, что способ использования кеша $ acc поможет? Могу ли я найти его, посмотрев файл .gpu, созданный «-ta = tesla: nollvm, keep» или я должен сделать что-то еще? Большое спасибо –

+0

Кроме того, в случае использования текстурной памяти, как я могу поместить массив «A» в память текстуры в openacc? –

+0

Привет, Behazd, у меня действительно нет правила быстрого определения того, как определить, помогает ли использование «кеша» или нет.Реализация «кеша» оказалась очень сложной для компилятора. Хотя PGI значительно улучшился с «кешем» в наших выпусках 15.x, у нас все еще осталось несколько дел, которые нуждаются в улучшении. Следовательно, у вас может быть допустимый прецедент, но компилятор не оптимизирует его, как мог. –

Смежные вопросы