如何正确地将标志的CMake列表(分号sep)传递给set_target_properties



CMake列表本质上只是分号分隔的字符串,但如果将这样的变量传递给命令,它确实会扩展为多个参数-例如,

set(FLAGS f1 f2 f3)
# now FLAGS == 'f1;f2;f3'
add_custom_command(
  ...
  COMMAND my_cmd ${FLAGS}
  ...
)

将正确地调用CCD_ 1。

现在,如果我用做这件事

set_target_properties(
  myTarget PROPERTIES
  LINK_FLAGS  "${LD_FLAGS}"
)

扩展没有发生,我最终得到了一个包含分号的LD_FLAG——没有用,而不是将它扩展成一个空格分隔的字符串。

有没有什么方法可以使它在我将列表传递给LINK_FLAGS属性(或任何有列表的属性)时,扩展为多个参数,而不仅仅是一个?

我不认为set_target_properties可以自动进行扩展,但您可以使用string (REPLACE ...)将列表扩展为空格分隔的字符串:

string (REPLACE ";" " " LD_FLAGS_STR "${LD_FLAGS}")
set_target_properties(
  myTarget PROPERTIES
  LINK_FLAGS  "${LD_FLAGS_STR}"
)

要使用cmake List作为列表,请使用

${LD_FLAG}

对于使用cmake列表作为字符串(即列表项用";"分隔),请使用

"${LD_FLAG}"

因此,在您的情况下,只需删除"就足够了。

set_property命令是为这个设计的

http://www.cmake.org/cmake/help/v3.0/command/set_property.html

set_property(TARGET tgt PROPERTY LINK_FLAGS foo bar)

我像字符串一样使用它

set(FLAGS " f1 f2 f3")

注意前面的空格,它允许您连接其他标志集。

对于更复杂的项目,而不是如果elses,你也可以做双重扩展技巧:

set(GCC_FLAGS " -Wl,--relax")
set(DIAB_FLAGS " -tPPCE500ES:cross")
set(MSVC_FLAGS " /RAINBOW_CRAP)
# ...
# ...LINUX_FLAGS, WINDOWS_FLAGS, etc...

set_target_properties(
  myTarget PROPERTIES
  LINK_FLAGS  "${${COMPILER}_FLAGS} ${${SYSTEM}_FLAGS}"
)
# COMPILER and SYSTEM is set somewhere else, in toolchain files for example
separate_arguments(LD_FLAGS_AS_LIST  NATIVE_COMMAND  LD_FLAGS)
set_target_properties(
  myTarget PROPERTIES
  LINK_FLAGS  "${LD_FLAGS_AS_LIST}"
)

从CMake 3.12开始,您可以使用此处描述的list(JOIN <list> <glue> <output variable>)命令:

set(FLAGS f1 f2 f3)
# now FLAGS == 'f1;f2;f3'
list(JOIN FLAGS " " FLAGS) # Note: Overwrites FLAGS variable
# now FLAGS == 'f1 f2 f3'
add_custom_command(
  ...
  COMMAND my_cmd ${FLAGS}
  ...
)

这比使用string(REPLACE ...)更直接一些。

在cmake 3.x中,有几种方法

顶级CMakeLists.txt文件看起来像这样:

# The name of the included file could be anything,
# it doesn't have to be called CMakeLists.txt
include(foo/CMakeLists.txt)
include(bar/CMakeLists.txt)
add_executable(myApp ${myApp_SOURCES})

子目录文件的结构如下:

list(APPEND myApp_SOURCES
    ${CMAKE_CURRENT_LIST_DIR}/foo.cpp
    ${CMAKE_CURRENT_LIST_DIR}/foo_p.cpp
)

使用target_sources()增强源文件处理

最新更新