1 // © 2016 and later: Unicode, Inc. and others. 2 // License & terms of use: http://www.unicode.org/copyright.html 3 /******************************************************************** 4 * COPYRIGHT: 5 * Copyright (c) 1997-2016, International Business Machines Corporation and 6 * others. All Rights Reserved. 7 ********************************************************************/ 8 9 10 /** 11 * IntlTest is a base class for tests. */ 12 13 #ifndef _INTLTEST 14 #define _INTLTEST 15 16 // The following includes utypes.h, uobject.h and unistr.h 17 #include "unicode/fmtable.h" 18 #include "unicode/testlog.h" 19 #include "unicode/uniset.h" 20 21 U_NAMESPACE_USE 22 23 #if U_PLATFORM == U_PF_OS390 24 // avoid collision with math.h/log() 25 // this must be after including utypes.h so that U_PLATFORM is actually defined 26 #pragma map(IntlTest::log( const UnicodeString &message ),"logos390") 27 #endif 28 29 //----------------------------------------------------------------------------- 30 //convenience classes to ease porting code that uses the Java 31 //string-concatenation operator (moved from findword test by rtg) 32 UnicodeString UCharToUnicodeString(UChar c); 33 UnicodeString Int64ToUnicodeString(int64_t num); 34 UnicodeString DoubleToUnicodeString(double num); 35 //UnicodeString operator+(const UnicodeString& left, int64_t num); // Some compilers don't allow this because of the long type. 36 UnicodeString operator+(const UnicodeString& left, long num); 37 UnicodeString operator+(const UnicodeString& left, unsigned long num); 38 UnicodeString operator+(const UnicodeString& left, double num); 39 UnicodeString operator+(const UnicodeString& left, char num); 40 UnicodeString operator+(const UnicodeString& left, short num); 41 UnicodeString operator+(const UnicodeString& left, int num); 42 UnicodeString operator+(const UnicodeString& left, unsigned char num); 43 UnicodeString operator+(const UnicodeString& left, unsigned short num); 44 UnicodeString operator+(const UnicodeString& left, unsigned int num); 45 UnicodeString operator+(const UnicodeString& left, float num); 46 #if !UCONFIG_NO_FORMATTING 47 UnicodeString toString(const Formattable& f); // liu 48 UnicodeString toString(int32_t n); 49 #endif 50 UnicodeString toString(UBool b); 51 52 //----------------------------------------------------------------------------- 53 54 // Use the TESTCASE macro in subclasses of IntlTest. Define the 55 // runIndexedTest method in this fashion: 56 // 57 //| void MyTest::runIndexedTest(int32_t index, UBool exec, 58 //| const char* &name, char* /*par*/) { 59 //| switch (index) { 60 //| TESTCASE(0,TestSomething); 61 //| TESTCASE(1,TestSomethingElse); 62 //| TESTCASE(2,TestAnotherThing); 63 //| default: name = ""; break; 64 //| } 65 //| } 66 #define TESTCASE(id,test) \ 67 case id: \ 68 name = #test; \ 69 if (exec) { \ 70 logln(#test "---"); \ 71 logln(); \ 72 test(); \ 73 } \ 74 break 75 76 // More convenient macros. These allow easy reordering of the test cases. 77 // 78 //| void MyTest::runIndexedTest(int32_t index, UBool exec, 79 //| const char* &name, char* /*par*/) { 80 //| TESTCASE_AUTO_BEGIN; 81 //| TESTCASE_AUTO(TestSomething); 82 //| TESTCASE_AUTO(TestSomethingElse); 83 //| TESTCASE_AUTO(TestAnotherThing); 84 //| TESTCASE_AUTO_END; 85 //| } 86 #define TESTCASE_AUTO_BEGIN \ 87 for(;;) { \ 88 int32_t testCaseAutoNumber = 0 89 90 #define TESTCASE_AUTO(test) \ 91 if (index == testCaseAutoNumber++) { \ 92 name = #test; \ 93 if (exec) { \ 94 logln(#test "---"); \ 95 logln(); \ 96 test(); \ 97 } \ 98 break; \ 99 } 100 101 #define TESTCASE_AUTO_CLASS(TestClass) \ 102 if (index == testCaseAutoNumber++) { \ 103 name = #TestClass; \ 104 if (exec) { \ 105 logln(#TestClass "---"); \ 106 logln(); \ 107 TestClass test; \ 108 callTest(test, par); \ 109 } \ 110 break; \ 111 } 112 113 #define TESTCASE_AUTO_CREATE_CLASS(TestClass) \ 114 if (index == testCaseAutoNumber++) { \ 115 name = #TestClass; \ 116 if (exec) { \ 117 logln(#TestClass "---"); \ 118 logln(); \ 119 LocalPointer<IntlTest> test(create##TestClass()); \ 120 callTest(*test, par); \ 121 } \ 122 break; \ 123 } 124 125 #define TESTCASE_AUTO_END \ 126 name = ""; \ 127 break; \ 128 } 129 130 #define TEST_ASSERT_TRUE(x) \ 131 assertTrue(#x, (x), FALSE, FALSE, __FILE__, __LINE__) 132 133 #define TEST_ASSERT_STATUS(x) \ 134 assertSuccess(#x, (x), FALSE, __FILE__, __LINE__) 135 136 class IntlTest : public TestLog { 137 public: 138 139 IntlTest(); 140 // TestLog has a virtual destructor. 141 142 virtual UBool runTest( char* name = NULL, char* par = NULL, char *baseName = NULL); // not to be overidden 143 144 virtual UBool setVerbose( UBool verbose = TRUE ); 145 virtual UBool setNoErrMsg( UBool no_err_msg = TRUE ); 146 virtual UBool setQuick( UBool quick = TRUE ); 147 virtual UBool setLeaks( UBool leaks = TRUE ); 148 virtual UBool setNotime( UBool no_time = TRUE ); 149 virtual UBool setWarnOnMissingData( UBool warn_on_missing_data = TRUE ); 150 virtual int32_t setThreadCount( int32_t count = 1); 151 152 virtual int32_t getErrors( void ); 153 virtual int32_t getDataErrors (void ); 154 155 virtual void setCaller( IntlTest* callingTest ); // for internal use only 156 virtual void setPath( char* path ); // for internal use only 157 158 virtual void log( const UnicodeString &message ); 159 160 virtual void logln( const UnicodeString &message ); 161 162 virtual void logln( void ); 163 164 /** 165 * Replaces isICUVersionAtLeast and isICUVersionBefore 166 * log that an issue is known. 167 * Usually used this way: 168 * <code>if( ... && logKnownIssue("12345", "some bug")) continue; </code> 169 * @param ticket ticket string, "12345" or "cldrbug:1234" 170 * @param message optional message string 171 * @return true if test should be skipped 172 */ 173 UBool logKnownIssue( const char *ticket, const UnicodeString &message ); 174 /** 175 * Replaces isICUVersionAtLeast and isICUVersionBefore 176 * log that an issue is known. 177 * Usually used this way: 178 * <code>if( ... && logKnownIssue("12345", "some bug")) continue; </code> 179 * @param ticket ticket string, "12345" or "cldrbug:1234" 180 * @return true if test should be skipped 181 */ 182 UBool logKnownIssue( const char *ticket ); 183 /** 184 * Replaces isICUVersionAtLeast and isICUVersionBefore 185 * log that an issue is known. 186 * Usually used this way: 187 * <code>if( ... && logKnownIssue("12345", "some bug")) continue; </code> 188 * @param ticket ticket string, "12345" or "cldrbug:1234" 189 * @param message optional message string 190 * @return true if test should be skipped 191 */ 192 UBool logKnownIssue( const char *ticket, const char *fmt, ...); 193 194 virtual void info( const UnicodeString &message ); 195 196 virtual void infoln( const UnicodeString &message ); 197 198 virtual void infoln( void ); 199 200 virtual void err(void); 201 202 virtual void err( const UnicodeString &message ); 203 204 virtual void errln( const UnicodeString &message ); 205 206 virtual void dataerr( const UnicodeString &message ); 207 208 virtual void dataerrln( const UnicodeString &message ); 209 210 void errcheckln(UErrorCode status, const UnicodeString &message ); 211 212 // convenience functions: sprintf() + errln() etc. 213 void log(const char *fmt, ...); 214 void logln(const char *fmt, ...); 215 void info(const char *fmt, ...); 216 void infoln(const char *fmt, ...); 217 void err(const char *fmt, ...); 218 void errln(const char *fmt, ...); 219 void dataerr(const char *fmt, ...); 220 void dataerrln(const char *fmt, ...); 221 222 /** 223 * logs an error (even if status==U_ZERO_ERROR), but 224 * calls dataerrln() or errln() depending on the type of error. 225 * Does not report the status code. 226 * @param status parameter for selecting whether errln or dataerrln is called. 227 */ 228 void errcheckln(UErrorCode status, const char *fmt, ...); 229 230 // Print ALL named errors encountered so far 231 void printErrors(); 232 233 // print known issues. return TRUE if there were any. 234 UBool printKnownIssues(); 235 236 virtual void usage( void ) ; 237 238 /** 239 * Returns a uniform random value x, with 0.0 <= x < 1.0. Use 240 * with care: Does not return all possible values; returns one of 241 * 714,025 values, uniformly spaced. However, the period is 242 * effectively infinite. See: Numerical Recipes, section 7.1. 243 * 244 * @param seedp pointer to seed. Set *seedp to any negative value 245 * to restart the sequence. 246 */ 247 static float random(int32_t* seedp); 248 249 /** 250 * Convenience method using a global seed. 251 */ 252 static float random(); 253 254 255 /** 256 * Integer random numbers, similar to C++ std::minstd_rand, with the same algorithm 257 * and constants. Allow additional access to internal state, for use by monkey tests, 258 * which need to recreate previous random sequences beginning near a failure point. 259 */ 260 class icu_rand { 261 public: 262 icu_rand(uint32_t seed = 1); 263 ~icu_rand(); 264 void seed(uint32_t seed); 265 uint32_t operator()(); 266 /** 267 * Get a seed corresponding to the current state of the generator. 268 * Seeding any generator with this value will cause it to produce the 269 * same sequence as this one will from this point forward. 270 */ 271 uint32_t getSeed(); 272 private: 273 uint32_t fLast; 274 }; 275 276 277 278 enum { kMaxProps = 16 }; 279 280 virtual void setProperty(const char* propline); 281 virtual const char* getProperty(const char* prop); 282 283 /* JUnit-like assertions. Each returns TRUE if it succeeds. */ 284 UBool assertTrue(const char* message, UBool condition, UBool quiet=FALSE, UBool possibleDataError=FALSE, const char *file=NULL, int line=0); 285 UBool assertFalse(const char* message, UBool condition, UBool quiet=FALSE, UBool possibleDataError=FALSE); 286 /** 287 * @param possibleDataError - if TRUE, use dataerrln instead of errcheckln on failure 288 * @return TRUE on success, FALSE on failure. 289 */ 290 UBool assertSuccess(const char* message, UErrorCode ec, UBool possibleDataError=FALSE, const char *file=NULL, int line=0); 291 UBool assertEquals(const char* message, const UnicodeString& expected, 292 const UnicodeString& actual, UBool possibleDataError=FALSE); 293 UBool assertEquals(const char* message, const char* expected, const char* actual); 294 UBool assertEquals(const char* message, UBool expected, UBool actual); 295 UBool assertEquals(const char* message, int32_t expected, int32_t actual); 296 UBool assertEquals(const char* message, int64_t expected, int64_t actual); 297 UBool assertEquals(const char* message, double expected, double actual); 298 UBool assertEquals(const char* message, UErrorCode expected, UErrorCode actual); 299 UBool assertEquals(const char* message, const UnicodeSet& expected, const UnicodeSet& actual); 300 #if !UCONFIG_NO_FORMATTING 301 UBool assertEquals(const char* message, const Formattable& expected, 302 const Formattable& actual, UBool possibleDataError=FALSE); 303 UBool assertEquals(const UnicodeString& message, const Formattable& expected, 304 const Formattable& actual); 305 #endif 306 UBool assertTrue(const UnicodeString& message, UBool condition, UBool quiet=FALSE, UBool possibleDataError=FALSE); 307 UBool assertFalse(const UnicodeString& message, UBool condition, UBool quiet=FALSE, UBool possibleDataError=FALSE); 308 UBool assertSuccess(const UnicodeString& message, UErrorCode ec); 309 UBool assertEquals(const UnicodeString& message, const UnicodeString& expected, 310 const UnicodeString& actual, UBool possibleDataError=FALSE); 311 UBool assertEquals(const UnicodeString& message, const char* expected, const char* actual); 312 UBool assertEquals(const UnicodeString& message, UBool expected, UBool actual); 313 UBool assertEquals(const UnicodeString& message, int32_t expected, int32_t actual); 314 UBool assertEquals(const UnicodeString& message, int64_t expected, int64_t actual); 315 UBool assertEquals(const UnicodeString& message, double expected, double actual); 316 UBool assertEquals(const UnicodeString& message, UErrorCode expected, UErrorCode actual); 317 UBool assertEquals(const UnicodeString& message, const UnicodeSet& expected, const UnicodeSet& actual); 318 319 virtual void runIndexedTest( int32_t index, UBool exec, const char* &name, char* par = NULL ); // overide ! 320 321 virtual UBool runTestLoop( char* testname, char* par, char *baseName ); 322 323 virtual int32_t IncErrorCount( void ); 324 325 virtual int32_t IncDataErrorCount( void ); 326 327 virtual UBool callTest( IntlTest& testToBeCalled, char* par ); 328 329 330 UBool verbose; 331 UBool no_err_msg; 332 UBool quick; 333 UBool leaks; 334 UBool warn_on_missing_data; 335 UBool no_time; 336 int32_t threadCount; 337 338 private: 339 UBool LL_linestart; 340 int32_t LL_indentlevel; 341 342 int32_t errorCount; 343 int32_t dataErrorCount; 344 IntlTest* caller; 345 char* testPath; // specifies subtests 346 347 char basePath[1024]; 348 char currName[1024]; // current test name 349 350 //FILE *testoutfp; 351 void *testoutfp; 352 353 const char* proplines[kMaxProps]; 354 int32_t numProps; 355 356 protected: 357 358 virtual void LL_message( UnicodeString message, UBool newline ); 359 360 // used for collation result reporting, defined here for convenience 361 362 static UnicodeString &prettify(const UnicodeString &source, UnicodeString &target); 363 static UnicodeString prettify(const UnicodeString &source, UBool parseBackslash=FALSE); 364 // digits=-1 determines the number of digits automatically 365 static UnicodeString &appendHex(uint32_t number, int32_t digits, UnicodeString &target); 366 static UnicodeString toHex(uint32_t number, int32_t digits=-1); 367 static inline UnicodeString toHex(int32_t number, int32_t digits=-1) { 368 return toHex((uint32_t)number, digits); 369 } 370 371 public: 372 static void setICU_DATA(); // Set up ICU_DATA if necessary. 373 374 static const char* pathToDataDirectory(); 375 376 public: 377 UBool run_phase2( char* name, char* par ); // internally, supports reporting memory leaks 378 static const char* loadTestData(UErrorCode& err); 379 virtual const char* getTestDataPath(UErrorCode& err); 380 static const char* getSourceTestData(UErrorCode& err); 381 static char *getUnidataPath(char path[]); 382 383 // static members 384 public: 385 static IntlTest* gTest; 386 static const char* fgDataDir; 387 388 }; 389 390 void it_log( UnicodeString message ); 391 void it_logln( UnicodeString message ); 392 void it_logln( void ); 393 void it_info( UnicodeString message ); 394 void it_infoln( UnicodeString message ); 395 void it_infoln( void ); 396 void it_err(void); 397 void it_err( UnicodeString message ); 398 void it_errln( UnicodeString message ); 399 void it_dataerr( UnicodeString message ); 400 void it_dataerrln( UnicodeString message ); 401 402 /** 403 * This is a variant of cintltst/ccolltst.c:CharsToUChars(). 404 * It converts a character string into a UnicodeString, with 405 * unescaping \u sequences. 406 */ 407 extern UnicodeString CharsToUnicodeString(const char* chars); 408 409 /* alias for CharsToUnicodeString */ 410 extern UnicodeString ctou(const char* chars); 411 412 #endif // _INTLTEST 413