我想将 openMP 程序转换为 cuda c。
我试图在网络和 sdk 上找到我的方式。但是材料超出了我的水平。
我的 c 程序循环遍历n=2^30
索引并添加每个索引的权重。
1) 正确的 grid_size 和 block_size 是多少?
我的猜测是复制openMP并做
grid_size=n/max_number_of_cuda_threads;
block_size=1;
2) 如何在 cuda 中实现 openMP 缩减?
我尝试acudaMemcpy
然后减少标准c中的数组,但它似乎很慢。
我看着thrust
图书馆和它的reduce
经营者。但我看不到如何将它与我当前的代码集成。
程序.c
#include <math.h>
#include <omp.h>
float get_weigth_of_index(long index,float* data){
int i;
float v=0;
for(i=0;i<4;i++)
v+=index*data[i];
return v;
}
int main(){
long i;
float r=0;
long n=pow(2,30);
float data[4]={0,1,2,3};
#pragma omp parallel for reduction (+:r)
for(i=0;i<n;i++)
r+=get_weigth_of_index(i,data);
return 0;
}
程序.cu
#include <stdlib.h>
#include <stdio.h>
#include <omp.h>
#include <math.h>
__device__ float get_weigth_of_index(long index,float* data){
int i;
float v=0;
for(i=0;i<4;i++)
v+=index*data[i];
return v;
}
__global__ void looper(long max_number_of_cuda_threads, float* data,float* result){
long bid=blockIdx.x;
long start=bid*max_number_of_cuda_threads;
long end=start+max_number_of_cuda_threads;
long i;
float r=0;
for(i=start;i<end;i++)
r+=get_weigth_of_index(i,data);
result[bid]=r;
}
int main(){
long n=pow(2,30);
int max_number_of_cuda_threads=1024; //I'm not sure it's correct
long grid_size=n/max_number_of_cuda_threads;
long block_size=1;
float data_host[4]={0,1,2,3};
float* data_device=0;
float* result_device=0;
cudaMalloc((void**)&data_device, sizeof(int)*4);
cudaMemcpy(data_device, data_host, sizeof(int)*4, cudaMemcpyHostToDevice);
cudaMalloc((void**)&result_device, sizeof(float)*grid_size);
looper<<<grid_size,block_size>>>(max_number_of_cuda_threads,data_device,result_device);
//reduction with standard c: cudaMemcpy seems slow
float* result_host=(float*)malloc(sizeof(float)*grid_size);
cudaMemcpy(result_host, result_device, sizeof(float)*grid_size, cudaMemcpyDeviceToHost);
long i;
float v=0;
#pragma omp parallel for reduction(+:v)
for(i=0;i<grid_size;i++)
v+=result_host[i];
printf("result:%f",v);
return 0;
}
我的显卡
Device 0: "Tesla M2050"
Number of multiprocessors: 14
Number of cores: 448
Total amount of constant memory: 65536 bytes
Total amount of shared memory per block: 49152 bytes
Total number of registers available per block: 32768
Warp size: 32
Maximum number of threads per block: 1024
Maximum sizes of each dimension of a block: 1024 x 1024 x 64
Maximum sizes of each dimension of a grid: 65535 x 65535 x 1
Maximum memory pitch: 2147483647 bytes
Texture alignment: 512 bytes