Ошибка nvlink: неопределенная ссылка на * в 'Debug/*.cu.obj' (Отдельная компиляция CUDA, Visual Studio 2013)

У меня есть очень простой строковый класс, объявленный и определенный в StringT.cu и StringT.cpp соответственно.

StringT.cu

#ifndef STRING_T_CU
#define STRING_T_CU

#include "cuda_runtime.h"

class StringT
{
public:
   static const int MAX_LEN = 15;

   __host__ __device__ StringT(char const * s);
   __host__ __device__ ~StringT();
   __host__ __device__ char* Get();

private:
   char* str;
};

#endif

StringT.cpp

#include "StringT.cu"

#include <stdlib.h>
#include <malloc.h>

StringT::StringT(char const * s)
{
   str = (char*)malloc(MAX_LEN + 1);
   int k;
   for (k = 0; *s != NULL; ++s, ++k) {
      if (k > MAX_LEN) {
         break;
      }
      str[k] = *s;
   }
   str[k] = '\0';
}

StringT::~StringT()
{
   free(str);
}

char* StringT::Get()
{
   return str;
}

Я хочу сделать простой вызов класса в kernel.cu.

kernel.cu

#include "cuda_runtime.h"
#include "device_launch_parameters.h"

#include <stdio.h>

#include "StringT.cu"
#include "CudaUtil.h"

__global__ void kernel()
{
   StringT s("aa");
   printf("%s", s.Get());
}

int main()
{
   kernel <<< 1, 1 >>> ();
   checkCudaErrors(cudaDeviceSynchronize());
   checkCudaErrors(cudaGetLastError());

   return 0;
}

Однако этот код не компилируется, выдавая такие ошибки, как:

1> CUDALINK: ошибка nvlink: неопределенная ссылка на '_ZN7StringTC1EPKc' в 'Debug/kernel.cu.obj'

1> CUDALINK: ошибка nvlink: неопределенная ссылка на '_ZN7StringT3GetEv' в 'Debug/kernel.cu.obj'

1> CUDALINK: ошибка nvlink: неопределенная ссылка на '_ZN7StringTD1Ev' в 'Debug/kernel.cu.obj'

Как видите, все методы определены. Я также попытался изменить библиотеку времени выполнения, как указано в этом сообщении. Я должен добавить, что я включил перемещаемый код устройства, так как я планирую использовать динамический параллелизм. Тем временем я наткнулся на этот документ и нашел некоторые инструкции в разделе "Использование отдельной компиляции в CUDA". Тем не менее, я использую Visual Studio для этого проекта и не уверен, как именно изменить настройки компилятора. Я пытался добавить все виды вещей в

C/C++ -> Командная строка -> Дополнительные параметры

CUDA C/C++ -> Командная строка -> Дополнительные параметры

Компоновщик -> Командная строка -> Дополнительные параметры

CUDA Linker -> Командная строка -> Дополнительные параметры

Но все еще не заставил это работать. У кого-нибудь есть подсказка?

Отредактировано Я переименовал файлы, содержащие объявление и определение класса строки:

StringT.cuh

#ifndef STRING_T_CUH
#define STRING_T_CUH

#include "cuda_runtime.h"

class StringT
{
public:
   static const int MAX_LEN = 15;

   __host__ __device__ StringT(char const * s);
   __host__ __device__ ~StringT();
   __host__ __device__ char* Get();

private:
   char* str;
};

#endif

StringT.cu

#include "StringT.cuh"

#include <stdlib.h>
#include <malloc.h>

__host__ __device__ StringT::StringT(char const * s)
{
   str = (char*)malloc(MAX_LEN + 1);
   int k;
   for (k = 0; *s != NULL; ++s, ++k) {
      if (k > MAX_LEN) {
         break;
      }
      str[k] = *s;
   }
   str[k] = '\0';
}

__host__ __device__ StringT::~StringT()
{
   free(str);
}

__host__ __device__ char* StringT::Get()
{
   return str;
}

Я создал проект с шаблоном, который поставляется с опцией интеграции vs из установки CUDA 8.0, изменил перемещаемый код на true и arch на sm_61, compute_61 (у меня GTX 1080 Ti).

Сообщения об ошибках, после того как я изменил детализацию вывода на подробные, были:

1> CUDALINK: ошибка nvlink: неопределенная ссылка на '_ZN7StringTC1EPKc' в 'Debug/kernel.cu.obj'

1> CUDALINK: ошибка nvlink: неопределенная ссылка на '_ZN7StringT3GetEv' в 'Debug/kernel.cu.obj'

1> CUDALINK: ошибка nvlink: неопределенная ссылка на '_ZN7StringTD1Ev' в 'Debug/kernel.cu.obj'

С другой стороны, мне удалось скомпилировать и запустить код, расширив один из примеров проектов, "simpleSeparateCompilation". Тем не менее, я не вижу никаких дополнительных параметров командной строки. Это работает для меня на данный момент, но, конечно, я не решил исходную проблему.

1 ответ

Решение

При использовании visual studio переименование из.cpp в.cu и / или.h в.cuh не работает / не работает.

Чтобы сгенерировать код устройства, необходимо добавить "Файл CUDA C/C++" или "Заголовок CUDA C/C++" вместо "Файл C++" и "Файл заголовка", в дополнение к включению

  1. код перемещаемого устройства (Свойства -> Свойства конфигурации -> CUDA C/C++ -> Общий -> Создать код перемещаемого устройства)
  2. привязка устройства (Свойства -> Свойства конфигурации -> CUDA Linker -> Общие -> Выполнить привязку устройства)
Другие вопросы по тегам