Skip to content

Commit b742bc0

Browse files
committed
Add API header compile tests for C
This will enable any future changes to the header to be tested. These additional build checks are only executed if BUILD_TESTING is enabled (e.g. in our automated build checks) to speed up release builds.
1 parent 3a79ff4 commit b742bc0

File tree

4 files changed

+121
-0
lines changed

4 files changed

+121
-0
lines changed

cmake/TestAPIHeaders.cmake

+51
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
cmake_minimum_required(VERSION 3.21 FATAL_ERROR)
2+
3+
# Compile-test C API headers
4+
macro(TEST_API_HEADERS _target _include_dirs _includes)
5+
set(_test_project_dir "${CMAKE_CURRENT_BINARY_DIR}/${_target}")
6+
set(HEADER_TEST_OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${_target}.done)
7+
8+
add_custom_command(OUTPUT ${HEADER_TEST_OUTPUT}
9+
# Create test project directory
10+
COMMAND ${CMAKE_COMMAND}
11+
ARGS
12+
-E make_directory "${_test_project_dir}"
13+
14+
# Copy project CMake file into it
15+
COMMAND ${CMAKE_COMMAND}
16+
ARGS
17+
-E copy_if_different "${CMAKE_SOURCE_DIR}/cmake/TestAPIHeadersProject.cmake" "${_test_project_dir}/CMakeLists.txt"
18+
19+
# Delete any existing build dir to re-run all checks
20+
COMMAND ${CMAKE_COMMAND}
21+
ARGS
22+
-E rm -Rf "${_test_project_dir}/build"
23+
24+
# Configure the test project
25+
COMMAND ${CMAKE_COMMAND}
26+
ARGS
27+
-S ${_test_project_dir}
28+
-B ${_test_project_dir}/build
29+
-DCMAKE_TOOLCHAIN_FILE=${CMAKE_TOOLCHAIN_FILE}
30+
-DCMAKE_C_FLAGS=${CMAKE_C_FLAGS}
31+
-DCMAKE_VERBOSE_MAKEFILE=${CMAKE_VERBOSE_MAKEFILE}
32+
"-DINCLUDE_FILES=${_includes}"
33+
"-DINCLUDE_DIRS=${_include_dirs}"
34+
-DOUTPUT_FILE=${HEADER_TEST_OUTPUT}
35+
36+
DEPENDS
37+
${CMAKE_SOURCE_DIR}/cmake/TestAPIHeaders.cmake
38+
${CMAKE_SOURCE_DIR}/cmake/TestAPIHeadersProject.cmake
39+
${_includes}
40+
41+
VERBATIM
42+
COMMENT "Testing C API headers: ${_target}"
43+
)
44+
45+
add_custom_target(${_target} ALL
46+
DEPENDS ${HEADER_TEST_OUTPUT}
47+
)
48+
49+
unset(_test_project_dir)
50+
51+
endmacro()

cmake/TestAPIHeadersProject.cmake

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
cmake_minimum_required(VERSION 3.21 FATAL_ERROR)
2+
3+
project(TestAPIHeaders
4+
LANGUAGES C
5+
)
6+
7+
include(CheckIncludeFile)
8+
9+
set(CMAKE_REQUIRED_INCLUDES "${INCLUDE_DIRS}")
10+
11+
foreach(INCLUDE_HEADER ${INCLUDE_FILES})
12+
cmake_path(GET INCLUDE_HEADER FILENAME INCLUDE_FILENAME)
13+
string(REPLACE "." "_" INCLUDE_FILENAME "${INCLUDE_FILENAME}")
14+
check_include_file(${INCLUDE_HEADER} PROJECTM_${INCLUDE_FILENAME}_INCLUDE_OK)
15+
if(NOT PROJECTM_${INCLUDE_FILENAME}_INCLUDE_OK)
16+
message(FATAL_ERROR "projectM API include file ${INCLUDE_HEADER} does not compile on its own!\nSee logs in ${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/ for additional information.")
17+
endif()
18+
endforeach()
19+
20+
file(TOUCH ${OUTPUT_FILE})

tests/libprojectM/CMakeLists.txt

+26
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,31 @@
11
find_package(GTest 1.10 REQUIRED NO_MODULE)
22

3+
# Compile-test C API headers
4+
set(INCLUDE_FILES
5+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/types.h
6+
7+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/audio.h
8+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/callbacks.h
9+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/core.h
10+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/debug.h
11+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/memory.h
12+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/parameters.h
13+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/render_opengl.h
14+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/touch.h
15+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/user_sprites.h
16+
17+
# Convenience header last, so it doesn't obscure issues with a single header above.
18+
${CMAKE_SOURCE_DIR}/src/api/include/projectM-4/projectM.h
19+
)
20+
21+
get_target_property(API_HEADER_INCLUDE_DIRS libprojectM::API INTERFACE_INCLUDE_DIRECTORIES)
22+
23+
include(TestAPIHeaders)
24+
test_api_headers(TestMainAPIHeaders
25+
"${API_HEADER_INCLUDE_DIRS}"
26+
"${INCLUDE_FILES}"
27+
)
28+
329
add_executable(projectM-unittest
430
WaveformAlignerTest.cpp
531
PresetFileParserTest.cpp

tests/playlist/CMakeLists.txt

+24
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,30 @@ endif()
44

55
find_package(GTest 1.10 REQUIRED NO_MODULE)
66

7+
# Compile-test C API headers
8+
set(INCLUDE_FILES
9+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_types.h
10+
11+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_callbacks.h
12+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_core.h
13+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_filter.h
14+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_items.h
15+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_memory.h
16+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist_playback.h
17+
18+
# Convenience header last, so it doesn't obscure issues with a single header above.
19+
${CMAKE_SOURCE_DIR}/src/playlist/api/projectM-4/playlist.h
20+
)
21+
22+
get_target_property(API_HEADER_INCLUDE_DIRS_MAIN libprojectM::API INTERFACE_INCLUDE_DIRECTORIES)
23+
get_target_property(API_HEADER_INCLUDE_DIRS_PLAYLIST projectM_playlist_main INTERFACE_INCLUDE_DIRECTORIES)
24+
25+
include(TestAPIHeaders)
26+
test_api_headers(TestPlaylistAPIHeaders
27+
"${API_HEADER_INCLUDE_DIRS_MAIN};${API_HEADER_INCLUDE_DIRS_PLAYLIST}"
28+
"${INCLUDE_FILES}"
29+
)
30+
731
add_executable(projectM-playlist-unittest
832
$<TARGET_OBJECTS:projectM_playlist_main>
933
APITest.cpp

0 commit comments

Comments
 (0)