diff options
| author | 0scar <qgt268@alumni.ku.dk> | 2023-07-28 09:45:33 +0000 |
|---|---|---|
| committer | 0scar <qgt268@alumni.ku.dk> | 2023-07-28 10:30:42 +0000 |
| commit | 22db1a2e1b41bed7d5083ce68888a583881d58bf (patch) | |
| tree | b42b453e3911e49cec026929f81cbf5a289313b6 | |
| parent | 6c16f339224a4736f4ed57d15bb3e5f968a635ab (diff) | |
Flesh out cmakelists & streamline some functions
| -rw-r--r-- | CMakeLists.txt | 138 | ||||
| -rw-r--r-- | docs/cmake-integration.md | 9 | ||||
| -rw-r--r-- | include/engine/logging.h | 6 | ||||
| -rw-r--r-- | src/logging.c | 1 | ||||
| -rw-r--r-- | src/rendering.c | 8 | ||||
| -rw-r--r-- | src/state.c | 9 | ||||
| -rw-r--r-- | src/ui_rendering.c | 6 | ||||
| -rw-r--r-- | tools/cmake/DawAddState.cmake | 44 |
8 files changed, 157 insertions, 64 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt index 6067c5c..655e664 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,13 +1,57 @@ -cmake_minimum_required(VERSION 3.16) +cmake_minimum_required(VERSION 3.24) +project(daw VERSION 0.0.1 LANGUAGES C) -if(NOT DEFINED PROJECT_NAME) +# We really don't want any in-source builds +set(CMAKE_DISABLE_IN_SOURCE_BUILD ON CACHE BOOL "Prevents cmake -S. -B.") +set(CMAKE_DISABLE_SOURCE_CHANGES ON CACHE BOOL "Prevent writing files to CMAKE_SOURCE_DIR under configure") + +if(NOT CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME) set(NOT_SUBPROJECT ON) else() set(NOT_SUBPROJECT OFF) endif() -option(ENGINE_DEBUG "Compile engine with debugging features" OFF) -option(ENGINE_HOT_RELOADING "Compile with hot-reloading enabled (only works with debug mode)" ON) +include(CMakeDependentOption) + +option(ASAN "Enable address sanitizer") +option(UBSAN "Enable undefined behaviour sanitizer") + +cmake_dependent_option(DAW_BUILD_DEBUG + "Compile daw engine with debugging features" ON + "CMAKE_BUILD_TYPE STREQUAL Debug" OFF) + +# unused +cmake_dependent_option(DAW_BUILD_HOTRELOAD + "Compile daw engine with hot reloading enabled" ON + "NOT CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME;CMAKE_BUILD_TYPE STREQUAL Debug;NOT WIN32" OFF) + +cmake_dependent_option(DAW_BUILD_ASAN + "Compile daw engine with address sanitizer (asan)" ON + "DAW_BUILD_DEBUG;ASAN" OFF) + +cmake_dependent_option(DAW_BUILD_UBSAN + "Compile daw engine with undefined behaviour sanitizer (ubsan)" ON + "DAW_BUILD_DEBUG;UBSAN" OFF) + +# unused +cmake_dependent_option(DAW_BUILD_STANDALONE + # Would require us to enable dynamically registered states. + "Compile daw as a standalone library. This is not implemented yet." OFF + "TRUE" OFF) + +# unused +cmake_dependent_option(DAW_BUILD_TOOLS + "Build tools to manipulate a daw project" ON + "CMAKE_PROJECT_NAME STREQUAL PROJECT_NAME" OFF) + +if("${CMAKE_BUILD_TYPE}" STREQUAL "Release") + message("Enabling LTO") + set(${CMAKE_INTERPROCEDURAL_OPTIMIZATION} TRUE) +endif() + +if(DAW_BUILD_UBSAN AND DAW_BUILD_ASAN) + message(FATAL_ERROR "You cannot build both asan and ubsan") +endif() set(ENGINE_SOURCES src/btree.c @@ -25,64 +69,54 @@ set(ENGINE_SOURCES src/vector.c ) -add_library(engine ${ENGINE_SOURCES}) +add_library(daw + ${ENGINE_SOURCES}) -target_include_directories(engine PUBLIC - include - ${CMAKE_BINARY_DIR}/include - ${ENGINE_INCLUDE}) -target_link_libraries(engine SDL2 SDL2_image SDL2_ttf m) -target_compile_features(engine PRIVATE c_std_99) +target_include_directories(daw PUBLIC + include ${CMAKE_BINARY_DIR}/include ${ENGINE_INCLUDE}) -configure_file(${CMAKE_CURRENT_LIST_DIR}/state_type_list.h.in - ${CMAKE_BINARY_DIR}/include/state_type_list.h) +target_link_libraries(${PROJECT_NAME} + SDL2 SDL2_image SDL2_ttf + $<$<NOT:$<PLATFORM_ID:Windows>>:m> + $<$<AND:$<NOT:$<C_COMPILER_ID:MSVC>>,$<BOOL:${DAW_BUILD_UBSAN}>>:ubsan> +) -configure_file(${CMAKE_CURRENT_LIST_DIR}/include_states.h.in - ${CMAKE_BINARY_DIR}/include/include_states.h) +target_compile_features(${PROJECT_NAME} PRIVATE c_std_99) +target_compile_options(${PROJECT_NAME} PUBLIC + $<$<NOT:$<C_COMPILER_ID:MSVC>>:-Wall -Wextra -pedantic> + $<$<C_COMPILER_ID:MSVC>:/W4> + # Debug related flags. sorry windows, you're just not that important. + $<$<AND:$<NOT:$<C_COMPILER_ID:MSVC>>,$<BOOL:${DAW_BUILD_DEBUG}>>:-Og -ggdb3 -fno-omit-frame-pointer> + $<$<AND:$<NOT:$<C_COMPILER_ID:MSVC>>,$<BOOL:${DAW_BUILD_ASAN}>>:-fsanitize=address -fsanitize=leak -fsanitize-address-use-after-scope> + $<$<AND:$<NOT:$<C_COMPILER_ID:MSVC>>,$<BOOL:${DAW_BUILD_UBSAN}>>:-fsanitize=undefined -fsanitize-undefined-trap-on-error -fno-sanitize-recover> -# Add the directory to the list of states -# The directorys contents will be compiled into a shared object file and linked -# to the main executable -macro(add_state STATEDIR) - if(NOT_SUBPROJECT) - else() - set_property(TARGET engine - APPEND PROPERTY INCLUDE_DIRECTORIES - ${CMAKE_SOURCE_DIR}/state_${STATEDIR}/include) + $<$<AND:$<NOT:$<C_COMPILER_ID:MSVC>>,$<NOT:$<BOOL:${DAW_BUILD_DEBUG}>>>:-O2 -flto=auto -fuse-linker-plugin -ffat-lto-objects -funroll-loops -ffast-math -fno-signed-zeros -fno-trapping-math -ffunction-sections -fdata-sections> +) - file(APPEND ${CMAKE_BINARY_DIR}/include/state_type_list.h - "State(${STATEDIR})\n") +target_compile_definitions(${PROJECT_NAME} PUBLIC + $<$<BOOL:${DAW_BUILD_DEBUG}>:DAW_BUILD_DEBUG> +) - file(APPEND ${CMAKE_BINARY_DIR}/include/include_states.h - "#include <states/${STATEDIR}.h>\n") - file(GLOB STATE_SOURCES - LIST_DIRECTORIES false - state_${STATEDIR}/src/*.c - ) +configure_file(${CMAKE_CURRENT_LIST_DIR}/state_type_list.h.in + ${CMAKE_BINARY_DIR}/include/state_type_list.h) - # TODO: When state reloading is implemented properly, add MODULE library - # option In general, this should only be available when debugging. - if(BUILD_SHARED_LIBS) - add_library(${STATEDIR} SHARED ${STATE_SOURCES}) - else() - add_library(${STATEDIR} OBJECT ${STATE_SOURCES}) - endif() +configure_file(${CMAKE_CURRENT_LIST_DIR}/include_states.h.in + ${CMAKE_BINARY_DIR}/include/include_states.h) - target_include_directories(${STATEDIR} PUBLIC - state_${STATEDIR}/include - engine/include - ${CMAKE_BINARY_DIR}/include - include - ) - set_property(TARGET engine - APPEND PROPERTY LINK_LIBRARIES - ${STATEDIR}) +list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}/tools/cmake") +if (NOT NOT_SUBPROJECT) + set(CMAKE_MODULE_PATH "${CMAKE_MODULE_PATH}" PARENT_SCOPE) +endif() +include(DawAddState) - endif() - list(APPEND STATE_LIST ${STATEDIR}) - #list(APPEND ENGINE_INCLUDE state_${STATEDIR}/include) -endmacro() +message("Configured ${PROJECT_NAME} ${PROJECT_VERSION}") +message("Build type: ${CMAKE_BUILD_TYPE}") +message("enable debug: ${DAW_BUILD_DEBUG}") +message("enable hotreload: ${DAW_BUILD_HOTRELOAD}") +message("enable asan: ${DAW_BUILD_ASAN}") +message("enable ubsan: ${DAW_BUILD_UBSAN}") +message("build tools: ${DAW_BUILD_TOOLS}") diff --git a/docs/cmake-integration.md b/docs/cmake-integration.md new file mode 100644 index 0000000..1b688e0 --- /dev/null +++ b/docs/cmake-integration.md @@ -0,0 +1,9 @@ +# Cmake targets + +The preferred way to include daw in your CMake project is to use `FetchContent`: +```CMake +FetchContent_Declare(daw + GIT_REPOSITORY https://github.com/0undefined/daw.git + GIT_TAG latest +) +``` diff --git a/include/engine/logging.h b/include/engine/logging.h index 1365a5b..0ac5025 100644 --- a/include/engine/logging.h +++ b/include/engine/logging.h @@ -34,8 +34,12 @@ void LOG(const char *fmt, ...); void INFO_(const char *fmt, ...); void INFO(const char *fmt, ...); -#define _DEBUG(...) __DEBUG(__FILE__,__LINE__, __func__, __VA_ARGS__) +#ifdef DAW_BUILD_DEBUG +#define DEBUG(fmt, ...) __DEBUG(__FILE__,__LINE__, __func__, fmt, __VA_ARGS__) void __DEBUG(const char* file, const i32 line, const char* func, const char *fmt, ...); +#else +#define DEBUG(...) +#endif void WARN(const char *fmt, ...); diff --git a/src/logging.c b/src/logging.c index 2ca5368..e8c2199 100644 --- a/src/logging.c +++ b/src/logging.c @@ -1,4 +1,5 @@ #include <stdlib.h> +#include <engine/types.h> #include <engine/logging.h> char *itoa(i32 x) { diff --git a/src/rendering.c b/src/rendering.c index 755eda0..580be9e 100644 --- a/src/rendering.c +++ b/src/rendering.c @@ -22,7 +22,7 @@ i32 drawcall_len = 0; /* Clear the screen, * To be used inbetween draw calls */ void render_begin(Window *w) { -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG SDL_SetRenderDrawColor(w->renderer, 0x10, 0x0a, 0x33, 0x00); #else SDL_SetRenderDrawColor(w->renderer, 0x00, 0x00, 0x00, 0x00); @@ -42,7 +42,7 @@ void render_present(Window *w) { break; case RenderDrawCallType_Sprite: { -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG if (dc.data.sprite.sprite == NULL) { __asm__("int3;"); WARN("Sprite %lx in drawcall %d/%d had NULL reference", dc.data.sprite.sprite, i, drawcall_len); @@ -110,7 +110,7 @@ void engine_draw_uitree(UITree *t) { void engine_draw_sprite(Sprite *s, v2_i32 *pos, f32 scale) { if (drawcall_len + 1 >= drawcall_limit) return; -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG if (s == NULL) __asm__("int3;"); #endif drawcalls[drawcall_len++] = (RenderDrawCall){ @@ -127,7 +127,7 @@ void engine_draw_sprite(Sprite *s, v2_i32 *pos, f32 scale) { void engine_draw_sprite_ex(Sprite *s, v2_i32 *pos, f32 scale, Engine_color colormod) { if (drawcall_len + 1 >= drawcall_limit) return; -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG if (s == NULL) __asm__("int3;"); #endif drawcalls[drawcall_len++] = (RenderDrawCall){ diff --git a/src/state.c b/src/state.c index 6b1f9c8..ee8b2fd 100644 --- a/src/state.c +++ b/src/state.c @@ -1,4 +1,5 @@ #include <engine/state.h> +#include <engine/logging.h> #include <include_states.h> @@ -23,7 +24,7 @@ void State_init(StateType type, memory *mem) { #undef State case STATE_null: case STATE_quit: - _DEBUG("Got %s state.\n", StateTypeStr[type]); + DEBUG("Got %s state.\n", StateTypeStr[type]); break; default: exit(EXIT_FAILURE); @@ -42,7 +43,7 @@ void State_free(StateType type, memory *mem) { #undef State case STATE_null: case STATE_quit: - _DEBUG("Got %s state.\n", StateTypeStr[type]); + DEBUG("Got %s state.\n", StateTypeStr[type]); break; default: exit(EXIT_FAILURE); @@ -62,7 +63,7 @@ StateType (*State_updateFunc(StateType type))(void*) { #undef State case STATE_null: case STATE_quit: - return NULL; //_DEBUG("Got %s state.\n", StateTypeStr[type]); + return NULL; //DEBUG("Got %s state.\n", StateTypeStr[type]); break; default: exit(EXIT_FAILURE); @@ -82,7 +83,7 @@ StateType State_update(StateType type, memory *mem) { #undef State case STATE_null: case STATE_quit: - _DEBUG("Got %s state.\n", StateTypeStr[type]); + DEBUG("Got %s state.\n", StateTypeStr[type]); break; default: exit(EXIT_FAILURE); diff --git a/src/ui_rendering.c b/src/ui_rendering.c index 7024e0b..a831a66 100644 --- a/src/ui_rendering.c +++ b/src/ui_rendering.c @@ -64,7 +64,7 @@ void render_container(Window *w, UITree_container *t) { SDL_RenderDrawRect(w->renderer, &r); -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG r.x += t->padding; r.y += t->padding; r.w -= t->padding * 2; @@ -162,7 +162,7 @@ void render_title(Window *w, UITree_title *t) { NULL, &r); -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG SDL_SetRenderDrawColor(w->renderer, 0xFF, 0xFF, @@ -196,7 +196,7 @@ void render_text(Window *w, UITree_text *t) { NULL, &r); -#ifdef DEBUG +#ifdef DAW_BUILD_DEBUG SDL_SetRenderDrawColor(w->renderer, 0xFF, 0xFF, diff --git a/tools/cmake/DawAddState.cmake b/tools/cmake/DawAddState.cmake new file mode 100644 index 0000000..a20aac7 --- /dev/null +++ b/tools/cmake/DawAddState.cmake @@ -0,0 +1,44 @@ +# Add the directory to the list of states. +# The directories contents will be compiled into a shared object file and linked +# to the main daw library +macro(daw_add_state STATEDIR) + set_property(TARGET daw + APPEND PROPERTY INCLUDE_DIRECTORIES + ${CMAKE_SOURCE_DIR}/state_${STATEDIR}/include) + + file(APPEND ${CMAKE_BINARY_DIR}/include/state_type_list.h + "State(${STATEDIR})\n") + + file(APPEND ${CMAKE_BINARY_DIR}/include/include_states.h + "#include <states/${STATEDIR}.h>\n") + + file(GLOB STATE_SOURCES + LIST_DIRECTORIES false + state_${STATEDIR}/src/*.c + ) + + # TODO: When state reloading is implemented properly, add MODULE library + # option In general, this should only be available when debugging. + if(BUILD_SHARED_LIBS) + if(DAW_BUILD_DEBUG AND DAW_BUILD_HOTRELOAD) + add_library(${STATEDIR} MODULE ${STATE_SOURCES}) + else() + add_library(${STATEDIR} SHARED ${STATE_SOURCES}) + endif() + else() + add_library(${STATEDIR} OBJECT ${STATE_SOURCES}) + endif() + + target_include_directories(${STATEDIR} PUBLIC + state_${STATEDIR}/include + ${daw_SOURCE_DIR}/include + ${CMAKE_BINARY_DIR}/include + include + ) + + set_property(TARGET daw + APPEND PROPERTY LINK_LIBRARIES + ${STATEDIR}) + + list(APPEND STATE_LIST ${STATEDIR}) +endmacro() |
