Is this really a better style to use generator expressions every time?

# either
target_compile_options(Greeter PUBLIC "$<$<BOOL:${MSVC}>:/permissive->")
# or
if(MSVC)
   target_compile_options(Greeter PUBLIC /permissive)
endif()

the first line generates on unix the GreeterTarget.cmake contents:

# Create imported target Greeter::Greeter
add_library(Greeter::Greeter STATIC IMPORTED)

set_target_properties(Greeter::Greeter PROPERTIES
  INTERFACE_COMPILE_OPTIONS "\$<\$<BOOL:>:/permissive->"
  INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include/Greeter-1.0"
)

These two options are 100% equivalent, because ${MSVC} in the genex will be evaluated immediately (i.e. at configure time). So it comes down fully to code style preference, which is subjective (but I find the if-based form more readable).

For a case where configure-time vs. generate-time can be different, see a recent question of mine.

But the generator expression pollute on unix hosts the installed cmake config package!

Eh, “no one” looks at those. In any case, the right thing, especially for compiler and linker flags, is to use a genex. The consumer of your package might not be using MSVC. MinGW isn’t going to understand /permissive. You should do:

target_compile_options(Greeter
  PUBLIC
    "$<$<COMPILE_LANG_AND_ID:C,MSVC>:/permissive>") # or CXX
1 Like