mirror of
https://github.com/espressif/esp-idf.git
synced 2026-10-01 10:40:47 +03:00
The idf_create_size_report function allows for the creation of size report targets based on the generated link map file. The size report targets are created using the TARGET option name: "<target>", "<target>-files", and "<target>-components". These size report targets are added to the idf_default_project with the TARGET set to "size", resulting in the creation of "size", "size-files", and "size-components" targets for the default project. Signed-off-by: Frantisek Hrbata <frantisek.hrbata@espressif.com>
291 lines
10 KiB
CMake
291 lines
10 KiB
CMake
# SPDX-FileCopyrightText: 2025 Espressif Systems (Shanghai) CO LTD
|
|
# SPDX-License-Identifier: Apache-2.0
|
|
|
|
# Simple project for basic cmakev2 testing
|
|
# Run: cmake -S . -B build
|
|
cmake_minimum_required(VERSION 3.22)
|
|
|
|
include($ENV{IDF_PATH}/tools/cmakev2/idf.cmake)
|
|
|
|
project(cmakev2
|
|
VERSION 1.2.3
|
|
LANGUAGES C CXX ASM)
|
|
|
|
add_custom_target(flash)
|
|
|
|
idf_project_init()
|
|
|
|
# Test component priority
|
|
function(test_component_priority)
|
|
# Set the idf component to be replaced with a testing component of higher
|
|
# priority.
|
|
set(component_name "esp_system")
|
|
|
|
# Check that idf component is between discovered components.
|
|
__get_component_interface(COMPONENT "${component_name}"
|
|
OUTPUT component_interface)
|
|
if("${component_interface}" STREQUAL "NOTFOUND")
|
|
idf_die("Component '${component_name}' not found")
|
|
endif()
|
|
|
|
# Check that idf component has "idf_components" as source.
|
|
idf_component_get_property(component_source
|
|
${component_interface}
|
|
COMPONENT_SOURCE)
|
|
if(NOT "${component_source}" STREQUAL "idf_components")
|
|
idf_die("Unexpected idf component '${component_name}' source '${component_source}'")
|
|
endif()
|
|
|
|
# Create fake component with same name as idf component.
|
|
set(component_dir "${CMAKE_CURRENT_BINARY_DIR}/${component_name}")
|
|
file(MAKE_DIRECTORY "${component_dir}")
|
|
file(TOUCH "${component_dir}/CMakeLists.txt")
|
|
|
|
# Initialize fake component with higher "project_components" priority.
|
|
idf_build_get_property(component_prefix PREFIX)
|
|
__init_component(DIRECTORY "${component_dir}"
|
|
PREFIX "${component_prefix}"
|
|
SOURCE "project_components")
|
|
|
|
# Check that the idf component was replaced with fake component.
|
|
idf_component_get_property(component_source
|
|
${component_interface}
|
|
COMPONENT_SOURCE)
|
|
if(NOT "${component_source}" STREQUAL "project_components")
|
|
idf_die("Unexpected fake component '${component_name}' source '${component_source}'")
|
|
endif()
|
|
|
|
idf_component_get_property(component_dir
|
|
${component_interface}
|
|
COMPONENT_DIR)
|
|
if(NOT "${component_dir}" STREQUAL "${CMAKE_CURRENT_BINARY_DIR}/${component_name}")
|
|
idf_die("Unexpected fake component '${component_name}' directory '${component_dir}'")
|
|
endif()
|
|
__dump_component_properties("${component_name}")
|
|
endfunction()
|
|
|
|
# Test that IDF_VERSION and IDF_VER build property is set
|
|
function(test_idf_version)
|
|
if(NOT DEFINED IDF_VERSION_MAJOR OR
|
|
NOT DEFINED IDF_VERSION_MINOR OR
|
|
NOT DEFINED IDF_VERSION_PATCH OR
|
|
NOT DEFINED ENV{IDF_VERSION})
|
|
idf_die("IDF_VERSION not set")
|
|
endif()
|
|
idf_build_get_property(idf_ver IDF_VER)
|
|
if(NOT idf_ver)
|
|
idf_die("IDF_VER build property not set")
|
|
endif()
|
|
endfunction()
|
|
|
|
# Test that Python interpreter is set
|
|
function(test_python)
|
|
if(NOT DEFINED PYTHON OR "${PYTHON}" STREQUAL "")
|
|
idf_die("PYTHON variable not defined or empty")
|
|
endif()
|
|
endfunction()
|
|
|
|
# Test that toolchain is properly set
|
|
function(test_toolchain)
|
|
if(NOT IDF_TOOLCHAIN)
|
|
idf_die("IDF_TOOLCHAIN variable not defined or empty")
|
|
endif()
|
|
if(NOT CMAKE_TOOLCHAIN_FILE)
|
|
idf_die("CMAKE_TOOLCHAIN_FILE variable not defined or empty")
|
|
endif()
|
|
idf_build_get_property(toolchain IDF_TOOLCHAIN)
|
|
if(NOT toolchain)
|
|
idf_die("IDF_TOOLCHAIN build property not set")
|
|
endif()
|
|
idf_build_get_property(toolchain_file IDF_TOOLCHAIN_FILE)
|
|
if(NOT toolchain_file)
|
|
idf_die("IDF_TOOLCHAIN_FILE build property not set")
|
|
endif()
|
|
endfunction()
|
|
|
|
# Test idf_build_library
|
|
function(test_idf_build_library)
|
|
# Create idflibtest with specific set of components and test that it
|
|
# contains them.
|
|
set(components app_trace app_update bootloader bootloader_support bt cmock)
|
|
|
|
set(idflib idflibtest)
|
|
idf_build_library("${idflib}" COMPONENTS "${components}")
|
|
|
|
if(NOT TARGET "${idflib}")
|
|
idf_die("'${idflib}' not created")
|
|
endif()
|
|
|
|
idf_library_get_property(lib_components "${idflib}" LIBRARY_COMPONENTS)
|
|
if(NOT "${lib_components}" STREQUAL "${components}")
|
|
idf_die("Library '${idflib}' components '${lib_components}' do not match "
|
|
"expected components '${components}'")
|
|
endif()
|
|
|
|
# Create idflibtest2 without specifying COMPONENTS and test that it
|
|
# contains all discovered components.
|
|
set(idflib idflibtest2)
|
|
idf_build_library("${idflib}")
|
|
|
|
if(NOT TARGET "${idflib}")
|
|
idf_die("'${idflib}' not created")
|
|
endif()
|
|
|
|
idf_library_get_property(lib_components "${idflib}" LIBRARY_COMPONENTS)
|
|
idf_build_get_property(component_names COMPONENTS_DISCOVERED)
|
|
if(NOT "${lib_components}" STREQUAL "${component_names}")
|
|
idf_die("Library '${idflib}' components '${lib_components}' do not match "
|
|
"COMPONENTS_DISCOVERED")
|
|
endif()
|
|
endfunction()
|
|
|
|
function(test_kconfig)
|
|
# Check that kconfig output files were generated
|
|
idf_build_get_property(config_dir CONFIG_DIR)
|
|
set(output_files sdkconfig.h sdkconfig.cmake sdkconfig.json)
|
|
|
|
foreach(file ${output_files})
|
|
set(file_path "${config_dir}/${file}")
|
|
if(NOT EXISTS "${file_path}")
|
|
idf_die("Missing kconfig output: ${file_path}")
|
|
endif()
|
|
file(SIZE "${file_path}" file_size)
|
|
if(file_size EQUAL 0)
|
|
idf_die("Empty kconfig output: ${file_path}")
|
|
endif()
|
|
endforeach()
|
|
|
|
# Check that kconfig targets were created
|
|
set(targets menuconfig confserver save-defconfig)
|
|
foreach(target ${targets})
|
|
if(NOT TARGET ${target})
|
|
idf_die("Missing kconfig target: ${target}")
|
|
endif()
|
|
endforeach()
|
|
endfunction()
|
|
|
|
# Test that PROJECT_NAME and PROJECT_VER build property is set and contain
|
|
# values provided in project() call.
|
|
function(test_project_properties)
|
|
idf_build_get_property(project_name PROJECT_NAME)
|
|
if(NOT project_name)
|
|
idf_die("PROJECT_NAME build property not set")
|
|
endif()
|
|
if(NOT "${project_name}" STREQUAL "${PROJECT_NAME}")
|
|
idf_die("PROJECT_NAME build property '${project_name}' != '${PROJECT_NAME}'")
|
|
endif()
|
|
idf_build_get_property(project_ver PROJECT_VER)
|
|
if(NOT project_ver)
|
|
idf_die("PROJECT_VER build property not set")
|
|
endif()
|
|
if(NOT "${project_ver}" STREQUAL "${PROJECT_VERSION}")
|
|
idf_die("PROJECT_VER build property '${project_ver}' != '${PROJECT_VERSION}'")
|
|
endif()
|
|
endfunction()
|
|
|
|
# Test that the targets for component1 and component2 are created when
|
|
# component2 is included.
|
|
function(test_include_component)
|
|
idf_build_library(idflibtest3 COMPONENTS component2)
|
|
idf_component_get_property(component_real_target
|
|
component2
|
|
COMPONENT_REAL_TARGET)
|
|
if(NOT TARGET ${component_real_target})
|
|
idf_die("Missing component2 target")
|
|
endif()
|
|
|
|
# Test that component1 is included as a dependency of component2.
|
|
idf_component_get_property(component_real_target
|
|
component1
|
|
COMPONENT_REAL_TARGET)
|
|
if(NOT TARGET ${component_real_target})
|
|
idf_die("Missing component1 target")
|
|
endif()
|
|
endfunction()
|
|
|
|
# Add two executables fatfs_example and hello_world_example, generate
|
|
# binary images for them and add flash and menuconfig targets.
|
|
# After configuration these can be build with
|
|
# idf.py hello_world_example_bin
|
|
# idf.py fatfs_example_bin
|
|
# or simply
|
|
# idf.py hello_world_example-flash monitor
|
|
# idf.py fatfs-flash monitor
|
|
# The menuconfig can be invoked with
|
|
# idf.py --no-hints menuconfig-hello_world
|
|
# idf.py --no-hints menuconfig-fatfs
|
|
# The confserver can be invoked with
|
|
# idf.py confserver-hello_world
|
|
# idf.py confserver-fatfs
|
|
function(test_executable)
|
|
idf_build_executable(fatfs_example
|
|
COMPONENTS fatfs_example
|
|
MAPFILE_TARGET fatfs_example_mapfile)
|
|
idf_build_binary(fatfs_example
|
|
TARGET fatfs_example_bin
|
|
OUTPUT_FILE fatfs_example.bin)
|
|
idf_check_binary_size(fatfs_example_bin)
|
|
idf_flash_binary(fatfs_example_bin
|
|
TARGET fatfs_example-flash
|
|
NAME fatfs_example)
|
|
idf_create_menuconfig(fatfs_example
|
|
TARGET menuconfig-fatfs)
|
|
idf_build_generate_metadata(fatfs_example_bin
|
|
OUTPUT_FILE project_description_fatfs.json)
|
|
idf_create_confserver(fatfs_example
|
|
TARGET confserver-fatfs)
|
|
|
|
if(TARGET fatfs_example_mapfile)
|
|
idf_create_size_report(fatfs_example_mapfile
|
|
TARGET fatfs-size)
|
|
endif()
|
|
|
|
|
|
idf_build_executable(hello_world_example
|
|
COMPONENTS hello_world_example
|
|
MAPFILE_TARGET hello_world_example_mapfile)
|
|
idf_build_binary(hello_world_example
|
|
TARGET hello_world_example_bin
|
|
OUTPUT_FILE hello_world_example.bin)
|
|
idf_check_binary_size(hello_world_example_bin)
|
|
idf_flash_binary(hello_world_example_bin
|
|
TARGET hello_world_example-flash
|
|
NAME hello_world_example)
|
|
idf_create_menuconfig(hello_world_example
|
|
TARGET menuconfig-hello_world)
|
|
idf_build_generate_metadata(hello_world_example_bin
|
|
OUTPUT_FILE project_description_hello_world.json)
|
|
idf_create_confserver(hello_world_example
|
|
TARGET confserver-hello_world)
|
|
|
|
if(TARGET hello_world_example_mapfile)
|
|
idf_create_size_report(hello_world_example_mapfile
|
|
TARGET hello-size)
|
|
endif()
|
|
endfunction()
|
|
|
|
# Run tests
|
|
test_idf_version()
|
|
test_python()
|
|
test_toolchain()
|
|
test_idf_build_library()
|
|
test_project_properties()
|
|
test_include_component()
|
|
test_executable()
|
|
|
|
# Create default project
|
|
idf_project_default()
|
|
|
|
# The kconfig test also verifies whether kconfig-related targets, such as
|
|
# menuconfig, are created. These targets are now generated within
|
|
# idf_project_default rather than globally, so this test should be run only
|
|
# after the default project is created.
|
|
test_kconfig()
|
|
|
|
# Call this test last because it replaces the ESP system component.
|
|
test_component_priority()
|
|
|
|
__dump_all_properties()
|
|
|
|
message("ALL TESTS PASSED")
|