From d17e538ea18ab987f685ead3f46686f4f3eb03af Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sat, 1 Jun 2024 21:28:26 +0200 Subject: [PATCH 01/30] #102 fix macos image slide address computation that failed when launching test with relative path --- clove-unit.h | 53 +++++++++++++++++++++++++++++++++++++++------------- 1 file changed, 40 insertions(+), 13 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index a88008d..317e12c 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -90,6 +90,7 @@ __CLOVE_EXTERN_C char* __clove_path_rel_to_abs_exec_path(const char* rel_path); __CLOVE_EXTERN_C bool __clove_path_is_relative(const char* path); __CLOVE_EXTERN_C void __clove_path_to_os(char* path); __CLOVE_EXTERN_C char* __clove_path_basepath(const char* path); +__CLOVE_EXTERN_C char* __clove_path_to_absolute(const char* path); #pragma endregion // Path Decl #pragma region PRIVATE - Memory Decl @@ -896,6 +897,8 @@ double __clove_math_decimald(unsigned char precision) { #include #include #include +#include + char* __clove_path_concat(const char separator, const char* path1, const char* path2) { size_t count = __clove_string_length(path1) + 1 + __clove_string_length(path2) + 1; char* path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, count); @@ -959,6 +962,18 @@ char* __clove_path_basepath(const char* a_path) { __clove_path_to_os(base_path); return base_path; } +char* __clove_path_to_absolute(const char* rel_path) { + char* result = NULL; +#if _WIN32 + result = __CLOVE_MEMORY_MALLOC_TYPE_N(char, _MAX_PATH); + //if( _fullpath( full, partialPath, _MAX_PATH ) != NULL ) + _fullpath(result, rel_path, _MAX_PATH ); +#else + result = __CLOVE_MEMORY_MALLOC_TYPE_N(char, PATH_MAX); + realpath(rel_path, result); // NULL +#endif + return result; +} #pragma endregion // Path Impl #pragma region PRIVATE - Console Impl @@ -3742,26 +3757,29 @@ int __clove_symbols_for_each_function_by_prefix(__clove_symbols_context_t* conte #include #include #include - typedef struct __clove_symbols_macos_module_t { void* handle; size_t size; //mmap handle size; intptr_t address; //module base address } __clove_symbols_macos_module_t; -intptr_t __clove_symbols_macos_image_slide(const char* path) -{ + +bool __clove_symbols_macos_image_slide(const char* abs_path, intptr_t* out_address) +{ + //NOTE: dyld image names are in absolute path. So tu properly compare, need to pass an abs_path to this function. for (uint32_t i = 0; i < _dyld_image_count(); i++) { - if (strcmp(_dyld_get_image_name(i), path) == 0) - return _dyld_get_image_vmaddr_slide(i); + if (strcmp(_dyld_get_image_name(i), abs_path) == 0) { + *out_address = _dyld_get_image_vmaddr_slide(i); + return true; + } } - return 0; + return false; } -int __clove_symbols_macos_open_module_handle(const char* module_path, __clove_symbols_macos_module_t* out_module) { +int __clove_symbols_macos_open_module_handle(const char* module_abs_path, __clove_symbols_macos_module_t* out_module) { int fd; - if ((fd = open(module_path, O_RDONLY)) < 0) { + if ((fd = open(module_abs_path, O_RDONLY)) < 0) { return 1; } @@ -3780,7 +3798,11 @@ int __clove_symbols_macos_open_module_handle(const char* module_path, __clove_sy out_module->handle = map; out_module->size = st.st_size; - out_module->address = __clove_symbols_macos_image_slide(module_path); + bool found = __clove_symbols_macos_image_slide(module_abs_path, &out_module->address); + if (!found) { + puts("cannot find image slide"); + return 4; + } return 0; } @@ -3801,7 +3823,7 @@ struct load_command* __clove_symbols_macos_find_command(struct mach_header_64* h } int __clove_symbols_for_each_function_by_prefix(__clove_symbols_context_t* context, __clove_symbols_function_action action) { - const char* module_path = __clove_exec_path; + const char* module_path = __clove_get_exec_path(); __clove_symbols_macos_module_t module; if (__clove_symbols_macos_open_module_handle(module_path, &module) != 0) { return 1; }; @@ -4054,8 +4076,12 @@ int main(int argc, char* argv[]) {\ } int __clove_runner_auto(int argc, char* argv[]) { - __clove_exec_path = argv[0]; - __clove_exec_base_path = __clove_path_basepath(argv[0]); + //__clove_exec_path = argv[0]; + __clove_exec_path = __clove_path_to_absolute(argv[0]); + __clove_exec_base_path = __clove_path_basepath(__clove_exec_path); + + //puts(__clove_exec_path); + //puts(__clove_exec_base_path); //argc = 5; //const char* argv2[] = {"exec", "-i", "*.ActShortThanExpForthCharDiff", "-r", "pretty"}; @@ -4083,6 +4109,7 @@ int __clove_runner_auto(int argc, char* argv[]) { __clove_vector_free(&cmd_handlers); __clove_cmdline_free(&cmdline); + free(__clove_exec_path); free(__clove_exec_base_path); return cmd_result; } @@ -4298,4 +4325,4 @@ void __clove_exec_suite(__clove_suite_t* suite, size_t test_counter, size_t* pas #pragma GCC diagnostic pop #endif -#endif //__CLOVE_H +#endif //__CLOVE_H \ No newline at end of file From 4bc8f5c194f6358f91e7f3af3c2cfdc1bd35b821 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sat, 1 Jun 2024 21:29:20 +0200 Subject: [PATCH 02/30] #102 fix github ci regression on ubuntu 22.04 where has been removed gcc-13 --- .github/workflows/ci_action.yml | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/.github/workflows/ci_action.yml b/.github/workflows/ci_action.yml index c031b9e..1c9d7f8 100644 --- a/.github/workflows/ci_action.yml +++ b/.github/workflows/ci_action.yml @@ -73,7 +73,7 @@ jobs: cd ${{ github.workspace }} build_ubuntu: name: Build ubuntu_${{matrix.compiler.c}}-${{matrix.compiler.v}} - runs-on: ubuntu-latest + runs-on: ubuntu-22.04 strategy: fail-fast: false matrix: @@ -102,14 +102,24 @@ jobs: with: version: "${{ matrix.compiler.v }}" env: true # set CC / CXX variable + - name: Install GCC (if needed) + # Installing GCC-13 due to regression introduced in ubuntu 22.04 image + # https://github.com/actions/runner-images/issues/9866 + if: ${{ matrix.compiler.c == 'gcc' && matrix.compiler.v == 13 }} + run: | + sudo add-apt-repository ppa:ubuntu-toolchain-r/test -y + sudo apt-get update -y + sudo apt-get install gcc-13 + sudo apt-get install g++-13 - name: Set Compiler # only if CC / CXX are not already set from new installation run: | if [ -z "${CC}" ]; then echo "CC=${{matrix.compiler.c}}-${{matrix.compiler.v}}" >> "$GITHUB_ENV" echo "CXX=${{matrix.compiler.cpp}}-${{matrix.compiler.v}}" >> "$GITHUB_ENV" + else + echo CC=$CC + echo CXX=$CXX fi - echo CC=$CC - echo CXX=$CXX - name: Compile run: | echo "== CMAKE VERSION ==" From 959e11920d5602d579a070953c0e8d0c5948bc4b Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sat, 1 Jun 2024 21:31:24 +0200 Subject: [PATCH 03/30] #102 restore newline at end of file --- clove-unit.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/clove-unit.h b/clove-unit.h index 317e12c..b7edb96 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -4325,4 +4325,4 @@ void __clove_exec_suite(__clove_suite_t* suite, size_t test_counter, size_t* pas #pragma GCC diagnostic pop #endif -#endif //__CLOVE_H \ No newline at end of file +#endif //__CLOVE_H From ee73804c4a86b970f2a9150c5d922263201bbd41 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sun, 16 Jun 2024 16:28:10 +0200 Subject: [PATCH 04/30] #102 refactor, improve naming, extract __clove_string_last_indexof --- README.md | 8 +-- clove-unit.h | 80 ++++++++++++++++------------- tests/functs/src/unit/path_test.c | 16 +++++- tests/functs/src/unit/string_test.c | 7 +++ 4 files changed, 68 insertions(+), 43 deletions(-) diff --git a/README.md b/README.md index 2371d60..48b0cc2 100644 --- a/README.md +++ b/README.md @@ -236,10 +236,10 @@ Assertions that can be used within a `CLOVE_TEST` definition. Helper APIs to support test implementation. -| API | Description | -|--------------------------|------------------------------------------------------------| -| `CLOVE_EXEC_PATH()` | Macro to easily retrieve executable path as a `char*` | -| `CLOVE_EXEC_BASE_PATH()` | Macro to easily retrieve executable base path as a `char*` | +| API | Description | +|--------------------------|---------------------------------------------------------------------------| +| `CLOVE_EXEC_PATH()` | Macro to easily retrieve executable absolute path as a `const char*` | +| `CLOVE_EXEC_BASE_PATH()` | Macro to easily retrieve executable absolute base path as a `const char*` | ## Command-Line API diff --git a/clove-unit.h b/clove-unit.h index b7edb96..2ab602a 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -43,10 +43,10 @@ #include __CLOVE_EXTERN_C void __clove_utils_empty_funct(void); -extern char* __clove_exec_path; -extern char* __clove_exec_base_path; -__CLOVE_EXTERN_C const char* __clove_get_exec_base_path(void); -__CLOVE_EXTERN_C const char* __clove_get_exec_path(void); +extern char* __clove_exec_abs_path; +extern char* __clove_exec_abs_basepath; +__CLOVE_EXTERN_C const char* __clove_utils_get_exec_abs_path(void); +__CLOVE_EXTERN_C const char* __clove_utils_get_exec_abs_basepath(void); //Switch implementation for pointer types #define __CLOVE_SWITCH_BEG(X) \ @@ -147,6 +147,7 @@ __CLOVE_EXTERN_C char* __clove_string_csv_escape(const char* string); __CLOVE_EXTERN_C void __clove_string_ellipse(const char* string, size_t str_len, size_t pos, char* out, size_t out_size); __CLOVE_EXTERN_C void __clove_string_replace_char(char* path, char find, char replace); __CLOVE_EXTERN_C void __clove_string_pad_right(char* dest, size_t dest_size, size_t str_target_len); +__CLOVE_EXTERN_C int __clove_string_last_indexof(const char* source, char character); #pragma endregion // String Decl #pragma region PRIVATE - String View Decl @@ -863,13 +864,14 @@ __CLOVE_EXTERN_C void __clove_exec_suite(__clove_suite_t* suite, size_t test_cou #include void __clove_utils_empty_funct(void) { } -const char* __clove_get_exec_base_path(void) { - return __clove_exec_base_path; +const char* __clove_utils_get_exec_abs_path(void) { + return __clove_exec_abs_path; } -const char* __clove_get_exec_path(void) { - return __clove_exec_path; +const char* __clove_utils_get_exec_abs_basepath(void) { + return __clove_exec_abs_basepath; } + #pragma endregion // Utils Impl #pragma region PRIVATE - Math Impl @@ -925,7 +927,7 @@ const char* __clove_path_relative(const char* abs_path, const char* base_path) { } char* __clove_path_rel_to_abs_exec_path(const char* rel_path) { - const char* base_path = __clove_get_exec_base_path(); + const char* base_path = __clove_utils_get_exec_abs_basepath(); char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, rel_path); return abs_path; } @@ -944,24 +946,25 @@ void __clove_path_to_os(char* path) { char* __clove_path_basepath(const char* a_path) { // Find the last path separator character in the input path. - const char* last_char = a_path + __clove_string_length(a_path) - 1; - while (last_char > a_path && *last_char != '/' && *last_char != '\\') { - --last_char; - } - + int last_char_win = __clove_string_last_indexof(a_path, '\\'); + int last_char_uni = __clove_string_last_indexof(a_path, '/'); //or unix or win eventually + int last_char_index = last_char_win > last_char_uni ? last_char_win : last_char_uni; + // If there are no separators in the path, return the current directory path. - if (last_char == a_path) { + if (last_char_index <= 0) { static char dot_path[3] = { '.', __CLOVE_PATH_SEPARATOR, '\0' }; return __clove_string_strdup(dot_path); + } else { + // Calculate base path length based on the position of the last path separator. + size_t base_length = (size_t)(last_char_index + 1); + char* base_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, base_length); + __clove_string_strncpy(base_path, base_length, a_path, base_length - 1); + __clove_path_to_os(base_path); + return base_path; } - // Calculate base path length based on the position of the last path separator. - size_t base_length = last_char - a_path; - char* base_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, base_length + 1); - __clove_string_strncpy(base_path, base_length + 1, a_path, base_length); - __clove_path_to_os(base_path); - return base_path; } + char* __clove_path_to_absolute(const char* rel_path) { char* result = NULL; #if _WIN32 @@ -1355,6 +1358,13 @@ void __clove_string_pad_right(char* dest, size_t dest_size, size_t str_target_le __clove_memory_memset(pad_beg , pad_len, '.'); *pad_end = '\0'; } + +int __clove_string_last_indexof(const char* source, char character) { + const char* char_ptr = strrchr(source, character); + if (char_ptr == NULL) return -1; + return (int)(char_ptr - source); +} + #pragma endregion //String Impl #pragma region PRIVATE - String View Impl @@ -3823,7 +3833,7 @@ struct load_command* __clove_symbols_macos_find_command(struct mach_header_64* h } int __clove_symbols_for_each_function_by_prefix(__clove_symbols_context_t* context, __clove_symbols_function_action action) { - const char* module_path = __clove_get_exec_path(); + const char* module_path = __clove_utils_get_exec_abs_path(); __clove_symbols_macos_module_t module; if (__clove_symbols_macos_open_module_handle(module_path, &module) != 0) { return 1; }; @@ -3986,7 +3996,7 @@ int __clove_symbols_funct_name_comparator(void* f1, void* f2) { } int __clove_symbols_for_each_function_by_prefix(__clove_symbols_context_t* context, __clove_symbols_function_action action) { - const char* module_path = __clove_exec_path; + const char* module_path = CLOVE_EXEC_PATH; __clove_symbols_lixux_module_t module; if (__clove_symbols_lixux_open_module_handle(module_path, &module) != 0) { return 1; } @@ -4066,8 +4076,8 @@ int __clove_symbols_for_each_function_by_prefix(__clove_symbols_context_t* conte #pragma region PRIVATE - Run Impl #define __CLOVE_RUNNER_AUTO() \ -char* __clove_exec_path;\ -char* __clove_exec_base_path;\ +char* __clove_exec_abs_path;\ +char* __clove_exec_abs_basepath;\ __CLOVE_ASSERT_CHECK_E_DECL() \ __CLOVE_TEST_RESULT_E_DECL() \ __CLOVE_GENERIC_TYPE_E_DECL() \ @@ -4076,12 +4086,8 @@ int main(int argc, char* argv[]) {\ } int __clove_runner_auto(int argc, char* argv[]) { - //__clove_exec_path = argv[0]; - __clove_exec_path = __clove_path_to_absolute(argv[0]); - __clove_exec_base_path = __clove_path_basepath(__clove_exec_path); - - //puts(__clove_exec_path); - //puts(__clove_exec_base_path); + __clove_exec_abs_path = __clove_path_to_absolute(argv[0]); + __clove_exec_abs_basepath = __clove_path_basepath(__clove_exec_abs_path); //argc = 5; //const char* argv2[] = {"exec", "-i", "*.ActShortThanExpForthCharDiff", "-r", "pretty"}; @@ -4109,8 +4115,8 @@ int __clove_runner_auto(int argc, char* argv[]) { __clove_vector_free(&cmd_handlers); __clove_cmdline_free(&cmdline); - free(__clove_exec_path); - free(__clove_exec_base_path); + free(__clove_exec_abs_path); + free(__clove_exec_abs_basepath); return cmd_result; } @@ -4202,13 +4208,13 @@ void __clove_exec_suite(__clove_suite_t* suite, size_t test_counter, size_t* pas #pragma region PUBLIC #pragma region PUBLIC - UTILS /* - * Provide the executable path + * Provide the executable absolute path */ -#define CLOVE_EXEC_PATH() __clove_get_exec_path() +#define CLOVE_EXEC_PATH() __clove_utils_get_exec_abs_path() /* - * Provide the executable base path + * Provide the executable absolute base path */ -#define CLOVE_EXEC_BASE_PATH() __clove_get_exec_base_path() +#define CLOVE_EXEC_BASE_PATH() __clove_utils_get_exec_abs_basepath() #pragma endregion //UTILS #pragma region PUBLIC - ASSERTS diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index 64a10d2..f6ab97a 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -17,8 +17,6 @@ CLOVE_TEST(AbsolutePathFromExecBasePath) { char* result = __clove_path_rel_to_abs_exec_path("path/to/append"); CLOVE_NOT_NULL(result); } -#include -#include CLOVE_TEST(BasePathForJustExecutable) { char expected[3] = { '.', __CLOVE_PATH_SEPARATOR, '\0' }; @@ -83,3 +81,17 @@ CLOVE_TEST(GetRelativePathFromAbsPath) { result = __clove_path_relative(abs_path, ""); CLOVE_STRING_EQ(abs_path, result); } + +CLOVE_TEST(ConvertToAbsolutePath) { + char* result = __clove_path_to_absolute("/abs/path/file.c"); + + #ifdef _WIN32 + const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c + CLOVE_STRING_EQ("\\abs\\path\\file.c", result_without_unit); + #else + CLOVE_STRING_EQ("/abs/path/file.c", result); + #endif + + free(result); +} + diff --git a/tests/functs/src/unit/string_test.c b/tests/functs/src/unit/string_test.c index 9d87bbd..2ecfac6 100644 --- a/tests/functs/src/unit/string_test.c +++ b/tests/functs/src/unit/string_test.c @@ -47,4 +47,11 @@ CLOVE_TEST(StringIsEqualsAny) { CLOVE_IS_FALSE(__clove_string_equal_any("mystring", 1, "one")); CLOVE_IS_TRUE(__clove_string_equal_any("mystring", 3, "one", "two", "mystring")); CLOVE_IS_FALSE(__clove_string_equal_any("mystring", 2, "one", "two")); +} + +CLOVE_TEST(StringLastIndexOf) { + CLOVE_INT_EQ(-1, __clove_string_last_indexof("hello_o", 'a')); + CLOVE_INT_EQ( 6, __clove_string_last_indexof("hello_o", 'o')); + CLOVE_INT_EQ( 3, __clove_string_last_indexof("hello_o", 'l')); + CLOVE_INT_EQ( 1, __clove_string_last_indexof("hello_o", 'e')); } \ No newline at end of file From 4de451d0de475297073f0e14cf10bdb7142b4da3 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sun, 16 Jun 2024 16:34:34 +0200 Subject: [PATCH 05/30] #102 introduce __clove_memory_free --- clove-unit.h | 75 +++++++++++++---------- tests/functs/src/inte/cmd_help_test.c | 2 +- tests/functs/src/inte/cmd_invalid_test.c | 2 +- tests/functs/src/inte/cmd_run_test.c | 14 ++--- tests/functs/src/inte/cmd_testlist_test.c | 2 +- tests/functs/src/inte/cmd_version_test.c | 2 +- tests/functs/src/unit/path_test.c | 6 +- tests/functs/src/unit/string_test.c | 2 +- tests/functs/src/unit/stringview_test.c | 2 +- tests/functs/src/utils/utils.c | 2 +- tests/perfs/utils/perf_generator.c | 4 +- 11 files changed, 60 insertions(+), 53 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index 2ab602a..725f5b8 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -99,6 +99,7 @@ __CLOVE_EXTERN_C void* __clove_memory_calloc(size_t size); __CLOVE_EXTERN_C void* __clove_memory_realloc(void* source, size_t size); __CLOVE_EXTERN_C bool __clove_memory_memcpy(void* dest, size_t dest_size, const void* src, size_t src_size); __CLOVE_EXTERN_C bool __clove_memory_memset(void* dest, size_t size, unsigned char value); +__CLOVE_EXTERN_C void __clove_memory_free(void* source); #define __CLOVE_MEMORY_MALLOC_TYPE_N(TYPE, COUNT) (TYPE*)__clove_memory_malloc(sizeof(TYPE) * COUNT) #define __CLOVE_MEMORY_MALLOC_TYPE(TYPE) __CLOVE_MEMORY_MALLOC_TYPE_N(TYPE, 1) @@ -1061,6 +1062,12 @@ bool __clove_memory_memcpy(void* dest, size_t dest_size, const void* src, size_t bool __clove_memory_memset(void* dest, size_t size, unsigned char value) { return memset(dest, value, size) != NULL; } + +void __clove_memory_free(void* source) +{ + free(source); +} + #pragma endregion //Memory Impl #pragma region PRIVATE - String Impl @@ -1570,7 +1577,7 @@ size_t __clove_stack_pop(__clove_stack_t* stack) { void __clove_stack_free(__clove_stack_t* stack) { if (!stack) return; - free(stack->items); + __clove_memory_free(stack->items); stack->items = NULL; stack->capacity = 0; stack->count = 0; @@ -1676,12 +1683,12 @@ void __clove_vector_free(__clove_vector_t* vector) { } if (vector->items) { - free(vector->items); + __clove_memory_free(vector->items); vector->items = NULL; } if (vector->swap_temp) { - free(vector->swap_temp); + __clove_memory_free(vector->swap_temp); vector->swap_temp = NULL; } vector->capacity = 0; @@ -1819,18 +1826,18 @@ void __clove_map_free(__clove_map_t* map) { while(current) { __clove_map_node_t* next = current->next; - free(current->key); + __clove_memory_free(current->key); if (map->item_dtor) { //if dtor set, means map become owner of the item (and its memory) map->item_dtor(current->value); - free(current->value); + __clove_memory_free(current->value); } - free(current); + __clove_memory_free(current); current = next; } } - free(map->hashmap); + __clove_memory_free(map->hashmap); map->hashmap = NULL; map->hashmap_size = 0; map->count = 0; @@ -2098,7 +2105,7 @@ __clove_cmdline_errno_t __clove_cmdline_handle_run_tests(__clove_cmdline_t* cmd) stream->free(stream); __clove_vector_free(&includes); __clove_vector_free(&excludes); - free(base_path_fixed); + __clove_memory_free(base_path_fixed); //Result if (run_result == 1) return __CLOVE_CMD_ERRNO_GENERIC; @@ -2183,7 +2190,7 @@ __clove_cmdline_errno_t __clove_cmdline_handle_list_tests(__clove_cmdline_t* cmd report->free(report); stream->free(stream); - free(base_path_os); + __clove_memory_free(base_path_os); __clove_vector_free(&context.suites); __clove_vector_free((__clove_vector_t*)context.includes); __clove_vector_free((__clove_vector_t*)context.excludes); @@ -2234,12 +2241,12 @@ void __clove_vector_test_ctor(void* test) { void __clove_vector_test_dtor(void* test_ptr) { __clove_test_t* test = (__clove_test_t*)test_ptr; - free(test->name); + __clove_memory_free(test->name); //See CLOVE_STRING_EQ and CLOVE_STRING_NE where string allocation happens if (test->result == __CLOVE_TEST_RESULT_FAILED && test->issue.data_type == __CLOVE_GENERIC_STRING) { - free(test->issue.expected._string); - free(test->issue.actual._string); + __clove_memory_free(test->issue.expected._string); + __clove_memory_free(test->issue.actual._string); } } #pragma endregion @@ -2268,7 +2275,7 @@ void __clove_vector_suite_ctor(void* suite_ptr) { void __clove_vector_suite_dtor(void* suite_ptr) { __clove_suite_t* suite = (__clove_suite_t*)suite_ptr; - free(suite->name); + __clove_memory_free(suite->name); __clove_vector_free(&suite->tests); } #pragma endregion // Suite Impl @@ -2473,7 +2480,7 @@ bool __clove_stream_console_has_ansi_support(__clove_stream_t* stream) { void __clove_stream_console_free(__clove_stream_t* stream) { - free(stream); + __clove_memory_free(stream); } __clove_stream_file_t* __clove_stream_file_new(const char* file_path) { @@ -2515,8 +2522,8 @@ bool __clove_stream_file_has_ansi_support(struct __clove_stream_t* _this) { void __clove_stream_file_free(__clove_stream_t* stream) { __clove_stream_file_t* _this = (__clove_stream_file_t*)stream; _this->file = NULL; - free((char*)_this->file_path); - free(_this); + __clove_memory_free((char*)_this->file_path); + __clove_memory_free(_this); } //In Memory Stream @@ -2563,7 +2570,7 @@ bool __clove_stream_memory_has_ansi_support(__clove_stream_t* stream) { void __clove_stream_memory_free(__clove_stream_t* stream) { __clove_vector_free(&((__clove_stream_memory_t*)stream)->lines); - free(stream); + __clove_memory_free(stream); } char* __clove_stream_memory_get_line(__clove_stream_memory_t* mem_stream, size_t index) { @@ -2648,7 +2655,7 @@ __clove_report_pretty_t* __clove_report_run_tests_pretty_new(__clove_stream_t* s } void __clove_report_pretty_free(__clove_report_t* report) { - free(report); + __clove_memory_free(report); } void __clove_report_pretty_start(__clove_report_t* _this, __clove_vector_t* suites, size_t test_count) { @@ -2871,8 +2878,8 @@ void __clove_report_pretty_end_test(__clove_report_t* _this, __clove_suite_t* su char* exp_escaped = __clove_string_escape(exp); char* act_escaped = __clove_string_escape(act); __clove_string_sprintf(msg, sizeof(msg), "%sexpected \"%s\" but was \"%s\"", non, exp_escaped, act_escaped); - free(exp_escaped); - free(act_escaped); + __clove_memory_free(exp_escaped); + __clove_memory_free(act_escaped); } else { char exp_short[16]; @@ -2882,8 +2889,8 @@ void __clove_report_pretty_end_test(__clove_report_t* _this, __clove_suite_t* su char* exp_escaped = __clove_string_escape(exp_short); char* act_escaped = __clove_string_escape(act_short); __clove_string_sprintf(msg, sizeof(msg), "%sexpected [%zu]\"%s\" but was [%zu]\"%s\"", non, exp_len, exp_escaped, act_len, act_escaped); - free(exp_escaped); - free(act_escaped); + __clove_memory_free(exp_escaped); + __clove_memory_free(act_escaped); } } __CLOVE_SWITCH_CASE(__CLOVE_GENERIC_PTR) { @@ -2966,7 +2973,7 @@ __clove_report_run_tests_csv_t* __clove_report_run_tests_csv_new(__clove_stream_ } void __clove_report_run_tests_csv_free(__clove_report_t* report) { - free(report); + __clove_memory_free(report); } void __clove_report_run_tests_csv_start(__clove_report_t* _this, __clove_vector_t* suites, size_t test_count) { @@ -3077,7 +3084,7 @@ void __clove_report_run_tests_csv_print_data(__clove_report_run_tests_csv_t* ins __CLOVE_SWITCH_CASE(__CLOVE_GENERIC_STRING) { char* escaped = __clove_string_csv_escape(data->_string); instance->stream->writef(instance->stream, "%s", escaped); - free(escaped); + __clove_memory_free(escaped); } __CLOVE_SWITCH_CASE(__CLOVE_GENERIC_PTR) instance->stream->writef(instance->stream, "%p", data->_ptr); @@ -3122,7 +3129,7 @@ __clove_report_json_t* __clove_report_run_tests_json_new(__clove_stream_t* strea void __clove_report_json_free(__clove_report_t* report) { __clove_report_json_t* instance = (__clove_report_json_t*)report; __clove_vector_free(&instance->cached_suites); - free(report); + __clove_memory_free(report); } void __clove_report_json_start(__clove_report_t* _this, __clove_vector_t* suites, size_t test_count) { @@ -3240,7 +3247,7 @@ void __clove_report_json_print_data(__clove_report_json_t* instance, __clove_tes __CLOVE_SWITCH_CASE(__CLOVE_GENERIC_STRING) { char* escaped = __clove_string_escape(data->_string); instance->stream->writef(instance->stream, "%s", escaped); - free(escaped); + __clove_memory_free(escaped); } __CLOVE_SWITCH_CASE(__CLOVE_GENERIC_PTR) instance->stream->writef(instance->stream, "%p", data->_ptr); @@ -3292,7 +3299,7 @@ void __clove_report_json_end_test(__clove_report_t* _this, __clove_suite_t* suit instance->stream->writef(instance->stream, "\t\t\t\t\"tests\" : {\n"); instance->suite_tests_counter = 0; - free(escaped_file); + __clove_memory_free(escaped_file); instance->is_first_suite_test = false; } @@ -3357,7 +3364,7 @@ __clove_report_list_tests_pretty_t* __clove_report_list_tests_pretty_new(__clove return _this; } void __clove_report_list_tests_pretty_free(__clove_report_list_tests_t* _this) { - free((__clove_report_list_tests_pretty_t*)_this); + __clove_memory_free((__clove_report_list_tests_pretty_t*)_this); } void __clove_report_list_tests_pretty_begin(__clove_report_list_tests_t* _this, size_t suite_count, size_t test_count) { __clove_report_list_tests_pretty_t* pretty = (__clove_report_list_tests_pretty_t*)_this; @@ -3424,7 +3431,7 @@ __clove_report_list_tests_csv_t* __clove_report_list_tests_csv_new(__clove_strea return _this; } void __clove_report_list_tests_csv_free(__clove_report_list_tests_t* _this) { - free((__clove_report_list_tests_csv_t*)_this); + __clove_memory_free((__clove_report_list_tests_csv_t*)_this); } void __clove_report_list_tests_csv_begin(__clove_report_list_tests_t* _this, size_t suite_count, size_t test_count) { __CLOVE_UNUSED_VAR(test_count); @@ -3485,7 +3492,7 @@ __clove_report_list_tests_json_t* __clove_report_list_tests_json_new(__clove_str return _this; } void __clove_report_list_tests_json_free(__clove_report_list_tests_t* _this) { - free((__clove_report_list_tests_json_t*)_this); + __clove_memory_free((__clove_report_list_tests_json_t*)_this); } void __clove_report_list_tests_json_begin(__clove_report_list_tests_t* _this, size_t suite_count, size_t test_count) { @@ -3541,7 +3548,7 @@ void __clove_report_list_tests_json_end_test(__clove_report_list_tests_t* _this, json->stream->writef(json->stream, "\t\t\t\t\"file\" : \"%s\",\n", escaped_file); json->stream->writef(json->stream, "\t\t\t\t\"tests\" : [\n"); - free(escaped_file); + __clove_memory_free(escaped_file); json->is_suite_first_test = false; } json->stream->writef(json->stream, "\t\t\t\t\t{\n"); @@ -3996,7 +4003,7 @@ int __clove_symbols_funct_name_comparator(void* f1, void* f2) { } int __clove_symbols_for_each_function_by_prefix(__clove_symbols_context_t* context, __clove_symbols_function_action action) { - const char* module_path = CLOVE_EXEC_PATH; + const char* module_path = __clove_utils_get_exec_abs_path(); __clove_symbols_lixux_module_t module; if (__clove_symbols_lixux_open_module_handle(module_path, &module) != 0) { return 1; } @@ -4115,8 +4122,8 @@ int __clove_runner_auto(int argc, char* argv[]) { __clove_vector_free(&cmd_handlers); __clove_cmdline_free(&cmdline); - free(__clove_exec_abs_path); - free(__clove_exec_abs_basepath); + __clove_memory_free(__clove_exec_abs_path); + __clove_memory_free(__clove_exec_abs_basepath); return cmd_result; } diff --git a/tests/functs/src/inte/cmd_help_test.c b/tests/functs/src/inte/cmd_help_test.c index 1402d75..2eece8e 100644 --- a/tests/functs/src/inte/cmd_help_test.c +++ b/tests/functs/src/inte/cmd_help_test.c @@ -9,7 +9,7 @@ CLOVE_SUITE_SETUP() { } CLOVE_SUITE_TEARDOWN() { - if (cmd_out) free(cmd_out); + if (cmd_out) __clove_memory_free(cmd_out); } /* diff --git a/tests/functs/src/inte/cmd_invalid_test.c b/tests/functs/src/inte/cmd_invalid_test.c index 394be35..95cd768 100644 --- a/tests/functs/src/inte/cmd_invalid_test.c +++ b/tests/functs/src/inte/cmd_invalid_test.c @@ -9,7 +9,7 @@ CLOVE_SUITE_SETUP() { } CLOVE_SUITE_TEARDOWN() { - if (cmd_out) free(cmd_out); + if (cmd_out) __clove_memory_free(cmd_out); } //Note: Important for this unit test is to demostrate that with invalid params the process ends gracefully diff --git a/tests/functs/src/inte/cmd_run_test.c b/tests/functs/src/inte/cmd_run_test.c index 4f0cebc..27e4288 100644 --- a/tests/functs/src/inte/cmd_run_test.c +++ b/tests/functs/src/inte/cmd_run_test.c @@ -13,7 +13,7 @@ CLOVE_SUITE_SETUP() { } CLOVE_SUITE_TEARDOWN() { - if (cmd_out) free(cmd_out); + if (cmd_out) __clove_memory_free(cmd_out); } CLOVE_TEST(JsonReportWithOptOonFile) { @@ -28,8 +28,8 @@ CLOVE_TEST(JsonReportWithOptOonFile) { CLOVE_IS_TRUE(file_exists(report_path)); file_delete(report_path); - free(base_path); - free(report_path); + __clove_memory_free(base_path); + __clove_memory_free(report_path); } CLOVE_TEST(JsonReportWithOptOuputOnFile) { @@ -44,8 +44,8 @@ CLOVE_TEST(JsonReportWithOptOuputOnFile) { CLOVE_IS_TRUE(file_exists(report_path)); file_delete(report_path); - free(base_path); - free(report_path); + __clove_memory_free(base_path); + __clove_memory_free(report_path); } CLOVE_TEST(JsonReportWithOptOuputOnStdoutAsDefault) { @@ -226,8 +226,8 @@ CLOVE_TEST(DefaultReportWithOptOonFile) { CLOVE_IS_TRUE(file_exists(report_path)); file_delete(report_path); - free(base_path); - free(report_path); + __clove_memory_free(base_path); + __clove_memory_free(report_path); } CLOVE_TEST(DefaultReportWithOptT) { diff --git a/tests/functs/src/inte/cmd_testlist_test.c b/tests/functs/src/inte/cmd_testlist_test.c index b9664d3..40d0b2c 100644 --- a/tests/functs/src/inte/cmd_testlist_test.c +++ b/tests/functs/src/inte/cmd_testlist_test.c @@ -9,7 +9,7 @@ CLOVE_SUITE_SETUP() { } CLOVE_SUITE_TEARDOWN() { - if (cmd_out) free(cmd_out); + if (cmd_out) __clove_memory_free(cmd_out); } /* diff --git a/tests/functs/src/inte/cmd_version_test.c b/tests/functs/src/inte/cmd_version_test.c index c2eb84b..a410136 100644 --- a/tests/functs/src/inte/cmd_version_test.c +++ b/tests/functs/src/inte/cmd_version_test.c @@ -9,7 +9,7 @@ CLOVE_SUITE_SETUP() { } CLOVE_SUITE_TEARDOWN() { - if (cmd_out) free(cmd_out); + if (cmd_out) __clove_memory_free(cmd_out); } CLOVE_TEST(RunVersionWithOptV) { diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index f6ab97a..fbd3668 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -30,7 +30,7 @@ CLOVE_TEST(BasePathForFullPath) { char* result = __clove_path_basepath("/path/to/directory/file.txt"); CLOVE_STRING_EQ(expected, result); - free(result); + __clove_memory_free(result); } CLOVE_TEST(BasePathForDirectory) { @@ -39,7 +39,7 @@ CLOVE_TEST(BasePathForDirectory) { char* result = __clove_path_basepath("/path/to/directory/"); CLOVE_STRING_EQ(expected, result); - free(result); + __clove_memory_free(result); } CLOVE_TEST(PathToOs) { @@ -92,6 +92,6 @@ CLOVE_TEST(ConvertToAbsolutePath) { CLOVE_STRING_EQ("/abs/path/file.c", result); #endif - free(result); + __clove_memory_free(result); } diff --git a/tests/functs/src/unit/string_test.c b/tests/functs/src/unit/string_test.c index 2ecfac6..59f307c 100644 --- a/tests/functs/src/unit/string_test.c +++ b/tests/functs/src/unit/string_test.c @@ -27,7 +27,7 @@ CLOVE_TEST(StringEscaping) { const char* expected = "\\\"Hello\\nWorld\\\""; char* actual = __clove_string_escape(to_escape); CLOVE_STRING_EQ(expected, actual); - free(actual); + __clove_memory_free(actual); } CLOVE_TEST(StringStartsWith) { diff --git a/tests/functs/src/unit/stringview_test.c b/tests/functs/src/unit/stringview_test.c index de52ad2..b6a7a09 100644 --- a/tests/functs/src/unit/stringview_test.c +++ b/tests/functs/src/unit/stringview_test.c @@ -96,7 +96,7 @@ CLOVE_TEST(AsString) { char* result = __clove_string_view_as_string(&vw1); CLOVE_STRING_EQ("Hello", result); - free(result); + __clove_memory_free(result); } CLOVE_TEST(EndWithUsingOffsetOnSuffix) { diff --git a/tests/functs/src/utils/utils.c b/tests/functs/src/utils/utils.c index fb3ce0b..9d2f354 100644 --- a/tests/functs/src/utils/utils.c +++ b/tests/functs/src/utils/utils.c @@ -31,7 +31,7 @@ const char* cmd_fmt(const char* format, ...) { va_start(args, format); __clove_string_vsprintf(result, sizeof(result), format_ext, args); va_end(args); - free(format_ext); + __clove_memory_free(format_ext); return result; } #else diff --git a/tests/perfs/utils/perf_generator.c b/tests/perfs/utils/perf_generator.c index f187140..bb53f68 100644 --- a/tests/perfs/utils/perf_generator.c +++ b/tests/perfs/utils/perf_generator.c @@ -55,7 +55,7 @@ int main(int argc, char* argv[]) { } fclose(file); - free(path); - free(file_path); + __clove_memory_free(path); + __clove_memory_free(file_path); return 0; } \ No newline at end of file From 1dc68e085e6e403e0bb922e25d584ab24403c7d1 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sun, 16 Jun 2024 17:29:17 +0200 Subject: [PATCH 06/30] #102 leverage unix relapath behaviour to work with unexistent paths (like windows api does) --- clove-unit.h | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index 725f5b8..443e504 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -88,6 +88,7 @@ __CLOVE_EXTERN_C char* __clove_path_concat(const char separator, const char* pat __CLOVE_EXTERN_C const char* __clove_path_relative(const char* abs_path, const char* base_path); __CLOVE_EXTERN_C char* __clove_path_rel_to_abs_exec_path(const char* rel_path); __CLOVE_EXTERN_C bool __clove_path_is_relative(const char* path); +__CLOVE_EXTERN_C bool __clove_path_is_absolute(const char* path); __CLOVE_EXTERN_C void __clove_path_to_os(char* path); __CLOVE_EXTERN_C char* __clove_path_basepath(const char* path); __CLOVE_EXTERN_C char* __clove_path_to_absolute(const char* path); @@ -934,12 +935,16 @@ char* __clove_path_rel_to_abs_exec_path(const char* rel_path) { } bool __clove_path_is_relative(const char* path) { - if (__clove_string_startswith(path, "\\")) return false; //windows - if (__clove_string_length(path) > 2 && path[1] == ':') return false; //windows + if (__clove_string_startswith(path, "\\")) return false; //windows (match the main unit) + if (__clove_string_length(path) > 2 && path[1] == ':') return false; //windows (contains unit:) if (__clove_string_startswith(path, "/")) return false; //unix or Windows return true; } +bool __clove_path_is_absolute(const char* path) { + return !__clove_path_is_relative(path); +} + void __clove_path_to_os(char* path) { __clove_string_replace_char(path, '/', __CLOVE_PATH_SEPARATOR); __clove_string_replace_char(path, '\\', __CLOVE_PATH_SEPARATOR); @@ -975,6 +980,20 @@ char* __clove_path_to_absolute(const char* rel_path) { #else result = __CLOVE_MEMORY_MALLOC_TYPE_N(char, PATH_MAX); realpath(rel_path, result); // NULL + + //case where rel_path not really exists on fs + //(in this case only the first subpath of the rel_path is added by realpath) + if (!__clove_string_endswith(rel_path)) { + if (__clove_path_is_absolute(rel_path)) { + __clove_string_strcpy(result, _MAX_PATH, rel_path); + } else { //relative + realpath(result, ".", _MAX_PATH); + if (!__clove_string_endswith(result, "/")) { + __clove_string_strcat(result, _MAX_PATH, "/"); + } + __clove_string_strcat(result, _MAX_PATH, rel_path); + } + } #endif return result; } From 7ddc1aad4c78ae7f29e084f9e8ee4b118a42a944 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sun, 16 Jun 2024 17:30:42 +0200 Subject: [PATCH 07/30] fix realpath call --- clove-unit.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/clove-unit.h b/clove-unit.h index 443e504..b9a3521 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -987,7 +987,7 @@ char* __clove_path_to_absolute(const char* rel_path) { if (__clove_path_is_absolute(rel_path)) { __clove_string_strcpy(result, _MAX_PATH, rel_path); } else { //relative - realpath(result, ".", _MAX_PATH); + realpath(result, "."); if (!__clove_string_endswith(result, "/")) { __clove_string_strcat(result, _MAX_PATH, "/"); } From c87dac053043ee407cfcd416061154becf81d6c1 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sun, 16 Jun 2024 17:42:26 +0200 Subject: [PATCH 08/30] #102 improve realpath unix management --- clove-unit.h | 10 +++++----- tests/functs/src/unit/path_test.c | 15 ++++++++++++++- 2 files changed, 19 insertions(+), 6 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index b9a3521..4b3c130 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -983,15 +983,15 @@ char* __clove_path_to_absolute(const char* rel_path) { //case where rel_path not really exists on fs //(in this case only the first subpath of the rel_path is added by realpath) - if (!__clove_string_endswith(rel_path)) { + if (!__clove_string_endswith(result, rel_path)) { if (__clove_path_is_absolute(rel_path)) { - __clove_string_strcpy(result, _MAX_PATH, rel_path); + __clove_string_strcpy(result, PATH_MAX, rel_path); } else { //relative - realpath(result, "."); + realpath(".", result); if (!__clove_string_endswith(result, "/")) { - __clove_string_strcat(result, _MAX_PATH, "/"); + __clove_string_strcat(result, PATH_MAX, "/"); } - __clove_string_strcat(result, _MAX_PATH, rel_path); + __clove_string_strcat(result, PATH_MAX, rel_path); } } #endif diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index fbd3668..14328ba 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -82,7 +82,7 @@ CLOVE_TEST(GetRelativePathFromAbsPath) { CLOVE_STRING_EQ(abs_path, result); } -CLOVE_TEST(ConvertToAbsolutePath) { +CLOVE_TEST(ConvertAbsToAbsolutePath) { char* result = __clove_path_to_absolute("/abs/path/file.c"); #ifdef _WIN32 @@ -95,3 +95,16 @@ CLOVE_TEST(ConvertToAbsolutePath) { __clove_memory_free(result); } +CLOVE_TEST(ConvertRelToAbsolutePath) { + char* result = __clove_path_to_absolute("rel/path/file.c"); + + #ifdef _WIN32 + const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c + CLOVE_STRING_EQ("\\rel\\path\\file.c", result_without_unit); + #else + CLOVE_IS_TRUE(__clove_string_startswith(result, "/")); + CLOVE_IS_TRUE(__clove_string_endswith(result, "/rel/path/file.c")); + #endif + + __clove_memory_free(result); +} From efc31e806b8192a6b912c005f6de87b8ba6d7293 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Sun, 16 Jun 2024 17:48:47 +0200 Subject: [PATCH 09/30] #102 fix absolute path unit test for windows --- tests/functs/src/unit/path_test.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index 14328ba..75df4b6 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -97,10 +97,11 @@ CLOVE_TEST(ConvertAbsToAbsolutePath) { CLOVE_TEST(ConvertRelToAbsolutePath) { char* result = __clove_path_to_absolute("rel/path/file.c"); - + puts(result); #ifdef _WIN32 const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c - CLOVE_STRING_EQ("\\rel\\path\\file.c", result_without_unit); + CLOVE_IS_TRUE(__clove_string_startswith(result_without_unit, "\\")); + CLOVE_IS_TRUE(__clove_string_endswith(result_without_unit, "\\rel\\path\\file.c")); #else CLOVE_IS_TRUE(__clove_string_startswith(result, "/")); CLOVE_IS_TRUE(__clove_string_endswith(result, "/rel/path/file.c")); From b4e2007cd72935bb7e28691a623167cbd23739bc Mon Sep 17 00:00:00 2001 From: Cristian Prieto Date: Mon, 17 Jun 2024 19:37:50 +0200 Subject: [PATCH 10/30] Make header library available for FetchContent --- CMakeLists.txt | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 632888c..04de3c7 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,6 +2,9 @@ cmake_minimum_required(VERSION 3.18) project(CLoveUnit LANGUAGES C) include(CTest) +add_library(CloveUnit INTERFACE) +target_include_directories(CloveUnit INTERFACE "${CMAKE_CURRENT_LIST_DIR}") + #[[ add_subdirectory(tests/functs) if (DEFINED CLOVE_CMAKE__CI_TRIGGERED) @@ -17,17 +20,17 @@ endif() ]] if (CLOVE_CMAKE__UC_BUILD) - add_subdirectory(tests/functs) - add_subdirectory(tests/stricts/clove-c) - add_subdirectory(tests/stricts/clove-cpp) - add_subdirectory(examples/clove101) - add_subdirectory(examples/clovepp) + add_subdirectory(tests/functs) + add_subdirectory(tests/stricts/clove-c) + add_subdirectory(tests/stricts/clove-cpp) + add_subdirectory(examples/clove101) + add_subdirectory(examples/clovepp) endif() if (CLOVE_CMAKE__UC_SANITY) - add_subdirectory(tests/stricts/clove-sanity) + add_subdirectory(tests/stricts/clove-sanity) endif() if (CLOVE_CMAKE__UC_PERFS) - add_subdirectory(tests/perfs) + add_subdirectory(tests/perfs) endif() From 876a3b44ad90153e03907046c62759ef3512ef94 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Tue, 18 Jun 2024 16:01:41 +0200 Subject: [PATCH 11/30] #102 improve absolute path test and overall utils tests organization --- clove-unit.h | 32 +++- tests/functs/src/inte/cmd_run_test.c | 18 +-- tests/functs/src/unit/path_test.c | 37 ++++- tests/functs/src/unit/report_csv_test.c | 15 +- .../functs/src/unit/report_json_failed_test.c | 7 +- tests/functs/src/unit/report_json_full_test.c | 15 +- .../src/unit/report_pretty_failures_test.c | 2 +- .../functs/src/unit/report_pretty_full_test.c | 2 +- .../src/unit/report_pretty_skipped_test.c | 2 +- .../functs/src/utils/{utils.c => cmd_utils.c} | 71 +-------- tests/functs/src/utils/cmd_utils.h | 3 + tests/functs/src/utils/domain_utils.c | 2 +- tests/functs/src/utils/file_utils.c | 138 ++++++++++++++++++ tests/functs/src/utils/file_utils.h | 10 ++ tests/functs/src/utils/str_utils.c | 38 +++++ tests/functs/src/utils/str_utils.h | 6 + tests/functs/src/utils/utils.h | 17 +-- 17 files changed, 290 insertions(+), 125 deletions(-) rename tests/functs/src/utils/{utils.c => cmd_utils.c} (60%) create mode 100644 tests/functs/src/utils/cmd_utils.h create mode 100644 tests/functs/src/utils/file_utils.c create mode 100644 tests/functs/src/utils/file_utils.h create mode 100644 tests/functs/src/utils/str_utils.c create mode 100644 tests/functs/src/utils/str_utils.h diff --git a/clove-unit.h b/clove-unit.h index 4b3c130..591c8f9 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -951,24 +951,46 @@ void __clove_path_to_os(char* path) { } char* __clove_path_basepath(const char* a_path) { + bool last_char_is_win = __clove_string_endswith(a_path, "\\"); + bool last_char_is_uni = __clove_string_endswith(a_path, "/"); + + //__CLOVE_UNUSED_VAR(last_char_is_win); + //__CLOVE_UNUSED_VAR(last_char_is_uni); + + + size_t source_len = __clove_string_length(a_path); + size_t tmp_len = source_len + 1; + char* tmp_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, tmp_len); //take account for '\0' + + if (last_char_is_win || last_char_is_uni) + { + source_len--; + } + + __clove_string_strncpy(tmp_path, tmp_len, a_path, source_len); + + // Find the last path separator character in the input path. - int last_char_win = __clove_string_last_indexof(a_path, '\\'); - int last_char_uni = __clove_string_last_indexof(a_path, '/'); //or unix or win eventually + int last_char_win = __clove_string_last_indexof(tmp_path, '\\'); + int last_char_uni = __clove_string_last_indexof(tmp_path, '/'); //or unix or win eventually int last_char_index = last_char_win > last_char_uni ? last_char_win : last_char_uni; // If there are no separators in the path, return the current directory path. + char* result = NULL; if (last_char_index <= 0) { static char dot_path[3] = { '.', __CLOVE_PATH_SEPARATOR, '\0' }; - return __clove_string_strdup(dot_path); + result = __clove_string_strdup(dot_path); } else { // Calculate base path length based on the position of the last path separator. size_t base_length = (size_t)(last_char_index + 1); char* base_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, base_length); - __clove_string_strncpy(base_path, base_length, a_path, base_length - 1); + __clove_string_strncpy(base_path, base_length, tmp_path, base_length - 1); __clove_path_to_os(base_path); - return base_path; + result = base_path; } + __clove_memory_free(tmp_path); + return result; } char* __clove_path_to_absolute(const char* rel_path) { diff --git a/tests/functs/src/inte/cmd_run_test.c b/tests/functs/src/inte/cmd_run_test.c index 27e4288..b190415 100644 --- a/tests/functs/src/inte/cmd_run_test.c +++ b/tests/functs/src/inte/cmd_run_test.c @@ -19,15 +19,15 @@ CLOVE_SUITE_TEARDOWN() { CLOVE_TEST(JsonReportWithOptOonFile) { char* base_path = __clove_path_basepath(RES_PRJ01_EXEC_PATH); char* report_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, "cmd_json_report.json"); - //file_delete(report_path); + //utils_file_delete(report_path); const char* cmd = cmd_fmt("\"%s\" -r json -o \"%s\"", RES_PRJ01_EXEC_PATH, report_path); int cmd_code = exec_cmd(cmd, &cmd_out); CLOVE_INT_EQ(__CLOVE_CMD_ERRNO_OK, cmd_code); - CLOVE_IS_TRUE(file_exists(report_path)); + CLOVE_IS_TRUE(utils_file_exists(report_path)); - file_delete(report_path); + utils_file_delete(report_path); __clove_memory_free(base_path); __clove_memory_free(report_path); } @@ -35,15 +35,15 @@ CLOVE_TEST(JsonReportWithOptOonFile) { CLOVE_TEST(JsonReportWithOptOuputOnFile) { char* base_path = __clove_path_basepath(RES_PRJ01_EXEC_PATH); char* report_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, "cmd_json_report.json"); - //file_delete(report_path); + //utils_file_delete(report_path); const char* cmd = cmd_fmt("\"%s\" -r json --output \"%s\"", RES_PRJ01_EXEC_PATH, report_path); int cmd_code = exec_cmd(cmd, &cmd_out); CLOVE_INT_EQ(__CLOVE_CMD_ERRNO_OK, cmd_code); - CLOVE_IS_TRUE(file_exists(report_path)); + CLOVE_IS_TRUE(utils_file_exists(report_path)); - file_delete(report_path); + utils_file_delete(report_path); __clove_memory_free(base_path); __clove_memory_free(report_path); } @@ -217,15 +217,15 @@ CLOVE_TEST(DefaultReportIncludeOverExcludeOneTest) { CLOVE_TEST(DefaultReportWithOptOonFile) { char* base_path = __clove_path_basepath(RES_PRJ01_EXEC_PATH); char* report_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, "cmd_console_report.txt"); - //file_delete(report_path); + //utils_file_delete(report_path); const char* cmd = cmd_fmt("\"%s\" -o \"%s\"", RES_PRJ01_EXEC_PATH, report_path); int cmd_code = exec_cmd(cmd, &cmd_out); CLOVE_INT_EQ(__CLOVE_CMD_ERRNO_OK, cmd_code); - CLOVE_IS_TRUE(file_exists(report_path)); + CLOVE_IS_TRUE(utils_file_exists(report_path)); - file_delete(report_path); + utils_file_delete(report_path); __clove_memory_free(base_path); __clove_memory_free(report_path); } diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index 75df4b6..50d1240 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -1,5 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_PathTest #include "clove-unit.h" +#include "utils/utils.h" CLOVE_TEST(PathConcatenation) { char* result = __clove_path_concat('/', "path/to/first", "second"); @@ -33,8 +34,8 @@ CLOVE_TEST(BasePathForFullPath) { __clove_memory_free(result); } -CLOVE_TEST(BasePathForDirectory) { - char expected[] = "\\path\\to\\directory"; +CLOVE_TEST(BasePathForDirectoryEndingWithSlash) { + char expected[] = "\\path\\to"; __clove_path_to_os (expected); char* result = __clove_path_basepath("/path/to/directory/"); @@ -82,7 +83,7 @@ CLOVE_TEST(GetRelativePathFromAbsPath) { CLOVE_STRING_EQ(abs_path, result); } -CLOVE_TEST(ConvertAbsToAbsolutePath) { +CLOVE_TEST(ConvertUnexistentAbsToAbsolutePath) { char* result = __clove_path_to_absolute("/abs/path/file.c"); #ifdef _WIN32 @@ -95,9 +96,8 @@ CLOVE_TEST(ConvertAbsToAbsolutePath) { __clove_memory_free(result); } -CLOVE_TEST(ConvertRelToAbsolutePath) { +CLOVE_TEST(ConvertUnexistentRelToAbsolutePath) { char* result = __clove_path_to_absolute("rel/path/file.c"); - puts(result); #ifdef _WIN32 const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c CLOVE_IS_TRUE(__clove_string_startswith(result_without_unit, "\\")); @@ -109,3 +109,30 @@ CLOVE_TEST(ConvertRelToAbsolutePath) { __clove_memory_free(result); } + +CLOVE_TEST(ConvertExistentAbsToAbsolutePath) { + char* cwd_path = utils_cwd(); + char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "my/path/"); + utils_mkdirs(abs_path); + + char* result = __clove_path_to_absolute("my/path/"); + + #ifdef _WIN32 + const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c + CLOVE_IS_TRUE(__clove_string_startswith(result_without_unit, "\\")); + CLOVE_IS_TRUE(__clove_string_endswith(result_without_unit, "\\my\\path\\")); + #else + CLOVE_IS_TRUE(__clove_string_startswith(result, "/")); + CLOVE_IS_TRUE(__clove_string_endswith(result, "my/path/")); + #endif + + + //rmdir + char* abs_path_parent = __clove_path_basepath(abs_path); + utils_rmdir(abs_path_parent); + + __clove_memory_free(result); + __clove_memory_free(cwd_path); + __clove_memory_free(abs_path); + __clove_memory_free(abs_path_parent); +} diff --git a/tests/functs/src/unit/report_csv_test.c b/tests/functs/src/unit/report_csv_test.c index 1124180..e7d55f8 100644 --- a/tests/functs/src/unit/report_csv_test.c +++ b/tests/functs/src/unit/report_csv_test.c @@ -1,7 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_ReportCsvTest #include "clove-unit.h" #include "utils/utils.h" -#include "utils/domain_utils.h" static __clove_report_run_tests_csv_t* report; static __clove_stream_file_t* stream; @@ -32,7 +31,7 @@ CLOVE_TEST(EmptyReport) { base->end(base, 0, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" @@ -56,7 +55,7 @@ CLOVE_TEST(ReportOneSuiteWithOnePassedTest) { base->end(base, 1, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" @@ -80,7 +79,7 @@ CLOVE_TEST(ReportOneSuiteWithOneSkippedTest) { base->end(base, 0, 1, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" @@ -107,7 +106,7 @@ CLOVE_TEST(ReportOneSuiteWithTwoTests) { base->end(base, 1, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" @@ -140,7 +139,7 @@ CLOVE_TEST(ReportTwoSuitesWithOnePassedTestEach) { base->end(base, 2, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" @@ -175,7 +174,7 @@ CLOVE_TEST(ReportOneSuiteWithOneTestFailedWithString) { base->end(base, 0, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" @@ -210,7 +209,7 @@ CLOVE_TEST(ReportOneSuiteWithOneTestFailedWithFail) { base->end(base, 0, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "Suite,Test,Status,Duration,File,Line,Assert,Type,Expected,Actual\n" diff --git a/tests/functs/src/unit/report_json_failed_test.c b/tests/functs/src/unit/report_json_failed_test.c index dcbb8c1..466f74f 100644 --- a/tests/functs/src/unit/report_json_failed_test.c +++ b/tests/functs/src/unit/report_json_failed_test.c @@ -1,7 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_ReportJsonFailedTest #include "clove-unit.h" #include "utils/utils.h" -#include "utils/domain_utils.h" static __clove_report_json_t* report; static __clove_stream_file_t* stream; @@ -31,7 +30,7 @@ CLOVE_TEST(EmptyReport) { base->end(base, 0, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -66,7 +65,7 @@ CLOVE_TEST(ReportOneSuiteWithOnePassedTest) { base->end(base, 1, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -104,7 +103,7 @@ CLOVE_TEST(ReportOneSuiteWithTwoTests) { base->end(base, 1, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" diff --git a/tests/functs/src/unit/report_json_full_test.c b/tests/functs/src/unit/report_json_full_test.c index bdabb10..34452b0 100644 --- a/tests/functs/src/unit/report_json_full_test.c +++ b/tests/functs/src/unit/report_json_full_test.c @@ -1,7 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_ReportJsonFullTest #include "clove-unit.h" #include "utils/utils.h" -#include "utils/domain_utils.h" static __clove_report_json_t* report; static __clove_stream_file_t* stream; @@ -29,7 +28,7 @@ CLOVE_TEST(EmptyReport) { base->end(base, 0, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -64,7 +63,7 @@ CLOVE_TEST(ReportOneSuiteWithOnePassedTest) { base->end(base, 1, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -107,7 +106,7 @@ CLOVE_TEST(ReportOneSuiteWithOneSkippedTest) { base->end(base, 0, 1, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -154,7 +153,7 @@ CLOVE_TEST(ReportOneSuiteWithTwoTests) { base->end(base, 1, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -214,7 +213,7 @@ CLOVE_TEST(ReportTwoSuitesWithOnePassedTestEach) { base->end(base, 2, 0, 0); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -275,7 +274,7 @@ CLOVE_TEST(ReportOneSuiteWithOneFailAssertTest) { base->end(base, 0, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" @@ -332,7 +331,7 @@ CLOVE_TEST(ReportOneSuiteWithOneFailSizetAssertTest) { base->end(base, 0, 0, 1); const char* file_path = stream->file_path; - const char* actual = read_file(file_path); + const char* actual = utils_file_read(file_path); const char* expected = "{\n" diff --git a/tests/functs/src/unit/report_pretty_failures_test.c b/tests/functs/src/unit/report_pretty_failures_test.c index 44b1a6a..87b63c8 100644 --- a/tests/functs/src/unit/report_pretty_failures_test.c +++ b/tests/functs/src/unit/report_pretty_failures_test.c @@ -1,6 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_ReportPrettyFailuresModeTest #include "clove-unit.h" -#include "utils/domain_utils.h" +#include "utils/utils.h" static __clove_report_pretty_t* report; static __clove_stream_memory_t* stream; diff --git a/tests/functs/src/unit/report_pretty_full_test.c b/tests/functs/src/unit/report_pretty_full_test.c index b510680..0be722b 100644 --- a/tests/functs/src/unit/report_pretty_full_test.c +++ b/tests/functs/src/unit/report_pretty_full_test.c @@ -1,6 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_ReportPrettyTest #include "clove-unit.h" -#include "utils/domain_utils.h" +#include "utils/utils.h" static __clove_report_pretty_t* report; static __clove_stream_memory_t* stream; diff --git a/tests/functs/src/unit/report_pretty_skipped_test.c b/tests/functs/src/unit/report_pretty_skipped_test.c index 1aa5058..b762d95 100644 --- a/tests/functs/src/unit/report_pretty_skipped_test.c +++ b/tests/functs/src/unit/report_pretty_skipped_test.c @@ -1,6 +1,6 @@ #define CLOVE_SUITE_NAME UNIT_ReportPrettyDetailSkippedTest #include "clove-unit.h" -#include "utils/domain_utils.h" +#include "utils/utils.h" static __clove_report_pretty_t* report; static __clove_stream_memory_t* stream; diff --git a/tests/functs/src/utils/utils.c b/tests/functs/src/utils/cmd_utils.c similarity index 60% rename from tests/functs/src/utils/utils.c rename to tests/functs/src/utils/cmd_utils.c index 9d2f354..aebefd7 100644 --- a/tests/functs/src/utils/utils.c +++ b/tests/functs/src/utils/cmd_utils.c @@ -1,15 +1,14 @@ -#include "utils.h" +#include "utils/cmd_utils.h" #include - #include #include #include #include #include -#include FILE* pipe_open(const char* cmd, const char* mode); int pipe_close(FILE* pipe); + #ifdef _WIN32 FILE* pipe_open(const char* cmd, const char* mode) { return _popen(cmd, mode); @@ -93,69 +92,3 @@ int exec_cmd(const char* cmd, char** output) { int result_code = pipe_close(pipe); return result_code; } - -bool file_exists(const char* path) { - struct stat buffer; - return stat(path, &buffer) == 0; -} - -/* -bool file_exists(const char* path) { - FILE* file = __clove_file_open(path, "r"); - if (!file) return false; - fclose(file); - return true; -} - */ - -void file_delete(const char* path) { - if (file_exists(path)) - remove(path); -} - -//NOTE: Dangerous if in future will run test multithreaded -// Eventually improve with mutex or https://en.cppreference.com/w/c/atomic/atomic_flag -const char* str_fmt(const char* format, ...) { - static char result[1024]; - va_list args; - va_start(args, format); - __clove_string_vsprintf(result, sizeof(result), format, args); - va_end(args); - return result; -} - -void str_split(const char* str, char delim, __clove_vector_t* out_lines) { - __CLOVE_VECTOR_INIT(out_lines, char*); - char* source = __clove_string_strdup(str); - char delim_str[2] = {delim, '\0'}; - - #ifdef _WIN32 - char* context; - char *token = strtok_s(source, delim_str, &context); - #else - char *token = strtok(source, delim_str); - #endif //_WIN32 - - while (token != NULL) { - __CLOVE_VECTOR_ADD(out_lines, char*, token); - - #ifdef _WIN32 - token = strtok_s(NULL, delim_str, &context); - #else - token = strtok(NULL, delim_str); - #endif //_WIN32 - } -} - -char* read_file(const char* path) { - FILE* file = __clove_file_open(path, "rb"); - fseek(file, 0, SEEK_END); - size_t file_size = ftell(file); - rewind(file); - - char* result = (char*)malloc(file_size + 1); - result[file_size] = '\0'; - size_t bytes_read = fread(result, file_size, 1, file); - fclose(file); - return result; -} \ No newline at end of file diff --git a/tests/functs/src/utils/cmd_utils.h b/tests/functs/src/utils/cmd_utils.h new file mode 100644 index 0000000..5b3cc00 --- /dev/null +++ b/tests/functs/src/utils/cmd_utils.h @@ -0,0 +1,3 @@ +#pragma once +int exec_cmd(const char* cmd, char** output); +const char* cmd_fmt(const char* format, ...); diff --git a/tests/functs/src/utils/domain_utils.c b/tests/functs/src/utils/domain_utils.c index 1f7ec57..a2fbc15 100644 --- a/tests/functs/src/utils/domain_utils.c +++ b/tests/functs/src/utils/domain_utils.c @@ -1,4 +1,4 @@ -#include "domain_utils.h" +#include "utils/domain_utils.h" __clove_suite_t create_suite(const char* name) { __clove_suite_t suite; diff --git a/tests/functs/src/utils/file_utils.c b/tests/functs/src/utils/file_utils.c new file mode 100644 index 0000000..bcca431 --- /dev/null +++ b/tests/functs/src/utils/file_utils.c @@ -0,0 +1,138 @@ +#include "file_utils.h" +#include +#include +#include +#include +#include + +#ifdef _WIN32 +#include +#include +#include +static void _utils_os_mkdir(const char* path) { + _mkdir(path); +} + +static int _utils_os_rmdir_recurs(const char* dir) { + int dir_len = strlen(dir); + int len = dir_len + 2; // Extra space for double null termination + char* tempDir = (char*) malloc(len * sizeof(char)); + if (!tempDir) { + printf("Error: Failed to open directory: %s\n", dir); + return -1; + } + + memset(tempDir, 0, len * sizeof(char)); + __clove_memory_memcpy(tempDir, len, dir, dir_len); + + SHFILEOPSTRUCTA fileOp = { + NULL, + FO_DELETE, + tempDir, + NULL, + FOF_NOCONFIRMATION | FOF_NOERRORUI | FOF_SILENT, + false, + 0, + "" }; + + int ret = SHFileOperationA(&fileOp); + free(tempDir); + return ret; // 0 on success, non-zero on failure +} + +#else +#include +#include +#include +//#include +#include +static void _utils_os_mkdir(const char* path) { + _mkdir(path, 0775); +} + +static int _utils_os_rmdir_recurs(const char* dirPath) { + DIR* d = opendir(dirPath); + if (!d) { + printf("Error: Failed to open directory: %s\n", dirPath); + return -1; + } + + struct dirent *entry; + int ret = 0; + + while ((entry = readdir(d)) != NULL) { + if (strcmp(entry->d_name, ".") != 0 && strcmp(entry->d_name, "..") != 0) { + char fullPath[PATH_MAX]; + snprintf(fullPath, sizeof(fullPath), "%s/%s", dirPath, entry->d_name); + + if (entry->d_type == DT_DIR) { + ret = _utils_os_rmdir_recurs(fullPath); + } + else { + ret = remove(fullPath); + } + + if (ret != 0) { + printf("Error: Failed to remove %s\n", fullPath); + break; // Error occurred + } + } + } + + closedir(d); + if (ret == 0 && rmdir(dirPath) != 0) { + printf("Error: Failed to remove directory: %s\n", dirPath); + return -1; + } +#endif + +char* utils_cwd() { + //eventually _getcwd (windows) and getcwd (posix) can be used + return __clove_path_to_absolute("."); +} + +void utils_mkdirs(char* path) { + __clove_path_to_os(path); + + char* current_path = path; + while(true) { + char* next_sep_ptr = (char*)__clove_string_strstr(current_path, __CLOVE_PATH_SEPARATOR_STR); + if (next_sep_ptr == NULL) break; + + *next_sep_ptr = '\0'; + //eventually check if path exists to avoid mkdir call + _utils_os_mkdir(path); + *next_sep_ptr = __CLOVE_PATH_SEPARATOR; + + current_path = next_sep_ptr + 1; + } +} + +void utils_rmdir(char* path) { + _utils_os_rmdir_recurs(path); +} + +char* utils_file_read(const char* path) { + FILE* file = __clove_file_open(path, "rb"); + fseek(file, 0, SEEK_END); + size_t file_size = ftell(file); + rewind(file); + + char* result = (char*)malloc(file_size + 1); + result[file_size] = '\0'; + size_t bytes_read = fread(result, file_size, 1, file); + fclose(file); + return result; +} + +bool utils_file_exists(const char* path) { + struct stat buffer; + return stat(path, &buffer) == 0; +} + +void utils_file_delete(const char* path) { + if (utils_file_exists(path)) + remove(path); +} + + diff --git a/tests/functs/src/utils/file_utils.h b/tests/functs/src/utils/file_utils.h new file mode 100644 index 0000000..a16ad57 --- /dev/null +++ b/tests/functs/src/utils/file_utils.h @@ -0,0 +1,10 @@ +#pragma once +#include + +void utils_mkdirs(char* path); +void utils_rmdir(char* path); +char* utils_cwd(); + +bool utils_file_exists(const char* path); +void utils_file_delete(const char* path); +char* utils_file_read(const char* path); \ No newline at end of file diff --git a/tests/functs/src/utils/str_utils.c b/tests/functs/src/utils/str_utils.c new file mode 100644 index 0000000..96c50dd --- /dev/null +++ b/tests/functs/src/utils/str_utils.c @@ -0,0 +1,38 @@ +#include "utils/str_utils.h" +#include +#include + +//NOTE: Dangerous if in future will run test multithreaded +// Eventually improve with mutex or https://en.cppreference.com/w/c/atomic/atomic_flag +const char* str_fmt(const char* format, ...) { + static char result[1024]; + va_list args; + va_start(args, format); + __clove_string_vsprintf(result, sizeof(result), format, args); + va_end(args); + return result; +} + +void str_split(const char* str, char delim, __clove_vector_t* out_lines) { + __CLOVE_VECTOR_INIT(out_lines, char*); + char* source = __clove_string_strdup(str); + char delim_str[2] = {delim, '\0'}; + + #ifdef _WIN32 + char* context; + char *token = strtok_s(source, delim_str, &context); + #else + char *token = strtok(source, delim_str); + #endif //_WIN32 + + while (token != NULL) { + __CLOVE_VECTOR_ADD(out_lines, char*, token); + + #ifdef _WIN32 + token = strtok_s(NULL, delim_str, &context); + #else + token = strtok(NULL, delim_str); + #endif //_WIN32 + } +} + diff --git a/tests/functs/src/utils/str_utils.h b/tests/functs/src/utils/str_utils.h new file mode 100644 index 0000000..f101360 --- /dev/null +++ b/tests/functs/src/utils/str_utils.h @@ -0,0 +1,6 @@ +#pragma once + +typedef struct __clove_vector_t __clove_vector_t; + +const char* str_fmt(const char* format, ...); +void str_split(const char* str, char delim, __clove_vector_t* out_lines); diff --git a/tests/functs/src/utils/utils.h b/tests/functs/src/utils/utils.h index 2e802fa..0ee4760 100644 --- a/tests/functs/src/utils/utils.h +++ b/tests/functs/src/utils/utils.h @@ -1,14 +1,5 @@ #pragma once -#include -#include -#include - -typedef struct __clove_vector_t __clove_vector_t; - -int exec_cmd(const char* cmd, char** output); -bool file_exists(const char* path); -void file_delete(const char* path); -const char* str_fmt(const char* format, ...); -const char* cmd_fmt(const char* format, ...); -void str_split(const char* str, char delim, __clove_vector_t* out_lines); -char* read_file(const char* path); +#include "utils/cmd_utils.h" +#include "utils/str_utils.h" +#include "utils/file_utils.h" +#include "utils/domain_utils.h" From f8211f8648c14a34f1572bf51b49164748f9e56e Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Tue, 18 Jun 2024 23:25:07 +0200 Subject: [PATCH 12/30] #102 improve unix test --- clove-unit.h | 26 +++++++++++- tests/functs/src/unit/path_test.c | 65 ++++++++++++++++++++--------- tests/functs/src/utils/file_utils.c | 23 +++++++++- 3 files changed, 92 insertions(+), 22 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index 591c8f9..d717264 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -902,6 +902,7 @@ double __clove_math_decimald(unsigned char precision) { #include #include #include +#include char* __clove_path_concat(const char separator, const char* path1, const char* path2) { size_t count = __clove_string_length(path1) + 1 + __clove_string_length(path2) + 1; @@ -993,6 +994,11 @@ char* __clove_path_basepath(const char* a_path) { return result; } +static bool __clove_path_exists(const char* path) { + struct stat buffer; + return stat(path, &buffer) == 0; +} + char* __clove_path_to_absolute(const char* rel_path) { char* result = NULL; #if _WIN32 @@ -1001,8 +1007,25 @@ char* __clove_path_to_absolute(const char* rel_path) { _fullpath(result, rel_path, _MAX_PATH ); #else result = __CLOVE_MEMORY_MALLOC_TYPE_N(char, PATH_MAX); - realpath(rel_path, result); // NULL + if (__clove_path_exists(rel_path)) { + realpath(rel_path, result); // NULL + } else { + if (__clove_path_is_absolute(rel_path)) { + __clove_string_strcpy(result, PATH_MAX, rel_path); + } else { //relative + realpath(".", result); //getcwd + if (!__clove_string_endswith(result, "/")) { + __clove_string_strcat(result, PATH_MAX, "/"); + } + if (__clove_string_startswith(rel_path, "./")) { + rel_path = rel_path + 2; + } + + __clove_string_strcat(result, PATH_MAX, rel_path); + } + } +/* //case where rel_path not really exists on fs //(in this case only the first subpath of the rel_path is added by realpath) if (!__clove_string_endswith(result, rel_path)) { @@ -1016,6 +1039,7 @@ char* __clove_path_to_absolute(const char* rel_path) { __clove_string_strcat(result, PATH_MAX, rel_path); } } +*/ #endif return result; } diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index 50d1240..98768ad 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -97,35 +97,60 @@ CLOVE_TEST(ConvertUnexistentAbsToAbsolutePath) { } CLOVE_TEST(ConvertUnexistentRelToAbsolutePath) { + char* cwd_path = utils_cwd(); + char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "rel/path/file.c"); + char* result = __clove_path_to_absolute("rel/path/file.c"); - #ifdef _WIN32 - const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c - CLOVE_IS_TRUE(__clove_string_startswith(result_without_unit, "\\")); - CLOVE_IS_TRUE(__clove_string_endswith(result_without_unit, "\\rel\\path\\file.c")); - #else - CLOVE_IS_TRUE(__clove_string_startswith(result, "/")); - CLOVE_IS_TRUE(__clove_string_endswith(result, "/rel/path/file.c")); - #endif + CLOVE_STRING_EQ(abs_path, result); __clove_memory_free(result); + __clove_memory_free(cwd_path); + __clove_memory_free(abs_path); } -CLOVE_TEST(ConvertExistentAbsToAbsolutePath) { +CLOVE_TEST(ConvertExistentRelToAbsolutePath) { char* cwd_path = utils_cwd(); - char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "my/path/"); + //puts(cwd_path); + char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "my/path"); utils_mkdirs(abs_path); - char* result = __clove_path_to_absolute("my/path/"); + char* result = __clove_path_to_absolute("my/path"); - #ifdef _WIN32 - const char* result_without_unit = result + 2; //e.g. c:\abs\path\file.c => \abs\path\file.c - CLOVE_IS_TRUE(__clove_string_startswith(result_without_unit, "\\")); - CLOVE_IS_TRUE(__clove_string_endswith(result_without_unit, "\\my\\path\\")); - #else - CLOVE_IS_TRUE(__clove_string_startswith(result, "/")); - CLOVE_IS_TRUE(__clove_string_endswith(result, "my/path/")); - #endif + CLOVE_STRING_EQ(abs_path, result); + + //rmdir + char* abs_path_parent = __clove_path_basepath(abs_path); + utils_rmdir(abs_path_parent); + + __clove_memory_free(result); + __clove_memory_free(cwd_path); + __clove_memory_free(abs_path); + __clove_memory_free(abs_path_parent); +} +/* +CLOVE_TEST(ConvertUnexistentToAbsoluteWithEndingSlashIsRemoved) { + char* cwd_path = utils_cwd(); + char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "rel/path"); + + char* result = __clove_path_to_absolute("./rel/path/"); + + CLOVE_STRING_EQ(abs_path, result); + + __clove_memory_free(result); + __clove_memory_free(cwd_path); + __clove_memory_free(abs_path); +} + + +CLOVE_TEST(ConvertExistentToAbsoluteWithEndingSlashIsRemoved) { + char* cwd_path = utils_cwd(); + char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "my/path"); + utils_mkdirs(abs_path); + + char* result = __clove_path_to_absolute("my/path/"); + + CLOVE_STRING_EQ(abs_path, result); //rmdir char* abs_path_parent = __clove_path_basepath(abs_path); @@ -136,3 +161,5 @@ CLOVE_TEST(ConvertExistentAbsToAbsolutePath) { __clove_memory_free(abs_path); __clove_memory_free(abs_path_parent); } + +*/ \ No newline at end of file diff --git a/tests/functs/src/utils/file_utils.c b/tests/functs/src/utils/file_utils.c index bcca431..c7869d5 100644 --- a/tests/functs/src/utils/file_utils.c +++ b/tests/functs/src/utils/file_utils.c @@ -40,6 +40,14 @@ static int _utils_os_rmdir_recurs(const char* dir) { return ret; // 0 on success, non-zero on failure } +static char* _utils_os_cwd() { + char buffer[_MAX_PATH]; + _getcwd(buffer, sizeof(buffer)); + + char* result = __clove_string_strdup(buffer); + return result; +} + #else #include #include @@ -47,7 +55,7 @@ static int _utils_os_rmdir_recurs(const char* dir) { //#include #include static void _utils_os_mkdir(const char* path) { - _mkdir(path, 0775); + mkdir(path, 0775); } static int _utils_os_rmdir_recurs(const char* dirPath) { @@ -84,11 +92,22 @@ static int _utils_os_rmdir_recurs(const char* dirPath) { printf("Error: Failed to remove directory: %s\n", dirPath); return -1; } + return 0; +} + +static char* _utils_os_cwd() { + char buffer[PATH_MAX]; + getcwd(buffer, sizeof(buffer)); + + char* result = __clove_string_strdup(buffer); + return result; +} #endif char* utils_cwd() { //eventually _getcwd (windows) and getcwd (posix) can be used - return __clove_path_to_absolute("."); + //return __clove_path_to_absolute("."); + return _utils_os_cwd(); } void utils_mkdirs(char* path) { From 3a9582c1301dce08e512281a5cf0f127d75684b3 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 00:04:18 +0200 Subject: [PATCH 13/30] #102 fix windows test --- clove-unit.h | 54 ++++++++++++++-------------- tests/functs/src/inte/cmd_run_test.c | 6 ++-- tests/functs/src/unit/path_test.c | 47 +++--------------------- 3 files changed, 34 insertions(+), 73 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index d717264..6720e7a 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -84,13 +84,14 @@ __CLOVE_EXTERN_C double __clove_math_decimald(unsigned char precision); #define __CLOVE_PATH_SEPARATOR_STR "/" #endif //_WIN32 -__CLOVE_EXTERN_C char* __clove_path_concat(const char separator, const char* path1, const char* path2); +__CLOVE_EXTERN_C char* __clove_path_concat(const char* path1, const char* path2, const char separator); __CLOVE_EXTERN_C const char* __clove_path_relative(const char* abs_path, const char* base_path); __CLOVE_EXTERN_C char* __clove_path_rel_to_abs_exec_path(const char* rel_path); __CLOVE_EXTERN_C bool __clove_path_is_relative(const char* path); __CLOVE_EXTERN_C bool __clove_path_is_absolute(const char* path); __CLOVE_EXTERN_C void __clove_path_to_os(char* path); __CLOVE_EXTERN_C char* __clove_path_basepath(const char* path); +__CLOVE_EXTERN_C bool __clove_path_exists(const char* path); __CLOVE_EXTERN_C char* __clove_path_to_absolute(const char* path); #pragma endregion // Path Decl @@ -904,7 +905,13 @@ double __clove_math_decimald(unsigned char precision) { #include #include -char* __clove_path_concat(const char separator, const char* path1, const char* path2) { +#ifdef _WIN32 + #define __CLOVE_PATH_MAX_LEN _MAX_PATH +#else + #define __CLOVE_PATH_MAX_LEN PATH_MAX +#endif //_WIN32 + +char* __clove_path_concat(const char* path1, const char* path2, const char separator) { size_t count = __clove_string_length(path1) + 1 + __clove_string_length(path2) + 1; char* path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, count); @@ -931,7 +938,7 @@ const char* __clove_path_relative(const char* abs_path, const char* base_path) { char* __clove_path_rel_to_abs_exec_path(const char* rel_path) { const char* base_path = __clove_utils_get_exec_abs_basepath(); - char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, rel_path); + char* abs_path = __clove_path_concat(base_path, rel_path, __CLOVE_PATH_SEPARATOR); return abs_path; } @@ -951,50 +958,41 @@ void __clove_path_to_os(char* path) { __clove_string_replace_char(path, '\\', __CLOVE_PATH_SEPARATOR); } -char* __clove_path_basepath(const char* a_path) { - bool last_char_is_win = __clove_string_endswith(a_path, "\\"); - bool last_char_is_uni = __clove_string_endswith(a_path, "/"); - - //__CLOVE_UNUSED_VAR(last_char_is_win); - //__CLOVE_UNUSED_VAR(last_char_is_uni); - - - size_t source_len = __clove_string_length(a_path); - size_t tmp_len = source_len + 1; - char* tmp_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, tmp_len); //take account for '\0' - - if (last_char_is_win || last_char_is_uni) - { - source_len--; - } +char* __clove_path_basepath(const char* path) { + char temp_path[__CLOVE_PATH_MAX_LEN]; + __clove_string_strcpy(temp_path, sizeof(temp_path), path); - __clove_string_strncpy(tmp_path, tmp_len, a_path, source_len); + //Remove last path separator character if any + bool last_char_is_win = __clove_string_endswith(path, "\\"); + bool last_char_is_uni = __clove_string_endswith(path, "/"); + if (last_char_is_win || last_char_is_uni) { + size_t last_index = __clove_string_length(temp_path) - 1; + temp_path[last_index] = '\0'; + } - // Find the last path separator character in the input path. - int last_char_win = __clove_string_last_indexof(tmp_path, '\\'); - int last_char_uni = __clove_string_last_indexof(tmp_path, '/'); //or unix or win eventually + int last_char_win = __clove_string_last_indexof(temp_path, '\\'); + int last_char_uni = __clove_string_last_indexof(temp_path, '/'); //or unix or win eventually int last_char_index = last_char_win > last_char_uni ? last_char_win : last_char_uni; // If there are no separators in the path, return the current directory path. char* result = NULL; - if (last_char_index <= 0) { + if (last_char_index < 0) { static char dot_path[3] = { '.', __CLOVE_PATH_SEPARATOR, '\0' }; result = __clove_string_strdup(dot_path); } else { // Calculate base path length based on the position of the last path separator. size_t base_length = (size_t)(last_char_index + 1); - char* base_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, base_length); - __clove_string_strncpy(base_path, base_length, tmp_path, base_length - 1); + char* base_path = __CLOVE_MEMORY_MALLOC_TYPE_N(char, base_length); + __clove_string_strncpy(base_path, base_length, temp_path, base_length - 1); __clove_path_to_os(base_path); result = base_path; } - __clove_memory_free(tmp_path); return result; } -static bool __clove_path_exists(const char* path) { +bool __clove_path_exists(const char* path) { struct stat buffer; return stat(path, &buffer) == 0; } diff --git a/tests/functs/src/inte/cmd_run_test.c b/tests/functs/src/inte/cmd_run_test.c index b190415..5ddd269 100644 --- a/tests/functs/src/inte/cmd_run_test.c +++ b/tests/functs/src/inte/cmd_run_test.c @@ -18,7 +18,7 @@ CLOVE_SUITE_TEARDOWN() { CLOVE_TEST(JsonReportWithOptOonFile) { char* base_path = __clove_path_basepath(RES_PRJ01_EXEC_PATH); - char* report_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, "cmd_json_report.json"); + char* report_path = __clove_path_concat(base_path, "cmd_json_report.json", __CLOVE_PATH_SEPARATOR); //utils_file_delete(report_path); const char* cmd = cmd_fmt("\"%s\" -r json -o \"%s\"", RES_PRJ01_EXEC_PATH, report_path); @@ -34,7 +34,7 @@ CLOVE_TEST(JsonReportWithOptOonFile) { CLOVE_TEST(JsonReportWithOptOuputOnFile) { char* base_path = __clove_path_basepath(RES_PRJ01_EXEC_PATH); - char* report_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, "cmd_json_report.json"); + char* report_path = __clove_path_concat(base_path, "cmd_json_report.json", __CLOVE_PATH_SEPARATOR); //utils_file_delete(report_path); const char* cmd = cmd_fmt("\"%s\" -r json --output \"%s\"", RES_PRJ01_EXEC_PATH, report_path); @@ -216,7 +216,7 @@ CLOVE_TEST(DefaultReportIncludeOverExcludeOneTest) { CLOVE_TEST(DefaultReportWithOptOonFile) { char* base_path = __clove_path_basepath(RES_PRJ01_EXEC_PATH); - char* report_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, base_path, "cmd_console_report.txt"); + char* report_path = __clove_path_concat(base_path, "cmd_console_report.txt", __CLOVE_PATH_SEPARATOR); //utils_file_delete(report_path); const char* cmd = cmd_fmt("\"%s\" -o \"%s\"", RES_PRJ01_EXEC_PATH, report_path); diff --git a/tests/functs/src/unit/path_test.c b/tests/functs/src/unit/path_test.c index 98768ad..f16a6f4 100644 --- a/tests/functs/src/unit/path_test.c +++ b/tests/functs/src/unit/path_test.c @@ -1,15 +1,15 @@ #define CLOVE_SUITE_NAME UNIT_PathTest -#include "clove-unit.h" +#include #include "utils/utils.h" CLOVE_TEST(PathConcatenation) { - char* result = __clove_path_concat('/', "path/to/first", "second"); + char* result = __clove_path_concat("path/to/first", "second", '/'); CLOVE_ULLONG_EQ(20, __clove_string_length(result)); CLOVE_STRING_EQ("path/to/first/second", result); } CLOVE_TEST(PathConcatConvertingSeparator) { - char* result = __clove_path_concat('\\', "path/to/first", "second"); + char* result = __clove_path_concat("path/to/first", "second", '\\'); CLOVE_ULLONG_EQ(20, __clove_string_length(result)); CLOVE_STRING_EQ("path\\to\\first\\second", result); } @@ -98,7 +98,7 @@ CLOVE_TEST(ConvertUnexistentAbsToAbsolutePath) { CLOVE_TEST(ConvertUnexistentRelToAbsolutePath) { char* cwd_path = utils_cwd(); - char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "rel/path/file.c"); + char* abs_path = __clove_path_concat(cwd_path, "rel/path/file.c", __CLOVE_PATH_SEPARATOR); char* result = __clove_path_to_absolute("rel/path/file.c"); CLOVE_STRING_EQ(abs_path, result); @@ -110,8 +110,7 @@ CLOVE_TEST(ConvertUnexistentRelToAbsolutePath) { CLOVE_TEST(ConvertExistentRelToAbsolutePath) { char* cwd_path = utils_cwd(); - //puts(cwd_path); - char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "my/path"); + char* abs_path = __clove_path_concat(cwd_path, "my/path", __CLOVE_PATH_SEPARATOR); utils_mkdirs(abs_path); char* result = __clove_path_to_absolute("my/path"); @@ -127,39 +126,3 @@ CLOVE_TEST(ConvertExistentRelToAbsolutePath) { __clove_memory_free(abs_path); __clove_memory_free(abs_path_parent); } - -/* -CLOVE_TEST(ConvertUnexistentToAbsoluteWithEndingSlashIsRemoved) { - char* cwd_path = utils_cwd(); - char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "rel/path"); - - char* result = __clove_path_to_absolute("./rel/path/"); - - CLOVE_STRING_EQ(abs_path, result); - - __clove_memory_free(result); - __clove_memory_free(cwd_path); - __clove_memory_free(abs_path); -} - - -CLOVE_TEST(ConvertExistentToAbsoluteWithEndingSlashIsRemoved) { - char* cwd_path = utils_cwd(); - char* abs_path = __clove_path_concat(__CLOVE_PATH_SEPARATOR, cwd_path, "my/path"); - utils_mkdirs(abs_path); - - char* result = __clove_path_to_absolute("my/path/"); - - CLOVE_STRING_EQ(abs_path, result); - - //rmdir - char* abs_path_parent = __clove_path_basepath(abs_path); - utils_rmdir(abs_path_parent); - - __clove_memory_free(result); - __clove_memory_free(cwd_path); - __clove_memory_free(abs_path); - __clove_memory_free(abs_path_parent); -} - -*/ \ No newline at end of file From 99da1b3b1eb534b1ba27d25d9938670f9ad65969 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 00:19:43 +0200 Subject: [PATCH 14/30] #102 fix sanity --- clove-unit.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/clove-unit.h b/clove-unit.h index 6720e7a..ad42461 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -983,7 +983,7 @@ char* __clove_path_basepath(const char* path) { } else { // Calculate base path length based on the position of the last path separator. size_t base_length = (size_t)(last_char_index + 1); - char* base_path = __CLOVE_MEMORY_MALLOC_TYPE_N(char, base_length); + char* base_path = __CLOVE_MEMORY_CALLOC_TYPE_N(char, base_length); __clove_string_strncpy(base_path, base_length, temp_path, base_length - 1); __clove_path_to_os(base_path); result = base_path; From 7c68c4b6d2afaefc3b14d0f16c1ad02f724540bd Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 00:26:28 +0200 Subject: [PATCH 15/30] #102 improve error logging for macos image slide --- clove-unit.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/clove-unit.h b/clove-unit.h index ad42461..fec09d3 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -3880,7 +3880,8 @@ int __clove_symbols_macos_open_module_handle(const char* module_abs_path, __clov out_module->size = st.st_size; bool found = __clove_symbols_macos_image_slide(module_abs_path, &out_module->address); if (!found) { - puts("cannot find image slide"); + //TODO: add logging api like __clove_log_erro(frmt, args) + printf("[ERRO] cannot find image slide for: %s", module_abs_path); return 4; } return 0; From 3f84c8ae027e72337c455b68b9c0a5db2cbde06f Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 10:10:52 +0200 Subject: [PATCH 16/30] changed library target name to clove-unit --- CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 04de3c7..8b9715b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,8 +2,8 @@ cmake_minimum_required(VERSION 3.18) project(CLoveUnit LANGUAGES C) include(CTest) -add_library(CloveUnit INTERFACE) -target_include_directories(CloveUnit INTERFACE "${CMAKE_CURRENT_LIST_DIR}") +add_library(clove-unit INTERFACE) +target_include_directories(clove-unit INTERFACE "${CMAKE_CURRENT_LIST_DIR}") #[[ add_subdirectory(tests/functs) From a7d424114725b697da7644db80e2641e41185a44 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 10:24:42 +0200 Subject: [PATCH 17/30] #104 add guard to avoid including dev targets when using FetchContent --- CMakeLists.txt | 34 +++++++++++++++++++++------------- 1 file changed, 21 insertions(+), 13 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 8b9715b..6991b38 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -19,18 +19,26 @@ add_subdirectory(tests/perfs) endif() ]] -if (CLOVE_CMAKE__UC_BUILD) - add_subdirectory(tests/functs) - add_subdirectory(tests/stricts/clove-c) - add_subdirectory(tests/stricts/clove-cpp) - add_subdirectory(examples/clove101) - add_subdirectory(examples/clovepp) -endif() +#[[ + In case this is the root project add dev targets. + To avoid targets pollution when using FetchContent were only the target library is required +]] +if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) -if (CLOVE_CMAKE__UC_SANITY) - add_subdirectory(tests/stricts/clove-sanity) -endif() + if (CLOVE_CMAKE__UC_BUILD) + add_subdirectory(tests/functs) + add_subdirectory(tests/stricts/clove-c) + add_subdirectory(tests/stricts/clove-cpp) + add_subdirectory(examples/clove101) + add_subdirectory(examples/clovepp) + endif() -if (CLOVE_CMAKE__UC_PERFS) - add_subdirectory(tests/perfs) -endif() + if (CLOVE_CMAKE__UC_SANITY) + add_subdirectory(tests/stricts/clove-sanity) + endif() + + if (CLOVE_CMAKE__UC_PERFS) + add_subdirectory(tests/perfs) + endif() + +endif() \ No newline at end of file From a6cf7a173e62154f8bbcb7455afc082ee9e9cc8e Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 10:44:27 +0200 Subject: [PATCH 18/30] #104 add minimum compile feature to c11 to library --- CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/CMakeLists.txt b/CMakeLists.txt index 6991b38..8238502 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -4,6 +4,7 @@ include(CTest) add_library(clove-unit INTERFACE) target_include_directories(clove-unit INTERFACE "${CMAKE_CURRENT_LIST_DIR}") +target_compile_features(clove-unit INTERFACE c_std_11) #[[ add_subdirectory(tests/functs) From 29b430df69ed1bde5e41e0a5cf0b7001b4a366a4 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 10:48:51 +0200 Subject: [PATCH 19/30] #104 add minimum compile feature to c11 to library --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 8238502..da74270 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,6 +1,5 @@ cmake_minimum_required(VERSION 3.18) project(CLoveUnit LANGUAGES C) -include(CTest) add_library(clove-unit INTERFACE) target_include_directories(clove-unit INTERFACE "${CMAKE_CURRENT_LIST_DIR}") @@ -25,6 +24,7 @@ endif() To avoid targets pollution when using FetchContent were only the target library is required ]] if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) + include(CTest) if (CLOVE_CMAKE__UC_BUILD) add_subdirectory(tests/functs) From 4977935702fe64cd9f77cfa776a83f237292d20a Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 10:56:41 +0200 Subject: [PATCH 20/30] #104 improve comments --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index da74270..3e843d1 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -20,7 +20,7 @@ endif() ]] #[[ - In case this is the root project add dev targets. + In case this is the root project add dev targets (Development mode). To avoid targets pollution when using FetchContent were only the target library is required ]] if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) From 2c9fe5943667044249c7b1c7945d166a62be760c Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Wed, 19 Jun 2024 14:33:02 +0200 Subject: [PATCH 21/30] #104 improved readme to include documentation about cmake fetchcontent usage --- README.md | 62 +++++++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 58 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 2371d60..6a28f86 100644 --- a/README.md +++ b/README.md @@ -19,7 +19,7 @@ Consider also supporting `CLove-Unit` development becoming a [**sponsor**](https * [Features](#features) * [IDE Extensions](#ide-extensions) -* [Supported Package Managers](#supported-package-managers) +* [How to Integrate](#how-to-integrate) * [How It Works](#how-it-works) * [Getting Started](#getting-started) * [Programming API](#programming-api) @@ -48,11 +48,65 @@ For those who prefer a UI oriented test executor, `CLove-Unit` is supported on t Have a look and enjoy ;-) -## Supported Package Managers +## How to Integrate -`CLove-Unit` is also available on the following Package Managers: +`CLove-Unit` can be imported in your project in the following ways: +- Sourcing the header file +- Using a Package Manager +- Using CMake -* [Conan](https://conan.io/center/recipes/clove-unit) +### Sourcing the Header file +Being an header-only library, you can just download [clove-unit.h](./clove-unit.h) file and include it in your project. + +```c +#include "clove-unit.h" +``` + +Then remember to properly configure your compiler include paths. + +### Using a Package Manager +`CLove-Unit` is currently available on the following Package Managers: + +* [Conan](https://conan.io): read [here](https://conan.io/center/recipes/clove-unit) for details on how to import it. + +### Using CMake +In case you still need dependency management, but you want to avoid Package Manager configuration complexity, you can use standard mechansim provided by `CMake` such as [FetchContent](https://cmake.org/cmake/help/latest/module/FetchContent.html) and [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html). + +> CMake library is named `clove-unit` + +Here a few examples: + +* **FetchContent** + + ```cmake + cmake_minimum_required(VERSION 3.18) + project(TestProject C) + + Include(FetchContent) + FetchContent_Declare( + clove-unit + GIT_REPOSITORY https://github.com/fdefelici/clove-unit.git + GIT_TAG master # or eventually any branch, tag or commit sha + ) + FetchContent_MakeAvailable(clove-unit) + + add_executable(tests ) + target_link_libraries(tests clove-unit) + ``` + +* [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html) + + First download `CLove-Unit` repository and then point properly to it like this: + + ```cmake + cmake_minimum_required(VERSION 3.18) + project(TestProject C) + + add_subdirectory() + + add_executable(tests ) + target_link_libraries(tests clove-unit) + ``` ## How It Works From 55b30b5ec5c7bbc800495f1b770370a72c11fc7a Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 13:55:14 +0200 Subject: [PATCH 22/30] #107 add install configuration to enable find_package --- CMakeLists.txt | 87 ++++++++++++++++++++++++----- cmake/in/clove-unit-config.cmake.in | 5 ++ cmake/modules/JoinPaths.cmake | 23 ++++++++ 3 files changed, 100 insertions(+), 15 deletions(-) create mode 100644 cmake/in/clove-unit-config.cmake.in create mode 100644 cmake/modules/JoinPaths.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index 3e843d1..9c23ac6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,23 +1,80 @@ cmake_minimum_required(VERSION 3.18) -project(CLoveUnit LANGUAGES C) +set(CLOVE_SOURCE_DIR ${CMAKE_CURRENT_LIST_DIR}) +list(INSERT CMAKE_MODULE_PATH 0 ${CLOVE_SOURCE_DIR}/cmake/modules) + +# Extract CLOVE_VERSION from header file +set(CLOVE_VERSION_REGEX "#define __CLOVE_VERSION_.*[ \t]+(.+)") +file(STRINGS "${CLOVE_SOURCE_DIR}/clove-unit.h" CLOVE_VERSION REGEX ${CLOVE_VERSION_REGEX}) +list(TRANSFORM CLOVE_VERSION REPLACE ${CLOVE_VERSION_REGEX} "\\1") +string(JOIN "." CLOVE_VERSION ${CLOVE_VERSION}) + +# Configure Project +project( + CLoveUnit + VERSION ${CLOVE_VERSION} + DESCRIPTION "Single-header Unit Testing framework for C (interoperable with C++) with test autodiscovery feature" + HOMEPAGE_URL "https://github.com/fdefelici/clove-unit" + LANGUAGES C +) + +include(JoinPaths) +include(GNUInstallDirs) +include(CMakePackageConfigHelpers) + +join_paths(CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}" clove-unit ${PROJECT_VERSION}) + +# Library Target definition and configuration add_library(clove-unit INTERFACE) -target_include_directories(clove-unit INTERFACE "${CMAKE_CURRENT_LIST_DIR}") +add_library(clove-unit::clove-unit ALIAS clove-unit) + +target_include_directories( + clove-unit INTERFACE + $ + $ +) + target_compile_features(clove-unit INTERFACE c_std_11) -#[[ -add_subdirectory(tests/functs) -if (DEFINED CLOVE_CMAKE__CI_TRIGGERED) - add_subdirectory(tests/stricts/clove-c) - add_subdirectory(tests/stricts/clove-cpp) - add_subdirectory(examples/clove101) - add_subdirectory(examples/clovepp) -endif() +# Install command stuffs for enabling find_package usage +install( + TARGETS clove-unit + EXPORT clove-unit-targets + INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} +) + +write_basic_package_version_file( + clove-unit-config-version.cmake + VERSION ${PROJECT_VERSION} + COMPATIBILITY AnyNewerVersion +) + +configure_package_config_file( + ${CLOVE_SOURCE_DIR}/cmake/in/clove-unit-config.cmake.in + clove-unit-config.cmake + INSTALL_DESTINATION ${CMAKE_INSTALL_PREFIX}/cmake +) + +install( + FILES ${CLOVE_SOURCE_DIR}/clove-unit.h + DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} +) + +install( + FILES + ${PROJECT_BINARY_DIR}/clove-unit-config.cmake + ${PROJECT_BINARY_DIR}/clove-unit-config-version.cmake + DESTINATION ${CMAKE_INSTALL_PREFIX}/cmake +) + +install( + EXPORT clove-unit-targets + #NAMESPACE clove-unit:: + DESTINATION ${CMAKE_INSTALL_PREFIX}/cmake +) + +export(PACKAGE clove-unit) -if (DEFINED CLOVE_CMAKE__ENABLE_PERFS) -add_subdirectory(tests/perfs) -endif() -]] #[[ In case this is the root project add dev targets (Development mode). @@ -42,4 +99,4 @@ if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) add_subdirectory(tests/perfs) endif() -endif() \ No newline at end of file +endif() diff --git a/cmake/in/clove-unit-config.cmake.in b/cmake/in/clove-unit-config.cmake.in new file mode 100644 index 0000000..6d9ec93 --- /dev/null +++ b/cmake/in/clove-unit-config.cmake.in @@ -0,0 +1,5 @@ +@PACKAGE_INIT@ + +set(CLOVE_VERSION "@PROJECT_VERSION@") +include("${CMAKE_CURRENT_LIST_DIR}/clove-unit-targets.cmake") +check_required_components("@PROJECT_NAME@") \ No newline at end of file diff --git a/cmake/modules/JoinPaths.cmake b/cmake/modules/JoinPaths.cmake new file mode 100644 index 0000000..ce80aff --- /dev/null +++ b/cmake/modules/JoinPaths.cmake @@ -0,0 +1,23 @@ +# This module provides function for joining paths +# known from most languages +# +# SPDX-License-Identifier: (MIT OR CC0-1.0) +# Copyright 2020 Jan Tojnar +# https://github.com/jtojnar/cmake-snips +# +# Modelled after Python’s os.path.join +# https://docs.python.org/3.7/library/os.path.html#os.path.join +# Windows not supported +function(join_paths joined_path first_path_segment) + set(temp_path "${first_path_segment}") + foreach(current_segment IN LISTS ARGN) + if(NOT ("${current_segment}" STREQUAL "")) + if(IS_ABSOLUTE "${current_segment}") + set(temp_path "${current_segment}") + else() + set(temp_path "${temp_path}/${current_segment}") + endif() + endif() + endforeach() + set(${joined_path} "${temp_path}" PARENT_SCOPE) +endfunction() \ No newline at end of file From 3c04be9f07ac270c0d4d7952d64de199d5bdf891 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 14:43:28 +0200 Subject: [PATCH 23/30] #107 add find_package documentation --- CMakeLists.txt | 1 + README.md | 29 ++++++++++++++++++++++++++--- 2 files changed, 27 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 9c23ac6..a13e356 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -79,6 +79,7 @@ export(PACKAGE clove-unit) #[[ In case this is the root project add dev targets (Development mode). To avoid targets pollution when using FetchContent were only the target library is required + Note: PROJECT_IS_TOP_LEVEL cmake variable exists in version 3.21+ ]] if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) include(CTest) diff --git a/README.md b/README.md index 21ac741..b3c2bf9 100644 --- a/README.md +++ b/README.md @@ -70,9 +70,9 @@ Then remember to properly configure your compiler include paths. * [Conan](https://conan.io): read [here](https://conan.io/center/recipes/clove-unit) for details on how to import it. ### Using CMake -In case you still need dependency management, but you want to avoid Package Manager configuration complexity, you can use standard mechansim provided by `CMake` such as [FetchContent](https://cmake.org/cmake/help/latest/module/FetchContent.html) and [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html). +In case you still need dependency management, but you want to avoid Package Manager configuration complexity, you can use standard mechansim provided by `CMake` such as [FetchContent](https://cmake.org/cmake/help/latest/module/FetchContent.html), [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html) and [find_package](https://cmake.org/cmake/help/latest/command/find_package.html). -> CMake library is named `clove-unit` +> NOTE: CMake library is named `clove-unit` Here a few examples: @@ -94,7 +94,7 @@ Here a few examples: target_link_libraries(tests clove-unit) ``` -* [add_subdirectory](https://cmake.org/cmake/help/latest/command/add_subdirectory.html) +* **add_subdirectory** First download `CLove-Unit` repository and then point properly to it like this: @@ -108,6 +108,29 @@ Here a few examples: target_link_libraries(tests clove-unit) ``` +* **find_package** + + First download `CLove-Unit` repository and then run cmake install command on it. + + Package will be installed in at following path: `` + + Eventually you may want to customize [CMAKE_INSTALL_PREFIX](https://cmake.org/cmake/help/latest/variable/CMAKE_INSTALL_PREFIX.html) variable to override cmake default installation path for packages. + + + Then use the package as follow: + ```cmake + cmake_minimum_required(VERSION 3.18) + project(TestProject C) + + find_package(clove-unit REQUIRED PATHS ) + + # or more strict + # find_package(clove-unit EXACT REQUIRED PATHS ) + + add_executable(tests ) + target_link_libraries(tests clove-unit) + ``` + ## How It Works `CLove-Unit` is built upon these fundamental concepts: From 0e463b38de46049a30c6fe57c53bc1b99254f5ec Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 15:26:26 +0200 Subject: [PATCH 24/30] #105 converted input variables to option --- .github/workflows/ci_action.yml | 24 ++++++++++++------------ CMakeLists.txt | 6 ++++++ README.md | 2 +- tests/stricts/clove-cpp/CMakeLists.txt | 2 +- 4 files changed, 20 insertions(+), 14 deletions(-) diff --git a/.github/workflows/ci_action.yml b/.github/workflows/ci_action.yml index 1c9d7f8..d22cc01 100644 --- a/.github/workflows/ci_action.yml +++ b/.github/workflows/ci_action.yml @@ -30,7 +30,7 @@ jobs: echo "== CMAKE VERSION ==" cmake --version echo "== CMAKE CONFIGURE ==" - cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_BUILD=true + cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_BUILD=ON echo "== CMAKE BUILD ==" cmake --build ${{env.BUILD_DIR}} --config Release - name: List Build @@ -61,7 +61,7 @@ jobs: echo "== CMAKE VERSION ==" cmake --version echo "== CMAKE CONFIGURE ==" - cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_BUILD=true + cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_BUILD=ON echo "== CMAKE BUILD ==" cmake --build ${{env.BUILD_DIR}} --config Release - name: List Build @@ -78,14 +78,14 @@ jobs: fail-fast: false matrix: compiler: - - {c: gcc, cpp: g++, v: 11, strict: false} - - {c: gcc, cpp: g++, v: 12, strict: false} - - {c: gcc, cpp: g++, v: 13, strict: true} - - {c: clang, cpp: clang++, v: 13, strict: true} - - {c: clang, cpp: clang++, v: 14, strict: true} - - {c: clang, cpp: clang++, v: 15, strict: true} - - {c: clang, cpp: clang++, v: 16, strict: true} - - {c: clang, cpp: clang++, v: 17, strict: true} + - {c: gcc, cpp: g++, v: 11, strict: OFF} + - {c: gcc, cpp: g++, v: 12, strict: OFF} + - {c: gcc, cpp: g++, v: 13, strict: ON} + - {c: clang, cpp: clang++, v: 13, strict: ON} + - {c: clang, cpp: clang++, v: 14, strict: ON} + - {c: clang, cpp: clang++, v: 15, strict: ON} + - {c: clang, cpp: clang++, v: 16, strict: ON} + - {c: clang, cpp: clang++, v: 17, strict: ON} defaults: run: shell: bash @@ -125,7 +125,7 @@ jobs: echo "== CMAKE VERSION ==" cmake --version echo "== CMAKE CONFIGURE ==" - cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_BUILD=true -DCLOVE_CMAKE__CPP_STRICT_WARN_AS_ERROR=${{matrix.compiler.strict}} + cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_BUILD=ON -DCLOVE_CMAKE__CPP_STRICT_WARN_AS_ERROR=${{matrix.compiler.strict}} echo "== CMAKE BUILD ==" cmake --build ${{env.BUILD_DIR}} --config Release - name: List Build @@ -153,7 +153,7 @@ jobs: echo "== CMAKE VERSION ==" cmake --version echo "== CMAKE CONFIGURE ==" - cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_SANITY=true + cmake -B${{env.BUILD_DIR}} -DCLOVE_CMAKE__UC_SANITY=ON echo "== CMAKE BUILD ==" cmake --build ${{env.BUILD_DIR}} --config Release - name: List Build diff --git a/CMakeLists.txt b/CMakeLists.txt index a13e356..cdf7701 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -22,6 +22,7 @@ include(JoinPaths) include(GNUInstallDirs) include(CMakePackageConfigHelpers) +# Eventually CMAKE_INSTALL_PREFIX can be overridden by the user to change base installation path for the package join_paths(CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}" clove-unit ${PROJECT_VERSION}) # Library Target definition and configuration @@ -84,6 +85,11 @@ export(PACKAGE clove-unit) if(CMAKE_CURRENT_SOURCE_DIR STREQUAL CMAKE_SOURCE_DIR) include(CTest) + option(CLOVE_CMAKE__UC_BUILD "enable build use case" OFF) + option(CLOVE_CMAKE__UC_SANITY "enable sanity check use case" OFF) + option(CLOVE_CMAKE__UC_PERFS "enable performance test use case" OFF) + option(CLOVE_CMAKE__CPP_STRICT_WARN_AS_ERROR "threat compilation warning as error" OFF) + if (CLOVE_CMAKE__UC_BUILD) add_subdirectory(tests/functs) add_subdirectory(tests/stricts/clove-c) diff --git a/README.md b/README.md index b3c2bf9..212bbfc 100644 --- a/README.md +++ b/README.md @@ -112,7 +112,7 @@ Here a few examples: First download `CLove-Unit` repository and then run cmake install command on it. - Package will be installed in at following path: `` + Package will be installed in at following path: `/clove-unit/` Eventually you may want to customize [CMAKE_INSTALL_PREFIX](https://cmake.org/cmake/help/latest/variable/CMAKE_INSTALL_PREFIX.html) variable to override cmake default installation path for packages. diff --git a/tests/stricts/clove-cpp/CMakeLists.txt b/tests/stricts/clove-cpp/CMakeLists.txt index b4693da..c87c77f 100644 --- a/tests/stricts/clove-cpp/CMakeLists.txt +++ b/tests/stricts/clove-cpp/CMakeLists.txt @@ -7,7 +7,7 @@ target_include_directories(StrictCloveCpp PRIVATE ../../../) set_property(TARGET StrictCloveCpp PROPERTY CXX_STANDARD 11) -if (NOT DEFINED CLOVE_CMAKE__CPP_STRICT_WARN_AS_ERROR OR CLOVE_CMAKE__CPP_STRICT_WARN_AS_ERROR EQUAL TRUE) +if (CLOVE_CMAKE__CPP_STRICT_WARN_AS_ERROR) set_property(TARGET StrictCloveCpp PROPERTY COMPILE_WARNING_AS_ERROR ON) endif() From 536e44ac917fdc2a8da6fa782a6bca0a6d955e1f Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 16:34:49 +0200 Subject: [PATCH 25/30] refactor cmake modules --- CMakeLists.txt | 10 +++------- cmake/modules/CLoveModules.cmake | 2 ++ cmake/modules/_ExtractVersion.cmake | 9 +++++++++ cmake/modules/{JoinPaths.cmake => _JoinPaths.cmake} | 2 +- 4 files changed, 15 insertions(+), 8 deletions(-) create mode 100644 cmake/modules/CLoveModules.cmake create mode 100644 cmake/modules/_ExtractVersion.cmake rename cmake/modules/{JoinPaths.cmake => _JoinPaths.cmake} (92%) diff --git a/CMakeLists.txt b/CMakeLists.txt index cdf7701..5bedae1 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -3,11 +3,8 @@ cmake_minimum_required(VERSION 3.18) set(CLOVE_SOURCE_DIR ${CMAKE_CURRENT_LIST_DIR}) list(INSERT CMAKE_MODULE_PATH 0 ${CLOVE_SOURCE_DIR}/cmake/modules) -# Extract CLOVE_VERSION from header file -set(CLOVE_VERSION_REGEX "#define __CLOVE_VERSION_.*[ \t]+(.+)") -file(STRINGS "${CLOVE_SOURCE_DIR}/clove-unit.h" CLOVE_VERSION REGEX ${CLOVE_VERSION_REGEX}) -list(TRANSFORM CLOVE_VERSION REPLACE ${CLOVE_VERSION_REGEX} "\\1") -string(JOIN "." CLOVE_VERSION ${CLOVE_VERSION}) +include(CloveModules) +clove_get_version(CLOVE_VERSION) # Configure Project project( @@ -18,12 +15,11 @@ project( LANGUAGES C ) -include(JoinPaths) include(GNUInstallDirs) include(CMakePackageConfigHelpers) # Eventually CMAKE_INSTALL_PREFIX can be overridden by the user to change base installation path for the package -join_paths(CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}" clove-unit ${PROJECT_VERSION}) +clove_join_paths(CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}" clove-unit ${PROJECT_VERSION}) # Library Target definition and configuration add_library(clove-unit INTERFACE) diff --git a/cmake/modules/CLoveModules.cmake b/cmake/modules/CLoveModules.cmake new file mode 100644 index 0000000..9be37d8 --- /dev/null +++ b/cmake/modules/CLoveModules.cmake @@ -0,0 +1,2 @@ +include(_ExtractVersion) +include(_JoinPaths) \ No newline at end of file diff --git a/cmake/modules/_ExtractVersion.cmake b/cmake/modules/_ExtractVersion.cmake new file mode 100644 index 0000000..0c099a3 --- /dev/null +++ b/cmake/modules/_ExtractVersion.cmake @@ -0,0 +1,9 @@ +# Extract clove version from clove-unit.h file +function(clove_get_version out_version) + set(CLOVE_VERSION_REGEX "#define __CLOVE_VERSION_.*[ \t]+(.+)") + file(STRINGS "${CMAKE_CURRENT_LIST_DIR}/clove-unit.h" CLOVE_VERSION REGEX ${CLOVE_VERSION_REGEX}) + list(TRANSFORM CLOVE_VERSION REPLACE ${CLOVE_VERSION_REGEX} "\\1") + string(JOIN "." CLOVE_VERSION ${CLOVE_VERSION}) + set(${out_version} "${CLOVE_VERSION}" PARENT_SCOPE) +endfunction() + diff --git a/cmake/modules/JoinPaths.cmake b/cmake/modules/_JoinPaths.cmake similarity index 92% rename from cmake/modules/JoinPaths.cmake rename to cmake/modules/_JoinPaths.cmake index ce80aff..684032f 100644 --- a/cmake/modules/JoinPaths.cmake +++ b/cmake/modules/_JoinPaths.cmake @@ -8,7 +8,7 @@ # Modelled after Python’s os.path.join # https://docs.python.org/3.7/library/os.path.html#os.path.join # Windows not supported -function(join_paths joined_path first_path_segment) +function(clove_join_paths joined_path first_path_segment) set(temp_path "${first_path_segment}") foreach(current_segment IN LISTS ARGN) if(NOT ("${current_segment}" STREQUAL "")) From 4ed32a0451747b0feb575b5c5b4c654c4dd8491a Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 16:35:36 +0200 Subject: [PATCH 26/30] prepare version 2.4.5 --- clove-unit.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/clove-unit.h b/clove-unit.h index fec09d3..a25e7b5 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -10,8 +10,8 @@ #define __CLOVE_VERSION_MAJOR 2 #define __CLOVE_VERSION_MINOR 4 -#define __CLOVE_VERSION_PATCH 4 -#define __CLOVE_VERSION "2.4.4" +#define __CLOVE_VERSION_PATCH 5 +#define __CLOVE_VERSION "2.4.5" //Preventing "unknown-pragmas" warning on GCC <= 12 for '#pragma region' usage //NOTE1: GCC and G++ v13+ support '#pragma region' by the way. From 297805ed64f032a95fa0ed605a19882fe159de5a Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 16:35:53 +0200 Subject: [PATCH 27/30] prepare version 2.4.5 --- clove-unit.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/clove-unit.h b/clove-unit.h index a25e7b5..dd01157 100644 --- a/clove-unit.h +++ b/clove-unit.h @@ -1,6 +1,6 @@ /* * clove-unit - * v2.4.4 + * v2.4.5 * Single-Header Unit Testing library for C/C++ * https://github.com/fdefelici/clove-unit * From 7a1e3c93e80657eae428c273de03127e928402a3 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 16:40:38 +0200 Subject: [PATCH 28/30] update github action for nodejs obsolescence --- .github/workflows/ci_action.yml | 8 ++++---- .github/workflows/release_action.yml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/ci_action.yml b/.github/workflows/ci_action.yml index d22cc01..f1017d8 100644 --- a/.github/workflows/ci_action.yml +++ b/.github/workflows/ci_action.yml @@ -22,7 +22,7 @@ jobs: BUILD_DIR: ${{ github.workspace }}\build steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: List Workspace run: dir /a ${{ github.workspace }} - name: Compile @@ -53,7 +53,7 @@ jobs: BUILD_DIR: ${{ github.workspace }}/build steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: List Workspace run: ls -la ${{ github.workspace }} - name: Compile @@ -93,7 +93,7 @@ jobs: BUILD_DIR: ${{ github.workspace }}/build steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: List Workspace run: ls -la ${{ github.workspace }} - name: Install Clang (if needed) @@ -145,7 +145,7 @@ jobs: BUILD_DIR: ${{ github.workspace }}/build steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: List Workspace run: ls -la ${{ github.workspace }} - name: Compile diff --git a/.github/workflows/release_action.yml b/.github/workflows/release_action.yml index 8235ab2..5e9a8e2 100644 --- a/.github/workflows/release_action.yml +++ b/.github/workflows/release_action.yml @@ -8,7 +8,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Upload Release Asset id: upload-release-asset uses: actions/upload-release-asset@v1 From 43643bf00812182f6f59a27ce2a1cc9cf75151a6 Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 16:42:23 +0200 Subject: [PATCH 29/30] fix naming in cmakelist --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 5bedae1..9afcf3e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -3,7 +3,7 @@ cmake_minimum_required(VERSION 3.18) set(CLOVE_SOURCE_DIR ${CMAKE_CURRENT_LIST_DIR}) list(INSERT CMAKE_MODULE_PATH 0 ${CLOVE_SOURCE_DIR}/cmake/modules) -include(CloveModules) +include(CLoveModules) clove_get_version(CLOVE_VERSION) # Configure Project From c3efbbe1ce07432bfb8f7199dbb3a4f8644577fe Mon Sep 17 00:00:00 2001 From: Federico De Felici Date: Thu, 20 Jun 2024 17:09:55 +0200 Subject: [PATCH 30/30] updated conan badge to show version --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 212bbfc..e1c17e7 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,4 @@ -# CLove-Unit · [![version](https://img.shields.io/github/v/release/fdefelici/clove-unit?label=latest&sort=semver)](./clove-unit.h) [![workflow](https://img.shields.io/github/actions/workflow/status/fdefelici/clove-unit/ci_action.yml)](https://github.com/fdefelici/clove-unit/actions/workflows/ci_action.yml) [![conan](https://img.shields.io/badge/conan-available-blueviolet)](https://conan.io/center/recipes/clove-unit) [![Discord channel](https://img.shields.io/discord/1167864219190964255?logo=discord&logoColor=violet)](https://discord.gg/Mjx4YRQfFt) +# CLove-Unit · [![version](https://img.shields.io/github/v/release/fdefelici/clove-unit?label=latest&sort=semver)](./clove-unit.h) [![workflow](https://img.shields.io/github/actions/workflow/status/fdefelici/clove-unit/ci_action.yml)](https://github.com/fdefelici/clove-unit/actions/workflows/ci_action.yml) [![conan](https://img.shields.io/conan/v/clove-unit)](https://conan.io/center/recipes/clove-unit) [![Discord channel](https://img.shields.io/discord/1167864219190964255?logo=discord&logoColor=violet)](https://discord.gg/Mjx4YRQfFt) `CLove-Unit` is a single-header unit testing library designed for C (compatible with C++).