UnitTest.h 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229
  1. #ifndef _TEST_SUITE_H_
  2. #define _TEST_SUITE_H_
  3. #include <string>
  4. #include <sstream>
  5. #include <cstring>
  6. #ifdef __GNUC__
  7. #define TEST_GCC_VERSION (__GNUC__ * 10000 + __GNUC_MINOR__ * 100)
  8. #if (TEST_GCC_VERSION >= 29600)
  9. #define test_likely(x) __builtin_expect((long)((bool)(x)),1)
  10. #define test_unlikely(x) __builtin_expect((long)((bool)(x)),0)
  11. #else
  12. #define test_likely(x) x
  13. #define test_unlikely(x) x
  14. #endif
  15. #else
  16. #define test_likely(x) x
  17. #define test_unlikely(x) x
  18. #endif
  19. #include <limits>
  20. template <typename T>
  21. union unittest_numUnion {
  22. unittest_numUnion(T _v) : val(_v){}
  23. T val;
  24. unsigned char c[sizeof(T)];
  25. };
  26. template<typename T>
  27. static bool unittest_isNAN(T num){
  28. unittest_numUnion<T> orig(num);
  29. static unittest_numUnion<T> sig_nan(std::numeric_limits<T>::signaling_NaN());
  30. bool isNAN = true;
  31. for(size_t i = 0; i < sizeof(T); ++i){
  32. if (orig.c[i] != sig_nan.c[i]){
  33. isNAN = false;
  34. break;
  35. }
  36. }
  37. if (isNAN) return true;
  38. static unittest_numUnion<T> quiet_nan(std::numeric_limits<T>::quiet_NaN());
  39. for(size_t i = 0; i < sizeof(T); ++i){
  40. if (orig.c[i] != quiet_nan.c[i]){
  41. return false;
  42. }
  43. }
  44. return true;
  45. }
  46. class UnitTest {
  47. public:
  48. static void SelfCheck(void);
  49. static void PushFailure(const std::string & fail);
  50. static void PushSuccess(const std::string & pass);
  51. static void echo_(const std::string & out);
  52. static std::string ToString(void);
  53. static std::string ToHTML(void);
  54. static void SaveTo(const std::string & location);
  55. static void SetReturnOnFail(bool option);
  56. static bool GetReturnOnFail(void);
  57. static void SetEcho(bool option);
  58. static void SetPrefix(const std::string & prefix);
  59. static std::string GetPrefix(void);
  60. static void StartTime(void);
  61. static inline bool _floatsAreEqual(const double & one, const double & two){
  62. return (one > two) ? (one - two) < .000001 : (one - two) > -.000001;
  63. }
  64. };
  65. #define MakePre()\
  66. std::string pre = UnitTest::GetPrefix();\
  67. if (test_unlikely(pre.empty())){\
  68. std::stringstream out;\
  69. out << __FILE__ << ":" << __LINE__;\
  70. pre = out.str();\
  71. }\
  72. pre += ": ";
  73. #define FAIL(stri)\
  74. MakePre()\
  75. UnitTest::PushFailure(pre + std::string(stri));\
  76. if (UnitTest::GetReturnOnFail()) return;
  77. #define PASS(stri)\
  78. MakePre();\
  79. UnitTest::PushSuccess(pre + std::string(stri));\
  80. #define assertUnitTest()\
  81. UnitTest::SelfCheck();
  82. #define assertTrue(cond)\
  83. if (test_unlikely(!(cond))){\
  84. FAIL(#cond);\
  85. } else {\
  86. PASS(#cond);\
  87. }
  88. #define assertFalse(cond)\
  89. if (test_unlikely(cond)){\
  90. FAIL(#cond);\
  91. } else {\
  92. PASS(#cond);\
  93. }
  94. #define assertTrue_Primitive(cond, leftside, rightside)\
  95. if (test_unlikely(!(cond))){\
  96. std::stringstream unit_out;\
  97. unit_out << #cond;\
  98. unit_out << ", Left side: " << leftside;\
  99. unit_out << ", Right side: " << rightside;\
  100. FAIL(unit_out.str());\
  101. } else {\
  102. PASS(#cond);\
  103. }
  104. //needs to copy it so that if its a function call it only does it once
  105. #define assertNAN(type, one)\
  106. {\
  107. type val = (type)one;\
  108. std::string lag(#one);\
  109. lag += " not a number";\
  110. if (test_likely(unittest_isNAN<type>(one))){\
  111. PASS(lag)\
  112. } else {\
  113. FAIL(lag)\
  114. }\
  115. }
  116. #define assertFloatEquals(one, two)\
  117. assertTrue(UnitTest::_floatsAreEqual(one, two))
  118. #define assertEquals(one, two)\
  119. assertTrue((one) == (two))
  120. #define assertNotEquals(one, two)\
  121. assertTrue((one) != (two))
  122. #define assertGreaterThan(one, two)\
  123. assertTrue((one) > (two))
  124. #define assertGreaterThanEqualTo(one, two)\
  125. assertTrue((one) >= (two))
  126. #define assertLessThan(one, two)\
  127. assertTrue((one) < (two))
  128. #define assertLessThanEqualTo(one, two)\
  129. assertTrue((one) <= (two))
  130. #define assertEquals_Primitive(one, two)\
  131. assertTrue_Primitive((one) == (two), one, two)
  132. #define assertNotEquals_Primitive(one, two)\
  133. assertTrue_Primitive((one) != (two), one, two)
  134. #define assertGreaterThan_Primitive(one, two)\
  135. assertTrue_Primitive((one) > (two), one, two)
  136. #define assertGreaterThanEqualTo_Primitive(one, two)\
  137. assertTrue_Primitive((one) >= (two), one, two)
  138. #define assertLessThan_Primitive(one, two)\
  139. assertTrue_Primitive((one) < (two), one, two)
  140. #define assertLessThanEqualTo_Primitive(one, two)\
  141. assertTrue_Primitive((one) <= (two), one, two)
  142. #define assertNull(one)\
  143. assertTrue(one == NULL);
  144. #define assertNotNull(one)\
  145. assertTrue(one != NULL);
  146. #define assertCStringEquals(one, two)\
  147. if (test_unlikely(strcmp(one, two))){\
  148. FAIL(std::string(#one) + "==" + #two);\
  149. } else {\
  150. PASS(std::string(#one) + "==" + #two);\
  151. }
  152. #define assertCStringNotEquals(one, two)\
  153. if (test_unlikely(!strcmp(one, two))){\
  154. FAIL(std::string(#one) + "!=" + #two);\
  155. } else {\
  156. PASS(std::string(#one) + "!=" + #two);\
  157. }
  158. #define assertCStringEqualsW(one, two)\
  159. if (test_unlikely(wcscmp(one, two))){\
  160. FAIL(std::string(#one) + "==" + #two);\
  161. } else {\
  162. PASS(std::string(#one) + "==" + #two);\
  163. }
  164. #define assertCStringNotEqualsW(one, two)\
  165. if (test_unlikely(!wcscmp(one, two))){\
  166. FAIL(std::string(#one) + "!=" + #two);\
  167. } else {\
  168. PASS(std::string(#one) + "!=" + #two);\
  169. }
  170. #define assertException(code, exc)\
  171. {\
  172. bool failed = false;\
  173. try {\
  174. code;\
  175. } catch (exc){\
  176. PASS(std::string(#exc) + " caught");\
  177. failed = true;\
  178. }\
  179. if (test_unlikely(!failed)){ FAIL(std::string(#exc) + " not caught");}\
  180. }
  181. #define echo(something)\
  182. {\
  183. std::stringstream somet;\
  184. somet << something;\
  185. UnitTest::echo_(somet.str());\
  186. }
  187. #endif