From cd1e69e13d8dc1df57b5f371edc3f23ceb9bafc1 Mon Sep 17 00:00:00 2001 From: Mitya Selivanov <0x7fffff@guattari.ru> Date: Mon, 8 Aug 2022 02:50:03 +0400 Subject: Add tests --- CMakeLists.txt | 6 +- source/kit_test/CMakeLists.txt | 2 +- source/kit_test/run_tests.c | 132 -------------------------- source/kit_test/test.c | 147 +++++++++++++++++++++++++++++ source/kit_test/test.h | 14 ++- source/test/CMakeLists.txt | 1 + source/test/programs/CMakeLists.txt | 21 +++++ source/test/programs/too_many_assertions.c | 12 +++ source/test/programs/too_many_tests.c | 13 +++ source/test/unittests/CMakeLists.txt | 4 +- source/test/unittests/test_duration.test.c | 18 ++++ 11 files changed, 223 insertions(+), 147 deletions(-) delete mode 100644 source/kit_test/run_tests.c create mode 100644 source/kit_test/test.c create mode 100644 source/test/programs/CMakeLists.txt create mode 100644 source/test/programs/too_many_assertions.c create mode 100644 source/test/programs/too_many_tests.c create mode 100644 source/test/unittests/test_duration.test.c diff --git a/CMakeLists.txt b/CMakeLists.txt index 01fbba9..97d2d10 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -11,7 +11,6 @@ set(KIT_LIBRARY kit) set(KIT_TEST_LIBRARY kit_test) set(KIT_TEST_SUITE kit_test_suite) set(KIT_TARGETS kit-targets) -set(KIT_UNITTESTS kit-unittests) if(NOT DEFINED CMAKE_BUILD_PARALLEL_LEVEL) set(CMAKE_BUILD_PARALLEL_LEVEL 4) @@ -67,11 +66,10 @@ if(KIT_ENABLE_TESTING) endif() add_test( - NAME ${KIT_UNITTESTS} + NAME ${KIT_LIBRARY}_unittests COMMAND ${KIT_TEST_SUITE}) - set_tests_properties( - ${KIT_UNITTESTS} + ${KIT_LIBRARY}_unittests PROPERTIES TIMEOUT "30") endif() diff --git a/source/kit_test/CMakeLists.txt b/source/kit_test/CMakeLists.txt index f7315a1..25b9d81 100644 --- a/source/kit_test/CMakeLists.txt +++ b/source/kit_test/CMakeLists.txt @@ -1,6 +1,6 @@ target_sources( ${KIT_TEST_LIBRARY} PRIVATE - run_tests.c + test.c PUBLIC $) diff --git a/source/kit_test/run_tests.c b/source/kit_test/run_tests.c deleted file mode 100644 index 1bb6e67..0000000 --- a/source/kit_test/run_tests.c +++ /dev/null @@ -1,132 +0,0 @@ -#include "test.h" - -#include -#include - -kit_tests_list_t kit_tests_list = { 0 }; - -static void report(int i, char const *file, int line, int ok) { - int const n = kit_tests_list.tests[i].assertions++; - - if (n >= KIT_TEST_ASSERTIONS_LIMIT) - return; - - kit_tests_list.tests[i].file[n] = file; - kit_tests_list.tests[i].line[n] = line; - kit_tests_list.tests[i].status[n] = ok; -} - -static long long ns_to_ms(long long ns) { - return (ns + 500000) / 1000000; -} - -static long long sec_to_ms(long long sec) { - return 1000 * sec; -} - -enum { white, yellow, red, green }; - -static void color_code(int term_color, int c) { - if (term_color) { - if (c == white) - printf("\x1b[37m"); - if (c == yellow) - printf("\x1b[33m"); - if (c == red) - printf("\x1b[31m"); - if (c == green) - printf("\x1b[32m"); - } -} - -int kit_run_tests(int argc, char **argv) { - int fail_test_count = 0; - int fail_assertion_count = 0; - int total_assertion_count = 0; - int status = 0; - int term_color = 1; - - for (int i = 0; i < argc; i++) - if (strcmp("--no-term-color", argv[i]) == 0) - term_color = 0; - - for (int i = 0; i < kit_tests_list.size; i++) { - color_code(term_color, yellow); - printf("[ RUN... ] %s ", kit_tests_list.tests[i].test_name); - color_code(term_color, white); - - struct timespec begin, end; - timespec_get(&begin, TIME_UTC); - - kit_tests_list.tests[i].test_fn(i, report); - - timespec_get(&end, TIME_UTC); - int duration = (int) (ns_to_ms(end.tv_nsec - begin.tv_nsec) + - sec_to_ms(end.tv_sec - begin.tv_sec)); - - printf("\r"); - - int test_status = 1; - - for (int j = 0; j < kit_tests_list.tests[i].assertions; j++) - if (kit_tests_list.tests[i].status[j] == 0) { - fail_assertion_count++; - test_status = 0; - } - - if (kit_tests_list.tests[i].assertions >= - KIT_TEST_ASSERTIONS_LIMIT) - test_status = 0; - - total_assertion_count += kit_tests_list.tests[i].assertions; - - if (test_status == 0) { - color_code(term_color, red); - printf("[ RUN ] %s\n", kit_tests_list.tests[i].test_name); - printf("[ FAILED ] %s - %d ms\n", - kit_tests_list.tests[i].test_name, duration); - color_code(term_color, white); - fail_test_count++; - status = 1; - } else { - color_code(term_color, green); - printf("[ RUN ] %s\n", kit_tests_list.tests[i].test_name); - printf("[ OK ] %s - %d ms\n", - kit_tests_list.tests[i].test_name, duration); - color_code(term_color, white); - } - } - - printf("\n%d of %d tests passed.\n", - kit_tests_list.size - fail_test_count, kit_tests_list.size); - - printf("%d of %d assertions passed.\n\n", - total_assertion_count - fail_assertion_count, - total_assertion_count); - - if (status != 0) { - for (int i = 0; i < kit_tests_list.size; i++) { - if (kit_tests_list.tests[i].assertions >= - KIT_TEST_ASSERTIONS_LIMIT) - printf("Too many assertions for \"%s\" in \"%s\"!\n", - kit_tests_list.tests[i].test_name, - kit_tests_list.tests[i] - .file[KIT_TEST_ASSERTIONS_LIMIT - 1]); - else - for (int j = 0; j < kit_tests_list.tests[i].assertions; j++) - if (!kit_tests_list.tests[i].status[j]) - printf("Assertion on line %d in \"%s\" failed\n", - kit_tests_list.tests[i].line[j], - kit_tests_list.tests[i].file[j]); - } - - printf("\n"); - } - - if (kit_tests_list.size == KIT_TESTS_SIZE_LIMIT) { - printf("Too many tests!"); - status = 1; - } - - return status; -} diff --git a/source/kit_test/test.c b/source/kit_test/test.c new file mode 100644 index 0000000..db3c68c --- /dev/null +++ b/source/kit_test/test.c @@ -0,0 +1,147 @@ +#include "test.h" + +#include +#include + +kit_tests_list_t kit_tests_list = { 0 }; + +static void report(int i, char const *file, int line, int ok) { + int const n = kit_tests_list.tests[i].assertions++; + + if (n >= KIT_TEST_ASSERTIONS_LIMIT) + return; + + kit_tests_list.tests[i].file[n] = file; + kit_tests_list.tests[i].line[n] = line; + kit_tests_list.tests[i].status[n] = ok; +} + +static long long ns_to_ms(long long ns) { + return (ns + 500000) / 1000000; +} + +static long long sec_to_ms(long long sec) { + return 1000 * sec; +} + +enum { white, yellow, red, green }; + +static void color_code(int term_color, int c) { + if (term_color) { + if (c == white) + printf("\x1b[37m"); + if (c == yellow) + printf("\x1b[33m"); + if (c == red) + printf("\x1b[31m"); + if (c == green) + printf("\x1b[32m"); + } +} + +void kit_test_register(char const *name, kit_test_run_fn fn) { + int n = kit_tests_list.size++; + if (n < KIT_TESTS_SIZE_LIMIT) { + kit_tests_list.tests[n].test_fn = fn; + strcpy(kit_tests_list.tests[n].test_name, name); + kit_tests_list.tests[n].assertions = 0; + } +} + +int kit_run_tests(int argc, char **argv) { + int success_count = 0; + int fail_assertion_count = 0; + int total_assertion_count = 0; + int status = 0; + int term_color = 1; + + for (int i = 0; i < argc; i++) + if (strcmp("--no-term-color", argv[i]) == 0) + term_color = 0; + + for (int i = 0; i < kit_tests_list.size && i < KIT_TESTS_SIZE_LIMIT; + i++) { + color_code(term_color, yellow); + printf("[ RUN... ] %s ", kit_tests_list.tests[i].test_name); + color_code(term_color, white); + + struct timespec begin, end; + timespec_get(&begin, TIME_UTC); + + kit_tests_list.tests[i].test_fn(i, report); + + timespec_get(&end, TIME_UTC); + int duration = (int) (ns_to_ms(end.tv_nsec - begin.tv_nsec) + + sec_to_ms(end.tv_sec - begin.tv_sec)); + + printf("\r"); + + int test_status = 1; + + for (int j = 0; j < kit_tests_list.tests[i].assertions; j++) + if (kit_tests_list.tests[i].status[j] == 0) { + fail_assertion_count++; + test_status = 0; + } + + if (kit_tests_list.tests[i].assertions > + KIT_TEST_ASSERTIONS_LIMIT) + test_status = 0; + + total_assertion_count += kit_tests_list.tests[i].assertions; + + if (test_status == 0) { + color_code(term_color, red); + printf("[ RUN ] %s\n", kit_tests_list.tests[i].test_name); + printf("[ FAILED ] %s", kit_tests_list.tests[i].test_name); + color_code(term_color, white); + if (duration > 0) + printf(" - %d ms", duration); + printf("\n"); + status = 1; + } else { + color_code(term_color, green); + printf("[ RUN ] %s\n", kit_tests_list.tests[i].test_name); + printf("[ OK ] %s", kit_tests_list.tests[i].test_name); + color_code(term_color, white); + if (duration > 0) + printf(" - %d ms", duration); + printf("\n"); + success_count++; + } + } + + printf("\n%d of %d tests passed.\n", success_count, + kit_tests_list.size); + + printf("%d of %d assertions passed.\n\n", + total_assertion_count - fail_assertion_count, + total_assertion_count); + + if (status != 0) { + for (int i = 0; + i < kit_tests_list.size && i < KIT_TESTS_SIZE_LIMIT; i++) { + if (kit_tests_list.tests[i].assertions > + KIT_TEST_ASSERTIONS_LIMIT) + printf("Too many assertions for \"%s\" in \"%s\"!\n", + kit_tests_list.tests[i].test_name, + kit_tests_list.tests[i] + .file[KIT_TEST_ASSERTIONS_LIMIT - 1]); + else + for (int j = 0; j < kit_tests_list.tests[i].assertions; j++) + if (!kit_tests_list.tests[i].status[j]) + printf("Assertion on line %d in \"%s\" failed\n", + kit_tests_list.tests[i].line[j], + kit_tests_list.tests[i].file[j]); + } + + printf("\n"); + } + + if (kit_tests_list.size > KIT_TESTS_SIZE_LIMIT) { + printf("Too many tests!\n\n"); + status = 1; + } + + return status; +} diff --git a/source/kit_test/test.h b/source/kit_test/test.h index fdbfbdc..4dc7aac 100644 --- a/source/kit_test/test.h +++ b/source/kit_test/test.h @@ -79,20 +79,17 @@ extern kit_tests_list_t kit_tests_list; # endif #endif +void kit_test_register(char const *name, kit_test_run_fn fn); + #define KIT_TEST(name) \ static void KIT_TEST_CONCAT3_(kit_test_run_, __LINE__, \ KIT_TEST_FILE)(int, \ kit_test_report_fn); \ KIT_TEST_ON_START_( \ KIT_TEST_CONCAT3_(kit_test_case_, __LINE__, KIT_TEST_FILE)) { \ - int n = kit_tests_list.size; \ - if (n < KIT_TESTS_SIZE_LIMIT) { \ - kit_tests_list.size++; \ - kit_tests_list.tests[n].test_fn = KIT_TEST_CONCAT3_( \ - kit_test_run_, __LINE__, KIT_TEST_FILE); \ - strcpy(kit_tests_list.tests[n].test_name, name); \ - kit_tests_list.tests[n].assertions = 0; \ - } \ + kit_test_register( \ + name, \ + KIT_TEST_CONCAT3_(kit_test_run_, __LINE__, KIT_TEST_FILE)); \ } \ static void KIT_TEST_CONCAT3_(kit_test_run_, __LINE__, \ KIT_TEST_FILE)( \ @@ -108,6 +105,7 @@ int kit_run_tests(int argc, char **argv); # define TEST KIT_TEST # define REQUIRE KIT_REQUIRE +# define test_register kit_test_register # define run_tests kit_run_tests #endif diff --git a/source/test/CMakeLists.txt b/source/test/CMakeLists.txt index 740981e..4435be1 100644 --- a/source/test/CMakeLists.txt +++ b/source/test/CMakeLists.txt @@ -1 +1,2 @@ add_subdirectory(unittests) +add_subdirectory(programs) diff --git a/source/test/programs/CMakeLists.txt b/source/test/programs/CMakeLists.txt new file mode 100644 index 0000000..4fd3660 --- /dev/null +++ b/source/test/programs/CMakeLists.txt @@ -0,0 +1,21 @@ +if(KIT_ENABLE_TESTING) + add_executable(too_many_tests too_many_tests.c) + target_link_libraries(too_many_tests ${KIT_TEST_LIBRARY}) + add_test( + NAME too_many_tests_test + COMMAND too_many_tests) + set_tests_properties( + too_many_tests_test + PROPERTIES + TIMEOUT "30") + + add_executable(too_many_assertions too_many_assertions.c) + target_link_libraries(too_many_assertions ${KIT_TEST_LIBRARY}) + add_test( + NAME too_many_assertions_test + COMMAND too_many_assertions) + set_tests_properties( + too_many_assertions_test + PROPERTIES + TIMEOUT "30") +endif() diff --git a/source/test/programs/too_many_assertions.c b/source/test/programs/too_many_assertions.c new file mode 100644 index 0000000..846970f --- /dev/null +++ b/source/test/programs/too_many_assertions.c @@ -0,0 +1,12 @@ +#include "../../kit_test/test.h" + +TEST("foo") { + for (int i = 0; i <= KIT_TEST_ASSERTIONS_LIMIT; i++) REQUIRE(1); +} + +int main(int argc, char **argv) { + if (run_tests(argc, argv) != 1) + return 1; + + return 0; +} diff --git a/source/test/programs/too_many_tests.c b/source/test/programs/too_many_tests.c new file mode 100644 index 0000000..9893e84 --- /dev/null +++ b/source/test/programs/too_many_tests.c @@ -0,0 +1,13 @@ +#include "../../kit_test/test.h" + +void bar(int index, kit_test_report_fn report) { } + +int main(int argc, char **argv) { + for (int i = 0; i <= KIT_TESTS_SIZE_LIMIT; i++) + test_register("foo", bar); + + if (run_tests(argc, argv) != 1) + return 1; + + return 0; +} diff --git a/source/test/unittests/CMakeLists.txt b/source/test/unittests/CMakeLists.txt index 37f7dbb..674f442 100644 --- a/source/test/unittests/CMakeLists.txt +++ b/source/test/unittests/CMakeLists.txt @@ -1,6 +1,6 @@ target_sources( ${KIT_TEST_SUITE} PRIVATE - async_function.test.c main.test.c string_ref.test.c - array_ref.test.c input_stream.test.c lower_bound.test.c + async_function.test.c test_duration.test.c main.test.c + string_ref.test.c array_ref.test.c input_stream.test.c lower_bound.test.c input_buffer.test.c dynamic_array.test.c) diff --git a/source/test/unittests/test_duration.test.c b/source/test/unittests/test_duration.test.c new file mode 100644 index 0000000..6de6c2e --- /dev/null +++ b/source/test/unittests/test_duration.test.c @@ -0,0 +1,18 @@ +#define KIT_TEST_FILE test_duration +#include "../../kit_test/test.h" + +#ifdef _WIN32 +# include +static void kit_sleep(int ms) { + Sleep(ms); +} +#else +# include +static void kit_sleep(int ms) { + usleep(ms * 1000); +} +#endif + +TEST("test duration") { + kit_sleep(100); +} -- cgit v1.2.3