nvcc 警告设备变量是主机变量 - 为啥?

Posted

技术标签:

【中文标题】nvcc 警告设备变量是主机变量 - 为啥?【英文标题】:nvcc warns about a device variable being a host variable - why?nvcc 警告设备变量是主机变量 - 为什么? 【发布时间】:2019-08-19 14:14:49 【问题描述】:

我一直在阅读 CUDA 编程指南中关于模板函数的内容,这样的东西是否有效?

#include <cstdio>

/* host struct */
template <typename T>
struct Test 
    T  *val;
    int size;
;

/* struct device */
template <typename T>
__device__ Test<T> *d_test;

/* test function */
template <typename T>
T __device__ testfunc() 
    return *d_test<T>->val;


/* test kernel */
__global__ void kernel() 
    printf("funcout = %g \n", testfunc<float>());

我得到了正确的结果,但有一个警告:

“警告:不能在设备函数中直接读取主机变量“d_test [with T=T]”?

testfunction 中的结构是否用*d_test&lt;float&gt;-&gt;val 实例化?

韩国, 伊吉

【问题讨论】:

【参考方案1】:

不幸的是,CUDA 编译器似乎通常在变量模板方面存在一些问题。如果您look at the assembly,您会发现一切正常。编译器显然会实例化变量模板并分配相应的设备对象。

.global .align 8 .u64 _Z6d_testIfE;

生成的代码使用这个对象,就像它应该做的那样

ld.global.u64   %rd3, [_Z6d_testIfE];

我认为这个警告是编译器错误。请注意,我无法在此处重现 CUDA 10 的问题,因此这个问题很可能现在已经修复。考虑更新你的编译器……

【讨论】:

我能够使用 -std=c++14 在 Fedora 29 上重现 CUDA 10.1 上的问题,所以我认为它可能仍然存在。感谢那些提交错误的人。 好的,谢谢!我正在使用带有 -std=c++14 的 devtoolset-8 中的 CentOS 7.6、CUDA 10.1 和 gcc (g++) 8.2.1 编译器。【参考方案2】:

@MichaelKenzel 是正确的。

这几乎可以肯定是一个 nvcc 错误 - 我现在有 filed(您可能需要一个帐户才能访问它。

另外请注意,我已经能够用更少的代码重现该问题:

template <typename T>
struct foo  int  val; ;

template <typename T>
__device__ foo<T> *x;

template <typename T>
int __device__ f()  return x<T>->val; 

__global__ void kernel()  int y = f<float>(); 

并查看result on GodBolt。

【讨论】:

以上是关于nvcc 警告设备变量是主机变量 - 为啥?的主要内容,如果未能解决你的问题,请参考以下文章

SwiftUI,为啥部分视图没有刷新? @State 变量未更新

为啥 c++ 编译器不会警告返回对局部变量的引用?

请教c语言中打印变量的大小被警告是为啥(VS2019/Debug/x64)?

有没有人真的让 NVCC 和英特尔编译器一起工作?

为啥当我在函数中声明一个名称为全局数组的局部数组时,bash 会引发未绑定变量警告?

从 CUDA 中的主机访问设备上的类成员数组指针