1

我有一个包含接口库的层的项目:

add_library(I INTERFACE)

然后这些接口库被实现多次,以适应应用程序的不同环境:

add_library(IA STATIC ...)
target_link_libraries(IA PUBLIC I)

add_library(IB STATIC ...)
target_link_libraries(IB PUBLIC I)

还有一些独立于应用程序的库,它们使用接口库。

add_library(Foo STATIC ...)
target_link_libraries(Foo PUBLIC I)

add_library(Bar STATIC ...)
target_link_libraries(Bar PUBLIC I)

最后,应用程序定义正在使用的接口库层的实现。

add_executable(ExeA ...)
target_link_libraries(ExeA Foo Bar IA)

add_executable(ExeB ...)
target_link_libraries(ExeB Foo Bar IB)

幸运的是,这没关系,只要在综合链接命令之后和中IA列出。FooBar

但是,I 的某些实现再次使用了应用程序独立库。在这些环境中,链接命令行变成这样:

IA Foo Bar

虽然它应该是

Foo Bar IA Foo Bar

这是有道理的,因为在编译时没有描述Foo/Bar依赖的显式依赖。IAExeA

在简单的情况下,我们很幸运,因为默认情况下链接命令行与调用中的顺序相同target_link_libraries

我正在使用gcc-arm-none-eabi交叉编译器。这是我尝试过的:

  • LINK_INTERFACE_MULTIPLICITY

    似乎不起作用。即使数字更大,生成的命令行仍然相同。

  • set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,--start-group")

    链接成功,但程序无法在目标硬件上正常运行。只有在连接调试器并重置后,它才会运行。奇怪的行为。

    当我用而不是显式链接Foo/时,命令行变为,然后一切正常。但我一般不能这样做,因为.BarIA--start-groupFoo Bar IA Foo BarExeB


  • 有没有办法在编译 ExeA 时定义 Foo / Bar 暂时依赖 IA,而在编译 ExeB 时暂时依赖 IB?
  • 关于如何处理如上所述的项目结构,是否有不同的方法?
4

0 回答 0