相关疑难解决方法(0)

cudaMemcpy分段错误

我已经被这个错误困扰了很长一段时间所以我决定在这里发布它.

调用cudaMemcpy时发生此分段错误:

CurrentGrid->cdata[i] = new float[size];
cudaMemcpy(CurrentGrid->cdata[i], Grid_dev->cdata[i], size*sizeof(float),\
                cudaMemcpyDeviceToHost);
Run Code Online (Sandbox Code Playgroud)

CurrentGrid并且Grid_dev分别指向grid主机和设备上的类对象,在此上下文中i = 0.类成员cdata是一个浮点类型指针数组.为了调试,这cudaMemcpy调用之前对的,我打印出来的每个元素的值Grid_Dev->cdata[i],地址CurrentGrid->cdata[i]Grid_dev->cdata[i]和的价值size,这一切看起来不错.但它仍然以"分段故障(核心转储)"结束,这是唯一的错误消息.cuda-memcheck只给出了"进程没有成功终止".我目前无法使用cuda-gdb.关于去哪儿的任何建议?

更新:现在看来我已经通过cudaMalloc解决了这个问题,设备上的另一个浮点指针A和cudaMemcpy的Grid_dev-> cdata [i]的值为A,然后是cudaMemcpy A来主机.所以上面写的代码段变成:

float * A;
cudaMalloc((void**)&A, sizeof(float));
...
...
cudaMemcpy(&A, &(Grid_dev->cdata[i]), sizeof(float *), cudaMemcpyDeviceToHost);    
CurrentGrid->cdata[i] = new float[size];
cudaMemcpy(CurrentGrid->cdata[i], A, size*sizeof(float), cudaMemcpyDeviceToHost);            
Run Code Online (Sandbox Code Playgroud)

我之所以这样做是因为valgrind突然出现了"8号无效读取",我认为这是指的Grid_dev->cdata[i].我用gdb再次检查它,打印出Grid_dev->cdata[i]NULL值.所以我想即使在这个cudaMemcpy调用中也无法直接取消引用设备指针.但为什么 ?根据这个帖子底部的评论,我们应该能够在cudaMemcpy函数中取消引用设备指针.

另外,我不知道cudaMalloc和cudaMemcpy如何工作的基本机制,但我认为cudaMalloc是一个指针,比如A,我们实际上指定这个指针指向设备上的某个地址.并且通过cudaMemcpy Grid_dev->cdata[i]到A,如上面的修改代码,我们重新分配指针A指向数组.那么,当它是cudaMalloced时,我们不会失去A指向的先前地址的轨道吗?这会导致内存泄漏吗?如果是的话,我应该如何妥善解决这种情况?谢谢!

作为参考,我将完整函数的代码放在下面发生此错误的代码中.

非常感谢!

__global__ void Print(grid *, int);
__global__ void Printcell(grid *, int);
void CopyDataToHost(param_t p, grid …
Run Code Online (Sandbox Code Playgroud)

c++ cuda segmentation-fault

9
推荐指数
1
解决办法
8213
查看次数

CUDA 将继承的类对象复制到设备

我有一个Parent类和一个继承Child类:

class Parent {};
class Child : public Parent {};
Run Code Online (Sandbox Code Playgroud)

有几个子类继承自Parent,但为了简单起见,我只包含了一个。这些继承的类对于我正在从事的项目是必需的。我还有另一个类的对象,我希望将其复制到设备上:

class CopyClass {
  public:
    Parent ** par;
};
Run Code Online (Sandbox Code Playgroud)

请注意,之所以Parent ** par;存在,是因为我需要一个Child对象列表,但它将使用哪个子对象(以及列表的长度)在编译时未知。这是我将CopyClass对象复制到设备上的尝试:

int length = 5;

//Instantiate object on the CPU
CopyClass cpuClass;
cpuClass.par = new Parent*[length];
for(int i = 0; i < length; ++i) cpuClass.par[i] = new Child;

//Copy object onto GPU
CopyClass * gpuClass;
cudaMalloc(&gpuClass,sizeof(CopyClass));
cudaMemcpy(gpuClass,&cpuClass,sizeof(CopyClass),cudaMemcpyHostToDevice);

//Copy dynamically allocated variables to GPU
Parent ** …
Run Code Online (Sandbox Code Playgroud)

c++ inheritance pointers cuda copy

3
推荐指数
1
解决办法
1798
查看次数

CUDA,使用2D和3D阵列

在线上有很多关于在CUDA上分配,复制,索引等2d和3d数组的问题。我得到了很多矛盾的答案,因此我试图汇编过去的问题,看看我是否可以提出正确的问题。

第一个链接:https : //devtalk.nvidia.com/default/topic/392370/how-to-cudamalloc-two-Dimension-array-/

问题:分配二维指针数组

用户解决方案:使用mallocPitch

“正确”的低效率解决方案:在for循环中为每行使用malloc和memcpy(荒谬的开销)

“更正确”的解决方案:将其压缩为1d数组的“专业意见”,有评论说没有人关注性能,但在gpu上使用2d指针结构

第二个链接:https : //devtalk.nvidia.com/default/topic/413905/passing-a-multiDimension-array-to-kernel-how-to-allocate-space-in-host-and-pass-to-device -/

问题:在主机上分配空间并将其传递给设备

子链接:https : //devtalk.nvidia.com/default/topic/398305/cuda-programming-and-performance/dynamically-allocate-array-of-structs/

子链接解决方案:在GPU上编码基于指针的结构是一种糟糕的体验,并且效率极低,因此将其压缩为一维数组。

第三个链接:在CUDA中的设备内存上分配2D阵列

问题:分配和传输二维数组

用户解决方案:使用mallocPitch

其他解决方案:将其展平

第四个链接:如何在CUDA中使用2D阵列?

问题:分配和遍历二维数组

提交的解决方案:不显示分配

其他解决方案:压扁

还有许多其他消息来源大多在说同样的话,但是在多个实例中,我看到有关GPU上指针结构的警告。

许多人认为分配指针数组的正确方法是为每行调用malloc和memcpy,但函数mallocPitch和memcpy2D存在。这些功能的效率有所降低吗?为什么这不是默认答案?

二维数组的另一个“正确”答案是将它们压缩成一个数组。我是否应该习惯生活中的事实?我对我的代码非常拘谨,对我来说感觉很不雅。

我正在考虑的另一种解决方案是使使用1d指针数组的矩阵类最大化,但是我找不到实现双括号运算符的方法。

还要根据此链接:将对象复制到设备?

和子链接答案:cudaMemcpy分段错误

这有点浮躁。

我想全部使用CUDA的类都具有2 / 3d数组,将这些转换为CUDA的1d数组会不会有很多开销?

我知道我已经问了很多问题,但总的来说,我应该习惯于将数组压缩为现实,还是可以使用二维分配和复制函数而不会产生不好的开销,例如在for中调用alloc和cpy的解决方案中环?

c++ arrays cuda

1
推荐指数
1
解决办法
3421
查看次数

标签 统计

c++ ×3

cuda ×3

arrays ×1

copy ×1

inheritance ×1

pointers ×1

segmentation-fault ×1