0

我是 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);
    }

提前谢谢,伊多

4

2 回答 2

1

它依赖于 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] 来完成。

于 2013-02-25T14:35:42.780 回答
0

在自己的项目中,我通过这种方式解决了这个问题:

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];

使用索引,您可以获取目标图像的元素。

于 2013-02-25T14:04:10.503 回答