尝试将结构复制到设备内存时 CUDA 参数无效 (cudaMemcpy)
CUDA invalid argument when trying to copy struct to device's memory (cudaMemcpy)
我试图弄清楚我应该如何创建一个注定要发送到设备的结构/类,但我一直得到这个"无效参数"CUDA错误。我做了一个显示错误的小示例:
#include <iostream>
#include <cstdio>
using namespace std;
#define CUDA_WARN(XXX)
do { if (XXX != cudaSuccess) cerr << "CUDA Error: " <<
cudaGetErrorString(XXX) << ", at line " << __LINE__
<< endl; cudaDeviceSynchronize(); } while (0)
struct P {
double x,y;
__host__ __device__ void init(const double &a, const double &b) {
x = a; y = b; }
};
int main(int argc, char **argv)
{
P hP, hQ, dP;
cout << "Size of P: " << sizeof(P) << endl;
CUDA_WARN(cudaMalloc((void**) &dP, sizeof(P)));
printf("dP: %pn", &dP); // print dP's address on the device
hP.init(1.2,-2.1);
hQ.init(0.,0.);
CUDA_WARN(cudaMemcpy(&dP, &hP, sizeof(P), cudaMemcpyHostToDevice));
CUDA_WARN(cudaMemcpy(&hQ, &dP, sizeof(P), cudaMemcpyDeviceToHost));
cout << "Copy back: " << hQ.x << "t" << hQ.y << endl;
dP.init(3.,3.);
CUDA_WARN(cudaMemcpy(&hP, &dP, sizeof(P), cudaMemcpyDeviceToHost));
cout << "Copy new: " << hP.x << "t" << hP.y << endl;
return 0;
}
我正在编译(我的卡是特斯拉C2050):
nvcc -arch sm_20 -o exec file.cu
得到的结果是:
Size of P: 16
dP: 0x7fff82d4b7b0
CUDA Error: invalid argument, at line 24
CUDA Error: invalid argument, at line 25
Copy back: 0 0
CUDA Error: invalid argument, at line 28
Copy new: 1.2 -2.1
------------------
(program exited with code: 0)
Press return to continue
如果你们能帮助我,谢谢你们!
======在@talonmies, @JackOLantern, @Robert Crovella评论后=======
谢谢,伙计们!你真的帮了大忙!根据注释,我可以纠正我的代码,现在它正在工作。只是为了注册最终解决方案:
#include <iostream>
#include <cstdio>
using namespace std;
#define CUDA_WARN(XXX)
do { if (XXX != cudaSuccess) cerr << "CUDA Error: " <<
cudaGetErrorString(XXX) << ", at line " << __LINE__
<< endl; cudaDeviceSynchronize(); } while (0)
struct P {
double x,y;
__host__ __device__ void init(const double &a, const double &b) {
x = a; y = b; }
};
/* INCLUDED KERNEL FUNCTION */
__global__ void dev_P_init(P *p, double a, double b) {
p->init(a,b);
}
int main(int argc, char **argv)
{
P hP, hQ, *dP; //*changed*
cout << "Size of P: " << sizeof(P) << endl;
CUDA_WARN(cudaMalloc((void**) &dP, sizeof(P)));
printf("dP: %pn", &dP); // print dP's address on the device
hP.init(1.2,-2.1);
hQ.init(0.,0.);
CUDA_WARN(cudaMemcpy(dP, &hP, sizeof(P), cudaMemcpyHostToDevice)); //*changed*
CUDA_WARN(cudaMemcpy(&hQ, dP, sizeof(P), cudaMemcpyDeviceToHost)); //*changed*
cout << "Copy back: " << hQ.x << "t" << hQ.y << endl;
dev_P_init<<< 1, 1 >>>(dP,3., 3.); //*call to kernel*
CUDA_WARN(cudaMemcpy(&hP, dP, sizeof(P), cudaMemcpyDeviceToHost)); //*changed*
cout << "Copy new: " << hP.x << "t" << hP.y << endl;
return 0;
}
校正输出:
Size of P: 16
dP: 0x7fff6fa2e498
Copy back: 1.2 -2.1
Copy new: 3 3
------------------
(program exited with code: 0)
Press return to continue
@talonmies已经注意到,&dP
不是一个有效的设备指针。实际上,dP
是驻留在主机上的一个变量,因此它的地址指向主机内存空间。与此相反,当dP
是指针时,cudaMalloc
将其值作为参数接收,其值指向设备内存空间。
这是你的代码的正确版本:
#include <iostream>
#include <cstdio>
using namespace std;
#define CUDA_WARN(XXX)
do { if (XXX != cudaSuccess) cerr << "CUDA Error: " <<
cudaGetErrorString(XXX) << ", at line " << __LINE__
<< endl; cudaDeviceSynchronize(); } while (0)
struct P {
double x,y;
__host__ __device__ void init(const double &a, const double &b) {
x = a; y = b; }
};
int main(int argc, char **argv)
{
P *dP;
P hP, hQ;
CUDA_WARN(cudaMalloc((void**) &dP, sizeof(P)));
CUDA_WARN(cudaMemcpy(dP, &hP, sizeof(P), cudaMemcpyHostToDevice));
CUDA_WARN(cudaMemcpy(&hQ, dP, sizeof(P), cudaMemcpyDeviceToHost));
CUDA_WARN(cudaMemcpy(&hP, dP, sizeof(P), cudaMemcpyDeviceToHost));
return 0;
}
相关文章:
- 如何反转整数参数包
- 使用C++库在Android项目中修改gradle中的cmake参数,用于插入指令的测试
- 如何使用默认参数等选择模板专业化
- 模板参数替换失败,并且未完成隐式转换
- 具有默认模板参数的多态类的模板推导失败
- 如何将函数作为CUDA内核参数传递
- 推力(cuda)错误:无法使用给定参数列表调用函数
- cuda 内核调用/传递参数中的编译错误
- CUDA 模板错误:没有与参数列表匹配的函数模板实例
- 用内核参数在CUDA内核中声明数组
- 函数成员作为 CUDA 内核的参数
- 如何在使用 CUDA 和 Matlab 时将矩阵作为参数
- 与CUDA/OpenMP兼容的`boost::numeric::odeint::runge_kutta-X`模板参数
- CUDA C++内核参数的模板化
- 尝试将结构复制到设备内存时 CUDA 参数无效 (cudaMemcpy)
- 关于CUDA中的const指针和参数传递
- 让eclipse解析或忽略CUDA内核启动参数
- 将常量参数传递给CUDA内核的最快(或最优雅)的方式
- CUDA中的内核参数传递
- 在cuda中作为模板参数