From dbcea23295b641f06a22774fb6f39b63e3714ff2 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Sat, 10 Jun 2023 17:44:42 -0700 Subject: [PATCH 1/9] brand new scrutiny --- .gitignore | 1 + build.sh | 34 +- examples/unit_tests.c | 116 +---- scrutiny/scrutiny.c | 970 ++++-------------------------------------- scrutiny/scrutiny.h | 632 +++------------------------ 5 files changed, 205 insertions(+), 1548 deletions(-) diff --git a/.gitignore b/.gitignore index 96de30a..4caafea 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,4 @@ examples/a.out build/scrutiny.a build/scrutiny.o +build diff --git a/build.sh b/build.sh index fab9343..9cfd84b 100755 --- a/build.sh +++ b/build.sh @@ -1,6 +1,34 @@ #!/usr/bin/bash -mkdir -p build/ -gcc -Wall -Wextra -c scrutiny/scrutiny.c -o build/scrutiny.o -ar rcs build/scrutiny.a build/scrutiny.o +# script assumes that the basename of the current directory (repository root) +# is the same name as the folder containing the projects source files. + +PROJECT_NAME="$(basename $(pwd))" +SOURCE_FILES=$(find "./$PROJECT_NAME/" -name "*.c") +HEADER_FILES=$(find "./$PROJECT_NAME/" -name "*.h") +HEADER_LIST="" + +for HEADER in $HEADER_FILES; do + HEADER_LIST="$HEADER_LIST $HEADER" +done + +mkdir build -p + +for FILE in $SOURCE_FILES; do + gcc -Wall -Wextra -c $FILE -o "build/$(basename $FILE).o" + + if [ "$?" != "0" ]; then + exit 1 + fi +done + +tar --create --file "build/$PROJECT_NAME-headers.tar" $HEADER_LIST + +OBJECT_FILES=$(find "./build/" -name "*.o" -printf "%p ") + +ar rcs "build/$PROJECT_NAME.a" $OBJECT_FILES + +if [ "$?" != "0" ]; then + exit 1 +fi diff --git a/examples/unit_tests.c b/examples/unit_tests.c index d03888a..74d9aa1 100755 --- a/examples/unit_tests.c +++ b/examples/unit_tests.c @@ -1,107 +1,29 @@ +#include #include "../scrutiny/scrutiny.h" -/* This macro expands to void. */ -SCRUTINY_UNIT_TEST add_test(void) -{ - int a = 3; - int b = 5; +SCRUTINY_UNIT_TEST(addition_test) { + int a = 2; + int b = 3; - /* Assert that a does not equal b. */ - scrutiny_assert_false(a == b); - - /* Asserts only document the failiure, they wont terminate execution. */ - - /* - * Assert that a + b is 8, scrutiny allows you to make more than one - * assertion in the same test, each assert is a "test case" and each given - * function is a "unit test". Scrutiny reports both in output. - */ - - scrutiny_assert_equal_int(a + b, 8); -} - -SCRUTINY_UNIT_TEST increment_test(void) -{ - size_t limit = 128; - - /* Because scrutiny allows for multiple asserts, you can run them in a loop. */ - for (size_t i = 0; i < limit; i++) - scrutiny_assert_false(limit == i); -} - -SCRUTINY_UNIT_TEST not_equal_test(void) -{ - /* - * Scrutiny can make equality assertion on arrays as well if given the - * length to compare to. - */ - - int arr1[] = { 1, 2, 3 }; - int arr2[] = { 1, 4, 9 }; - - /* - * We've seen alot of equality assertions, so how about we assert that the - * expected value is not equal to the actual value. - */ - - scrutiny_assert_not_equal_array(arr1, arr2, sizeof(int), 3); -} - -/* - * For this next bit we need to create a struct and custom comparison. - */ - -struct _MyStruct { - int value; - bool unequal; -}; - -typedef struct _MyStruct MyStruct; - -Scrutiny_ComparisonResult compare_my_struct(MyStruct* left, MyStruct* right) { - if (left->unequal || right->unequal) { - return SCRUTINY_UNEQUAL; - } - - if (left->value > right->value) { - return SCRUTINY_GREATOR_THAN; - } - - if (left->value < right->value) { - return SCRUTINY_LESS_THAN; - } - - return SCRUTINY_EQUAL; + scrutiny_assert_greater_than(b, a); + scrutiny_assert_less_than(a, b); + scrutiny_assert_no_greater_than(a, b); + scrutiny_assert_equal(5, a + b); } -SCRUTINY_UNIT_TEST custom_compare_test() { - MyStruct a = { .value = 3, .unequal = false }; - MyStruct b = { .value = 0, .unequal = false }; +SCRUTINY_UNIT_TEST(subtraction_test) { + int a = 2; + int b = 3; - scrutiny_assert_greator_than_struct(&a, &b, (Scrutiny_CompareFunction)compare_my_struct); - - a.unequal = true; - - scrutiny_assert_not_equal_struct(&a, &b, (Scrutiny_CompareFunction)compare_my_struct); + scrutiny_assert_equal(0, a - b); } -int main() -{ - Scrutiny_UnitTest scrutiny_unit_tests[] = - { - add_test, /* Pointer to our unit test. */ - increment_test, /* Another test. */ - not_equal_test, - NULL /* End the list. */ +int main() { + scrutiny_test_t tests[] = { + subtraction_test, + addition_test, + NULL }; - /* Runs all tests until terminating NULL pointer. */ - scrutiny_run_tests(scrutiny_unit_tests); - - /* Outputs test results to standard out. */ - scrutiny_output_test_results(stdout); - - /* Outputs easily parsable test results to a file. */ - scrutiny_output_test_results_parsable(fopen("out.txt", "w")); -} - + scrutiny_run_tests(tests); +} \ No newline at end of file diff --git a/scrutiny/scrutiny.c b/scrutiny/scrutiny.c index e81bb6a..f7dcc0a 100755 --- a/scrutiny/scrutiny.c +++ b/scrutiny/scrutiny.c @@ -1,885 +1,93 @@ -/* - * Copyright (c) 2023 Evan Overman (https://an-prata.it). Licensed under the MIT License. - * See LICENSE file in repository root for complete license text. - */ +// Copyright (c) 2023 Evan Overman (https://an-prata.it). Licensed under the MIT License. +// See LICENSE file in repository root for complete license text. +#include +#include #include "scrutiny.h" -#include -#define SCRUTINY_TEXT_NORMAL "\033[0m" -#define SCRUTINY_TEXT_BOLD "\033[1m" -#define SCRUTINY_TEXT_ITALIC "\033[3m" -#define SCRUTINY_TEXT_GREEN "\033[0;32m" -#define SCRUTINY_TEXT_BLUE "\033[0;44m" -#define SCRUTINY_TEXT_RED "\033[0;31m" - -#define assert_unsigned_generic(operator, expected, actual, file, function, line) test_file_expand_and_add(file); \ - if (!(expected operator actual)) { \ - succeeded_test_contract_and_remove(function); \ - failed_test_expand_and_add(function); \ - failed_test_print_failure_unsigned_integer(expected, actual, file, function, line, __func__); \ - return; \ - }\ - succeeded_test_expand_and_add(function) - -#define assert_signed_generic(operator, expected, actual, file, function, line) test_file_expand_and_add(file); \ - if (!(expected operator actual)) { \ - succeeded_test_contract_and_remove(function); \ - failed_test_expand_and_add(function); \ - failed_test_print_failure_signed_integer(expected, actual, file, function, line, __func__); \ - return; \ - }\ - succeeded_test_expand_and_add(function) - -#define assert_floating_generic(operator, expected, actual, file, function, line) test_file_expand_and_add(file); \ - if (!(expected operator actual)) { \ - succeeded_test_contract_and_remove(function); \ - failed_test_expand_and_add(function); \ - failed_test_print_failure_floating(expected, actual, file, function, line, __func__); \ - return; \ - }\ - succeeded_test_expand_and_add(function) - -typedef struct _InProgressAverage InProgressAverage; - -struct _InProgressAverage { - size_t divisor; - Clock running_total; -}; - -static Scrutiny_TestResults* test_results = NULL; -static Scrutiny_BenchmarkResults* benchmark_results = NULL; - -static bool compare_null_terminated_strings(const char* str0, const char* str1) { - for (size_t i = 0;; i++) { - if (str0[i] == '\0' && str1[i] == '\0') - return true; - if (str0[i] == '\0' && str1[i] == '\0') - return false; - if (str0[i] != str1[i]) - return false; - } -} - -static void succeeded_test_expand_and_add(const char* succeeded_test) { - if (test_results == NULL) - return; - - test_results->passed_cases++; - - for (size_t i = 0; i < test_results->passed_tests; i++) - if (compare_null_terminated_strings(test_results->passed_test_names[i], succeeded_test)) - return; - - /* If the test function has failed previously dont add it to the succeeded list. */ - for (size_t i = 0; i < test_results->failed_tests; i++) - if (compare_null_terminated_strings(test_results->failed_test_names[i], succeeded_test)) - return; - - test_results->passed_tests++; - test_results->passed_test_names = reallocarray(test_results->passed_test_names, test_results->passed_tests, sizeof(char*)); - test_results->passed_test_names[test_results->passed_tests - 1] = succeeded_test; -} - -static void succeeded_test_contract_and_remove(const char* test) { - if (test_results == NULL) - return; - - for (size_t i = 0; i < test_results->passed_tests; i++) { - if (compare_null_terminated_strings(test_results->passed_test_names[i], test)) { - if (i != test_results->passed_tests - 1) - test_results->passed_test_names[i] = test_results->passed_test_names[test_results->passed_tests - 1]; - - test_results->passed_tests--; - return; - } - } -} - -static void failed_test_expand_and_add(const char* failed_test) { - if (test_results == NULL) - return; - - test_results->failed_cases++; - - for (size_t i = 0; i < test_results->failed_tests; i++) - if (compare_null_terminated_strings(test_results->failed_test_names[i], failed_test)) - return; - - test_results->failed_tests++; - test_results->failed_test_names = reallocarray(test_results->failed_test_names, test_results->failed_tests, sizeof(char*)); - test_results->failed_test_names[test_results->failed_tests - 1] = failed_test; -} - -static void test_file_expand_and_add(const char* test_file) { - if (test_results == NULL) - return; - - for (size_t i = 0; i < test_results->files; i++) - if (compare_null_terminated_strings(test_results->file_names[i], test_file)) - return; - - test_results->files++; - test_results->file_names = reallocarray(test_results->file_names, test_results->files, sizeof(char*)); - test_results->file_names[test_results->files - 1] = test_file; -} - -static void benchmark_run_expand_and_add(const char* name, const char* file, Clock time) { - benchmark_results->benchmarks++; - benchmark_results->benchmark_names = reallocarray(benchmark_results->benchmark_names, benchmark_results->benchmarks, sizeof(char*)); - benchmark_results->benchmark_times = reallocarray(benchmark_results->benchmark_times, benchmark_results->benchmarks, sizeof(char*)); - benchmark_results->file_names = reallocarray(benchmark_results->file_names, benchmark_results->benchmarks, sizeof(char*)); - benchmark_results->benchmark_names[benchmark_results->benchmarks - 1] = name; - benchmark_results->benchmark_times[benchmark_results->benchmarks - 1] = time; - benchmark_results->file_names[benchmark_results->benchmarks - 1] = file; -} - -static void failed_test_print_failure(const char* expected, const char* actual, const char* file, const char* function, size_t line, const char* assert) { - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, assert, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, assert, line); - - printf("\tExpected: %s\n", expected); - printf("\tActual: %s\n", actual); - - if (test_results == NULL) - exit(EXIT_FAILURE); -} - -static void failed_test_print_failure_unsigned_integer(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line, const char* assert) { - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, assert, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, assert, line); - - printf("\tExpected: %zu\n", expected); - printf("\tActual: %zu\n", actual); - - if (test_results == NULL) - exit(EXIT_FAILURE); -} - -static void failed_test_print_failure_signed_integer(int64_t expected, int64_t actual, const char* file, const char* function, size_t line, const char* assert) { - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, assert, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, assert, line); - - printf("\tExpected: %zi\n", expected); - printf("\tActual: %zi\n", actual); - - if (test_results == NULL) - exit(EXIT_FAILURE); -} - -static void failed_test_print_failure_floating(long double expected, long double actual, const char* file, const char* function, size_t line, const char* assert) { - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, assert, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, assert, line); - - printf("\tExpected: %Lf\n", expected); - printf("\tActual: %Lf\n", actual); - - if (test_results == NULL) - exit(EXIT_FAILURE); -} - -#define ENUM_VARIANT_STRING_RETURN(VARIANT) \ -case VARIANT: \ - return "VARIANT" - -const char* scrutiny_comparison_result_get_name(Scrutiny_ComparisonResult comp_result) { - switch (comp_result) { - ENUM_VARIANT_STRING_RETURN(SCRUTINY_GREATOR_THAN); - ENUM_VARIANT_STRING_RETURN(SCRUTINY_EQUAL); - ENUM_VARIANT_STRING_RETURN(SCRUTINY_LESS_THAN); - ENUM_VARIANT_STRING_RETURN(SCRUTINY_UNEQUAL); - ENUM_VARIANT_STRING_RETURN(SCRUTINY_COMPARISON_FAILURE); - } -} - -void scrutiny_run_tests(Scrutiny_UnitTest* scrutiny_unit_tests) { - test_results = malloc(sizeof(scrutiny_get_test_results)); - memset(test_results, 0, sizeof(scrutiny_get_test_results)); - - for (size_t test = 0; scrutiny_unit_tests[test] != NULL; test++) - scrutiny_unit_tests[test](); -} - -void scrutiny_run_benchmarks(Scrutiny_Benchmark* scrutiny_benchmarks) { - benchmark_results = malloc(sizeof *benchmark_results); - memset(benchmark_results, 0, sizeof *benchmark_results); - - for (size_t benchmark = 0; scrutiny_benchmarks[benchmark] != NULL; benchmark++) - scrutiny_benchmarks[benchmark](); -} - -void scrutiny_run_benchmarks_n_times(Scrutiny_Benchmark* scrutiny_benchmarks, size_t n) { - benchmark_results = malloc(sizeof *benchmark_results); - memset(benchmark_results, 0, sizeof *benchmark_results); - - for (size_t benchmark = 0; scrutiny_benchmarks[benchmark] != NULL; benchmark++) - for (size_t i = 0; i < n; i++) - scrutiny_benchmarks[benchmark](); -} - -Scrutiny_TestResults* scrutiny_get_test_results(void) { - return test_results; -} - -Scrutiny_BenchmarkResults* scrutiny_get_benchmark_results(void) { - return benchmark_results; +#define TEXT_NORMAL "\033[0m" +#define TEXT_BOLD "\033[1m" +#define TEXT_ITALIC "\033[3m" +#define TEXT_GREEN "\033[0;32m" +#define TEXT_BLUE "\033[0;34m" +#define TEXT_RED "\033[0;31m" + +static void _scrutiny_run_tests(scrutiny_test_t* tests, bool with_stats) { + scrutiny_test_run_t test_run = { + .previous_function = NULL, + .current_test_result = SCRUTINY_SUCCESS, + + .asserts_passed = 0, + .asserts_failed = 0, + + .tests_passed = 0, + .tests_failed = 0, + }; + + for (unsigned int i = 0; tests[i]; i++) { + test_run.current_test_result = SCRUTINY_SUCCESS; + tests[i](&test_run); + + if (test_run.current_test_result == SCRUTINY_FAILURE) { + test_run.tests_failed++; + printf("(" TEXT_RED "x" TEXT_NORMAL ") test failed: " TEXT_BLUE TEXT_ITALIC "%s\n" TEXT_NORMAL, test_run.previous_function); + } else { + test_run.tests_passed++; + printf("(" TEXT_GREEN "" TEXT_NORMAL ") test passed: " TEXT_BLUE TEXT_ITALIC "%s\n" TEXT_NORMAL, test_run.previous_function); + } + } + + if (!with_stats) { + if (test_run.asserts_failed > 0) { + exit(EXIT_FAILURE); + } + + exit(EXIT_SUCCESS); + } + + double percent_tests_passed = 100.0 * (double)test_run.tests_passed / (double)(test_run.tests_failed + test_run.tests_passed); + double percent_asserts_passed = 100.0 * (double)test_run.asserts_passed / (double)(test_run.asserts_failed + test_run.asserts_passed); + + printf("\n\nscrutiny made %zu assertions from %zu tests\n", test_run.asserts_failed + test_run.asserts_passed, test_run.tests_failed + test_run.tests_passed); + + if (test_run.asserts_passed > 0) { + printf("\n(" TEXT_GREEN "" TEXT_NORMAL ") %zu of %zu tests passed (%2.1f%%)\n", test_run.tests_passed, test_run.tests_failed + test_run.tests_passed, percent_tests_passed); + printf("(" TEXT_GREEN "" TEXT_NORMAL ") %zu of %zu assertions passed (%2.1f%%)\n", test_run.asserts_passed, test_run.asserts_failed + test_run.asserts_passed, percent_asserts_passed); + } + + if (test_run.asserts_failed > 0) { + printf("\n(" TEXT_RED "x" TEXT_NORMAL ") %zu of %zu tests failed (%2.1f%%)\n", test_run.tests_failed, test_run.tests_failed + test_run.tests_passed, 100.0 - percent_tests_passed); + printf("(" TEXT_RED "x" TEXT_NORMAL ") %zu of %zu assertions failed (%2.1f%%)\n", test_run.asserts_failed, test_run.asserts_failed + test_run.asserts_passed, 100.0 - percent_asserts_passed); + exit(EXIT_FAILURE); + } + + exit(EXIT_SUCCESS); +} + +void scrutiny_run_tests(scrutiny_test_t* tests) { + _scrutiny_run_tests(tests, false); +} + +void scrutiny_run_tests_with_stats(scrutiny_test_t* tests) { + _scrutiny_run_tests(tests, true); +} + +bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line) { + if (test_run->previous_function != function) { + if (!succeeded && test_run->previous_function) { + printf("\n"); + } + + test_run->previous_function = function; + } + + if (!succeeded) { + test_run->current_test_result = SCRUTINY_FAILURE; + test_run->asserts_failed++; + printf(TEXT_RED TEXT_BOLD "ASSERT FAILED " TEXT_NORMAL TEXT_ITALIC "%s(%s) " TEXT_NORMAL ": " TEXT_ITALIC "line %zu " TEXT_NORMAL "of " TEXT_ITALIC "%s " TEXT_NORMAL "in " TEXT_BLUE TEXT_ITALIC "%s\n" TEXT_NORMAL, assert, condition, line, file, function); + } else { + test_run->asserts_passed++; + } + + return succeeded; } - -Scrutiny_Error scrutiny_output_test_results(File* out_file) { - if (out_file == NULL) - return SCRUTINY_ERROR_INVALID_ARGUMENT; - - long double percent_passed = ((long double)test_results->passed_tests / (long double)(test_results->passed_tests + test_results->failed_tests)) * 100.0; - long double percent_failed = ((long double)test_results->failed_tests / (long double)(test_results->passed_tests + test_results->failed_tests)) * 100.0; - long double percent_cases_passed = ((long double)test_results->passed_cases / (long double)(test_results->passed_cases + test_results->failed_cases)) * 100.0; - long double percent_cases_failed = ((long double)test_results->failed_cases / (long double)(test_results->passed_cases + test_results->failed_cases)) * 100.0; - - fprintf(out_file, "\nScrutiny ran %zu test cases, from %zu tests, in %zu files.\n\n", test_results->failed_cases + test_results->passed_cases, test_results->passed_tests + test_results->failed_tests, test_results->files); - - if (test_results->failed_tests > 0) - fprintf(out_file, "Failed tests:\n"); - - for (size_t i = 0; i < test_results->failed_tests; i++) - fprintf(out_file, SCRUTINY_TEXT_ITALIC "\t%s\n" SCRUTINY_TEXT_NORMAL, test_results->failed_test_names[i]); - - if (test_results->passed_cases > 0) { - fprintf(out_file, "\n(" SCRUTINY_TEXT_GREEN "" SCRUTINY_TEXT_NORMAL ") %zu of %zu tests passed (%2.1Lf%%).", test_results->passed_tests, test_results->passed_tests + test_results->failed_tests, percent_passed); - fprintf(out_file, "\t(" SCRUTINY_TEXT_GREEN "" SCRUTINY_TEXT_NORMAL ") %zu of %zu test cases passed (%2.1Lf%%).\n", test_results->passed_cases, test_results->passed_cases + test_results->failed_cases, percent_cases_passed); - } - - if (test_results->failed_cases > 0) { - fprintf(out_file, "(" SCRUTINY_TEXT_RED "x" SCRUTINY_TEXT_NORMAL ") %zu of %zu tests failed (%2.1Lf%%).", test_results->failed_tests, test_results->passed_tests + test_results->passed_tests, percent_failed); - fprintf(out_file, "\t(" SCRUTINY_TEXT_RED "x" SCRUTINY_TEXT_NORMAL ") %zu of %zu test cases failed (%2.1Lf%%).\n", test_results->failed_cases, test_results->passed_cases + test_results->failed_cases, percent_cases_failed); - } - - fflush(out_file); - - if (ferror(out_file)) - return SCRUTINY_ERROR_COULDNT_WRITE_TO_FILE; - - return SCRUTINY_ERROR_NONE; -} - -Scrutiny_Error scrutiny_output_benchmark_results(File* out_file) { - if (out_file == NULL) - return SCRUTINY_ERROR_INVALID_ARGUMENT; - - size_t unique_benchmarks = 0; - InProgressAverage* average_times = NULL; - const char** unique_benchmarks_names = NULL; - - for (size_t benchmark = 0; benchmark < benchmark_results->benchmarks; benchmark++) { - bool unique = true; - size_t index_non_unique; - - for (index_non_unique = 0; index_non_unique < unique_benchmarks; index_non_unique++) { - if (compare_null_terminated_strings(benchmark_results->benchmark_names[benchmark], unique_benchmarks_names[index_non_unique])) { - unique = false; - break; - } - } - - if (unique) { - unique_benchmarks++; - unique_benchmarks_names = reallocarray(unique_benchmarks_names, unique_benchmarks, sizeof(char*)); - average_times = reallocarray(average_times, unique_benchmarks, sizeof(InProgressAverage)); - unique_benchmarks_names[unique_benchmarks - 1] = benchmark_results->benchmark_names[benchmark]; - average_times[unique_benchmarks - 1].running_total = benchmark_results->benchmark_times[benchmark]; - average_times[unique_benchmarks - 1].divisor = 1; - continue; - } - - average_times[index_non_unique].running_total += benchmark_results->benchmark_times[benchmark]; - average_times[index_non_unique].divisor++; - } - - fprintf(out_file, "Scrutiny ran %zu unique benchmarks for a total of %zu benchmark runs.\n\n", unique_benchmarks, benchmark_results->benchmarks); - - for (size_t i = 0; i < unique_benchmarks; i++) { - Clock average_time = average_times[i].running_total / average_times[i].divisor; - long double average_seconds = (long double)average_time / (long double)CLOCKS_PER_SEC; - - if (average_seconds < 0.1) - fprintf(out_file, SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL ": %.1Lf ms (%.1Lf per/s)\n", unique_benchmarks_names[i], average_seconds * 1000, 1.0L / average_seconds); - else - fprintf(out_file, SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL ": %.3Lf s (%.1Lf per/s)\n", unique_benchmarks_names[i], average_seconds, 1.0L / average_seconds); - } - - if (ferror(out_file)) - return SCRUTINY_ERROR_COULDNT_WRITE_TO_FILE; - - return SCRUTINY_ERROR_NONE; -} - -Scrutiny_Error scrutiny_output_test_results_parsable(File* out_file) { - if (out_file == NULL) - return SCRUTINY_ERROR_INVALID_ARGUMENT; - - long double percent_passed = ((long double)test_results->passed_tests / (long double)(test_results->passed_tests + test_results->failed_tests)) * 100.0; - long double percent_failed = ((long double)test_results->failed_tests / (long double)(test_results->passed_tests + test_results->failed_tests)) * 100.0; - long double percent_cases_passed = ((long double)test_results->passed_cases / (long double)(test_results->passed_cases + test_results->failed_cases)) * 100.0; - long double percent_cases_failed = ((long double)test_results->failed_cases / (long double)(test_results->passed_cases + test_results->failed_cases)) * 100.0; - - fprintf(out_file, "ran %zu cases, %zu tests, %zu files\n\n", test_results->failed_cases + test_results->passed_cases, test_results->failed_tests + test_results->passed_tests, test_results->files); - - fprintf(out_file, "cases:\n"); - fprintf(out_file, "%zu/%zu passed (%2.1Lf%%)\n", test_results->passed_cases, test_results->passed_cases + test_results->failed_cases, percent_cases_passed); - fprintf(out_file, "%zu/%zu failed (%2.1Lf%%)\n\n", test_results->failed_cases, test_results->failed_cases + test_results->passed_cases, percent_cases_failed); - - fprintf(out_file, "tests:\n"); - fprintf(out_file, "%zu/%zu passed (%2.1Lf%%)\n", test_results->passed_tests, test_results->passed_tests+ test_results->failed_tests, percent_passed); - fprintf(out_file, "%zu/%zu failed (%2.1Lf%%)\n\n", test_results->failed_tests, test_results->passed_tests+ test_results->failed_tests, percent_failed); - - fprintf(out_file, "failed tests:\n"); - - for (size_t i = 0; i < test_results->failed_tests; i++) - fprintf(out_file, "%s\n", test_results->failed_test_names[i]); - - fflush(out_file); - - if (ferror(out_file)) - return SCRUTINY_ERROR_COULDNT_WRITE_TO_FILE; - - return SCRUTINY_ERROR_NONE; -} - -Scrutiny_Error scrutiny_output_benchmark_results_parsable(File* file) { - if (file == NULL) - return SCRUTINY_ERROR_INVALID_ARGUMENT; - - for (size_t i = 0; i < benchmark_results->benchmarks; i++) - fprintf(file, "%s:%Lf\n", benchmark_results->benchmark_names[i], (long double)benchmark_results->benchmark_times[i] / (long double)CLOCKS_PER_SEC); - - if (ferror(file)) - return SCRUTINY_ERROR_COULDNT_WRITE_TO_FILE; - - return SCRUTINY_ERROR_NONE; -} - -void scrutiny_clear_results(void) { - if (test_results != NULL) { - free(test_results->passed_test_names); - free(test_results->failed_test_names); - free(test_results->file_names); - free(test_results); - } - - if (benchmark_results != NULL) { - free(benchmark_results->benchmark_names); - free(benchmark_results->benchmark_times); - free(benchmark_results->file_names); - free(benchmark_results); - } - - test_results = NULL; - benchmark_results = NULL; -} - -void scrutiny_report_assert_pass(const char* file, const char* function) { - if (test_results == NULL) - return; - - test_file_expand_and_add(file); - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_fail(const char* file, const char* function, size_t line) { - if (test_results == NULL) - { - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - exit(EXIT_FAILURE); - } - - test_file_expand_and_add(file); - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); -} - -void scrutiny_report_assert_true(bool expression, const char* file, const char* function, size_t line) { - if (test_results == NULL && !expression) { - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - exit(EXIT_FAILURE); - } else if (test_results == NULL) { - return; - } - - test_file_expand_and_add(file); - - if (!expression) { - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); - return; - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_false(bool expression, const char* file, const char* function, size_t line) { - if (test_results == NULL && expression) { - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - exit(EXIT_FAILURE); - } else if (test_results == NULL) { - return; - } - - test_file_expand_and_add(file); - - if (expression) { - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); - return; - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_equal_ptr_data(void* expected, void* actual, size_t struct_size, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - uint8_t* expected_bytes = (uint8_t*)expected; - uint8_t* actual_bytes = (uint8_t*)actual; - - for (size_t i = 0; i < struct_size; i++) { - if (expected_bytes[i] != actual_bytes[i]) { - if (test_results == NULL) { - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - printf("\tExpected: %u at byte %zu\n", expected_bytes[i], i); - printf("\tActual: %u\n", actual_bytes[i]); - exit(EXIT_FAILURE); - } - - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); - printf("\tExpected: %u at byte %zu\n", expected_bytes[i], i); - printf("\tActual: %u\n", actual_bytes[i]); - return; - } - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_equal_array(void* expected, void* actual, size_t sizeof_type, size_t array_length, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - uint8_t* expected_bytes = (uint8_t*)expected; - uint8_t* actual_bytes = (uint8_t*)actual; - - for (size_t byte = 0; byte < sizeof_type * array_length; byte++) { - if (expected_bytes[byte] != actual_bytes[byte]) { - if (test_results == NULL) { - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - printf("\tDifference at index: %zu\n", byte / sizeof_type); - exit(EXIT_FAILURE); - } - - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); - printf("\tDifference at index: %zu\n", byte / sizeof_type); - return; - } - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_equal_string(char* expected, char* actual, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - if (!compare_null_terminated_strings(expected, actual)) { - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - failed_test_print_failure(expected, actual, file, function, line, __func__); - return; - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_equal_non_terminated_string(char* expected, char* actual, size_t size, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - for (size_t i = 0; i < size; i++) { - if (expected[i] != actual[i]) { - if (test_results == NULL) { - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - printf("\tExpected: %c at index %zu\n", expected[i], i); - printf("\tActual: %c\n", actual[i]); - exit(EXIT_FAILURE); - } - - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); - printf("\tExpected: %c at index %zu\n", expected[i], i); - printf("\tActual: %c\n", actual[i]); - return; - } - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_not_equal_ptr_data(void* expected, void* actual, size_t struct_size, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - uint8_t* expected_bytes = (uint8_t*)expected; - uint8_t* actual_bytes = (uint8_t*)actual; - - for (size_t i = 0; i < struct_size; i++) { - if (expected_bytes[i] != actual_bytes[i]) { - succeeded_test_expand_and_add(function); - return; - } - } - - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); -} - -void scrutiny_report_assert_not_equal_array(void* expected, void* actual, size_t sizeof_type, size_t array_length, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - uint8_t* expected_bytes = (uint8_t*)expected; - uint8_t* actual_bytes = (uint8_t*)actual; - - for (size_t byte = 0; byte < sizeof_type * array_length; byte++) { - if (expected_bytes[byte] != actual_bytes[byte]) { - succeeded_test_expand_and_add(function); - return; - } - } - - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); -} - -void scrutiny_report_assert_not_equal_string(char* expected, char* actual, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - if (compare_null_terminated_strings(expected, actual)) { - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - failed_test_print_failure(expected, actual, file, function, line, __func__); - return; - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_not_equal_non_terminated_string(char* expected, char* actual, size_t size, const char* file, const char* function, size_t line) { - test_file_expand_and_add(file); - - for (size_t i = 0; i < size; i++) { - if (expected[i] != actual[i]) { - succeeded_test_expand_and_add(function); - return; - } - } - - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); -} - - -void scrutiny_report_assert_equal_char(char expected, char actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_short(short expected, short actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int(int expected, int actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_long(long expected, long actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_long_long(long long expected, long long actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_float(float expected, float actual, const char* file, const char* function, size_t line) { assert_floating_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_double(double expected, double actual, const char* file, const char* function, size_t line) { assert_floating_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_long_double(long double expected, long double actual, const char* file, const char* function, size_t line) { assert_floating_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line) { assert_signed_generic(==, expected, actual, file, function, line); } -void scrutiny_report_assert_equal_ptr(void* expected, void* actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(==, (uintptr_t)expected, (uintptr_t)actual, file, function, line); } - -void scrutiny_report_assert_not_equal_char(char expected, char actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_short(short expected, short actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int(int expected, int actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_long(long expected, long actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_long_long(long long expected, long long actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_float(float expected, float actual, const char* file, const char* function, size_t line) { assert_floating_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_double(double expected, double actual, const char* file, const char* function, size_t line) { assert_floating_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_long_double(long double expected, long double actual, const char* file, const char* function, size_t line) { assert_floating_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line) { assert_signed_generic(!=, expected, actual, file, function, line); } -void scrutiny_report_assert_not_equal_ptr(void* expected, void* actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(!=, (uintptr_t)expected, (uintptr_t)actual, file, function, line); } - -void scrutiny_report_assert_greater_than_char(char expected, char actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_short(short expected, short actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int(int expected, int actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_long(long expected, long actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_long_long(long long expected, long long actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_float(float expected, float actual, const char* file, const char* function, size_t line) { assert_floating_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_double(double expected, double actual, const char* file, const char* function, size_t line) { assert_floating_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_long_double(long double expected, long double actual, const char* file, const char* function, size_t line) { assert_floating_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line) { assert_signed_generic(>, expected, actual, file, function, line); } -void scrutiny_report_assert_greater_than_ptr(void* expected, void* actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(>, (uintptr_t)expected, (uintptr_t)actual, file, function, line); } - -void scrutiny_report_assert_less_than_char(char expected, char actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_short(short expected, short actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int(int expected, int actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_long(long expected, long actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_long_long(long long expected, long long actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_float(float expected, float actual, const char* file, const char* function, size_t line) { assert_floating_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_double(double expected, double actual, const char* file, const char* function, size_t line) { assert_floating_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_long_double(long double expected, long double actual, const char* file, const char* function, size_t line) { assert_floating_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line) { assert_signed_generic(<, expected, actual, file, function, line); } -void scrutiny_report_assert_less_than_ptr(void* expected, void* actual, const char* file, const char* function, size_t line) { assert_unsigned_generic(<, (uintptr_t)expected, (uintptr_t)actual, file, function, line); } - -/* - - if (!(expected operator actual)) { \ - succeeded_test_contract_and_remove(function); \ - failed_test_expand_and_add(function); \ - failed_test_print_failure_unsigned_integer(expected, actual, file, function, line, __func__); \ - return; \ - }\ - succeeded_test_expand_and_add(function) - - - - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, assert, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, assert, line); - - printf("\tExpected: %zu\n", expected); - printf("\tActual: %zu\n", actual); - - if (test_results == NULL) - exit(EXIT_FAILURE); -*/ - -#define struct_compare(expected, actual, comp_function, file, function, line, assert, success_variant) \ - Scrutiny_ComparisonResult result; \ - if ((result = comp_function(expected, actual)) != success_variant) { \ - succeeded_test_contract_and_remove(function); \ - failed_test_expand_and_add(function); \ - if (test_results == NULL) \ - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, assert, function, line); \ - else \ - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, assert, line); \ - printf("\tExpected: %s\n", scrutiny_comparison_result_get_name(success_variant)); \ - printf("\tActual: %s\n", scrutiny_comparison_result_get_name(result)); \ - if (test_results == NULL) \ - exit(EXIT_FAILURE); \ - return; \ - } \ - succeeded_test_expand_and_add(function); - -void scrutiny_report_assert_equal_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line) { - struct_compare(expected, actual, comp_function, file, function, line, __func__, SCRUTINY_EQUAL); -} - -void scrutiny_report_assert_not_equal_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line) { - Scrutiny_ComparisonResult result; - - if ((result = comp_function(expected, actual)) != SCRUTINY_UNEQUAL - || result != SCRUTINY_GREATOR_THAN - || result != SCRUTINY_LESS_THAN - ) { - succeeded_test_contract_and_remove(function); - failed_test_expand_and_add(function); - - if (test_results == NULL) - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nASSERTION FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed in " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, __func__, function, line); - else - printf(SCRUTINY_TEXT_RED SCRUTINY_TEXT_BOLD "\nTEST FAILED" SCRUTINY_TEXT_NORMAL " (%s): " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " failed " SCRUTINY_TEXT_ITALIC "%s" SCRUTINY_TEXT_NORMAL " on line %zu\n\n", file, function, __func__, line); \ - - printf("\tExpected: %s or %s or %s\n", - scrutiny_comparison_result_get_name(SCRUTINY_UNEQUAL), - scrutiny_comparison_result_get_name(SCRUTINY_GREATOR_THAN), - scrutiny_comparison_result_get_name(SCRUTINY_LESS_THAN) - ); - printf("\tActual: %s\n", scrutiny_comparison_result_get_name(result)); - - if (test_results == NULL) - exit(EXIT_FAILURE); - return; - } - - succeeded_test_expand_and_add(function); -} - -void scrutiny_report_assert_greator_than_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line) { - struct_compare(expected, actual, comp_function, file, function, line, __func__, SCRUTINY_GREATOR_THAN); -} - -void scrutiny_report_assert_less_than_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line) { - struct_compare(expected, actual, comp_function, file, function, line, __func__, SCRUTINY_LESS_THAN); -} - - -void scrutiny_report_benchmark_time(Clock time, const char* file, const char* function, size_t line) { - benchmark_run_expand_and_add(function, file, time); -} - diff --git a/scrutiny/scrutiny.h b/scrutiny/scrutiny.h index 0e48956..5d8f221 100755 --- a/scrutiny/scrutiny.h +++ b/scrutiny/scrutiny.h @@ -1,580 +1,78 @@ -/* - * Copyright (c) 2023 Evan Overman (https://an-prata.it). Licensed under the MIT License. - * See LICENSE file in repository root for complete license text. - */ +// Copyright (c) 2023 Evan Overman (https://an-prata.it). Licensed under the MIT License. +// See LICENSE file in repository root for complete license text. #ifndef SCRUTINY_H #define SCRUTINY_H -#include -#include -#include #include -#include - -#define SCRUTINY_VERSION_MAJOR 1 -#define SCRUTINY_VERSION_MINOR 3 -#define SCRUTINY_VERSION_PATCH 0 - -/* - * Defined for convinience and code clarity, beyond that these definitions - * serve no purpose. - */ - -#define SCRUTINY_UNIT_TEST void -#define SCRUTINY_BENCHMARK void - -/* - * This collection of macros serves only to simplify assert calls by - * automatically adding the __FILE__, __LINE__, and __func__ macros as - * arguments to the function call for easier debugging. - */ - -#define scrutiny_assert_pass() scrutiny_report_assert_pass(__FILE__, __func__) -#define scrutiny_assert_fail() scrutiny_report_assert_fail(__FILE__, __func__, __LINE__) -#define scrutiny_assert_true(expression) scrutiny_report_assert_true(expression, __FILE__, __func__, __LINE__) -#define scrutiny_assert_false(expression) scrutiny_report_assert_false(expression, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_equal_ptr_data(expected, actual, struct_size) scrutiny_report_assert_equal_ptr_data(expected, actual, struct_size, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_array(expected, actual, sizeof_type, array_length) scrutiny_report_assert_equal_array(expected, actual, sizeof_type, array_length, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_string(expected, actual) scrutiny_report_assert_equal_string(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_non_terminated_string(expected, actual, size) scrutiny_report_assert_equal_non_terminated_string(expected, actual, size, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_not_equal_ptr_data(expected, actual, struct_size) scrutiny_report_assert_not_equal_ptr_data(expected, actual, struct_size, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_array(expected, actual, sizeof_type, array_length) scrutiny_report_assert_not_equal_array(expected, actual, sizeof_type, array_length, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_string(expected, actual) scrutiny_report_assert_not_equal_string(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_non_terminated_string(expected, actual, size) scrutiny_report_assert_not_equal_non_terminated_string(expected, actual, size, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_equal_char(expected, actual) scrutiny_report_assert_equal_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_unsigned_char(expected, actual) scrutiny_report_assert_equal_unsigned_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_short(expected, actual) scrutiny_report_assert_equal_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int(expected, actual) scrutiny_report_assert_equal_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_long(expected, actual) scrutiny_report_assert_equal_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_long_long(expected, actual) scrutiny_report_assert_equal_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_unsigned_short(expected, actual) scrutiny_report_assert_equal_unsigned_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_unsigned_int(expected, actual) scrutiny_report_assert_equal_unsigned_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_unsigned_long(expected, actual) scrutiny_report_assert_equal_unsigned_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_unsigned_long_long(expected, actual) scrutiny_report_assert_equal_unsigned_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_float(expected, actual) scrutiny_report_assert_equal_float(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_double(expected, actual) scrutiny_report_assert_equal_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_long_double(expected, actual) scrutiny_report_assert_equal_long_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int8_t(expected, actual) scrutiny_report_assert_equal_int8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int16_t(expected, actual) scrutiny_report_assert_equal_int16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int32_t(expected, actual) scrutiny_report_assert_equal_int32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int64_t(expected, actual) scrutiny_report_assert_equal_int64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_fast8_t(expected, actual) scrutiny_report_assert_equal_int_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_fast16_t(expected, actual) scrutiny_report_assert_equal_int_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_fast32_t(expected, actual) scrutiny_report_assert_equal_int_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_fast64_t(expected, actual) scrutiny_report_assert_equal_int_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_least8_t(expected, actual) scrutiny_report_assert_equal_int_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_least16_t(expected, actual) scrutiny_report_assert_equal_int_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_least32_t(expected, actual) scrutiny_report_assert_equal_int_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_int_least64_t(expected, actual) scrutiny_report_assert_equal_int_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint8_t(expected, actual) scrutiny_report_assert_equal_uint8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint16_t(expected, actual) scrutiny_report_assert_equal_uint16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint32_t(expected, actual) scrutiny_report_assert_equal_uint32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint64_t(expected, actual) scrutiny_report_assert_equal_uint64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_fast8_t(expected, actual) scrutiny_report_assert_equal_uint_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_fast16_t(expected, actual) scrutiny_report_assert_equal_uint_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_fast32_t(expected, actual) scrutiny_report_assert_equal_uint_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_fast64_t(expected, actual) scrutiny_report_assert_equal_uint_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_least8_t(expected, actual) scrutiny_report_assert_equal_uint_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_least16_t(expected, actual) scrutiny_report_assert_equal_uint_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_least32_t(expected, actual) scrutiny_report_assert_equal_uint_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uint_least64_t(expected, actual) scrutiny_report_assert_equal_uint_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_intptr_t(expected, actual) scrutiny_report_assert_equal_intptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uintptr_t(expected, actual) scrutiny_report_assert_equal_uintptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_intmax_t(expected, actual) scrutiny_report_assert_equal_intmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_uintmax_t(expected, actual) scrutiny_report_assert_equal_uintmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_size_t(expected, actual) scrutiny_report_assert_equal_size_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_ssize_t(expected, actual) scrutiny_report_assert_equal_ssize_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_enum(expected, actual) scrutiny_report_assert_equal_enum(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal_ptr(expected, actual) scrutiny_report_assert_equal_ptr(expected, actual, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_not_equal_char(expected, actual) scrutiny_report_assert_not_equal_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_unsigned_char(expected, actual) scrutiny_report_assert_not_equal_unsigned_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_short(expected, actual) scrutiny_report_assert_not_equal_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int(expected, actual) scrutiny_report_assert_not_equal_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_long(expected, actual) scrutiny_report_assert_not_equal_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_long_long(expected, actual) scrutiny_report_assert_not_equal_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_unsigned_short(expected, actual) scrutiny_report_assert_not_equal_unsigned_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_unsigned_int(expected, actual) scrutiny_report_assert_not_equal_unsigned_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_unsigned_long(expected, actual) scrutiny_report_assert_not_equal_unsigned_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_unsigned_long_long(expected, actual) scrutiny_report_assert_not_equal_unsigned_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_float(expected, actual) scrutiny_report_assert_not_equal_float(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_double(expected, actual) scrutiny_report_assert_not_equal_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_long_double(expected, actual) scrutiny_report_assert_not_equal_long_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int8_t(expected, actual) scrutiny_report_assert_not_equal_int8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int16_t(expected, actual) scrutiny_report_assert_not_equal_int16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int32_t(expected, actual) scrutiny_report_assert_not_equal_int32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int64_t(expected, actual) scrutiny_report_assert_not_equal_int64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_fast8_t(expected, actual) scrutiny_report_assert_not_equal_int_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_fast16_t(expected, actual) scrutiny_report_assert_not_equal_int_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_fast32_t(expected, actual) scrutiny_report_assert_not_equal_int_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_fast64_t(expected, actual) scrutiny_report_assert_not_equal_int_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_least8_t(expected, actual) scrutiny_report_assert_not_equal_int_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_least16_t(expected, actual) scrutiny_report_assert_not_equal_int_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_least32_t(expected, actual) scrutiny_report_assert_not_equal_int_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_int_least64_t(expected, actual) scrutiny_report_assert_not_equal_int_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint8_t(expected, actual) scrutiny_report_assert_not_equal_uint8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint16_t(expected, actual) scrutiny_report_assert_not_equal_uint16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint32_t(expected, actual) scrutiny_report_assert_not_equal_uint32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint64_t(expected, actual) scrutiny_report_assert_not_equal_uint64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_fast8_t(expected, actual) scrutiny_report_assert_not_equal_uint_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_fast16_t(expected, actual) scrutiny_report_assert_not_equal_uint_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_fast32_t(expected, actual) scrutiny_report_assert_not_equal_uint_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_fast64_t(expected, actual) scrutiny_report_assert_not_equal_uint_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_least8_t(expected, actual) scrutiny_report_assert_not_equal_uint_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_least16_t(expected, actual) scrutiny_report_assert_not_equal_uint_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_least32_t(expected, actual) scrutiny_report_assert_not_equal_uint_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uint_least64_t(expected, actual) scrutiny_report_assert_not_equal_uint_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_intptr_t(expected, actual) scrutiny_report_assert_not_equal_intptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uintptr_t(expected, actual) scrutiny_report_assert_not_equal_uintptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_intmax_t(expected, actual) scrutiny_report_assert_not_equal_intmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_uintmax_t(expected, actual) scrutiny_report_assert_not_equal_uintmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_size_t(expected, actual) scrutiny_report_assert_not_equal_size_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_ssize_t(expected, actual) scrutiny_report_assert_not_equal_ssize_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_enum(expected, actual) scrutiny_report_assert_not_equal_enum(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_ptr(expected, actual) scrutiny_report_assert_not_equal_ptr(expected, actual, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_greater_than_char(expected, actual) scrutiny_report_assert_greater_than_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_unsigned_char(expected, actual) scrutiny_report_assert_greater_than_unsigned_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_short(expected, actual) scrutiny_report_assert_greater_than_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int(expected, actual) scrutiny_report_assert_greater_than_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_long(expected, actual) scrutiny_report_assert_greater_than_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_long_long(expected, actual) scrutiny_report_assert_greater_than_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_unsigned_short(expected, actual) scrutiny_report_assert_greater_than_unsigned_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_unsigned_int(expected, actual) scrutiny_report_assert_greater_than_unsigned_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_unsigned_long(expected, actual) scrutiny_report_assert_greater_than_unsigned_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_unsigned_long_long(expected, actual) scrutiny_report_assert_greater_than_unsigned_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_float(expected, actual) scrutiny_report_assert_greater_than_float(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_double(expected, actual) scrutiny_report_assert_greater_than_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_long_double(expected, actual) scrutiny_report_assert_greater_than_long_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int8_t(expected, actual) scrutiny_report_assert_greater_than_int8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int16_t(expected, actual) scrutiny_report_assert_greater_than_int16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int32_t(expected, actual) scrutiny_report_assert_greater_than_int32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int64_t(expected, actual) scrutiny_report_assert_greater_than_int64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_fast8_t(expected, actual) scrutiny_report_assert_greater_than_int_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_fast16_t(expected, actual) scrutiny_report_assert_greater_than_int_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_fast32_t(expected, actual) scrutiny_report_assert_greater_than_int_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_fast64_t(expected, actual) scrutiny_report_assert_greater_than_int_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_least8_t(expected, actual) scrutiny_report_assert_greater_than_int_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_least16_t(expected, actual) scrutiny_report_assert_greater_than_int_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_least32_t(expected, actual) scrutiny_report_assert_greater_than_int_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_int_least64_t(expected, actual) scrutiny_report_assert_greater_than_int_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint8_t(expected, actual) scrutiny_report_assert_greater_than_uint8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint16_t(expected, actual) scrutiny_report_assert_greater_than_uint16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint32_t(expected, actual) scrutiny_report_assert_greater_than_uint32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint64_t(expected, actual) scrutiny_report_assert_greater_than_uint64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_fast8_t(expected, actual) scrutiny_report_assert_greater_than_uint_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_fast16_t(expected, actual) scrutiny_report_assert_greater_than_uint_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_fast32_t(expected, actual) scrutiny_report_assert_greater_than_uint_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_fast64_t(expected, actual) scrutiny_report_assert_greater_than_uint_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_least8_t(expected, actual) scrutiny_report_assert_greater_than_uint_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_least16_t(expected, actual) scrutiny_report_assert_greater_than_uint_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_least32_t(expected, actual) scrutiny_report_assert_greater_than_uint_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uint_least64_t(expected, actual) scrutiny_report_assert_greater_than_uint_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_intptr_t(expected, actual) scrutiny_report_assert_greater_than_intptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uintptr_t(expected, actual) scrutiny_report_assert_greater_than_uintptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_intmax_t(expected, actual) scrutiny_report_assert_greater_than_intmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_uintmax_t(expected, actual) scrutiny_report_assert_greater_than_uintmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_size_t(expected, actual) scrutiny_report_assert_greater_than_size_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_ssize_t(expected, actual) scrutiny_report_assert_greater_than_ssize_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_enum(expected, actual) scrutiny_report_assert_greater_than_enum(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_ptr(expected, actual) scrutiny_report_assert_greater_than_ptr(expected, actual, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_less_than_char(expected, actual) scrutiny_report_assert_less_than_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_unsigned_char(expected, actual) scrutiny_report_assert_less_than_unsigned_char(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_short(expected, actual) scrutiny_report_assert_less_than_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int(expected, actual) scrutiny_report_assert_less_than_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_long(expected, actual) scrutiny_report_assert_less_than_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_long_long(expected, actual) scrutiny_report_assert_less_than_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_unsigned_short(expected, actual) scrutiny_report_assert_less_than_unsigned_short(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_unsigned_int(expected, actual) scrutiny_report_assert_less_than_unsigned_int(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_unsigned_long(expected, actual) scrutiny_report_assert_less_than_unsigned_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_unsigned_long_long(expected, actual) scrutiny_report_assert_less_than_unsigned_long_long(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_float(expected, actual) scrutiny_report_assert_less_than_float(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_double(expected, actual) scrutiny_report_assert_less_than_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_long_double(expected, actual) scrutiny_report_assert_less_than_long_double(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int8_t(expected, actual) scrutiny_report_assert_less_than_int8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int16_t(expected, actual) scrutiny_report_assert_less_than_int16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int32_t(expected, actual) scrutiny_report_assert_less_than_int32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int64_t(expected, actual) scrutiny_report_assert_less_than_int64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_fast8_t(expected, actual) scrutiny_report_assert_less_than_int_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_fast16_t(expected, actual) scrutiny_report_assert_less_than_int_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_fast32_t(expected, actual) scrutiny_report_assert_less_than_int_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_fast64_t(expected, actual) scrutiny_report_assert_less_than_int_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_least8_t(expected, actual) scrutiny_report_assert_less_than_int_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_least16_t(expected, actual) scrutiny_report_assert_less_than_int_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_least32_t(expected, actual) scrutiny_report_assert_less_than_int_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_int_least64_t(expected, actual) scrutiny_report_assert_less_than_int_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint8_t(expected, actual) scrutiny_report_assert_less_than_uint8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint16_t(expected, actual) scrutiny_report_assert_less_than_uint16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint32_t(expected, actual) scrutiny_report_assert_less_than_uint32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint64_t(expected, actual) scrutiny_report_assert_less_than_uint64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_fast8_t(expected, actual) scrutiny_report_assert_less_than_uint_fast8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_fast16_t(expected, actual) scrutiny_report_assert_less_than_uint_fast16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_fast32_t(expected, actual) scrutiny_report_assert_less_than_uint_fast32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_fast64_t(expected, actual) scrutiny_report_assert_less_than_uint_fast64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_least8_t(expected, actual) scrutiny_report_assert_less_than_uint_least8_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_least16_t(expected, actual) scrutiny_report_assert_less_than_uint_least16_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_least32_t(expected, actual) scrutiny_report_assert_less_than_uint_least32_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uint_least64_t(expected, actual) scrutiny_report_assert_less_than_uint_least64_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_intptr_t(expected, actual) scrutiny_report_assert_less_than_intptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uintptr_t(expected, actual) scrutiny_report_assert_less_than_uintptr_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_intmax_t(expected, actual) scrutiny_report_assert_less_than_intmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_uintmax_t(expected, actual) scrutiny_report_assert_less_than_uintmax_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_size_t(expected, actual) scrutiny_report_assert_less_than_size_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_ssize_t(expected, actual) scrutiny_report_assert_less_than_ssize_t(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_enum(expected, actual) scrutiny_report_assert_less_than_enum(expected, actual, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_ptr(expected, actual) scrutiny_report_assert_less_than_ptr(expected, actual, __FILE__, __func__, __LINE__) - -#define scrutiny_assert_equal_struct(expected, actual, comp_function) \ -scrutiny_report_assert_equal_struct(expected, actual, comp_function, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal_struct(expected, actual, comp_function) \ -scrutiny_report_assert_not_equal_struct(expected, actual, comp_function, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greator_than_struct(expected, actual, comp_function) \ -scrutiny_report_assert_greator_than_struct(expected, actual, comp_function, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than_struct(expected, actual, comp_function) \ -scrutiny_report_assert_less_than_struct(expected, actual, comp_function, __FILE__, __func__, __LINE__) - -/* - * Use these macros in such a way that your benchmark may setup before starting - * the timer and free resources after stopping it. - */ - -#define scrutiny_benchamrk_start() Clock _scrutiny_benchmark_start_time = clock() -#define scrutiny_benchmark_finish() scrutiny_report_benchmark_time(clock() - _scrutiny_benchmark_start_time, __FILE__, __func__, __LINE__) - -enum _Scrutiny_Error { - SCRUTINY_ERROR_NONE, - SCRUTINY_ERROR_INVALID_ARGUMENT, - SCRUTINY_ERROR_COULDNT_WRITE_TO_FILE -}; - -enum _Scrutiny_ComparisonResult { - SCRUTINY_GREATOR_THAN = 1, - SCRUTINY_EQUAL = 0, - SCRUTINY_LESS_THAN = -1, - SCRUTINY_UNEQUAL = INT8_MAX, - SCRUTINY_COMPARISON_FAILURE = INT8_MIN, -}; - -typedef FILE File; -typedef int EnumValue; -typedef clock_t Clock; -typedef void (*Scrutiny_UnitTest)(void); -typedef void (*Scrutiny_Benchmark)(void); -typedef enum _Scrutiny_Error Scrutiny_Error; -typedef enum _Scrutiny_ComparisonResult Scrutiny_ComparisonResult; -typedef struct _Scrutiny_TestResults Scrutiny_TestResults; -typedef struct _Scrutiny_BenchmarkResults Scrutiny_BenchmarkResults; - -/* - * A function for comparing two custom types, takes a pointer to each object. - * Should return a comparison result. If returning a comparison failure any - * assertion using the comparison function will fail. The unequal variant is for - * comparisons that do not produce a greator or less result and for a not equal - * assertion to succeed any return value other than equal or failure will - * suffice. - */ -typedef Scrutiny_ComparisonResult (*Scrutiny_CompareFunction)(void*, void*); - -struct _Scrutiny_TestResults { - size_t failed_cases; - size_t passed_cases; - size_t failed_tests; - size_t passed_tests; - size_t files; - const char** failed_test_names; - const char** passed_test_names; - const char** file_names; -}; - -struct _Scrutiny_BenchmarkResults { - size_t benchmarks; - Clock* benchmark_times; - const char** benchmark_names; - const char** file_names; -}; - -/* - * Get the name of a comparison result as a constant c string. - */ -const char* scrutiny_comparison_result_get_name(Scrutiny_ComparisonResult comp_result); - -/* - * Runs all given test functions and prints the results. - * - * scrutiny_unit_tests should be an array of functions taking void parameters - * and returning void. The last element of this array should be a NULL pointer - * to terminate the array. - */ -void scrutiny_run_tests(Scrutiny_UnitTest* scrutiny_unit_tests); - -/* - * Run all given benchmars in the array. The last element of the array should - * be a terminating NULL pointer. - */ -void scrutiny_run_benchmarks(Scrutiny_Benchmark* scrutiny_benchmarks); -/* - * Like scrutiny_run_benchmarks() but runs all benchmarks multiple times. - */ -void scrutiny_run_benchmarks_n_times(Scrutiny_Benchmark* scrutiny_benchmarks, size_t n); +#define SCRUTINY_UNIT_TEST(name) void name(scrutiny_test_run_t* _scrutiny_test_run) + +#define scrutiny_assert(a) \ +_scrutiny_assert(a, __FILE__, __func__, __LINE__) +#define scrutiny_assert_equal(a, b) \ +_scrutiny_assert_equal(a, b, __FILE__, __func__, __LINE__) +#define scrutiny_assert_not_equal(a, b) \ +_scrutiny_assert_not_equal(a, b, __FILE__, __func__, __LINE__) +#define scrutiny_assert_greater_than(a, b) \ +_scrutiny_assert_greater_than(a, b, __FILE__, __func__, __LINE__) +#define scrutiny_assert_less_than(a, b) \ +_scrutiny_assert_less_than(a, b, __FILE__, __func__, __LINE__) +#define scrutiny_assert_greater_than_or_equal(a, b) \ +_scrutiny_assert_greater_than_or_equal(a, b, "scrutiny_assert_greater_than_or_equal", __FILE__, __func__, __LINE__) +#define scrutiny_assert_less_thanor_equal(a, b) \ +_scrutiny_assert_less_than_or_equal(a, b, "scrutiny_assert_less_thanor_equal", __FILE__, __func__, __LINE__) +#define scrutiny_assert_no_less_than(a, b) \ +_scrutiny_assert_greater_than_or_equal(a, b, "scrutiny_assert_no_less_than", __FILE__, __func__, __LINE__) +#define scrutiny_assert_no_greater_than(a, b) \ +_scrutiny_assert_less_than_or_equal(a, b, "scrutiny_assert_no_greater_than", __FILE__, __func__, __LINE__) + +#define _scrutiny_assert(a, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a), "scrutiny_assert", #a, file, func, line)) \ + return +#define _scrutiny_assert_equal(a, b, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a) == (b), "scrutiny_assert_equal", #a ", " #b, file, func, line)) \ + return +#define _scrutiny_assert_not_equal(a, b, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a) != (b), "scrutiny_assert_not_equal", #a ", " #b, file, func, line)) \ + return +#define _scrutiny_assert_greater_than(a, b, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a) > (b), "scrutiny_assert_greater_than", #a ", " #b, file, func, line)) \ + return +#define _scrutiny_assert_less_than(a, b, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a) < (b), "scrutiny_assert_less_than", #a ", " #b, file, func, line)) \ + return +#define _scrutiny_assert_greater_than_or_equal(a, b, assert, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a) >= (b), assert, #a ", " #b, file, func, line)) \ + return +#define _scrutiny_assert_less_than_or_equal(a, b, assert, file, func, line) \ +if (!_scrutiny_record_assert(_scrutiny_test_run, (a) <= (b), assert, #a ", " #b, file, func, line)) \ + return + +typedef enum { + SCRUTINY_SUCCESS = true, + SCRUTINY_FAILURE = false, +} scrutiny_test_result_t; + +typedef struct { + const char* previous_function; + scrutiny_test_result_t current_test_result; + unsigned long asserts_passed; + unsigned long asserts_failed; + unsigned long tests_passed; + unsigned long tests_failed; +} scrutiny_test_run_t; + +typedef void (*scrutiny_test_t)(scrutiny_test_run_t*); /* - * Gets the results of previously run tests. + * This function expected that `tests` points to a NULL terminated array of + * `scrutiny_test_t` function pointers. */ -Scrutiny_TestResults* scrutiny_get_test_results(void); - -/* - * Gets the results of previously run benchmarks. - */ -Scrutiny_BenchmarkResults* scrutiny_get_benchmark_results(void); - -/* - * Outputs test results to the given file. Tests must be run before outputting. - */ -Scrutiny_Error scrutiny_output_test_results(File* out_file); - -/* - * Outputs benchmark results to the given file. Like with test output - * benchmarks must be run beforehand. - */ -Scrutiny_Error scrutiny_output_benchmark_results(File* out_file); - -/* - * Outputs test results to the given file. Tests must be run before outputting. - * Output here is designed to be easier to parse using a script or other - * program. - */ -Scrutiny_Error scrutiny_output_test_results_parsable(File* out_file); - -/* - * Outputs a more easily parsable text to the given file for benchmark results. - */ -Scrutiny_Error scrutiny_output_benchmark_results_parsable(File* file); - -/* - * Clear scrutiny's record of test and benchmark runs, calling this will make - * assertions behave as state insurance in a program's runtime rather than a - * unit test assertion. Also clears all memory used by the results. - */ -void scrutiny_clear_results(void); - -/* - * The following functions, while not intended to be used directly, will not - * be a problem if used directly. In most cases the macros above should be used - * but if many asserts are run in a loop it may be useful to replace one of the - * arguments with a custom string in case the default report is not enough. - */ - -void scrutiny_report_assert_pass(const char* file, const char* function); /* Automatically asserts case passing. */ -void scrutiny_report_assert_fail(const char* file, const char* function, size_t line); /* Automatically asserts case failure. */ -void scrutiny_report_assert_true(bool expression, const char* file, const char* function, size_t line); /* Checks if the boolean expression is true. */ -void scrutiny_report_assert_false(bool expression, const char* file, const char* function, size_t line); /* Checks if the boolean expression is false. */ - -void scrutiny_report_assert_not_equal_ptr_data(void* expected, void* actual, size_t struct_size, const char* file, const char* function, size_t line); /* Checks if the data at the pointer expected is the same as actual. */ -void scrutiny_report_assert_not_equal_array(void* expected, void* actual, size_t sizeof_type, size_t array_length, const char* file, const char* function, size_t line); /* Checks if the expected array and actual array are equal. */ -void scrutiny_report_assert_not_equal_string(char* expected, char* actual, const char* file, const char* function, size_t line); /* Checks if the two strings are equal. */ -void scrutiny_report_assert_not_equal_non_terminated_string(char* expected, char* actual, size_t size, const char* file, const char* function, size_t line); /* Checks if the two strings are equal. */ - -void scrutiny_report_assert_equal_ptr_data(void* expected, void* actual, size_t struct_size, const char* file, const char* function, size_t line); /* Checks if the data at the pointer expected is the same as actual. */ -void scrutiny_report_assert_equal_array(void* expected, void* actual, size_t sizeof_type, size_t array_length, const char* file, const char* function, size_t line); /* Checks if the expected array and actual array are equal. */ -void scrutiny_report_assert_equal_string(char* expected, char* actual, const char* file, const char* function, size_t line); /* Checks if the two strings are equal. */ -void scrutiny_report_assert_equal_non_terminated_string(char* expected, char* actual, size_t size, const char* file, const char* function, size_t line); /* Checks if the two strings are equal. */ - -void scrutiny_report_assert_equal_char(char expected, char actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_short(short expected, short actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int(int expected, int actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_long(long expected, long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_long_long(long long expected, long long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_float(float expected, float actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_double(double expected, double actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_long_double(long double expected, long double actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_equal_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equal to actual. */ -void scrutiny_report_assert_equal_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equal to actual. */ -void scrutiny_report_assert_equal_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line); /* Checks if two enum values (ints) are the same. */ -void scrutiny_report_assert_equal_ptr(void* expected, void* actual, const char* file, const char* function, size_t line); /* Checks if the expected pointer and actual pointer are the same. */ - -void scrutiny_report_assert_not_equal_char(char expected, char actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_short(short expected, short actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int(int expected, int actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_long(long expected, long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_long_long(long long expected, long long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_float(float expected, float actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_double(double expected, double actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_long_double(long double expected, long double actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_not_equal_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equal to actual. */ -void scrutiny_report_assert_not_equal_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line); /* Checks if expected is equal to actual. */ -void scrutiny_report_assert_not_equal_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line); /* Checks if two enum values (ints) are the same. */ -void scrutiny_report_assert_not_equal_ptr(void* expected, void* actual, const char* file, const char* function, size_t line); /* Checks if the expected pointer and actual pointer are the same. */ - -void scrutiny_report_assert_greater_than_char(char expected, char actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_short(short expected, short actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int(int expected, int actual, const char* file, const char* function, size_t line); /* Checks if expected is equivilant to actual. */ -void scrutiny_report_assert_greater_than_long(long expected, long actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_long_long(long long expected, long long actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_float(float expected, float actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_double(double expected, double actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_long_double(long double expected, long double actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line); /* Checks if expected is greater than actual. */ -void scrutiny_report_assert_greater_than_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line); /* Checks if the expected enum value is greater than actual. */ -void scrutiny_report_assert_greater_than_ptr(void* expected, void* actual, const char* file, const char* function, size_t line); /* Checks if the expected pointer is greater than the actual pointer. */ - -void scrutiny_report_assert_less_than_char(char expected, char actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_unsigned_char(unsigned char expected, unsigned char actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_short(short expected, short actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int(int expected, int actual, const char* file, const char* function, size_t line); /* Checks if expected is elessnt to actual. */ -void scrutiny_report_assert_less_than_long(long expected, long actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_long_long(long long expected, long long actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_unsigned_short(unsigned short expected, unsigned short actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_unsigned_int(unsigned int expected, unsigned int actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_unsigned_long(unsigned long expected, unsigned long actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_unsigned_long_long(unsigned long long expected, unsigned long long actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_float(float expected, float actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_double(double expected, double actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_long_double(long double expected, long double actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int8_t(int8_t expected, int8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int16_t(int16_t expected, int16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int32_t(int32_t expected, int32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int64_t(int64_t expected, int64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_fast8_t(int_fast8_t expected, int_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_fast16_t(int_fast16_t expected, int_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_fast32_t(int_fast32_t expected, int_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_fast64_t(int_fast64_t expected, int_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_least8_t(int_least8_t expected, int_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_least16_t(int_least16_t expected, int_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_least32_t(int_least32_t expected, int_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_int_least64_t(int_least64_t expected, int_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint8_t(uint8_t expected, uint8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint16_t(uint16_t expected, uint16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint32_t(uint32_t expected, uint32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint64_t(uint64_t expected, uint64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_fast8_t(uint_fast8_t expected, uint_fast8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_fast16_t(uint_fast16_t expected, uint_fast16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_fast32_t(uint_fast32_t expected, uint_fast32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_fast64_t(uint_fast64_t expected, uint_fast64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_least8_t(uint_least8_t expected, uint_least8_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_least16_t(uint_least16_t expected, uint_least16_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_least32_t(uint_least32_t expected, uint_least32_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uint_least64_t(uint_least64_t expected, uint_least64_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_intptr_t(intptr_t expected, intptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uintptr_t(uintptr_t expected, uintptr_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_intmax_t(intmax_t expected, intmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_uintmax_t(uintmax_t expected, uintmax_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_size_t(size_t expected, size_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_ssize_t(ssize_t expected, ssize_t actual, const char* file, const char* function, size_t line); /* Checks if expected is less than actual. */ -void scrutiny_report_assert_less_than_enum(EnumValue expected, EnumValue actual, const char* file, const char* function, size_t line); /* Checks if the expected enum value is less than actual. */ -void scrutiny_report_assert_less_than_ptr(void* expected, void* actual, const char* file, const char* function, size_t line); /* Checks if the expected pointer is less than the actual pointer. */ - -void scrutiny_report_assert_equal_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line); -void scrutiny_report_assert_not_equal_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line); -void scrutiny_report_assert_greator_than_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line); -void scrutiny_report_assert_less_than_struct(void* expected, void* actual, Scrutiny_CompareFunction comp_function, const char* file, const char* function, size_t line); +void scrutiny_run_tests(scrutiny_test_t* tests); +void scrutiny_run_tests_with_stats(scrutiny_test_t* tests); -void scrutiny_report_benchmark_time(Clock time, const char* file, const char* function, size_t line); /* Records the given benchmark time. */ +bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line); #endif // SCRUTINY_H From 5f3d75ee6e5b5291a43fbfb6b1f88f54ff3c5310 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Mon, 12 Jun 2023 21:12:56 -0700 Subject: [PATCH 2/9] BENCHMARKS!!!!! --- examples/benchmarks.c | 44 +++++++++++++----------------------- scrutiny/scrutiny.c | 44 ++++++++++++++++++++++++++++++------ scrutiny/scrutiny.h | 52 ++++++++++++++++++++++++++++++++++++++++++- 3 files changed, 104 insertions(+), 36 deletions(-) diff --git a/examples/benchmarks.c b/examples/benchmarks.c index e59aa04..1dd7b11 100644 --- a/examples/benchmarks.c +++ b/examples/benchmarks.c @@ -1,55 +1,43 @@ #include "../scrutiny/scrutiny.h" +#include +#include -static bool is_prime(uint64_t n) -{ +static bool is_prime(unsigned long n) { if (n == 0 || n == 1) return false; - for (uint64_t i = 2; i < n / 2; i++) + for (unsigned long i = 2; i < n / 2; i++) if (n % i == 0) return false; return true; } -SCRUTINY_BENCHMARK primes_to_n_benchmark(void) -{ - const uint64_t n = 4096; - uint64_t largest_prime = 0; - - /* Starts the benchmark timer. */ - scrutiny_benchamrk_start(); +SCRUTINY_BENCHMARK(primes_to_n) { + const unsigned long n = 4096; + unsigned long largest_prime = 0; - /* Benchmark code, here we find the largest prime up to n. */ - for (uint64_t i = 0; i <= n; i++) + for (unsigned long i = 0; i <= n; i++) if (is_prime(i)) largest_prime = i; - /* Ends the benchmark timer. */ - scrutiny_benchmark_finish(); + scrutiny_bench_return(); +} - /* Use this space to free memory or I/O. */ +SCRUTINY_BENCHMARK(wait_1_sec) { + sleep(1); + scrutiny_bench_return(); } int main() { scrutiny_benchmark_t benchmarks[] = { - primes_to_n_benchmark, + primes_to_n, + wait_1_sec, NULL }; - /* Run all given benchmarks once. */ - //scrutiny_run_benchmarks(benchmarks); - - /* Run all given benchmarks the given number of times. */ - scrutiny_run_benchmarks_n_times(benchmarks, 16); - - /* Output test results. */ - scrutiny_output_benchmark_results(stdout); - - /* Output a more parsable results text. */ - //file_t* file = fopen("out.txt", "w"); - //scrutiny_output_benchmark_results_parsable(file); + scrutiny_run_benchmarks(benchmarks, 1); } diff --git a/scrutiny/scrutiny.c b/scrutiny/scrutiny.c index f7dcc0a..5456391 100755 --- a/scrutiny/scrutiny.c +++ b/scrutiny/scrutiny.c @@ -3,15 +3,9 @@ #include #include +#include #include "scrutiny.h" -#define TEXT_NORMAL "\033[0m" -#define TEXT_BOLD "\033[1m" -#define TEXT_ITALIC "\033[3m" -#define TEXT_GREEN "\033[0;32m" -#define TEXT_BLUE "\033[0;34m" -#define TEXT_RED "\033[0;31m" - static void _scrutiny_run_tests(scrutiny_test_t* tests, bool with_stats) { scrutiny_test_run_t test_run = { .previous_function = NULL, @@ -72,6 +66,42 @@ void scrutiny_run_tests_with_stats(scrutiny_test_t* tests) { _scrutiny_run_tests(tests, true); } +void scrutiny_run_benchmarks(scrutiny_benchmark_t* benchmarks, unsigned int passes) { + scrutiny_bench_run_t bench_run = { + .current_function = NULL, + .current_proc_start = -1, + .current_proc_end = -1, + }; + + for (unsigned int i = 0; benchmarks[i]; i++) { + const char* name_prefix; + double cpu_total = 0; + double total = 0; + + for (unsigned int j = 0; j < passes; j++) { + bench_run.current_proc_end = -1; + bench_run.current_proc_start = clock(); + gettimeofday(&bench_run.current_start, NULL); + + name_prefix = benchmarks[i](&bench_run); + + clock_t return_time = clock(); + if (bench_run.current_proc_end < 0) { + gettimeofday(&bench_run.current_end, NULL); + bench_run.current_proc_end = return_time; + } + + cpu_total += (double)(bench_run.current_proc_end - bench_run.current_proc_start) / CLOCKS_PER_SEC; + total += (double)(bench_run.current_end.tv_sec + bench_run.current_end.tv_usec / 1e+6) - (double)(bench_run.current_start.tv_sec + bench_run.current_start.tv_usec / 1e+6); + } + + cpu_total /= passes; + total /= passes; + + printf("%s" TEXT_BLUE TEXT_BOLD "%s " TEXT_NORMAL "- " TEXT_GREEN "%f seconds (%f seconds CPU time)" TEXT_NORMAL "\n", name_prefix, bench_run.current_function, total, cpu_total); + } +} + bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line) { if (test_run->previous_function != function) { if (!succeeded && test_run->previous_function) { diff --git a/scrutiny/scrutiny.h b/scrutiny/scrutiny.h index 5d8f221..05ca2cd 100755 --- a/scrutiny/scrutiny.h +++ b/scrutiny/scrutiny.h @@ -5,8 +5,40 @@ #define SCRUTINY_H #include +#include +#include + +#define TEXT_NORMAL "\033[0m" +#define TEXT_BOLD "\033[1m" +#define TEXT_ITALIC "\033[3m" +#define TEXT_GREEN "\033[0;32m" +#define TEXT_BLUE "\033[0;34m" +#define TEXT_RED "\033[0;31m" #define SCRUTINY_UNIT_TEST(name) void name(scrutiny_test_run_t* _scrutiny_test_run) +#define SCRUTINY_BENCHMARK(name) const char* name(scrutiny_bench_run_t* _scrutiny_bench_run) + +/* + * This macro may be used to overwrite the start time of the current benchmark. + * If not used the time that the benchmark function is called will be used as + * the start time. + */ +#define scrutiny_bench_start() _scrutiny_bench_run->current_start = clock() + +/* + * This macro may be used to set the end time of a benchmark run before the + * benchmark function returns. If not used the return time of the function will + * be considered the benchmark's completion time. + */ +#define scrutiny_bench_end() _scrutiny_bench_run->current_end = clock() + +/* + * This macro must be used at the end of a benchmark in order to set the + * benchmark's name. + */ +#define scrutiny_bench_return() \ +_scrutiny_bench_run->current_function = __func__; \ +return TEXT_ITALIC __FILE__ TEXT_NORMAL ": " #define scrutiny_assert(a) \ _scrutiny_assert(a, __FILE__, __func__, __LINE__) @@ -63,15 +95,33 @@ typedef struct { unsigned long tests_failed; } scrutiny_test_run_t; +typedef struct { + const char* current_function; + clock_t current_proc_start; + clock_t current_proc_end; + struct timeval current_start; + struct timeval current_end; +} scrutiny_bench_run_t; + typedef void (*scrutiny_test_t)(scrutiny_test_run_t*); +typedef const char* (*scrutiny_benchmark_t)(scrutiny_bench_run_t*); /* - * This function expected that `tests` points to a NULL terminated array of + * This function expects that `tests` points to a NULL terminated array of * `scrutiny_test_t` function pointers. */ void scrutiny_run_tests(scrutiny_test_t* tests); void scrutiny_run_tests_with_stats(scrutiny_test_t* tests); +/* + * This function expects that `benchmarks` points to a NULL terminated array of + * `scrutiny_benchmark_t` function pointers. This function will print both the + * time for execution and the CPU time spent running the benchmark. Usually + * these values will be nearly equal except in the event they call on I/O or + * functions like `sleep()`. + */ +void scrutiny_run_benchmarks(scrutiny_benchmark_t* benchmarks, unsigned int passes); + bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line); #endif // SCRUTINY_H From ae23dbc58b79ee937d2492e28c34aea72d5b4b08 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Tue, 13 Jun 2023 13:17:42 -0700 Subject: [PATCH 3/9] runtime assertions --- examples/unit_tests.c | 3 ++ scrutiny/scrutiny.c | 8 +++++ scrutiny/scrutiny.h | 82 +++++++++++++++++++++++++++++++++---------- 3 files changed, 75 insertions(+), 18 deletions(-) diff --git a/examples/unit_tests.c b/examples/unit_tests.c index 74d9aa1..36cbf34 100755 --- a/examples/unit_tests.c +++ b/examples/unit_tests.c @@ -1,4 +1,7 @@ #include + +#define SCRUTINY_DEBUG + #include "../scrutiny/scrutiny.h" SCRUTINY_UNIT_TEST(addition_test) { diff --git a/scrutiny/scrutiny.c b/scrutiny/scrutiny.c index 5456391..e05c0fa 100755 --- a/scrutiny/scrutiny.c +++ b/scrutiny/scrutiny.c @@ -102,6 +102,14 @@ void scrutiny_run_benchmarks(scrutiny_benchmark_t* benchmarks, unsigned int pass } } +bool _scrutiny_abort_assert(bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line) { + if (!succeeded) { + printf(TEXT_RED TEXT_BOLD "ASSERT FAILED " TEXT_NORMAL TEXT_ITALIC "%s(%s) " TEXT_NORMAL ": " TEXT_ITALIC "line %zu " TEXT_NORMAL "of " TEXT_ITALIC "%s " TEXT_NORMAL "in " TEXT_BLUE TEXT_ITALIC "%s\n" TEXT_NORMAL, assert, condition, line, file, function); + } + + exit(EXIT_FAILURE); +} + bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line) { if (test_run->previous_function != function) { if (!succeeded && test_run->previous_function) { diff --git a/scrutiny/scrutiny.h b/scrutiny/scrutiny.h index 05ca2cd..cdc0819 100755 --- a/scrutiny/scrutiny.h +++ b/scrutiny/scrutiny.h @@ -1,6 +1,14 @@ // Copyright (c) 2023 Evan Overman (https://an-prata.it). Licensed under the MIT License. // See LICENSE file in repository root for complete license text. +/* + * scrutiny.h + * + * You may define the SCRUTINY_TEST macro to make assertions behave in a testing + * manor. Without this definition they will behave like the standard library's + * `assert()` during the program's runtime. + */ + #ifndef SCRUTINY_H #define SCRUTINY_H @@ -40,24 +48,45 @@ _scrutiny_bench_run->current_function = __func__; \ return TEXT_ITALIC __FILE__ TEXT_NORMAL ": " -#define scrutiny_assert(a) \ -_scrutiny_assert(a, __FILE__, __func__, __LINE__) -#define scrutiny_assert_equal(a, b) \ -_scrutiny_assert_equal(a, b, __FILE__, __func__, __LINE__) -#define scrutiny_assert_not_equal(a, b) \ -_scrutiny_assert_not_equal(a, b, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than(a, b) \ -_scrutiny_assert_greater_than(a, b, __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_than(a, b) \ -_scrutiny_assert_less_than(a, b, __FILE__, __func__, __LINE__) -#define scrutiny_assert_greater_than_or_equal(a, b) \ -_scrutiny_assert_greater_than_or_equal(a, b, "scrutiny_assert_greater_than_or_equal", __FILE__, __func__, __LINE__) -#define scrutiny_assert_less_thanor_equal(a, b) \ -_scrutiny_assert_less_than_or_equal(a, b, "scrutiny_assert_less_thanor_equal", __FILE__, __func__, __LINE__) -#define scrutiny_assert_no_less_than(a, b) \ -_scrutiny_assert_greater_than_or_equal(a, b, "scrutiny_assert_no_less_than", __FILE__, __func__, __LINE__) -#define scrutiny_assert_no_greater_than(a, b) \ -_scrutiny_assert_less_than_or_equal(a, b, "scrutiny_assert_no_greater_than", __FILE__, __func__, __LINE__) +#ifdef SCRUTINY_DEBUG + #define scrutiny_assert(a) \ + _scrutiny_assert(a, __FILE__, __func__, __LINE__) + #define scrutiny_assert_equal(a, b) \ + _scrutiny_assert_equal(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_not_equal(a, b) \ + _scrutiny_assert_not_equal(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_greater_than(a, b) \ + _scrutiny_assert_greater_than(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_less_than(a, b) \ + _scrutiny_assert_less_than(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_greater_than_or_equal(a, b) \ + _scrutiny_assert_greater_than_or_equal(a, b, "scrutiny_assert_greater_than_or_equal", __FILE__, __func__, __LINE__) + #define scrutiny_assert_less_than_or_equal(a, b) \ + _scrutiny_assert_less_than_or_equal(a, b, "scrutiny_assert_less_thanor_equal", __FILE__, __func__, __LINE__) + #define scrutiny_assert_no_less_than(a, b) \ + _scrutiny_assert_greater_than_or_equal(a, b, "scrutiny_assert_no_less_than", __FILE__, __func__, __LINE__) + #define scrutiny_assert_no_greater_than(a, b) \ + _scrutiny_assert_less_than_or_equal(a, b, "scrutiny_assert_no_greater_than", __FILE__, __func__, __LINE__) +#else + #define scrutiny_assert(a) \ + _scrutiny_runtime_assert(a, __FILE__, __func__, __LINE__) + #define scrutiny_assert_equal(a, b) \ + _scrutiny_runtime_assert_equal(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_not_equal(a, b) \ + _scrutiny_runtime_assert_not_equal(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_greater_than(a, b) \ + _scrutiny_runtime_assert_greater_than(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_less_than(a, b) \ + _scrutiny_runtime_assert_less_than(a, b, __FILE__, __func__, __LINE__) + #define scrutiny_assert_greater_than_or_equal(a, b) \ + _scrutiny_runtime_assert_greater_than_or_equal(a, b, "scrutiny_assert_greater_than_or_equal", __FILE__, __func__, __LINE__) + #define scrutiny_assert_less_than_or_equal(a, b) \ + _scrutiny_runtime_assert_less_than_or_equal(a, b, "scrutiny_assert_less_thanor_equal", __FILE__, __func__, __LINE__) + #define scrutiny_assert_no_less_than(a, b) \ + _scrutiny_runtime_assert_greater_than_or_equal(a, b, "scrutiny_assert_no_less_than", __FILE__, __func__, __LINE__) + #define scrutiny_assert_no_greater_than(a, b) \ + _scrutiny_runtime_assert_less_than_or_equal(a, b, "scrutiny_assert_no_greater_than", __FILE__, __func__, __LINE__) +#endif // SCRUTINY_DEBUG #define _scrutiny_assert(a, file, func, line) \ if (!_scrutiny_record_assert(_scrutiny_test_run, (a), "scrutiny_assert", #a, file, func, line)) \ @@ -81,6 +110,21 @@ if (!_scrutiny_record_assert(_scrutiny_test_run, (a) >= (b), assert, #a ", " #b, if (!_scrutiny_record_assert(_scrutiny_test_run, (a) <= (b), assert, #a ", " #b, file, func, line)) \ return +#define _scrutiny_runtime_assert(a, file, func, line) \ +_scrutiny_abort_assert((a), "scrutiny_assert", #a, file, func, line) +#define _scrutiny_runtime_assert_equal(a, b, file, func, line) \ +_scrutiny_abort_assert((a) == (b), "scrutiny_assert_equal", #a ", " #b, file, func, line) +#define _scrutiny_runtime_assert_not_equal(a, b, file, func, line) \ +_scrutiny_abort_assert((a) != (b), "scrutiny_assert_not_equal", #a ", " #b, file, func, line) +#define _scrutiny_runtime_assert_greater_than(a, b, file, func, line) \ +_scrutiny_abort_assert((a) > (b), "scrutiny_assert_greater_than", #a ", " #b, file, func, line) +#define _scrutiny_runtime_assert_less_than(a, b, file, func, line) \ +_scrutiny_abort_assert((a) < (b), "scrutiny_assert_less_than", #a ", " #b, file, func, line) +#define _scrutiny_runtime_assert_greater_than_or_equal(a, b, assert, file, func, line) \ +_scrutiny_abort_assert((a) >= (b), assert, #a ", " #b, file, func, line) +#define _scrutiny_runtime_assert_less_than_or_equal(a, b, assert, file, func, line) \ +_scrutiny_abort_assert((a) <= (b), assert, #a ", " #b, file, func, line) + typedef enum { SCRUTINY_SUCCESS = true, SCRUTINY_FAILURE = false, @@ -122,6 +166,8 @@ void scrutiny_run_tests_with_stats(scrutiny_test_t* tests); */ void scrutiny_run_benchmarks(scrutiny_benchmark_t* benchmarks, unsigned int passes); +bool _scrutiny_abort_assert(bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line); + bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line); #endif // SCRUTINY_H From 9da953e0830dc5c94097e499a2b1c61c15b55fa4 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Tue, 13 Jun 2023 13:18:46 -0700 Subject: [PATCH 4/9] document use of `SCRUTINY_DEBUG` --- examples/unit_tests.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/examples/unit_tests.c b/examples/unit_tests.c index 36cbf34..ddbe502 100755 --- a/examples/unit_tests.c +++ b/examples/unit_tests.c @@ -1,5 +1,7 @@ #include +// This macro makes scrutiny's assertions not abort the program on failure and +// instead return from the current function. #define SCRUTINY_DEBUG #include "../scrutiny/scrutiny.h" From b8e84626c3b547a3a9d32da38c0d01a68ecc7e30 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Thu, 22 Jun 2023 17:03:34 -0700 Subject: [PATCH 5/9] finish up examples --- examples/benchmarks.c | 3 +++ examples/runtime_assertion.c | 19 +++++++------------ examples/unit_tests.c | 7 ++++++- 3 files changed, 16 insertions(+), 13 deletions(-) diff --git a/examples/benchmarks.c b/examples/benchmarks.c index 1dd7b11..560615f 100644 --- a/examples/benchmarks.c +++ b/examples/benchmarks.c @@ -24,6 +24,7 @@ SCRUTINY_BENCHMARK(primes_to_n) { scrutiny_bench_return(); } +// This benchmark will take a long time but much of it will be idle. SCRUTINY_BENCHMARK(wait_1_sec) { sleep(1); scrutiny_bench_return(); @@ -38,6 +39,8 @@ int main() NULL }; + // Scrutiny will output both the actual time and CPU time used when running + // a benchmark. scrutiny_run_benchmarks(benchmarks, 1); } diff --git a/examples/runtime_assertion.c b/examples/runtime_assertion.c index 393eb82..e1013c4 100644 --- a/examples/runtime_assertion.c +++ b/examples/runtime_assertion.c @@ -1,27 +1,22 @@ #include "../scrutiny/scrutiny.h" +#include -/* - * Shows how you can use scrutiny's assertions as an alternative to the - * standard library's during application runtime or debugging. - */ +// This time we dont define the `SCRUTINY_DEBUG` function so that we can use +// scrutiny's assertions during the runtime of our program. int main() { int a = 8; int b = 4; - scrutiny_assert_equal_int(a, b * 2); + scrutiny_assert_equal(a, b * 2); printf("Passed One!\n"); - /* - * If you want to make runtime assertions like this after running unit tests - * you will need to make a call to scrutiny_clear_results(). - */ - int arr1[] = { 2, 4, 6, 8 }; int arr2[] = { 2, 4, 5, 7 }; - scrutiny_assert_not_equal_array(arr1, arr2, sizeof(int), sizeof arr1); - scrutiny_assert_equal_int(arr1[2], arr2[2]); + for (unsigned int i = 0; i < sizeof(arr1) / sizeof(int); i++) { + scrutiny_assert_equal(arr1[i], arr2[i]); + } } diff --git a/examples/unit_tests.c b/examples/unit_tests.c index ddbe502..e1b1acd 100755 --- a/examples/unit_tests.c +++ b/examples/unit_tests.c @@ -1,7 +1,7 @@ #include // This macro makes scrutiny's assertions not abort the program on failure and -// instead return from the current function. +// instead return from the current function, which makes unit testing easier. #define SCRUTINY_DEBUG #include "../scrutiny/scrutiny.h" @@ -16,6 +16,7 @@ SCRUTINY_UNIT_TEST(addition_test) { scrutiny_assert_equal(5, a + b); } +// This test will fail. SCRUTINY_UNIT_TEST(subtraction_test) { int a = 2; int b = 3; @@ -31,4 +32,8 @@ int main() { }; scrutiny_run_tests(tests); + + // Using this macro will print some extra info at the end of the test run + // for when you need that 100% passed dopamine. + // scrutiny_run_tests_with_stats(tests); } \ No newline at end of file From 73b66192a7dcd5658f21b11f590481af1e7cc27b Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Thu, 22 Jun 2023 17:04:03 -0700 Subject: [PATCH 6/9] fix `_scrutiny_abort_assert()` --- scrutiny/scrutiny.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/scrutiny/scrutiny.c b/scrutiny/scrutiny.c index e05c0fa..c7cbf95 100755 --- a/scrutiny/scrutiny.c +++ b/scrutiny/scrutiny.c @@ -105,9 +105,10 @@ void scrutiny_run_benchmarks(scrutiny_benchmark_t* benchmarks, unsigned int pass bool _scrutiny_abort_assert(bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line) { if (!succeeded) { printf(TEXT_RED TEXT_BOLD "ASSERT FAILED " TEXT_NORMAL TEXT_ITALIC "%s(%s) " TEXT_NORMAL ": " TEXT_ITALIC "line %zu " TEXT_NORMAL "of " TEXT_ITALIC "%s " TEXT_NORMAL "in " TEXT_BLUE TEXT_ITALIC "%s\n" TEXT_NORMAL, assert, condition, line, file, function); + exit(EXIT_FAILURE); } - exit(EXIT_FAILURE); + return succeeded; } bool _scrutiny_record_assert(scrutiny_test_run_t* test_run, bool succeeded, const char* assert, const char* condition, const char* file, const char* function, unsigned long line) { From 66283cf9d211831b656cd6260e2773cc696625a2 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Mon, 10 Jul 2023 14:26:08 -0700 Subject: [PATCH 7/9] make comment a bit more accurate --- examples/unit_tests.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/examples/unit_tests.c b/examples/unit_tests.c index e1b1acd..114afe3 100755 --- a/examples/unit_tests.c +++ b/examples/unit_tests.c @@ -33,7 +33,9 @@ int main() { scrutiny_run_tests(tests); - // Using this macro will print some extra info at the end of the test run - // for when you need that 100% passed dopamine. + // Using this function will print some extra info at the end of the test run + // for when you need that 100% passed dopamine. You cant use both in the + // same run since they exit the program for you with a value inicative of + // test success. // scrutiny_run_tests_with_stats(tests); } \ No newline at end of file From 575ada7582e2daba2e6d16c56db4446fe1e5a6c2 Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Mon, 10 Jul 2023 14:27:22 -0700 Subject: [PATCH 8/9] comment edditions and corrections --- examples/benchmarks.c | 3 ++- examples/runtime_assertion.c | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/examples/benchmarks.c b/examples/benchmarks.c index 560615f..b7d1857 100644 --- a/examples/benchmarks.c +++ b/examples/benchmarks.c @@ -40,7 +40,8 @@ int main() }; // Scrutiny will output both the actual time and CPU time used when running - // a benchmark. + // a benchmark. Unlike when unit testing scrutiny will not exit the program + // here. scrutiny_run_benchmarks(benchmarks, 1); } diff --git a/examples/runtime_assertion.c b/examples/runtime_assertion.c index e1013c4..4088d0e 100644 --- a/examples/runtime_assertion.c +++ b/examples/runtime_assertion.c @@ -1,7 +1,7 @@ #include "../scrutiny/scrutiny.h" #include -// This time we dont define the `SCRUTINY_DEBUG` function so that we can use +// This time we dont define the `SCRUTINY_DEBUG` macro so that we can use // scrutiny's assertions during the runtime of our program. int main() From 30980d6a0908071ecee357203ad7b608bd5102af Mon Sep 17 00:00:00 2001 From: Evan Overman Date: Mon, 10 Jul 2023 14:27:46 -0700 Subject: [PATCH 9/9] formtting fix --- examples/runtime_assertion.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/examples/runtime_assertion.c b/examples/runtime_assertion.c index 4088d0e..26645ec 100644 --- a/examples/runtime_assertion.c +++ b/examples/runtime_assertion.c @@ -4,8 +4,7 @@ // This time we dont define the `SCRUTINY_DEBUG` macro so that we can use // scrutiny's assertions during the runtime of our program. -int main() -{ +int main() { int a = 8; int b = 4;