我在文件 template.cu 和 template.cuh 中定义了一个类模板。我使用主机和设备关键字将构造函数和析构函数标记为设备和主机可调用。
template.cuh
#pragma once
#include "cuda_runtime.h"
template<class T>
class Foo
{
public:
__host__ __device__
Foo();
__host__ __device__
~Foo();
};
template.cu
#include "template.cuh"
template<class T>
__host__ __device__
Foo<T>::Foo()
{
}
template<class T>
__host__ __device__
Foo<T>::~Foo()
{
}
// Instantiating template of type int
template
class Foo<int> ;
我的主要功能是 Kernel.cu 文件,其中包含 template.cuh 标头。我只是在主机和设备代码中实例化一个int类型的Foo对象。
#include "cuda_runtime.h"
#include "device_launch_parameters.h"
#include "template.cuh"
__global__ void addKernel(int *c, const int *a, const int *b)
{
Foo<int> f;
int i = threadIdx.x;
c[i] = a[i] + b[i];
}
int main()
{
Foo<int> t;
return 0;
}
当我在NVIDIA CUDA 6.5运行时类型的Visual Studio C ++项目中编译上述代码文件时,我得到以下日志的未解析的外部函数错误:
1> c:\Users\admin\documents\visual studio 2013\Projects\Test\Testtemplates>"C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v6.5\bin\nvcc.exe" -gencode=arch=compute_20,code=\"sm_20,compute_20\" --use-local-env --cl-version 2013 -ccbin "C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\bin" -I"C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v6.5\include" -I"C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v6.5\include" -G --keep-dir Debug -maxrregcount=0 --machine 32 --compile -cudart static -g -DWIN32 -D_DEBUG -D_CONSOLE -D_MBCS -Xcompiler "/EHsc /W3 /nologo /Od /Zi /RTC1 /MDd " -o Debug\kernel.cu.obj "c:\Users\admin\documents\visual studio 2013\Projects\Test\Testtemplates\kernel.cu"
1> ptxas fatal : Unresolved extern function '_ZN3FooIiEC1Ev'
1> kernel.cu
我在这里做错了什么?
答案 0 :(得分:4)
您收到此错误的原因是您没有使用设备代码链接。 看看这篇文章:Separate Compilation and Linking of CUDA C++ Device Code
我只是尝试了以下代码,它对我有用。请注意附加标记-dc
:
nvcc template.cu kernel.cu -dc
nvcc template.o kernel.o -o kernel
我对Visual Studio没有太多经验,我更喜欢使用CMake来为VS生成正确的设置。
以下 CMakeLists.txt 文件适用于Linux和gcc,您可以试试Windows和VS,然后将生成的项目设置与您使用的设置进行比较。
PROJECT(kernel)
FIND_PACKAGE(CUDA REQUIRED)
SET(CUDA_SEPARABLE_COMPILATION ON)
CUDA_ADD_EXECUTABLE(kernel template.cuh template.cu kernel.cu)