Pointers 如何将cudamaloc/cudaMemcpy用于指向包含指针的结构的指针?
我环顾了这个网站和其他网站,什么都没用。我在为我的具体案例发帖提问 我有一组矩阵,目标是使用内核让GPU对所有矩阵执行相同的操作。我很确定我可以让内核工作,但是我不能让cudamaloc/cudaMemcpy工作 我有一个指向矩阵结构的指针,它有一个名为elements的成员,指向一些float。我可以做所有非cuda mallocs的都很好 谢谢你的帮助 代码:Pointers 如何将cudamaloc/cudaMemcpy用于指向包含指针的结构的指针?,pointers,cuda,Pointers,Cuda,我环顾了这个网站和其他网站,什么都没用。我在为我的具体案例发帖提问 我有一组矩阵,目标是使用内核让GPU对所有矩阵执行相同的操作。我很确定我可以让内核工作,但是我不能让cudamaloc/cudaMemcpy工作 我有一个指向矩阵结构的指针,它有一个名为elements的成员,指向一些float。我可以做所有非cuda mallocs的都很好 谢谢你的帮助 代码: 谢谢 你必须知道你的内存在哪里。malloc分配主机内存,cudaMalloc分配设备上的内存,并返回指向该内存的指针。但是,此指针
谢谢 你必须知道你的内存在哪里。malloc分配主机内存,cudaMalloc分配设备上的内存,并返回指向该内存的指针。但是,此指针仅在设备函数中有效 您想要的可以通过以下方式实现:
typedef struct {
int width;
int height;
float* elements;
} Matrix;
int main void() {
int rows, cols, numMat = 2; // These are actually determined at run-time
Matrix* data = (Matrix*)malloc(numMat * sizeof(Matrix));
// ... Successfully read from file into "data" ...
Matrix* h_data = (Matrix*)malloc(numMat * sizeof(Matrix));
memcpy(h_data, data, numMat * sizeof(Matrix);
for (int i=0; i<numMat; i++){
cudaMalloc(&(h_data[i].elements), rows*cols*sizeof(float));
cudaMemcpy(h_data[i].elements, data[i].elements, rows*cols*sizeof(float)), cudaMemcpyHostToDevice);
}// matrix data is now on the gpu, now copy the "meta" data to gpu
Matrix* d_data;
cudaMalloc(&d_data, numMat*sizeof(Matrix));
cudaMemcpy(d_data, h_data, numMat*sizeof(Matrix));
// ... Do other things ...
}
这样不行。您已使用cudaMalloc分配了d_数据,并尝试访问主机上的d_数据[i],这是不可能的。更好的方法是使用malloc在主机上分配d_数据,然后使用cudaMalloc在设备上分配d_数据元素。不清楚您如何在设备代码中使用分配的结构。谢谢@sgar91。但是你说我在哪里尝试访问d_数据[I]?在第一个参数中:cudaMemcpyd_数据[I]。元素,数据[I]。元素,行*cols*sizeoffloat,cudamemcpyhostodevice;。试图访问主机上的设备指针。@sgar91-在设备代码中,我只需要能够操作每个矩阵的元素。我没有看到在成员位于设备上的主机上分配设备结构。你能举个简单的例子吗?非常感谢。谢谢@kronos,我会试试这个。使用中间指针h_数据是实现这一点的标准方法吗?这要视情况而定。它表示宿主代码中的开销,因为您必须将其他结构数据存储两次。这可能会导致错误。您可以做两件事:将设备指针打包到一个数组中,并将该数组传递给内核。该数组也必须在设备内存中分配,或者向结构中添加一个保存设备指针的字段。使用第二个选项,您可以在主机和设备端使用相同的结构,但可以通过元素和设备数据访问主机数据,比如说,通过d_元素。这非常有用。这让我怀疑我是否需要将任何东西完全放到设备上——如果我可以用主机指针调用内核到设备内存。再次感谢!
typedef struct {
int width;
int height;
float* elements;
} Matrix;
int main void() {
int rows, cols, numMat = 2; // These are actually determined at run-time
Matrix* data = (Matrix*)malloc(numMat * sizeof(Matrix));
// ... Successfully read from file into "data" ...
Matrix* h_data = (Matrix*)malloc(numMat * sizeof(Matrix));
memcpy(h_data, data, numMat * sizeof(Matrix);
for (int i=0; i<numMat; i++){
cudaMalloc(&(h_data[i].elements), rows*cols*sizeof(float));
cudaMemcpy(h_data[i].elements, data[i].elements, rows*cols*sizeof(float)), cudaMemcpyHostToDevice);
}// matrix data is now on the gpu, now copy the "meta" data to gpu
Matrix* d_data;
cudaMalloc(&d_data, numMat*sizeof(Matrix));
cudaMemcpy(d_data, h_data, numMat*sizeof(Matrix));
// ... Do other things ...
}
__global__ void doThings(Matrix* matrices)
{
matrices[i].elements[0] = 42;
}