CMakeLists.txt template for component that is shared with esp-idf and linux
Posted: Fri Oct 24, 2025 11:06 pm
I would appreciate help creating a template (layout) for a CMakeLists.txt script for a component that builds an element library shared by both esp-idf and linux C++ projects.
I use git submodules to embed this component into each kind of project. I've been doing this with success in esp-idf v4.4 which used register_component(), but in v5+ that has been deprecated and other changes cause CMake problems. In updating from Ubuntu 22.04 to 24.04 I had to update esp-idf to v5 (python issues) and that introduced the need to change from some deprecated cmake functions.
I will provide the CMakeLists.txt file I've used for a component I call cpp-common. Here is the dir structure:
Note: other parts of my project will use REQUIRES cpp-common to resolve dependencies on this component.
Here is the CMakeLists.txt file that worked well in v4.4 and with Linux project:
Unfortunately, when built with esp-idf v5, above CMakeLists.txt script, I get errors regarding esp_timers.h not found in cpp-common code.
I am not a CMake expert, as this script was written by someone else. I've tried to rewrite this script to use idf_component_register() as follows, but get a build errors I don't understand.
Here is my attempt to rewrite the script.... but fails:
My rewritten version of the CMakeLists.txt file above, generates an error:
I hope your help fixing my rewritten CMakeLists.txt file will help others who are sharing components across different cmake based build tools. Please show me correctly written scripts for this purpose.
Thanks
esp-idf v5.5.1
Ubuntu 24.04
I use git submodules to embed this component into each kind of project. I've been doing this with success in esp-idf v4.4 which used register_component(), but in v5+ that has been deprecated and other changes cause CMake problems. In updating from Ubuntu 22.04 to 24.04 I had to update esp-idf to v5 (python issues) and that introduced the need to change from some deprecated cmake functions.
I will provide the CMakeLists.txt file I've used for a component I call cpp-common. Here is the dir structure:
Code: Select all
.../
cpp-common
common/
subdir1/
code1.hpp
code1.cpp
subdir2/
code2.hpp
code2.cpp
CMakeLists.txt
Here is the CMakeLists.txt file that worked well in v4.4 and with Linux project:
Code: Select all
cmake_minimum_required(VERSION 3.16)
#Make sure this library has not already been built.
if (NOT TARGET cpp-common)
#If ESP32, register it as a component.
if(IDF_TARGET)
set(COMPONENT_ADD_INCLUDEDIRS
common
)
set(COMPONENT_REQUIRES "esp_timer" )
register_component()
endif()
project(cpp-common)
# Available CMake build options
option(BUILD_STATIC_LIBS "Build a static version of the library" OFF)
option(BUILD_RELEASE "Build the release version of the library" OFF)
# Determine the library build type (static/shared)
set(LIB_TYPE STATIC)
# Set the CMake build type (release/debug)
if(NOT ${BUILD_RELEASE})
set(CMAKE_BUILD_TYPE Debug)
endif()
# Set the CXX target version
set(CMAKE_CXX_STANDARD 17)
# Grab a listing of all the C/C++ source and header files.
file(GLOB_RECURSE GLOB_SOURCE_FILES "${CMAKE_CURRENT_SOURCE_DIR}/common/**/*.c*")
file(GLOB_RECURSE GLOB_HEADER_FILES "${CMAKE_CURRENT_SOURCE_DIR}/common/**/*.h*")
# Add the source files to the library
add_library(${PROJECT_NAME} ${LIB_TYPE} ${GLOB_SOURCE_FILES} ${GLOB_HEADER_FILES})
target_include_directories(${PROJECT_NAME} PUBLIC .)
if(IDF_TARGET)
target_include_directories(cpp-common PRIVATE ${IDF_INCLUDE_DIRECTORIES})
target_compile_options(cpp-common PUBLIC ${IDF_COMPILE_OPTIONS})
target_compile_options(cpp-common PUBLIC ${IDF_CXX_COMPILE_OPTIONS})
target_compile_options(cpp-common INTERFACE -std=gnu++17)
target_link_libraries(${COMPONENT_TARGET} INTERFACE cpp-common)
endif()
endif()
I am not a CMake expert, as this script was written by someone else. I've tried to rewrite this script to use idf_component_register() as follows, but get a build errors I don't understand.
Here is my attempt to rewrite the script.... but fails:
Code: Select all
cmake_minimum_required(VERSION 3.16)
#Make sure this library has not already been built.
if (NOT TARGET cpp-common)
# Available CMake build options
option(BUILD_STATIC_LIBS "Build a static version of the library" OFF)
option(BUILD_RELEASE "Build the release version of the library" OFF)
set(LIB_TYPE STATIC)
# Set the CMake build type (release/debug)
if(NOT ${BUILD_RELEASE})
set(CMAKE_BUILD_TYPE Debug)
endif()
# Set the CXX target version
set(CMAKE_CXX_STANDARD 17)
# Grab a listing of all the C/C++ source and header files.
file(GLOB_RECURSE GLOB_SOURCE_FILES "${CMAKE_CURRENT_SOURCE_DIR}/common/**/*.c*")
file(GLOB_RECURSE GLOB_HEADER_FILES "${CMAKE_CURRENT_SOURCE_DIR}/common/**/*.h*")
#If ESP32, register it as a component.
if(IDF_TARGET)
idf_component_register(SRCS ${GLOB_SOURCE_FILES}
INCLUDE_DIRS
common
REQUIRES
esp_timer)
endif()
project(cpp-common)
# Add the source files to the library
add_library(${PROJECT_NAME} ${LIB_TYPE} ${GLOB_SOURCE_FILES} ${GLOB_HEADER_FILES})
target_include_directories(${PROJECT_NAME} PUBLIC .)
if(IDF_TARGET)
target_include_directories(cpp-common PRIVATE ${IDF_INCLUDE_DIRECTORIES})
target_compile_options(cpp-common PUBLIC ${IDF_COMPILE_OPTIONS})
target_compile_options(cpp-common PUBLIC ${IDF_CXX_COMPILE_OPTIONS})
target_compile_options(cpp-common INTERFACE -std=gnu++17)
target_link_libraries(${COMPONENT_TARGET} INTERFACE cpp-common)
endif()
endif()
Code: Select all
ninja: error: build.ninja:19049: multiple rules generate esp-idf/cpp-common/libcpp-common.aThanks
esp-idf v5.5.1
Ubuntu 24.04