如何修改CMakeList.txt:找到的库,但是有链接错误

时间:2018-04-29 20:40:32

标签: c cmake clang linker-errors

我正在创建一个用cmake构建的C库,使用Mac OS进行开发。在CMakeList.txt中,我有以下

#htslib
find_package(htslib REQUIRED)
include_directories(${HTSLIB_INCLUDE_DIR})


target_link_libraries(projectname ${HTSlib_LIBRARIES})

cmake ..

之后输出
Found hstlib 

但是,在make时,我收到了链接器错误:

clang: error: linker command failed with exit code 1 (use -v to see invocation)

所以...它可以找到库,并且库肯定与sudo make install一起安装,但是只有这个库存在链接错误。

(1)我猜测find_package(htslib REQUIRED)正在寻找别的东西。我怎么知道什么?

(2)如何在CMakeList.txt中明确写入以找到我知道已正确安装的库?

1 个答案:

答案 0 :(得分:2)

  1. 使用VERBOSE=1 make查看链接器输出。搜索-lhtslib
  2. 阅读特定Find<LIB>.cmake
  3. 的文档

    您的具体问题:

    1. &#34;如何找到CMake找到的内容&#34;:使用cmake-guiccmake。它们都显示相同的信息,但一个是GUI,另一个是Curses接口。在高级模式(&#34; t&#34;在ccmake上),您将找到搜索到的包的所有变量。此外,您可以使用MESSAGE(STATUS "Found htslib at: ${htslib_LIBRARIES}")
    2. &#34;如何在库中明确写入CMakeLists.txt?&#34;请不要这样做! CMake旨在完全抽象出这类信息。您有两个选项,首先是好的选项:在命令行(或上面提到的GUI)中配置cmake以获取CMAKE_MODULES_PATH或更具体的提示到库-D htslib_PATH=/usr/local/.../(指向目录) libhts.dylib所在的地方。更糟糕的解决方案是向find_package提供一个提示。 find_package(htslib REQUIRED PATH /usr/local/lib)find_package(htslib REQUIRED HINT /usr/local/lib /some/second/path/where/it/may/be)
    3. 解决方案

      您的关联项目包含自定义FindHTSlib.cmake link。这个使用pkg_config来配置库。要复制您的问题,我使用 brew 来安装htslib。可以在brew info htslib下找到pkg-config文件(对我来说,/usr/local/Cellar/htslib/1.8/lib/htslib.pc告诉你)。所以,让我们给CMake提供必要的提示。

      我无法对此进行测试,因为对我而言,它直接找到了htslib包而没有进一步的提示。

      git clone https://github.com/D-Lo/bamdb # I am using version f5f03d0
      mkdir -p bamdb/build; cd bamdb/build
      brew install ck htslib lmdb
      cmake ..  # -G Ninja recommended, but needs brew install ninja
      make # lot's of missing symbols
      

      我建议将CMakeLists.txt最低要求的CMake版本从2.8更改为3.10(或至少3.6)。

      这是我得到的错误:

      [ 62%] Linking C shared library libbamdb.dylib
      /usr/local/Cellar/cmake/3.11.1/bin/cmake -E cmake_link_script CMakeFiles/libbamdb.dir/link.txt --verbose=1
      /Library/Developer/CommandLineTools/usr/bin/cc -Wall -g -std=gnu99 -fPIC -dynamiclib -Wl,-headerpad_max_install_names  -o libbamdb.dylib -install_name @rpath/libbamdb.dylib CMakeFiles/libbamdb.dir/src/bam_api.c.o CMakeFiles/libbamdb.dir/src/bam_lmdb.c.o CMakeFiles/libbamdb.dir/src/bamdb.c.o
      Undefined symbols for architecture x86_64:
        "_bam_destroy1", referenced from:
            _get_bam_row in bam_api.c.o
            _deserialize_func in bam_lmdb.c.o
      

      可以通过在行CMakeLists.txt之后的add_library(libbamdb ${SOURCES})中添加以下行来解决此问题:

      target_link_libraries(libbamdb ${LIBS})
      

      进一步说明:您现在拥有一个具有main功能的库。这是因为${SOURCES}用于构建可执行文件和库。这会产生意想不到的副作用。除非需要,否则不要这样做。