我是 CUDA 领域的初学者。我想对 x 帧(8 位黑白)执行简单的天真平均以减少噪声(或中值)。您建议如何为 X 图像分配内存?
这会好吗?
unsigned char** dev_imageStack = new unsigned char*[X];
for(int i = 0; i < X; i++)
{
cudaMalloc( (void**) &dev_imageStack[i], imageSize);
}
提前谢谢,伊多
我是 CUDA 领域的初学者。我想对 x 帧(8 位黑白)执行简单的天真平均以减少噪声(或中值)。您建议如何为 X 图像分配内存?
这会好吗?
unsigned char** dev_imageStack = new unsigned char*[X];
for(int i = 0; i < X; i++)
{
cudaMalloc( (void**) &dev_imageStack[i], imageSize);
}
提前谢谢,伊多
它依赖于 dev_imageStack 的使用。dev_imageStack 是一个指向 CPU 内存的指针,它持有指向 GPU 内存的指针。您将无法将 dev_imageStack 传递给内核并从中读取,并且您的内核很可能会崩溃。您可以将 dev_imageStack[0].. dev_imageStack[X] 传递给您的内核,因为这是指向 GPU 内存的指针。
如果您需要使用指针传递所有帧,我建议分配一个一维数组并在内核内执行帧偏移以获得正确的帧。
unsigned char* dev_imageStack;
cudaMalloc((void**)&dev_imageStack, imageSize*X);
当您使用它时,您应该通过使用 Y*imageSize 偏移到数组中来访问帧,其中 Y 是您要访问的帧。
如果您想以类似于您描述的方式进行操作,则必须这样做:
unsigned char** host_imageStack = new unsigned char*[X];
for(int i = 0; i < X; i++)
{
cudaMalloc( (void**) &host_imageStack[i], imageSize*sizeof(char));
cudaMemcpy(host_imageStack[i], "char_ptr_to_frame_i_on_host", imageSize*sizeof(char),cudaMemcpyHostToDevice);
}
unsigned char** dev_imageStack;
cudaMalloc((void**)&dev_imageStack, X*sizeof(char*));
cudaMemcpy(dev_imageStack,host_imageStack,X*sizeof(char*),cudaMemcpyHostToDevice);
现在您可以将 dev_imageStack 用作指向内核的 2D 指针。访问帧和像素将通过调用内核中的 dev_imageStack[frame_id][pixel_id] 来完成。
在自己的项目中,我通过这种方式解决了这个问题:
unsigned char* dev_imageStack;
cudaMalloc( (void**)&dev_imageStack, imageSize * frames );
unsigned char* dev_image1 = dev_imageStack;
unsigned char* dev_image2 = dev_image1 + imageSize;
...
unsigned char* dev_imageN = dev_imageN-1 + imageSize;
我只分配了一个大内存块并使用指向几个“子块”的指针。
如果你想要一个包含指向“子块”的指针的数组,你可以这样做。
void* dev_images;
cudaMalloc( (void**)&dev_images_tmp, frames * sizeof( unsigned char* ) );
unsigned char** dev_images = (unsigned char**)dev_images_tmp;
现在在内核中,您可以通过以下方式调用帧 x 的图像:
dev_images[x][index];
使用索引,您可以获取目标图像的元素。