如何告诉 CMake 在链接命令中不传递重复的库

Jia*_*ode 5 c linker cmake iar ninja

我在两个静态库libA和之间有循环依赖关系libB

add_library(LibA STATIC a.c)
add_library(LibB STATIC b.c)

# Circular dependency: LibA <-> LibB
target_link_libraries(LibA PRIVATE LibB)
target_link_libraries(LibB PRIVATE LibA)

add_executable(Example main.c)
target_link_libraries(Example PRIVATE LibA LibB)

Run Code Online (Sandbox Code Playgroud)

生成构建配置时,CMake 尝试通过将LibA和分别传递LibB给链接器两次来解决这些依赖关系:

ilinkarm.exe --silent CMakeFiles\Example.dir\main.c.o  LibA.lib  LibB.lib  LibA.lib  LibB.lib -o Example.exe
Run Code Online (Sandbox Code Playgroud)

然而,我使用的 IAR 链接器已经多次遍历库列表,如果LibALibB只列出一次就足够了。与重复项的链接仍然有效,但我收到以下警告:

[build] Warning[Li065]: duplicate file: "LibA.lib"
[build] Warning[Li065]: duplicate file: "LibB.lib"
Run Code Online (Sandbox Code Playgroud)

是否有可能告诉 CMake,链接器命令中的每个库都必须是唯一的,即使具有循环依赖项?

我尝试设置CMAKE_C_LINK_EXECUTABLE,但找不到<LINK_LIBRARIES>似乎已经包含重复项的替代方案。这就是为什么这一行会产生相同的警告:

set(CMAKE_C_LINK_EXECUTABLE "<CMAKE_LINKER> <OBJECTS> <LINK_FLAGS> <LINK_LIBRARIES> -o <TARGET>")
Run Code Online (Sandbox Code Playgroud)

CMake版本:3.26.3
Ninja版本:1.10.2
IAR版本:9.32.2

Ale*_*ing 2

通常这是由LINK_INTERFACE_MULTIPLICITY属性控制的。但是,CMake 不尊重以下属性的值2,因此从 CMake 3.26 开始无法执行此操作。请参阅此处的代码:

https://github.com/Kitware/CMake/blob/d9641980d2a223e0a6fe42ff23499e55f49fd6d5/Source/cmComputeLinkDepends.cxx#L1314-L1328

size_t cmComputeLinkDepends::ComputeComponentCount(NodeList const& nl)
{
  size_t count = 2;
  for (size_t ni : nl) {
    if (cmGeneratorTarget const* target = this->EntryList[ni].Target) {
      if (cmLinkInterface const* iface =
            target->GetLinkInterface(this->Config, this->Target)) {
        if (iface->Multiplicity > count) {
          count = iface->Multiplicity;
        }
      }
    }
  }
  return count;
}
Run Code Online (Sandbox Code Playgroud)

以下是 CMake 问题跟踪器的链接:https://gitlab.kitware.com/cmake/cmake/-/issues