【问题标题】:Linking OpenCV (with Cuda) with C++ code implementing CUDA function return linking error将 OpenCV(使用 Cuda)与实现 CUDA 函数的 C++ 代码链接返回链接错误
【发布时间】:2014-07-18 13:35:32
【问题描述】:

我在 OS X Mavericks (10.9.3) 上启用了 CUDA (6.0) 从源代码编译 OpenCV (2.4.6.1)。

现在我想混合使用 OpenCV 和 CUDA 创建自己的图像处理功能。让我们举一个简单的例子,我们有一个 OpenCV Mat 并且想对每个元素做一些事情,并希望通过使用 CUDA 并行化来加快速度。在我们的示例中,我们仅打印出每个 Mat 元素的值。不现实,但足以展示这个概念。

CUDA 头文件: print.cuh

#ifndef __PRINT_CUH__
#define __PRINT_CUH__

void print(const unsigned char * pixels, const int N);

#endif

CUDA 源文件: print.cu

#include <stdio.h>

// The device version
__global__ void cuda_print(const unsigned char * pixels, const int N)
{
    int tidX = blockIdx.x * blockDim.x + threadIdx.x;

    if( tidX >= N ) {
        return;
    }

    printf("pixel value @ %d = %d\n", tidX, pixels[tidX]);
}

// The host version
void print(const unsigned char * pixels, const int N) {
    int num_blocks = 10;
    int num_threads = 128;

    unsigned char * d_pixels;
    cudaMalloc( &d_pixels, sizeof(char) * N );
    cudaMemcpy( d_pixels, pixels, sizeof(char)*N, cudaMemcpyHostToDevice);

    cuda_print<<<num_blocks, num_threads>>>(d_pixels, N);
    cudaDeviceSynchronize(); // The above call is asynchronous, wait until it
                             // finishes before exiting the program!

}

C++ 代码,包括 OpenCV 和我们自己的 CUDA 代码: main.cpp

#include <opencv2/opencv.hpp>

#include "print.cuh"

int main(int argc, char ** argv )
{
    cv::Mat m(100,1,CV_8UC1, cv::Scalar(0));

    print(m.ptr(0), m.rows);

    return 0;
}

我们想将我们自己的 CUDA 代码编译成一个共享库并将其包含在我们的 main 中

CMAKE 设置: CMakeLists.txt

# CUDA CMAKE TEST 
cmake_minimum_required(VERSION 2.8)

# project name
project(CUDA_CMAKE)

# find dependencies 
find_package(OpenCV REQUIRED)
find_package(CUDA REQUIRED)

# this is necessary on OS X since CUDA only support the older libstdc++
IF(APPLE)
    SET(CUDA_HOST_COMPILER /usr/bin/clang CACHE FILEPATH "Setting clang as the CUDA compiler" FORCE)
    SET(CUDA_NVCC_FLAGS "-Xcompiler -stdlib=libstdc++; -Xlinker -stdlib=libstdc++; -arch=sm_20" CACHE STRING "Setting NVCC compiler flags" FORCE)
ENDIF()

# build a shared library with our CUDA code
CUDA_ADD_LIBRARY(cudaPrint 
    SHARED
    print.cu
)
TARGET_LINK_LIBRARIES(cudaPrint
    ${CUDA_LIBRARIES}
)

# build the C++ code and link with the CUDA code
ADD_EXECUTABLE(cuda_test 
    main.cpp 
)
TARGET_LINK_LIBRARIES(cuda_test
    cudaPrint ${OpenCV_LIBS}
)

构建的第一步工作正常,生成了 cudaPrint.dylib。 但是,在尝试构建可执行文件时,出现以下链接错误:

make all 
-- Configuring done
CMake Warning at CMakeLists.txt:29 (ADD_EXECUTABLE):
  Cannot generate a safe runtime search path for target cuda_test because
  there is a cycle in the constraint graph:

    dir 0 is [/Developer/NVIDIA/CUDA-5.5/lib]
      dir 1 must precede it due to runtime library [libcudart.dylib]
    dir 1 is [/usr/local/cuda/lib]
      dir 0 must precede it due to runtime library [libcudart.dylib]

  Some of these libraries may not be found correctly.


-- Generating done
-- Build files have been written to: /Users/navid/proj/CUDA/test_cuda_opencv/build
[ 50%] Built target cudaPrint
Linking CXX executable cuda_test
ld: can't map file, errno=22 file '/Developer/NVIDIA/CUDA-5.5/lib' for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[2]: *** [cuda_test] Error 1
make[1]: *** [CMakeFiles/cuda_test.dir/all] Error 2
make: *** [all] Error 2

看起来这个错误与 OpenCV (包括 CUDA 库)有关。我不确定,但我有一个解决方法,我将在下面发布。

【问题讨论】:

    标签: macos opencv cuda linker linker-errors


    【解决方案1】:

    所以看起来链接错误是由于通过${OpenCV_LIBS}libopencv_ts 传递给链接器,因为FIND_PACKAGE(OpenCV REQUIRED) 将所有OpenCV 库添加到${OpenCV_LIBS} 变量中。

    如果libopencv_ts 不需要,一个简单的解决方法是在我们要求CMAKE 查找包时指定我们明确需要哪些 OpenCV 库,例如FIND_PACKAGE(OpenCV REQUIRED COMPONENTS core highgui cuda).

    我不知道为什么 libopencv_ts 会产生这个循环错误以及如何解决它。

    【讨论】:

      猜你喜欢
      • 2018-12-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-23
      • 2013-04-30
      • 2012-08-30
      • 1970-01-01
      • 2011-07-14
      相关资源
      最近更新 更多