Go to the documentation of this file.
5 #ifndef BALL_CONCEPT_AUTODELETABLE_H
13 #ifndef BALL_DATATYPE_REGULAREXPRESSION_H
20 #ifdef BALL_HAS_SSTREAM
34 #define PRECISION(a) \
35 TEST::precision = (a);
50 #define START_TEST(class_name)\
55 bool all_tests = true;\
59 string exception_name = "";\
60 const char* version_string = BALL_RELEASE_STRING;\
61 bool newline = false;\
62 list<string> tmp_file_list;\
63 std::ifstream infile;\
64 std::ifstream templatefile;\
66 double precision = 1e-6;\
70 int main(int argc, char **argv)\
74 if (!strcmp(argv[1], "-v"))\
76 if (!strcmp(argv[1], "-V"))\
80 if ((argc > 2) || ((argc == 2) && (TEST::verbose == 0))) {\
81 std::cerr << "Checks " #class_name " class" << std::endl;\
83 std::cerr << "On successful operation it simply returns OK," << std::endl;\
84 std::cerr << "otherwise FAILURE is printed." << std::endl;\
85 std::cerr << "If called with an argument of -v, " << argv[0] << " prints detailed" << std::endl;\
86 std::cerr << "information about individual tests." << std::endl;\
87 std::cerr << "Option -V provides verbose information on" << std::endl;\
88 std::cerr << "every subtest." << std::endl;\
92 if (TEST::verbose > 0)\
93 std::cout << "Version: " << TEST::version_string << std::endl;\
112 catch (BALL::Exception::FileNotFound& e)\
114 TEST::this_test = false;\
116 TEST::all_tests = false;\
117 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
119 if (TEST::exception == 1) \
121 std::cout << std::endl << " (caught exception of type ";\
122 std::cout << e.getName();\
123 if ((e.getLine() > 0) && (!(e.getFile()[0] == '\0')))\
124 std::cout << " outside a subtest, which was thrown in line " << e.getLine() << " of file " << e.getFile();\
125 std::cout << " while looking for file " << e.getFilename();\
126 std::cout << " - unexpected!) " << std::endl;\
130 catch (BALL::Exception::GeneralException& e)\
132 TEST::this_test = false;\
134 TEST::all_tests = false;\
135 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
137 if (TEST::exception == 1) \
139 std::cout << std::endl << " (caught exception of type ";\
140 std::cout << e.getName();\
141 if ((e.getLine() > 0) && (!(e.getFile()[0] == '\0')))\
142 std::cout << " outside a subtest, which was thrown in line " << e.getLine() << " of file " << e.getFile();\
143 std::cout << " - unexpected!) " << std::endl;\
144 std::cout << " (message is: " << e.getMessage() << ")" << std::endl;\
148 catch (std::exception& e)\
150 TEST::this_test = false;\
152 TEST::all_tests = false;\
153 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
155 std::cout << std::endl << " (caught expected STL exception outside a subtest: " << e.what() << ")" << std::endl;\
162 TEST::this_test = false;\
164 TEST::all_tests = false;\
165 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
167 std::cout << std::endl << " (caught unidentified and unexpected exception outside a subtest!) " << std::endl;\
171 while (TEST::tmp_file_list.size() > 0 && TEST::verbose < 1)\
173 ::BALL::File::remove(TEST::tmp_file_list.back());\
174 TEST::tmp_file_list.pop_back();\
177 if (!TEST::all_tests)\
179 std::cout << "FAILED" << std::endl;\
182 std::cout << "PASSED" << std::endl;\
188 BALL::AutoDeletable::clearLastPtr(); \
206 #define CHECK(test_name) \
208 TEST::newline = false;\
209 if (TEST::verbose > 0)\
210 std::cout << "checking " << #test_name << "... " << std::flush;\
229 #define STATUS(message)\
230 if (TEST::verbose > 1)\
232 if (!TEST::newline) \
234 TEST::newline = true;\
235 std::cout << std::endl;\
237 std::cout << " status (line " << __LINE__ << "): " << message << std::endl;\
263 catch (BALL::Exception::FileNotFound& e)\
265 TEST::this_test = false;\
267 TEST::all_tests = false;\
268 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
270 if (TEST::exception == 1) \
272 std::cout << std::endl << " (caught exception of type ";\
273 std::cout << e.getName();\
274 if ((e.getLine() > 0) && (!(e.getFile()[0] == '\0')))\
275 std::cout << " outside a subtest, which was thrown in line " << e.getLine() << " of file " << e.getFile();\
276 std::cout << " while looking for file " << e.getFilename();\
277 std::cout << " - unexpected!) " << std::endl;\
280 catch (::BALL::Exception::GeneralException& e)\
282 TEST::this_test = false;\
284 TEST::all_tests = false;\
285 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
287 if (!TEST::newline) \
289 TEST::newline = true;\
290 std::cout << std::endl;\
292 std::cout << " (caught exception of type ";\
293 std::cout << e.getName();\
294 if ((e.getLine() > 0) && (!(e.getFile()[0] == '\0')))\
295 std::cout << ", which was thrown in line " << e.getLine() << " of file " << e.getFile();\
296 std::cout << " - unexpected!) " << std::endl;\
297 std::cout << " (message is: " << e.getMessage() << ")" << std::endl;\
302 TEST::this_test = false;\
304 TEST::all_tests = false;\
305 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
307 if (!TEST::newline) \
309 TEST::newline = true;\
310 std::cout << std::endl;\
312 std::cout << " (caught unidentified and unexpected exception!)" << std::endl;\
316 TEST::all_tests = TEST::all_tests && TEST::test;\
317 if (TEST::verbose > 0){\
321 std::cout << "passed" << std::endl;\
323 std::cout << "FAILED" << std::endl;\
334 #define NEW_TMP_FILE(filename)\
335 ::BALL::File::createTemporaryFilename(filename);\
336 TEST::tmp_file_list.push_back(filename);\
337 if (TEST::verbose > 1)\
339 if (!TEST::newline) \
341 TEST::newline = true;\
342 std::cout << std::endl;\
344 std::cout << " creating new temporary file '" << filename << "' (line " << __LINE__ << ")" << std::endl;\
354 #define NEW_TMP_FILE_WITH_SUFFIX(filename, suffix)\
355 ::BALL::File::createTemporaryFilename(filename, suffix);\
356 TEST::tmp_file_list.push_back(filename);\
357 if (TEST::verbose > 1)\
359 if (!TEST::newline) \
361 TEST::newline = true;\
362 std::cout << std::endl;\
364 std::cout << " creating new temporary file '" << filename << "' (line " << __LINE__ << ")" << std::endl;\
374 #define TEST_REAL_EQUAL(a,b) \
375 TEST::this_test = BALL_REAL_EQUAL((a), (b), TEST::precision); \
376 TEST::test = TEST::test && TEST::this_test;\
377 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
381 TEST::newline = true;\
382 std::cout << std::endl;\
384 std::cout << " (line " << __LINE__ << " TEST_REAL_EQUAL("<< #a << ", " << #b << "): got " << (a) << ", expected " << (b) << ") ";\
385 if (TEST::this_test)\
386 std::cout << " + " << std::endl;\
388 std::cout << " - " << std::endl;\
401 #define TEST_EQUAL(a,b) \
403 TEST::this_test = ((a) == (b));\
404 TEST::test = TEST::test && TEST::this_test;\
405 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
409 TEST::newline = true;\
410 std::cout << std::endl;\
412 std::cout << " (line " << __LINE__ << " TEST_EQUAL(" << #a << ", " << #b << "): got " << (a) << ", expected " << (b) << ") ";\
413 if (TEST::this_test)\
414 std::cout << " + " << std::endl;\
416 std::cout << " - " << std::endl;\
428 #define TEST_NOT_EQUAL(a,b) \
430 TEST::this_test = !((a) == (b));\
431 TEST::test = TEST::test && TEST::this_test;\
432 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
436 TEST::newline = true;\
437 std::cout << std::endl;\
439 std::cout << " (line " << __LINE__ << " TEST_NOT_EQUAL(" << #a << ", " << #b << "): got " << (a) << ", forbidden is " << (b) << ") ";\
440 if (TEST::this_test)\
441 std::cout << " + " << std::endl;\
443 std::cout << " - " << std::endl;\
457 #define TEST_EXCEPTION(exception_type, command) \
459 TEST::exception = 0;\
464 catch (exception_type&)\
466 TEST::exception = 1;\
468 catch (::BALL::Exception::GeneralException& e)\
470 TEST::exception = 2;\
471 TEST::exception_name = e.getName();\
475 TEST::exception = 3;\
477 TEST::this_test = (TEST::exception == 1);\
478 TEST::test = TEST::test && TEST::this_test;\
480 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
484 TEST::newline = true;\
485 std::cout << std::endl;\
487 std::cout << " (line " << __LINE__ << " TEST_EXCEPTION(" << #exception_type << ", " << #command << "): ";\
488 switch (TEST::exception)\
490 case 0: std::cout << " ERROR: no exception!) "; break;\
491 case 1: std::cout << " OK) "; break;\
492 case 2: std::cout << " ERROR: wrong exception: " << TEST::exception_name << ") "; break;\
493 case 3: std::cout << " ERROR: wrong exception!) "; break;\
495 if (TEST::this_test)\
496 std::cout << " + " << std::endl;\
498 std::cout << " - " << std::endl;\
511 #define TEST_PRECONDITION_EXCEPTION(command) \
513 TEST::exception = 0;\
518 catch (Exception::Precondition&)\
520 TEST::exception = 1;\
522 catch (::BALL::Exception::GeneralException& e)\
524 TEST::exception = 2;\
525 TEST::exception_name = e.getName();\
529 TEST::exception = 3;\
531 TEST::this_test = (TEST::exception == 1);\
532 TEST::test = TEST::test && TEST::this_test;\
534 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
538 TEST::newline = true;\
539 std::cout << std::endl;\
541 std::cout << " (line " << __LINE__ << " TEST_PRECONDITION_EXCEPTION(" << ", " << #command << "): ";\
542 switch (TEST::exception)\
544 case 0: std::cout << " ERROR: no exception!) "; break;\
545 case 1: std::cout << " OK) "; break;\
546 case 2: std::cout << " ERROR: wrong exception: " << TEST::exception_name << ") "; break;\
547 case 3: std::cout << " ERROR: wrong exception!) "; break;\
549 if (TEST::this_test)\
550 std::cout << " + " << std::endl;\
552 std::cout << " - " << std::endl;\
558 # define TEST_PRECONDITION_EXCEPTION(command)\
559 if (TEST::verbose > 1)\
561 std::cout << " TEST_EXCEPTION_PRECONDITION(" #command ") : (DEBUG mode disabled!)" << std::endl;\
571 #define ABORT_IF(condition) \
572 if (condition) break;
581 #define TEST_FILE(filename, templatename) \
583 TEST::equal_files = true;\
584 TEST::infile.open(filename, std::ios::in);\
585 TEST::templatefile.open(templatename, std::ios::in);\
587 if (TEST::infile.good() && TEST::templatefile.good())\
589 String TEST_FILE__template_line;\
590 String TEST_FILE__line;\
592 while (TEST::infile.good() && TEST::templatefile.good())\
594 TEST_FILE__template_line.getline(TEST::templatefile);\
595 TEST_FILE__line.getline(TEST::infile);\
597 TEST::equal_files &= (TEST_FILE__template_line == TEST_FILE__line);\
598 if (TEST_FILE__template_line != TEST_FILE__line)\
600 if (TEST::verbose > 0)\
604 TEST::newline = true;\
605 std::cout << std::endl;\
608 std::cout << " TEST_FILE: line mismatch:\n got: '" << TEST_FILE__line << "'\n expected: '" << TEST_FILE__template_line << "'" << std::endl;\
613 TEST::equal_files = false;\
615 if (TEST::verbose > 0)\
619 TEST::newline = true;\
620 std::cout << std::endl;\
623 std::cout << " (line " << __LINE__ << ": TEST_FILE(" << #filename << ", " << #templatename ;\
624 std::cout << ") : " << " cannot open file: \"";\
625 if (!TEST::infile.good())\
627 std::cout << filename << "\" (input file) ";\
629 if (!TEST::templatefile.good())\
631 std::cout << templatename << "\" (template file) ";\
633 std::cout << std::endl;\
637 TEST::infile.close();\
638 TEST::templatefile.close();\
639 TEST::infile.clear();\
640 TEST::templatefile.clear();\
642 TEST::this_test = TEST::equal_files;\
643 TEST::test = TEST::test && TEST::this_test;\
644 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
648 TEST::newline = true;\
649 std::cout << std::endl;\
651 std::cout << " (line " << __LINE__ << ": TEST_FILE("<< #filename << ", " << #templatename << "): ";\
652 if (TEST::this_test)\
654 std::cout << "true";\
656 std::cout << "false";\
659 if (TEST::this_test)\
661 std::cout << " + " << std::endl;\
663 std::cout << " - " << std::endl;\
677 #define TEST_FILE_REGEXP(filename, templatename) \
679 TEST::equal_files = true;\
680 TEST::infile.open(filename, std::ios::in);\
681 TEST::templatefile.open(templatename, std::ios::in);\
683 if (TEST::infile.good() && TEST::templatefile.good())\
685 String TEST_FILE__template_line;\
686 String TEST_FILE__line;\
688 while (TEST::infile.good() && TEST::templatefile.good())\
690 TEST_FILE__template_line.getline(TEST::templatefile);\
691 TEST_FILE__line.getline(TEST::infile);\
693 if ((TEST_FILE__template_line.size() > 0) && (TEST_FILE__template_line[0] == '/') && (TEST_FILE__template_line[1] != '/'))\
695 RegularExpression expression(TEST_FILE__template_line(1));\
696 bool match = expression.match(TEST_FILE__line);\
697 TEST::equal_files &= match;\
700 if (TEST::verbose > 0)\
704 TEST::newline = true;\
705 std::cout << std::endl;\
708 std::cout << " TEST_FILE_REGEXP: regexp mismatch: " << TEST_FILE__line << " did not match " << TEST_FILE__template_line(1) << "." << std::endl;\
712 TEST::equal_files &= (TEST_FILE__template_line == TEST_FILE__line);\
713 if (TEST_FILE__template_line != TEST_FILE__line)\
715 if (TEST::verbose > 0)\
719 TEST::newline = true;\
720 std::cout << std::endl;\
723 std::cout << " TEST_FILE: line mismatch:\n got: '" << TEST_FILE__line << "'\n expected: '" << TEST_FILE__template_line << "'" << std::endl;\
729 TEST::equal_files = false;\
731 if (TEST::verbose > 0)\
735 TEST::newline = true;\
736 std::cout << std::endl;\
739 std::cout << " (line " << __LINE__ << ": TEST_FILE_REGEXP(" << #filename << ", " << #templatename ;\
740 std::cout << ") : " << " cannot open file: \"";\
741 if (!TEST::infile.good())\
743 std::cout << filename << "\" (input file) ";\
745 if (!TEST::templatefile.good())\
747 std::cout << templatename << "\" (template file) ";\
749 std::cout << std::endl;\
753 TEST::infile.close();\
754 TEST::templatefile.close();\
755 TEST::infile.clear();\
756 TEST::templatefile.clear();\
758 TEST::this_test = TEST::equal_files;\
759 TEST::test = TEST::test && TEST::this_test;\
760 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
764 TEST::newline = true;\
765 std::cout << std::endl;\
767 std::cout << " (line " << __LINE__ << ": TEST_FILE_REGEXP("<< #filename << ", " << #templatename << "): ";\
768 if (TEST::this_test)\
770 std::cout << "true";\
772 std::cout << "false";\
775 if (TEST::this_test)\
777 std::cout << " + " << std::endl;\
779 std::cout << " - " << std::endl;\
797 #ifdef BALL_HAS_SSTREAM
798 #define CAPTURE_OUTPUT_LEVEL(level) \
800 std::ostringstream TEST_strstr;\
801 Log.remove(std::cout);\
802 Log.remove(std::cerr);\
803 Log.insert(TEST_strstr, level, level);
805 #define CAPTURE_OUTPUT_LEVEL(level) \
807 std::ostrstream TEST_strstr;\
808 Log.remove(std::cout);\
809 Log.remove(std::cerr);\
810 Log.insert(TEST_strstr, level, level);
825 #ifdef BALL_HAS_SSTREAM
826 #define CAPTURE_OUTPUT_LEVEL_RANGE(minlevel, maxlevel) \
828 std::ostringstream TEST_strstr;\
829 Log.remove(std::cout);\
830 Log.remove(std::cerr);\
831 Log.insert(TEST_strstr, minlevel, maxlevel);
833 #define CAPTURE_OUTPUT_LEVEL_RANGE(minlevel, maxlevel) \
835 std::ostrstream TEST_strstr;\
836 Log.remove(std::cout);\
837 Log.remove(std::cerr);\
838 Log.insert(TEST_strstr, minlevel, maxlevel);
845 #ifdef BALL_HAS_SSTREAM
846 #define COMPARE_OUTPUT(text) \
847 Log.remove(TEST_strstr);\
848 Log.insert(std::cout, LogStream::INFORMATION_LEVEL, LogStream::ERROR_LEVEL - 1);\
849 Log.insert(std::cerr, LogStream::ERROR_LEVEL);\
850 TEST::this_test = (::strncmp(TEST_strstr.str().c_str(), text, TEST_strstr.str().size()) == 0);\
851 TEST::test = TEST::test && TEST::this_test;\
853 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
856 char* TEST_strstr_contents = new char[TEST_strstr.str().size() + 1];\
857 ::strncpy(TEST_strstr_contents, TEST_strstr.str().c_str(), TEST_strstr.str().size());\
858 TEST_strstr_contents[TEST_strstr.str().size()] = '\0';\
862 TEST::newline = true;\
863 std::cout << std::endl;\
865 std::cout << " (line " << __LINE__ << " COMPARE_OUTPUT(" << #text << "): got '" << (TEST_strstr_contents) << "', expected '" << (text) << ") ";\
866 if (TEST::this_test)\
867 std::cout << " + " << std::endl;\
869 std::cout << " - " << std::endl;\
870 delete [] TEST_strstr_contents;\
874 #define COMPARE_OUTPUT(text) \
875 Log.remove(TEST_strstr);\
876 Log.insert(std::cout, LogStream::INFORMATION_LEVEL, LogStream::ERROR_LEVEL - 1);\
877 Log.insert(std::cerr, LogStream::ERROR_LEVEL);\
878 TEST::this_test = (::strncmp(TEST_strstr.str(), text, TEST_strstr.str()!=0?strlen(TEST_strstr.str()):0) == 0);\
879 TEST::test = TEST::test && TEST::this_test;\
881 if ((TEST::verbose > 1) || (!TEST::this_test && (TEST::verbose > 0)))\
884 char* TEST_strstr_contents = new char[TEST_strstr.str()!=0?strlen(TEST_strstr.str()):0 + 1];\
885 ::strncpy(TEST_strstr_contents, TEST_strstr.str(), TEST_strstr.str()!=0?strlen(TEST_strstr.str()):0);\
886 TEST_strstr_contents[TEST_strstr.str()!=0?strlen(TEST_strstr.str()):0] = '\0';\
890 TEST::newline = true;\
891 std::cout << std::endl;\
893 std::cout << " (line " << __LINE__ << " COMPARE_OUTPUT(" << #text << "): got '" << (TEST_strstr_contents) << "', expected '" << (text) << "') ";\
894 if (TEST::this_test)\
895 std::cout << " + " << std::endl;\
897 std::cout << " - " << std::endl;\
898 delete [] TEST_strstr_contents;\