diff --git a/Help/include/GENEX_NOTE_SOURCE_TARGET.rst b/Help/include/GENEX_NOTE_SOURCE_TARGET.rst new file mode 100644 index 0000000000..e4ea1a5a2f --- /dev/null +++ b/Help/include/GENEX_NOTE_SOURCE_TARGET.rst @@ -0,0 +1,3 @@ + +Generator expressions in |genex_subject| are evaluated separately for each +target that compiles the source file. diff --git a/Help/manual/cmake-generator-expressions.7.rst b/Help/manual/cmake-generator-expressions.7.rst index fdfc4da47f..ce9b17a6b8 100644 --- a/Help/manual/cmake-generator-expressions.7.rst +++ b/Help/manual/cmake-generator-expressions.7.rst @@ -2858,6 +2858,10 @@ These expressions look up the values of Note that for generator expressions in :ref:`Target Usage Requirements` this is the consuming target rather than the target specifying the requirement. + For generator expressions in + :ref:`source file properties `, this is the target + compiling the source file, so a source file shared by several targets can + be compiled differently by each. The expressions have special evaluation rules for some properties: diff --git a/Help/prop_sf/COMPILE_DEFINITIONS.rst b/Help/prop_sf/COMPILE_DEFINITIONS.rst index f0a8262c4d..4094508f41 100644 --- a/Help/prop_sf/COMPILE_DEFINITIONS.rst +++ b/Help/prop_sf/COMPILE_DEFINITIONS.rst @@ -23,6 +23,21 @@ definitions on source files. .. |genex_subject| replace:: ``COMPILE_DEFINITIONS`` .. include:: ../include/GENEX_NOTE_PER_SOURCE.rst +.. include:: ../include/GENEX_NOTE_SOURCE_TARGET.rst + +For example, ``foo.cpp`` is compiled with ``FOO=1`` in target ``A`` and with +``FOO=2`` in target ``B``, while ``bar.cpp`` is compiled without ``FOO``: + +.. code-block:: cmake + + add_library(A OBJECT foo.cpp bar.cpp) + add_library(B OBJECT foo.cpp bar.cpp) + + set_property(TARGET A PROPERTY FOO_VALUE 1) + set_property(TARGET B PROPERTY FOO_VALUE 2) + + set_property(SOURCE foo.cpp PROPERTY COMPILE_DEFINITIONS + "FOO=$") Prefer using generator expressions in :prop_sf:`!COMPILE_DEFINITIONS` over the deprecated :prop_sf:`COMPILE_DEFINITIONS_` property. diff --git a/Help/prop_sf/COMPILE_FLAGS.rst b/Help/prop_sf/COMPILE_FLAGS.rst index 7d48776395..e89ed2ec6d 100644 --- a/Help/prop_sf/COMPILE_FLAGS.rst +++ b/Help/prop_sf/COMPILE_FLAGS.rst @@ -11,6 +11,7 @@ Use :prop_sf:`COMPILE_DEFINITIONS` to pass additional preprocessor definitions. .. |genex_subject| replace:: ``COMPILE_FLAGS`` .. include:: ../include/GENEX_NOTE_PER_SOURCE.rst +.. include:: ../include/GENEX_NOTE_SOURCE_TARGET.rst .. note:: diff --git a/Help/prop_sf/COMPILE_OPTIONS.rst b/Help/prop_sf/COMPILE_OPTIONS.rst index e51ede33d1..91d67e55bc 100644 --- a/Help/prop_sf/COMPILE_OPTIONS.rst +++ b/Help/prop_sf/COMPILE_OPTIONS.rst @@ -11,6 +11,7 @@ file builds. The options will be added after target-wide options. .. |genex_subject| replace:: ``COMPILE_OPTIONS`` .. include:: ../include/GENEX_NOTE_PER_SOURCE.rst +.. include:: ../include/GENEX_NOTE_SOURCE_TARGET.rst Usage example: diff --git a/Help/prop_sf/INCLUDE_DIRECTORIES.rst b/Help/prop_sf/INCLUDE_DIRECTORIES.rst index a58b4a2fb9..1ad325fe4f 100644 --- a/Help/prop_sf/INCLUDE_DIRECTORIES.rst +++ b/Help/prop_sf/INCLUDE_DIRECTORIES.rst @@ -15,3 +15,4 @@ Relative paths should not be added to this property directly. .. |genex_subject| replace:: ``INCLUDE_DIRECTORIES`` .. include:: ../include/GENEX_NOTE_PER_SOURCE.rst +.. include:: ../include/GENEX_NOTE_SOURCE_TARGET.rst diff --git a/Tests/GeneratorExpression/CMakeLists.txt b/Tests/GeneratorExpression/CMakeLists.txt index 18b545ba36..92cf3129ed 100644 --- a/Tests/GeneratorExpression/CMakeLists.txt +++ b/Tests/GeneratorExpression/CMakeLists.txt @@ -412,6 +412,15 @@ if (CMAKE_GENERATOR MATCHES "Makefiles|Ninja|Watcom WMake|FASTBuild") PROPERTY INCLUDE_DIRECTORIES "${CMAKE_CURRENT_BINARY_DIR}" $<$:${CMAKE_CURRENT_BINARY_DIR}/sf_includes_COMPILE_LANGUAGE>) endif() +# Evaluate source file properties separately for each target compiling a shared source. +foreach (id IN ITEMS 1 2) + add_executable(srcgenex_shared_${id} srcgenex_shared.c) + set_property(TARGET srcgenex_shared_${id} PROPERTY SRCGENEX_SHARED_ID ${id}) + target_compile_definitions(srcgenex_shared_${id} PRIVATE EXPECTED_ID=${id}) +endforeach() +set_property(SOURCE srcgenex_shared.c + PROPERTY COMPILE_DEFINITIONS SHARED_ID=$) + #----------------------------------------------------------------------------- # Cover test properties with generator expressions. add_executable(echo echo.c) diff --git a/Tests/GeneratorExpression/srcgenex_shared.c b/Tests/GeneratorExpression/srcgenex_shared.c new file mode 100644 index 0000000000..2b48edc57a --- /dev/null +++ b/Tests/GeneratorExpression/srcgenex_shared.c @@ -0,0 +1,12 @@ +#ifndef SHARED_ID +# error SHARED_ID not defined +#endif + +#if SHARED_ID != EXPECTED_ID +# error SHARED_ID does not match EXPECTED_ID of the compiled target +#endif + +int main(void) +{ + return 0; +}