X-Git-Url: https://git.saurik.com/apple/icu.git/blobdiff_plain/b331163bffd790ced0e88b73f44f86d49ccc48a5..4f1e1a09ce4daed860e35d359ce2fceccb0764e8:/icuSources/test/intltest/intltest.cpp diff --git a/icuSources/test/intltest/intltest.cpp b/icuSources/test/intltest/intltest.cpp index cfd944a1..e85ba87f 100644 --- a/icuSources/test/intltest/intltest.cpp +++ b/icuSources/test/intltest/intltest.cpp @@ -1,6 +1,8 @@ +// © 2016 and later: Unicode, Inc. and others. +// License & terms of use: http://www.unicode.org/copyright.html /******************************************************************** * COPYRIGHT: - * Copyright (c) 1997-2014, International Business Machines Corporation and + * Copyright (c) 1997-2016, International Business Machines Corporation and * others. All Rights Reserved. ********************************************************************/ @@ -11,34 +13,37 @@ * IntlTest is a base class for tests. */ -#include -#include #include #include +#include #include +#include +#include -#include "unicode/unistr.h" -#include "unicode/ures.h" -#include "unicode/smpdtfmt.h" -#include "unicode/ucnv.h" -#include "unicode/uclean.h" -#include "unicode/timezone.h" +#include "unicode/ctest.h" // for str_timeDelta #include "unicode/curramt.h" +#include "unicode/locid.h" #include "unicode/putil.h" +#include "unicode/smpdtfmt.h" +#include "unicode/timezone.h" +#include "unicode/uclean.h" +#include "unicode/ucnv.h" +#include "unicode/unistr.h" +#include "unicode/ures.h" +#include "unicode/utf16.h" #include "intltest.h" + #include "caltztst.h" -#include "itmajor.h" -#include "cstring.h" -#include "umutex.h" -#include "uassert.h" #include "cmemory.h" -#include "uoptions.h" - +#include "cstring.h" +#include "itmajor.h" +#include "mutex.h" #include "putilimp.h" // for uprv_getRawUTCtime() -#include "unicode/locid.h" -#include "unicode/ctest.h" // for str_timeDelta +#include "uassert.h" #include "udbgutil.h" +#include "umutex.h" +#include "uoptions.h" #ifdef XP_MAC_CONSOLE #include @@ -105,6 +110,18 @@ Int64ToUnicodeString(int64_t num) return buffer; } +UnicodeString +DoubleToUnicodeString(double num) +{ + char buffer[64]; // nos changed from 10 to 64 + char danger = 'p'; // guard against overrunning the buffer (rtg) + + sprintf(buffer, "%1.14e", num); + assert(danger == 'p'); + + return buffer; +} + // [LIU] Just to get things working UnicodeString operator+(const UnicodeString& left, @@ -221,6 +238,12 @@ UnicodeString toString(UBool b) { return b ? UnicodeString("TRUE"):UnicodeString("FALSE"); } +UnicodeString toString(const UnicodeSet& uniset, UErrorCode& status) { + UnicodeString result; + uniset.toPattern(result, status); + return result; +} + // stephen - cleaned up 05/05/99 UnicodeString operator+(const UnicodeString& left, char num) { return left + (long)num; } @@ -262,18 +285,25 @@ IntlTest::appendHex(uint32_t number, { case 8: target += digitString[(number >> 28) & 0xF]; + U_FALLTHROUGH; case 7: target += digitString[(number >> 24) & 0xF]; + U_FALLTHROUGH; case 6: target += digitString[(number >> 20) & 0xF]; + U_FALLTHROUGH; case 5: target += digitString[(number >> 16) & 0xF]; + U_FALLTHROUGH; case 4: target += digitString[(number >> 12) & 0xF]; + U_FALLTHROUGH; case 3: target += digitString[(number >> 8) & 0xF]; + U_FALLTHROUGH; case 2: target += digitString[(number >> 4) & 0xF]; + U_FALLTHROUGH; case 1: target += digitString[(number >> 0) & 0xF]; break; @@ -545,7 +575,7 @@ IntlTest::IntlTest() warn_on_missing_data = FALSE; quick = FALSE; leaks = FALSE; - threadCount = 1; + threadCount = 12; testoutfp = stdout; LL_indentlevel = indentLevel_offset; numProps = 0; @@ -561,6 +591,7 @@ void IntlTest::setCaller( IntlTest* callingTest ) verbose = caller->verbose; no_err_msg = caller->no_err_msg; quick = caller->quick; + threadCount = caller->threadCount; testoutfp = caller->testoutfp; LL_indentlevel = caller->LL_indentlevel + indentLevel_offset; numProps = caller->numProps; @@ -685,10 +716,10 @@ UBool IntlTest::runTest( char* name, char* par, char *baseName ) return rval; } -// call individual tests, to be overriden to call implementations +// call individual tests, to be overridden to call implementations void IntlTest::runIndexedTest( int32_t /*index*/, UBool /*exec*/, const char* & /*name*/, char* /*par*/ ) { - // to be overriden by a method like: + // to be overridden by a method like: /* switch (index) { case 0: name = "First Test"; if (exec) FirstTest( par ); break; @@ -696,7 +727,7 @@ void IntlTest::runIndexedTest( int32_t /*index*/, UBool /*exec*/, const char* & default: name = ""; break; } */ - this->errln("*** runIndexedTest needs to be overriden! ***"); + this->errln("*** runIndexedTest needs to be overridden! ***"); } @@ -933,7 +964,7 @@ void IntlTest::log(const char *fmt, ...) vsprintf(buffer, fmt, ap); va_end(ap); if( verbose ) { - log(UnicodeString(buffer, "")); + log(UnicodeString(buffer, (const char *)NULL)); } } @@ -947,7 +978,7 @@ void IntlTest::logln(const char *fmt, ...) vsprintf(buffer, fmt, ap); va_end(ap); if( verbose ) { - logln(UnicodeString(buffer, "")); + logln(UnicodeString(buffer, (const char *)NULL)); } } @@ -960,7 +991,7 @@ UBool IntlTest::logKnownIssue(const char *ticket, const char *fmt, ...) /* sprintf it just to make sure that the information is valid */ vsprintf(buffer, fmt, ap); va_end(ap); - return logKnownIssue(ticket, UnicodeString(buffer, "")); + return logKnownIssue(ticket, UnicodeString(buffer, (const char *)NULL)); } UBool IntlTest::logKnownIssue(const char *ticket) { @@ -973,8 +1004,8 @@ UBool IntlTest::logKnownIssue(const char *ticket, const UnicodeString &msg) { char fullpath[2048]; strcpy(fullpath, basePath); strcat(fullpath, currName); - UnicodeString msg2 =msg; - UBool firstForTicket, firstForWhere; + UnicodeString msg2 = msg; + UBool firstForTicket = TRUE, firstForWhere = TRUE; knownList = udbg_knownIssue_openU(knownList, ticket, fullpath, msg2.getTerminatedBuffer(), &firstForTicket, &firstForWhere); msg2 = UNICODE_STRING_SIMPLE("(Known issue #") + @@ -998,7 +1029,7 @@ void IntlTest::info(const char *fmt, ...) /* sprintf it just to make sure that the information is valid */ vsprintf(buffer, fmt, ap); va_end(ap); - info(UnicodeString(buffer, "")); + info(UnicodeString(buffer, (const char *)NULL)); } void IntlTest::infoln(const char *fmt, ...) @@ -1010,7 +1041,7 @@ void IntlTest::infoln(const char *fmt, ...) /* sprintf it just to make sure that the information is valid */ vsprintf(buffer, fmt, ap); va_end(ap); - infoln(UnicodeString(buffer, "")); + infoln(UnicodeString(buffer, (const char *)NULL)); } void IntlTest::err(const char *fmt, ...) @@ -1021,7 +1052,7 @@ void IntlTest::err(const char *fmt, ...) va_start(ap, fmt); vsprintf(buffer, fmt, ap); va_end(ap); - err(UnicodeString(buffer, "")); + err(UnicodeString(buffer, (const char *)NULL)); } void IntlTest::errln(const char *fmt, ...) @@ -1032,7 +1063,7 @@ void IntlTest::errln(const char *fmt, ...) va_start(ap, fmt); vsprintf(buffer, fmt, ap); va_end(ap); - errln(UnicodeString(buffer, "")); + errln(UnicodeString(buffer, (const char *)NULL)); } void IntlTest::dataerrln(const char *fmt, ...) @@ -1043,7 +1074,7 @@ void IntlTest::dataerrln(const char *fmt, ...) va_start(ap, fmt); vsprintf(buffer, fmt, ap); va_end(ap); - dataerrln(UnicodeString(buffer, "")); + dataerrln(UnicodeString(buffer, (const char *)NULL)); } void IntlTest::errcheckln(UErrorCode status, const char *fmt, ...) @@ -1056,9 +1087,9 @@ void IntlTest::errcheckln(UErrorCode status, const char *fmt, ...) va_end(ap); if (status == U_FILE_ACCESS_ERROR || status == U_MISSING_RESOURCE_ERROR) { - dataerrln(UnicodeString(buffer, "")); + dataerrln(UnicodeString(buffer, (const char *)NULL)); } else { - errln(UnicodeString(buffer, "")); + errln(UnicodeString(buffer, (const char *)NULL)); } } @@ -1078,8 +1109,16 @@ UBool IntlTest::printKnownIssues() } } +static UMutex messageMutex = U_MUTEX_INITIALIZER; + void IntlTest::LL_message( UnicodeString message, UBool newline ) { + // Synchronize this function. + // All error messages generated by tests funnel through here. + // Multithreaded tests can concurrently generate errors, requiring synchronization + // to keep each message together. + Mutex lock(&messageMutex); + // string that starts with a LineFeed character and continues // with spaces according to the current indentation static const UChar indentUChars[] = { @@ -1095,6 +1134,7 @@ void IntlTest::LL_message( UnicodeString message, UBool newline ) 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32, 32 }; + U_ASSERT(1 + LL_indentlevel <= UPRV_LENGTHOF(indentUChars)); UnicodeString indent(FALSE, indentUChars, 1 + LL_indentlevel); char buffer[30000]; @@ -1166,6 +1206,10 @@ IntlTest::run_phase2( char* name, char* par ) // supports reporting memory leaks # define TRY_CNV_2 "sjis" #endif +#ifdef UNISTR_COUNT_FINAL_STRING_LENGTHS +U_CAPI void unistr_printLengths(); +#endif + int main(int argc, char* argv[]) { @@ -1181,7 +1225,7 @@ main(int argc, char* argv[]) const char *summary_file = NULL; UBool warnOnMissingData = FALSE; UBool defaultDataFound = FALSE; - int32_t threadCount = 1; + int32_t threadCount = 12; UErrorCode errorCode = U_ZERO_ERROR; UConverter *cnv = NULL; const char *warnOrErr = "Failure"; @@ -1266,9 +1310,8 @@ main(int argc, char* argv[]) "### Options are: verbose (v), all (a), noerrormsg (n), \n" "### exhaustive (e), leaks (l), -x xmlfile.xml, prop:=, \n" "### notime (T), \n" - "### threads: (Mulithreading must first be \n" - "### enabled otherwise this will be ignored. \n" - "### The default thread count is 1.),\n" + "### threads:\n" + "### (The default thread count is 12.),\n" "### (Specify either -all (shortcut -a) or a test name). \n" "### -all will run all of the tests.\n" "### \n" @@ -1331,11 +1374,7 @@ main(int argc, char* argv[]) fprintf(stdout, " notime (T) : %s\n", (no_time? "On" : "Off")); fprintf(stdout, " noknownissues (K) : %s\n", (noKnownIssues? "On" : "Off")); fprintf(stdout, " Warn on missing data (w) : %s\n", (warnOnMissingData? "On" : "Off")); -#if (ICU_USE_THREADS==0) - fprintf(stdout, " Threads : Disabled\n"); -#else fprintf(stdout, " Threads : %d\n", threadCount); -#endif for (int32_t i = 0; i < nProps; i++) { fprintf(stdout, " Custom property (prop:) : %s\n", props[i]); } @@ -1524,6 +1563,10 @@ main(int argc, char* argv[]) u_cleanup(); } +#ifdef UNISTR_COUNT_FINAL_STRING_LENGTHS + unistr_printLengths(); +#endif + fprintf(stdout, "--------------------------------------\n"); if (execCount <= 0) { @@ -1776,6 +1819,39 @@ float IntlTest::random() { return random(&RAND_SEED); } + +/* + * Integer random number class implementation. + * Similar to C++ std::minstd_rand, with the same algorithm & constants. + */ +IntlTest::icu_rand::icu_rand(uint32_t seed) { + seed = seed % 2147483647UL; + if (seed == 0) { + seed = 1; + } + fLast = seed; +} + +IntlTest::icu_rand::~icu_rand() {} + +void IntlTest::icu_rand::seed(uint32_t seed) { + if (seed == 0) { + seed = 1; + } + fLast = seed; +} + +uint32_t IntlTest::icu_rand::operator() () { + fLast = ((uint64_t)fLast * 48271UL) % 2147483647UL; + return fLast; +} + +uint32_t IntlTest::icu_rand::getSeed() { + return (uint32_t) fLast; +} + + + static inline UChar toHex(int32_t i) { return (UChar)(i + (i < 10 ? 0x30 : (0x41 - 10))); } @@ -1825,9 +1901,13 @@ UBool IntlTest::assertTrue(const char* message, UBool condition, UBool quiet, UB return condition; } -UBool IntlTest::assertFalse(const char* message, UBool condition, UBool quiet) { +UBool IntlTest::assertFalse(const char* message, UBool condition, UBool quiet, UBool possibleDataError) { if (condition) { - errln("FAIL: assertFalse() failed: %s", message); + if (possibleDataError) { + dataerrln("FAIL: assertTrue() failed: %s", message); + } else { + errln("FAIL: assertTrue() failed: %s", message); + } } else if (!quiet) { logln("Ok: %s", message); } @@ -1926,6 +2006,25 @@ UBool IntlTest::assertEquals(const char* message, return TRUE; } +UBool IntlTest::assertEquals(const char* message, + double expected, + double actual) { + bool bothNaN = std::isnan(expected) && std::isnan(actual); + if (expected != actual && !bothNaN) { + errln((UnicodeString)"FAIL: " + message + "; got " + + actual + + "; expected " + expected); + return FALSE; + } +#ifdef VERBOSE_ASSERTIONS + else { + logln((UnicodeString)"Ok: " + message + "; got " + actual); + } +#endif + return TRUE; +} + + UBool IntlTest::assertEquals(const char* message, UBool expected, UBool actual) { @@ -1943,6 +2042,43 @@ UBool IntlTest::assertEquals(const char* message, return TRUE; } + +UBool IntlTest::assertEquals(const char* message, + UErrorCode expected, + UErrorCode actual) { + if (expected != actual) { + errln((UnicodeString)"FAIL: " + message + "; got " + + u_errorName(actual) + + "; expected " + u_errorName(expected)); + return FALSE; + } +#ifdef VERBOSE_ASSERTIONS + else { + logln((UnicodeString)"Ok: " + message + "; got " + u_errorName(actual)); + } +#endif + return TRUE; +} + +UBool IntlTest::assertEquals(const char* message, + const UnicodeSet& expected, + const UnicodeSet& actual) { + IcuTestErrorCode status(*this, "assertEqualsUniSet"); + if (expected != actual) { + errln((UnicodeString)"FAIL: " + message + "; got " + + toString(actual, status) + + "; expected " + toString(expected, status)); + return FALSE; + } +#ifdef VERBOSE_ASSERTIONS + else { + logln((UnicodeString)"Ok: " + message + "; got " + toString(actual, status)); + } +#endif + return TRUE; +} + + #if !UCONFIG_NO_FORMATTING UBool IntlTest::assertEquals(const char* message, const Formattable& expected, @@ -1979,12 +2115,12 @@ static const char* extractToAssertBuf(const UnicodeString& message) { return ASSERT_BUF; } -UBool IntlTest::assertTrue(const UnicodeString& message, UBool condition, UBool quiet) { - return assertTrue(extractToAssertBuf(message), condition, quiet); +UBool IntlTest::assertTrue(const UnicodeString& message, UBool condition, UBool quiet, UBool possibleDataError) { + return assertTrue(extractToAssertBuf(message), condition, quiet, possibleDataError); } -UBool IntlTest::assertFalse(const UnicodeString& message, UBool condition, UBool quiet) { - return assertFalse(extractToAssertBuf(message), condition, quiet); +UBool IntlTest::assertFalse(const UnicodeString& message, UBool condition, UBool quiet, UBool possibleDataError) { + return assertFalse(extractToAssertBuf(message), condition, quiet, possibleDataError); } UBool IntlTest::assertSuccess(const UnicodeString& message, UErrorCode ec) { @@ -2018,6 +2154,21 @@ UBool IntlTest::assertEquals(const UnicodeString& message, int64_t actual) { return assertEquals(extractToAssertBuf(message), expected, actual); } +UBool IntlTest::assertEquals(const UnicodeString& message, + double expected, + double actual) { + return assertEquals(extractToAssertBuf(message), expected, actual); +} +UBool IntlTest::assertEquals(const UnicodeString& message, + UErrorCode expected, + UErrorCode actual) { + return assertEquals(extractToAssertBuf(message), expected, actual); +} +UBool IntlTest::assertEquals(const UnicodeString& message, + const UnicodeSet& expected, + const UnicodeSet& actual) { + return assertEquals(extractToAssertBuf(message), expected, actual); +} #if !UCONFIG_NO_FORMATTING UBool IntlTest::assertEquals(const UnicodeString& message,