CUDA 5.0“生成可重定位设备代码”导致无效的设备符号错误

时间:2013-03-18 02:44:29

标签: visual-studio-2010 cuda

我正在尝试使用CUDA 5进行单独编译。因此,我在Visual Studio 2010中将“生成可重定位设备代码”设置为“是(-rdc = true)”。程序编译时没有错误,但是, 当我尝试使用cudaMemcpyToSymbol初始化设备常量时,出现无效的设备符号错误。

即。我有以下常数

__constant__ float gdDomainOrigin[2];

并尝试使用

初始化它
cudaMemcpyToSymbol(gdDomainOrigin, mDomainOrigin, 2*sizeof(float));

导致错误。当我在没有上述选项集的情况下整体编译所有内容时,不会发生错误。有人可以帮帮我吗?

1 个答案:

答案 0 :(得分:0)

我无法重现这一点。如果从两个.cu文件构建一个应用程序,一个包含__constant__符号和一个简单内核,另一个包含运行时API咒语来填充该常量内存并调用内核,只有在启用了可重定位设备代码时才能运行 ,即:

__constant__ float gdDomainOrigin[2];

__global__
void kernel(float *inout)
{
    inout[0] = gdDomainOrigin[0];
    inout[1] = gdDomainOrigin[1];
}

#include <cstdio>

extern __constant__ float gdDomainOrigin;
extern __global__ void kernel(float *);

inline 
void gpuAssert(cudaError_t code, char * file, int line, bool Abort=true)
{
    if (code != 0) {
        fprintf(stderr, "GPUassert: %s %s %d\n",
                             cudaGetErrorString(code),file,line);
        if (Abort) exit(code);
    }       
}
#define gpuErrchk(ans) { gpuAssert((ans), __FILE__, __LINE__); }

int main(void)
{
    const float mDomainOrigin[2] = { 1.234f, 5.6789f };
    const size_t sz = sizeof(float) * size_t(2);

    float * dbuf, * hbuf;

    gpuErrchk( cudaFree(0) );
    gpuErrchk( cudaMemcpyToSymbol(gdDomainOrigin, mDomainOrigin, sz) );
    gpuErrchk( cudaMalloc((void **)&dbuf, sz) );

    kernel<<<1,1>>>(dbuf);
    gpuErrchk( cudaPeekAtLastError() );

    hbuf = new float[2];
    gpuErrchk( cudaMemcpy(hbuf, dbuf, sz, cudaMemcpyDeviceToHost) );

    fprintf(stdout, "%f %f\n", hbuf[0], hbuf[1]);

    return 0;
}

使用Kepler GPU在64位Linux系统上的CUDA 5中编译和运行这些产生以下内容:

$ nvcc -arch=sm_30 -o shared shared.cu shared_dev.cu 
$ ./shared 
GPUassert: invalid device symbol shared.cu 23

$ nvcc -arch=sm_30 -rdc=true -o shared shared.cu shared_dev.cu 
$ ./shared 
1.234000 5.678900

您可以看到,在第一次编译中,如果没有可重定位的GPU代码生成,则找不到该符号。在第二种情况下,通过可重定位的GPU代码生成,找到它,并且目标文件中的elf头看起来就像您期望的那样:

$ nvcc -arch=sm_30 -rdc=true -c shared_dev.cu 
$ cuobjdump -symbols shared_dev.o

Fatbin elf code:
================
arch = sm_30
code version = [1,6]
producer = cuda
host = linux
compile_size = 64bit
identifier = shared_dev.cu

symbols:
STT_SECTION      STB_LOCAL    .text._Z6kernelPf
STT_SECTION      STB_LOCAL    .nv.constant3
STT_SECTION      STB_LOCAL    .nv.constant0._Z6kernelPf
STT_CUDA_OBJECT  STB_LOCAL    _param
STT_SECTION      STB_LOCAL    .nv.callgraph
STT_FUNC         STB_GLOBAL   _Z6kernelPf
STT_CUDA_OBJECT  STB_GLOBAL   gdDomainOrigin

Fatbin ptx code:
================
arch = sm_30
code version = [3,1]
producer = cuda
host = linux
compile_size = 64bit
compressed
identifier = shared_dev.cu
ptxasOptions = --compile-only  

也许您可以尝试我的代码和编译/诊断步骤,看看Windows工具链会发生什么。