Ninja Multi-Config: Unexpected build through order-only dependency
In my project, I have a library called “Library” and a library called “LibraryTest”. They both compile from the same sources. The former is exported, the latter is compiled with address sanitation and linked against the test suite.
To get faster builds, I want to link the test suite against “Library” in the “Devel” configuration, with the intention/expectation that “LibraryTest” would not have to be compiled. In Release mode, both are compiled and the test suite is run. I’m using the Ninja Multi-Config generator. My list file looks like this:
cmake_minimum_required(VERSION 3.27)
project(Example LANGUAGES CXX)
add_library(Library lib.cc)
add_library(LibraryTest lib.cc)
target_compile_options(LibraryTest PUBLIC -fsanitize=address)
target_link_libraries(LibraryTest PUBLIC -fsanitize=address)
add_executable(test test.cc)
target_link_libraries(test Library$<$<CONFIG:Release>:Test>)
The list file works as expected, and the correct library is linked depending on the configuration. However, both libraries are always compiled. I am building with ninja -f build-Devel.ninja test
so in this case I would expect only the regular library to get built.
Looking at the generated Ninja file for “Devel”, the “Devel/test” target has an order-only dependency on the test library:
build Devel/test: CXX_EXECUTABLE_LINKER__test_Devel CMakeFiles/test.dir/Devel/test.cc.o | Devel/libLibrary.a || Devel/libLibrary.a Devel/libLibraryTest.a
Removing this order-only dependency stops building the test library.
I reported this on the discourse and it was suggested to create an issue for this.
My tests we done with CMake 3.27.8 and Ninja 1.11.1