IntegrateThis
IntegrateThis

Reputation: 962

Error Compiling C++/Cuda extension with Pytorch Cuda c++ in MSVC using CMake

I am trying to build a c++/cuda extension with Pytorch following the tutorial here, (with instructions how to use pytorch with c++ here). My environment details are:

I am using this cmake code where I set the include directory for python 3.6 and the library for python36.lib

cmake_minimum_required (VERSION 3.8)

project ("DAConvolution")

find_package(Torch REQUIRED)

# Add source to this project's executable.
add_executable (DAConvolution "DAConvolution.cpp" "DAConvolution.h")

include_directories("C:/Users/James/Anaconda3/envs/masters/include")
   
target_link_libraries(DAConvolution "${TORCH_LIBRARIES}" "C:/Users/James/Anaconda3/envs/masters/libs/python36.lib")

if (MSVC)
  file(GLOB TORCH_DLLS "${TORCH_INSTALL_PREFIX}/lib/*.dll")
  add_custom_command(TARGET DAConvolution
                     POST_BUILD
                     COMMAND ${CMAKE_COMMAND} -E copy_if_different
                     ${TORCH_DLLS}
                     $<TARGET_FILE_DIR:DAConvolution>)
endif (MSVC)

I set the CMake command arguments to be -DCMAKE_PREFIX_PATH=C:\libtorch (my path to libtorch debug mentioned above). I am building with the x64-debug option in MSVC version (as building with the x-64 Release option gives me a torch-NOTFOUND error).

The example DAConvolution.cpp file is:

#ifdef _DEBUG
#undef _DEBUG
#include <python.h>
#define _DEBUG
#else
#include <python.h>
#endif

#include <torch/extension.h>

Where I have undefined the _DEBUG flag so that the linker does not look for the python36_d.lib file (which I do not have).

I am getting a linking error:

enter image description here

Simply including torch.h works fine, but when I want to include the extension header thats when I get these problems, as it uses Pybind 11 I believe. Any insights much appreciated. I have tried to include all the info I can, but would be happy to give more information.

Upvotes: 0

Views: 2466

Answers (1)

Hossein
Hossein

Reputation: 25924

For Windows and with Visual studio, you are better to work with the Visual Studio rather than the CMake.

Just create a simple Console Application, go to the project's Properties, change the Configuration type to Dynamic Library (dll), Configure the include and Library directories, add the required enteries to your linker in Linker>Input (such as torch.lib, torch_cpu.lib, etc) and you are good to go click build, and if you have done everything correctly you'll get yourself a dll that you can use (e.g loading it using torch.classes.load_library from Python and use it.

The Python debug version is not shipped with Anaconda/ normal python distribution, but if you install the Microsoft Python distribution which I believe can be downloaded/installed from Visual Studio installer, its available.
Also starting from Python 3.8 I guess the debug binaries are also shipped.
In case they are not, see this.
For the cmake part you can follow something like the following. This is a butchered version taken from my own cmake that I made for my python extension some time ago.

Read it and change it based on your own requirements it should be straight forward :

# NOTE:‌
# TORCH_LIB_DIRS needs to be set. When calling cmake you can specify them like this:
# cmake -DCMAKE_PREFIX_PATH="somewhere/libtorch/share/cmake" -DTORCH_LIB_DIRS="/somewhere/lib" ..

cmake_minimum_required(VERSION 3.1 FATAL_ERROR)
project(DAConvolution)

find_package(Torch REQUIRED)
# we are using the C++17, if you are not change this or remove it altogether
set(CMAKE_CXX_STANDARD 17)

#define where your headers and libs are, specify for example where your DaConvolution.h resides!
include_directories( somewhere/Yourinclude_dir ${TORCH_INCLUDE_DIRS})

set(DAConvolution_SRC ./DAConvolution.cpp )

LINK_DIRECTORIES(${TORCH_LIB_DIRS})

add_library(
    DAConvolution
    SHARED
    ${DAConvolution_SRC}
  )

# if you use some custom libs, you previously built, specify its location here
# target_link_directories(DAConvolution PRIVATE somewhere/your_previously_built_stuff/libs)
target_link_libraries(DAConvolution ${TORCH_LIB_DIRS}/libc10.so)
target_link_libraries(DAConvolution ${TORCH_LIB_DIRS}/libtorch_cpu.so)

install(TARGETS DAConvolution LIBRARY DESTINATION lib )

Side note:
I made the cmake for Linux only, so under Windows, I always use Visual Studio (2019 to be exact), in the same way I explained earlier. its by far the best /easiest approach imho. Suit yourself and choose either of them that best fits your problem.

Upvotes: 2

Related Questions