Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/visual-studio-2012/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Cmake 与第三方库具有不同链接的可传递依赖项_Cmake - Fatal编程技术网

Cmake 与第三方库具有不同链接的可传递依赖项

Cmake 与第三方库具有不同链接的可传递依赖项,cmake,Cmake,我有一个有点复杂的问题。我有一个第三方依赖项,它是静态的(libthird.a)和共享的pic形式(libthird.so) 我有一个库,util,它依赖于libthird 我有一些依赖于util的应用程序,它们想静态链接libthird,我有一些需要生成的共享库,它们依赖于util,需要动态链接libthird 我目前的(工作)方法如下: add_library(third INTERFACE) target_link_libraries(third INTERFACE /path/to/li

我有一个有点复杂的问题。我有一个第三方依赖项,它是静态的(
libthird.a
)和共享的pic形式(
libthird.so

我有一个库,
util
,它依赖于
libthird

我有一些依赖于
util
的应用程序,它们想静态链接
libthird
,我有一些需要生成的共享库,它们依赖于
util
,需要动态链接
libthird

我目前的(工作)方法如下:

add_library(third INTERFACE)
target_link_libraries(third INTERFACE /path/to/libthird.a)
add_library(third_shared INTERFACE)
target_link_libraries(third_shared INTERFACE /path/to/libthird.so)

add_library(util ${UTIL_SOURCES})
add_library(util_shared ${UTIL_SOURCES}) # same sources again!!
target_link_libraries(util PUBLIC third)
target_link_libraries(util_shared PUBLIC third_shared)

add_executable(some_app ...)
target_link_libraries(some_app PRIVATE util)

add_library(some_shared_object ...)
target_link_libraries(some_shared_object PUBLIC util_shared)
foo/
  CMakeLists.txt
  include/
    foo.h
  src/
    foo.c
这很有效。但我正在两次构建
util
(实际上,还有大约六个库)。。。只是为了获得不同的链接器依赖项。在cmake中有更明智的方法吗


如果我只是在顶级
一些应用程序
一些共享对象
上设置
target\u link\u libraries()
,我会以错误的顺序发出链接器标志,因为
util
确实依赖于
第三方

您所采取的方法肯定是我见过的,我以前也用过。如果用于小型存档和/或一次性使用,则可以

对于以下示例,我假设项目结构如下:

add_library(third INTERFACE)
target_link_libraries(third INTERFACE /path/to/libthird.a)
add_library(third_shared INTERFACE)
target_link_libraries(third_shared INTERFACE /path/to/libthird.so)

add_library(util ${UTIL_SOURCES})
add_library(util_shared ${UTIL_SOURCES}) # same sources again!!
target_link_libraries(util PUBLIC third)
target_link_libraries(util_shared PUBLIC third_shared)

add_executable(some_app ...)
target_link_libraries(some_app PRIVATE util)

add_library(some_shared_object ...)
target_link_libraries(some_shared_object PUBLIC util_shared)
foo/
  CMakeLists.txt
  include/
    foo.h
  src/
    foo.c
因此,我还(天真地?)使用了以下方法,这是基于您可以从静态存档创建(至少在基于Unix的系统上)共享库的知识

project(foo C)

set(SOURCES
  "src/foo.c")

set(LIBNAME "foo")

add_library(${LIBNAME} STATIC ${SOURCES})

target_include_directories(${LIBNAME} PUBLIC "include")
target_compile_options(${LIBNAME} PUBLIC "-fPIC")

#

get_property(CUR_PREFIX TARGET ${LIBNAME} PROPERTY PREFIX)
get_property(CUR_SUFFIX TARGET ${LIBNAME} PROPERTY SUFFIX)
get_property(CUR_NAME TARGET ${LIBNAME} PROPERTY NAME)
get_property(CUR_OUTPUT_NAME TARGET ${LIBNAME} PROPERTY OUTPUT_NAME)
get_property(CUR_ARCHIVE_OUTPUT_NAME TARGET ${LIBNAME} PROPERTY ARCHIVE_OUTPUT_NAME)

message(STATUS "prefix: ${CUR_PREFIX}")
message(STATUS "suffix: ${CUR_SUFFIX}")
message(STATUS "name: ${CUR_NAME}")
message(STATUS "output name: ${CUR_OUTPUT_NAME}")
message(STATUS "archive name: ${CUR_ARCHIVE_OUTPUT_NAME}")

add_custom_command(TARGET ${LIBNAME} POST_BUILD 
  COMMAND ${CMAKE_C_COMPILER} -shared -o libfoo.so -Wl,--whole-archive libfoo.a -Wl,--no-whole-archive
  WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
这种方法尚未解决的问题是,我还没有找到一种可靠且可移植的方法来获取静态归档文件的名称(
libfoo.a
)。因此,所有这些
消息
命令;它们在您的平台上的行为可能会有所不同


cmake
也非常支持的最有效的方法是使用:

#cmake文件
cmake_最低要求(3.2版)
项目(FooC)
设置(源)
“src/foo.c”)
set(LIBNAME“foo”)
集合(LIBNAME_OBJ“${LIBNAME}_OBJ”)
添加库(${LIBNAME\u OBJ}对象${SOURCES})
目标目录(${LIBNAME\u OBJ}PUBLIC“include”)
目标编译选项(${LIBNAME\u OBJ}PUBLIC“-fPIC”)
#
添加库(${LIBNAME}共享$)
添加库(${LIBNAME}\u static$)
所有示例都使用cmake版本3.6.1进行了测试


希望这有帮助。如果您找到了更好的方法,请告诉我们。

让util_在utill周围共享一个薄包装是可行的,还是您真的在没有-fPIC的情况下附加到静态util库?