xmlreaderimpl/support/expat-2.0.1/tests/minicheck.c
changeset 300 b6d834208d33
parent 299 f06c5eba524d
child 301 1bfe4ecc6c10
equal deleted inserted replaced
299:f06c5eba524d 300:b6d834208d33
     1 /* Miniature re-implementation of the "check" library.
       
     2  *
       
     3  * This is intended to support just enough of check to run the Expat
       
     4  * tests.  This interface is based entirely on the portion of the
       
     5  * check library being used.
       
     6  */
       
     7 
       
     8 #include <stdio.h>
       
     9 #include <stdlib.h>
       
    10 #include <setjmp.h>
       
    11 #include <assert.h>
       
    12 
       
    13 #include "minicheck.h"
       
    14 
       
    15 Suite *
       
    16 suite_create(char *name)
       
    17 {
       
    18     Suite *suite = (Suite *) calloc(1, sizeof(Suite));
       
    19     if (suite != NULL) {
       
    20         suite->name = name;
       
    21     }
       
    22     return suite;
       
    23 }
       
    24 
       
    25 TCase *
       
    26 tcase_create(char *name)
       
    27 {
       
    28     TCase *tc = (TCase *) calloc(1, sizeof(TCase));
       
    29     if (tc != NULL) {
       
    30         tc->name = name;
       
    31     }
       
    32     return tc;
       
    33 }
       
    34 
       
    35 void
       
    36 suite_add_tcase(Suite *suite, TCase *tc) 
       
    37 {
       
    38     assert(suite != NULL);
       
    39     assert(tc != NULL);
       
    40     assert(tc->next_tcase == NULL);
       
    41 
       
    42     tc->next_tcase = suite->tests;
       
    43     suite->tests = tc;
       
    44 }
       
    45 
       
    46 void
       
    47 tcase_add_checked_fixture(TCase *tc,
       
    48                           tcase_setup_function setup,
       
    49                           tcase_teardown_function teardown)
       
    50 {
       
    51     assert(tc != NULL);
       
    52     tc->setup = setup;
       
    53     tc->teardown = teardown;
       
    54 }
       
    55 
       
    56 void
       
    57 tcase_add_test(TCase *tc, tcase_test_function test)
       
    58 {
       
    59     assert(tc != NULL);
       
    60     if (tc->allocated == tc->ntests) {
       
    61         int nalloc = tc->allocated + 100;
       
    62         size_t new_size = sizeof(tcase_test_function) * nalloc;
       
    63         tcase_test_function *new_tests = realloc(tc->tests, new_size);
       
    64         assert(new_tests != NULL);
       
    65         if (new_tests != tc->tests) {
       
    66             free(tc->tests);
       
    67             tc->tests = new_tests;
       
    68         }
       
    69         tc->allocated = nalloc;
       
    70     }
       
    71     tc->tests[tc->ntests] = test;
       
    72     tc->ntests++;
       
    73 }
       
    74 
       
    75 SRunner *
       
    76 srunner_create(Suite *suite)
       
    77 {
       
    78     SRunner *runner = calloc(1, sizeof(SRunner));
       
    79     if (runner != NULL) {
       
    80         runner->suite = suite;
       
    81     }
       
    82     return runner;
       
    83 }
       
    84 
       
    85 static jmp_buf env;
       
    86 
       
    87 static char const *_check_current_function = NULL;
       
    88 static int _check_current_lineno = -1;
       
    89 static char const *_check_current_filename = NULL;
       
    90 
       
    91 void
       
    92 _check_set_test_info(char const *function, char const *filename, int lineno)
       
    93 {
       
    94     _check_current_function = function;
       
    95     _check_current_lineno = lineno;
       
    96     _check_current_filename = filename;
       
    97 }
       
    98 
       
    99 
       
   100 static void
       
   101 add_failure(SRunner *runner, int verbosity)
       
   102 {
       
   103     runner->nfailures++;
       
   104     if (verbosity >= CK_VERBOSE) {
       
   105         printf("%s:%d: %s\n", _check_current_filename,
       
   106                _check_current_lineno, _check_current_function);
       
   107     }
       
   108 }
       
   109 
       
   110 void
       
   111 srunner_run_all(SRunner *runner, int verbosity)
       
   112 {
       
   113     Suite *suite;
       
   114     TCase *tc;
       
   115     assert(runner != NULL);
       
   116     suite = runner->suite;
       
   117     tc = suite->tests;
       
   118     while (tc != NULL) {
       
   119         int i;
       
   120         for (i = 0; i < tc->ntests; ++i) {
       
   121             runner->nchecks++;
       
   122 
       
   123             if (tc->setup != NULL) {
       
   124                 /* setup */
       
   125                 if (setjmp(env)) {
       
   126                     add_failure(runner, verbosity);
       
   127                     continue;
       
   128                 }
       
   129                 tc->setup();
       
   130             }
       
   131             /* test */
       
   132             if (setjmp(env)) {
       
   133                 add_failure(runner, verbosity);
       
   134                 continue;
       
   135             }
       
   136             (tc->tests[i])();
       
   137 
       
   138             /* teardown */
       
   139             if (tc->teardown != NULL) {
       
   140                 if (setjmp(env)) {
       
   141                     add_failure(runner, verbosity);
       
   142                     continue;
       
   143                 }
       
   144                 tc->teardown();
       
   145             }
       
   146         }
       
   147         tc = tc->next_tcase;
       
   148     }
       
   149     if (verbosity) {
       
   150         int passed = runner->nchecks - runner->nfailures;
       
   151         double percentage = ((double) passed) / runner->nchecks;
       
   152         int display = (int) (percentage * 100);
       
   153         printf("%d%%: Checks: %d, Failed: %d\n",
       
   154                display, runner->nchecks, runner->nfailures);
       
   155     }
       
   156 }
       
   157 
       
   158 void
       
   159 _fail_unless(int condition, const char *file, int line, char *msg)
       
   160 {
       
   161     /* Always print the error message so it isn't lost.  In this case,
       
   162        we have a failure, so there's no reason to be quiet about what
       
   163        it is.
       
   164     */
       
   165     if (msg != NULL)
       
   166         printf("%s", msg);
       
   167     longjmp(env, 1);
       
   168 }
       
   169 
       
   170 int
       
   171 srunner_ntests_failed(SRunner *runner)
       
   172 {
       
   173     assert(runner != NULL);
       
   174     return runner->nfailures;
       
   175 }
       
   176 
       
   177 void
       
   178 srunner_free(SRunner *runner)
       
   179 {
       
   180     free(runner->suite);
       
   181     free(runner);
       
   182 }