feat(cmakev2/utilities): add __set_property and __get_property helpers

The `idf_build_(set|get)_property` and
`idf_component_(set|get)_property` functions share a lot of similar
code. Move these common parts into new `__(set|get)_property` helper
functions. With the upcoming `idf_build_library` API function, we might
need to add properties for the interface target created for the library,
which would otherwise lead to yet another code duplication for setting
and getting library interface properties.

Update the current implementations of `idf_build_(set|get)_property` and
`idf_component_(set|get)_property` to utilize these new helper
functions.

Signed-off-by: Frantisek Hrbata <frantisek.hrbata@espressif.com>
This commit is contained in:
Frantisek Hrbata
2025-11-04 07:48:12 +01:00
parent 871ec46a79
commit b702d3c077
3 changed files with 133 additions and 24 deletions
+16 -11
View File
@@ -27,16 +27,16 @@ function(idf_build_set_property property value)
set(multi_value)
cmake_parse_arguments(ARG "${options}" "${one_value}" "${multi_value}" ${ARGN})
get_property(properties TARGET idf_build_properties PROPERTY BUILD_PROPERTIES)
if(NOT property IN_LIST properties)
list(APPEND properties "${property}")
set_property(TARGET idf_build_properties PROPERTY BUILD_PROPERTIES "${properties}")
endif()
set(append)
if(ARG_APPEND)
set_property(TARGET idf_build_properties APPEND PROPERTY "${property}" "${value}")
else()
set_property(TARGET idf_build_properties PROPERTY "${property}" "${value}")
set(append APPEND)
endif()
__set_property(TARGET idf_build_properties
PROPERTY "${property}"
PROPERTIES BUILD_PROPERTIES
VALUE "${value}"
${append})
endfunction()
#[[api
@@ -62,11 +62,16 @@ function(idf_build_get_property variable property)
if("${property}" STREQUAL BUILD_COMPONENTS)
idf_die("Build property 'BUILD_COMPONENTS' is not supported")
endif()
set(genexpr)
if(ARG_GENERATOR_EXPRESSION)
set(value "$<TARGET_PROPERTY:idf_build_properties,${property}>")
else()
get_property(value TARGET idf_build_properties PROPERTY ${property})
set(genexpr GENERATOR_EXPRESSION)
endif()
__get_property(TARGET idf_build_properties
PROPERTY "${property}"
OUTPUT value
${genexpr})
set(${variable} ${value} PARENT_SCOPE)
endfunction()
+17 -13
View File
@@ -28,17 +28,17 @@ function(idf_component_set_property component property value)
set(multi_value)
cmake_parse_arguments(ARG "${options}" "${one_value}" "${multi_value}" ${ARGN})
__get_component_interface_or_die(COMPONENT "${component}" OUTPUT component_interface)
get_property(properties TARGET ${component_interface} PROPERTY COMPONENT_PROPERTIES)
if(NOT property IN_LIST properties)
list(APPEND properties "${property}")
set_property(TARGET ${component_interface} PROPERTY COMPONENT_PROPERTIES "${properties}")
endif()
set(append)
if(ARG_APPEND)
set_property(TARGET ${component_interface} APPEND PROPERTY ${property} "${value}")
else()
set_property(TARGET ${component_interface} PROPERTY ${property} "${value}")
set(append APPEND)
endif()
__get_component_interface_or_die(COMPONENT "${component}" OUTPUT component_interface)
__set_property(TARGET "${component_interface}"
PROPERTY "${property}"
PROPERTIES COMPONENT_PROPERTIES
VALUE "${value}"
${append})
endfunction()
#[[api
@@ -61,12 +61,16 @@ function(idf_component_get_property variable component property)
set(multi_value)
cmake_parse_arguments(ARG "${options}" "${one_value}" "${multi_value}" ${ARGN})
__get_component_interface_or_die(COMPONENT "${component}" OUTPUT component_interface)
set(genexpr)
if(ARG_GENERATOR_EXPRESSION)
set(value "$<TARGET_PROPERTY:${component_interface},${property}>")
else()
get_property(value TARGET ${component_interface} PROPERTY ${property})
set(genexpr GENERATOR_EXPRESSION)
endif()
__get_component_interface_or_die(COMPONENT "${component}" OUTPUT component_interface)
__get_property(TARGET "${component_interface}"
PROPERTY "${property}"
OUTPUT value
${genexpr})
set(${variable} ${value} PARENT_SCOPE)
endfunction()
+100
View File
@@ -260,3 +260,103 @@ function(__get_sdkconfig_option)
set(${ARG_OUTPUT} "${value}" PARENT_SCOPE)
endfunction()
#[[
__set_property(TARGET <target>
PROPERTY <property>)
PROPERTIES <properties>
VALUE <value>
APPEND)
:TARGET[in]: The target name to attach the property.
:PROPERTY[in]: Property name.
:PROPERTIES[in]: The target property containing list of properties.
:VALUE[in]: Property value.
:APPEND: Append the value to the property's current value instead of
replacing it.
Set the ``PROPERTY`` to ``VALUE`` for the ``TARGET``, and also record the
``PROPERTY`` name in the list of all properties for the ``TARGET``. The
property name where all ``TARGET`` property names are stored is specified
by the ``PROPERTIES`` option. If ``APPEND`` is specified, the property will
be added rather than set.
Note: The cmake_parse_arguments function does not preserve empty arguments,
as explained in CMP0174. We do not verify if VALUE is defined because it
might have been passed as an empty string or list.
Note: The VALUE is treated as a multi-value because if a list is provided
as the value, CMake assigns only the first entry to the VALUE if parsed as
one-value. The remaining entries are stored in <prefix>_UNPARSED_ARGUMENTS.
#]]
function(__set_property)
set(options APPEND)
set(one_value TARGET PROPERTY PROPERTIES)
set(multi_value VALUE)
cmake_parse_arguments(ARG "${options}" "${one_value}" "${multi_value}" ${ARGN})
if(NOT DEFINED ARG_TARGET)
idf_die("TARGET option is required")
endif()
if(NOT DEFINED ARG_PROPERTY)
idf_die("PROPERTY option is required")
endif()
if(NOT DEFINED ARG_PROPERTIES)
idf_die("PROPERTIES option is required")
endif()
get_property(properties TARGET ${ARG_TARGET} PROPERTY ${ARG_PROPERTIES})
if(NOT ARG_PROPERTY IN_LIST properties)
list(APPEND properties "${ARG_PROPERTY}")
set_property(TARGET ${ARG_TARGET} PROPERTY ${ARG_PROPERTIES} "${properties}")
endif()
if(ARG_APPEND)
set_property(TARGET ${ARG_TARGET} APPEND PROPERTY ${ARG_PROPERTY} "${ARG_VALUE}")
else()
set_property(TARGET ${ARG_TARGET} PROPERTY ${ARG_PROPERTY} "${ARG_VALUE}")
endif()
endfunction()
#[[
__get_property(TARGET <target>
PROPERTY <property>)
OUTPUT <variable>
GENERATOR_EXPRESSION)
:TARGET[in]: The target from which to obtain the property value.
:PROPERTY[in]: Property name.
:OUTPUT[out]: Output variable to store the property value.
:GENERATOR_EXPRESSION: Obtain the generator expression for the property
rather than the actual value.
Get the value of the specified ``PROPERTY`` from ``TARGET`` and store it in
the ``OUTPUT`` variable.
#]]
function(__get_property)
set(options GENERATOR_EXPRESSION)
set(one_value TARGET PROPERTY OUTPUT)
set(multi_value)
cmake_parse_arguments(ARG "${options}" "${one_value}" "${multi_value}" ${ARGN})
if(NOT DEFINED ARG_TARGET)
idf_die("TARGET option is required")
endif()
if(NOT DEFINED ARG_PROPERTY)
idf_die("PROPERTY option is required")
endif()
if(NOT DEFINED ARG_OUTPUT)
idf_die("PROPERTIES option is required")
endif()
if(ARG_GENERATOR_EXPRESSION)
set(value "$<TARGET_PROPERTY:${ARG_TARGET},${ARG_PROPERTY}>")
else()
get_property(value TARGET ${ARG_TARGET} PROPERTY ${ARG_PROPERTY})
endif()
set(${ARG_OUTPUT} ${value} PARENT_SCOPE)
endfunction()