我厌倦了查看用于将数据复制到设备的所有 cuda 样板代码,因此我编写了这个包装函数:
void allocateAndCopyToDevice(void* device_array, const void* host_array, const size_t &count)
{
gpuErrchk(cudaMalloc((void**)&device_array, count));
gpuErrchk(cudaMemcpy(device_array, host_array, count, cudaMemcpyHostToDevice));
}
但由于某种原因,每当使用以这种方式初始化的数组时,都会导致内存访问越界。我使用的初始化代码如下所示:
cuDoubleComplex *d_cmplx;
allocateAndCopyToDevice(d_cmplx,cmplx,size*sizeof(cuDoubleComplex));
谁能解释一下为什么这不起作用?
<小时/>看到 immibis 的评论后,我意识到 cudaMalloc 需要一个指向指针的指针,因此我通过值将指针传递给指针:
void allocateAndCopyToDevice(void** device_array, const void* host_array, const size_t &count)
{
gpuErrchk(cudaMalloc(device_array, count));
gpuErrchk(cudaMemcpy(*device_array, host_array, count, cudaMemcpyHostToDevice));
}
初始化现在看起来像这样:
cuDoubleComplex *d_cmplx;
allocateAndCopyToDevice((void **)&d_cmplx,cmplx,size*sizeof(cuDoubleComplex));
它有效,但我仍然想知道是否有更好的方法来做到这一点?其他人如何处理 cuda 代码中的内存传输?
最佳答案
我会做类似的事情
template <typename T>
T* allocateAndCopyToDevice(const T* host_array, std::size_t count)
{
// some static_assert for allowed types: pod and built-in.
T* device_array = nullptr;
gpuErrchk(cudaMalloc(&device_array, count * sizeof(T)));
gpuErrchk(cudaMemcpy(device_array, host_array, count * sizeof(T), cudaMemcpyHostToDevice));
return device_array;
}
并使用它:
cuDoubleComplex *d_cmplx = allocateAndCopyToDevice(cmplx, size);
关于c++ - cudaMalloc 和 cudaMemcpy 的包装函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34572327/