Advertisement
Guest User

Untitled

a guest
Jan 20th, 2018
99
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.77 KB | None | 0 0
  1.  
  2. #include "cuda_runtime.h"
  3. #include "device_launch_parameters.h"
  4.  
  5. #include <stdio.h>
  6. #include <limits>
  7.  
  8. // mnożenie macierzy
  9. #include <windows.h>
  10.  
  11. // rozmiar tablicy
  12. const int N = 32;
  13.  
  14. // rozmiar bloku wątków
  15. const int BLOCK_SIZE = 16;
  16.  
  17. /////////////////////////////////////////////////////////////////////
  18. // funkcja kodu jądra wykonująca mnożenie macierzy C = A*B
  19. // korzysta wyłącznie z pamięci globalnej
  20. __global__ void findNearest(int* A, int* B, int* C)
  21. {
  22.     int idx = threadIdx.x + blockDim.x * blockIdx.x;
  23.  
  24.     int nearest_idx;
  25.     float nearest_dist = FLT_MAX;
  26.     int x = A[idx];
  27.     int y = B[idx];
  28.  
  29.     for (int i = 0; i < N; i++) {
  30.         if (i != idx) {
  31.             float dist = 0;
  32.             dist = sqrtf(powf(x - A[i], 2) + powf(y - B[i],2));
  33.             if (dist < nearest_dist) {
  34.                 nearest_dist = dist;
  35.                 nearest_idx = i;
  36.             }
  37.         }
  38.     }
  39.  
  40.     __syncthreads();
  41.  
  42.     C[idx] = nearest_idx;
  43. }
  44.  
  45. /////////////////////////////////////////////////////////////////////
  46. int main()
  47. {
  48.     // wybór karty na której zostana wykonane obliczenia
  49.     if (cudaSetDevice(0) != cudaSuccess)
  50.     {
  51.         printf("cudaSetDevice failed!  Do you have a CUDA-capable GPU installed?");
  52.  
  53.         return 0;
  54.     }
  55.  
  56.     // utworzenie macierzy A, B, C
  57.     size_t size = N * sizeof(int);
  58.     int *tabA_cpu = (int*)malloc(N * sizeof(int));
  59.     int *tabB_cpu = (int*)malloc(N * sizeof(int));
  60.     int *tabC_cpu = (int*)malloc(N * sizeof(int));
  61.  
  62.     if (!tabA_cpu || !tabB_cpu || !tabC_cpu)
  63.     {
  64.         printf("malloc failed!\n");
  65.  
  66.         return 0;
  67.     }
  68.  
  69.     for (int i = 0; i < N; ++i) {
  70.         tabA_cpu[i] = i;
  71.         tabB_cpu[i] = i;
  72.         tabC_cpu[i] = i;
  73.     }
  74.  
  75.     int *tabA_gpu;
  76.     int *tabB_gpu;
  77.     int *tabC_gpu;
  78.  
  79.     if (cudaMalloc((void**)&tabA_gpu, N * sizeof(int)) != cudaSuccess)
  80.     {
  81.         printf("cudaMalloc failed!\n");
  82.  
  83.         return 0;
  84.     }
  85.     if (cudaMalloc((void**)&tabB_gpu, N * sizeof(int)) != cudaSuccess)
  86.     {
  87.         printf("cudaMalloc failed!\n");
  88.  
  89.         return 0;
  90.     }
  91.     if (cudaMalloc((void**)&tabC_gpu, N * sizeof(int)) != cudaSuccess)
  92.     {
  93.         printf("cudaMalloc failed!\n");
  94.  
  95.         return 0;
  96.     }
  97.  
  98.     if (cudaMemcpy(tabA_gpu, tabA_cpu, size, cudaMemcpyHostToDevice) != cudaSuccess)
  99.     {
  100.         printf("cudaMemcpy failed!\n");
  101.  
  102.         return 0;
  103.     }
  104.     if (cudaMemcpy(tabB_gpu, tabB_cpu, size, cudaMemcpyHostToDevice) != cudaSuccess)
  105.     {
  106.         printf("cudaMemcpy failed!\n");
  107.  
  108.         return 0;
  109.     }
  110.     if (cudaMemcpy(tabC_gpu, tabC_cpu, size, cudaMemcpyHostToDevice) != cudaSuccess)
  111.     {
  112.         printf("cudaMemcpy failed!\n");
  113.  
  114.         return 0;
  115.     }
  116.  
  117.     // wywołanie funkcji kodu jądra; wykonywana przez dwuwymiarowe bloki wątków;
  118.     // bloki zgrupowane są w dwuwymiarową siatkę
  119.     dim3 dimBlock(BLOCK_SIZE);
  120.     dim3 dimGrid(N / BLOCK_SIZE);
  121.  
  122.     // utworzenie zdarzeń do pomiaru czasu obliczeń
  123.     cudaEvent_t start, stop;
  124.     cudaEventCreate(&start);
  125.     cudaEventCreate(&stop);
  126.  
  127.     // zarejestrowanie zdarzenia - początek obliczeń
  128.     cudaEventRecord(start, 0);
  129.  
  130.     // wywołanie odpowiedniego kodu jądra
  131.  
  132.     findNearest << <dimGrid, dimBlock >> >(tabA_gpu, tabB_gpu, tabC_gpu);
  133.  
  134.     // zarejestrowanie zdarzenia - koniec obliczeń
  135.     cudaEventRecord(stop, 0);
  136.  
  137.     // synchronizacja (oczekiwanie na zakończenie zdarzenia stop)
  138.     cudaEventSynchronize(stop);
  139.  
  140.     // wyznaczenie czasu obliczeń
  141.     float ms = 0;
  142.     cudaEventElapsedTime(&ms, start, stop);
  143.     printf("running time on GPU:  %20f [ms]\n", ms);
  144.  
  145.     // usunięcie zdarzeń
  146.     cudaEventDestroy(start);
  147.     cudaEventDestroy(stop);
  148.  
  149.     // odczytanie wynikowej macierzy C z pamięci karty
  150.     if (cudaMemcpy(tabC_cpu, tabC_gpu, size, cudaMemcpyDeviceToHost) != cudaSuccess)
  151.     {
  152.         printf("cudaMemcpy failed!\n");
  153.  
  154.         return false;
  155.     }
  156.  
  157.     // zwolnienie pamięci przydzielonej na karcie
  158.     cudaFree(tabA_gpu);
  159.     cudaFree(tabB_gpu);
  160.     cudaFree(tabC_gpu);
  161.  
  162.     cudaDeviceReset();
  163.  
  164.     for (int i = 0; i < N; i++) {
  165.         printf(i + " nearest point id: " + tabC_cpu[i]);
  166.         printf("\n");
  167.     }
  168.  
  169.     return 0;
  170. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement