1b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru/*********************************************************************** 2b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * COPYRIGHT: 38393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius * Copyright (c) 1997-2013, International Business Machines Corporation 4b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru * and others. All Rights Reserved. 5b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru ***********************************************************************/ 6b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 7b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "unicode/utypes.h" 8b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 9b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#if !UCONFIG_NO_FORMATTING 10b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 11b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "callimts.h" 12b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "caltest.h" 13b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "unicode/calendar.h" 14b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "unicode/gregocal.h" 15b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "unicode/datefmt.h" 16b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "unicode/smpdtfmt.h" 17b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#include "putilimp.h" 18c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru#include "cstring.h" 19b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 20b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste QueruU_NAMESPACE_USE 21b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruvoid CalendarLimitTest::runIndexedTest( int32_t index, UBool exec, const char* &name, char* /*par*/ ) 22b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru{ 23b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (exec) logln("TestSuite TestCalendarLimit"); 24b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru switch (index) { 25b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // Re-enable this later 26b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru case 0: 27c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru name = "TestCalendarExtremeLimit"; 28b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (exec) { 29c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln("TestCalendarExtremeLimit---"); logln(""); 30c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru TestCalendarExtremeLimit(); 31b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 32b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru break; 33c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru case 1: 34c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru name = "TestLimits"; 35c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (exec) { 36c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln("TestLimits---"); logln(""); 37c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru TestLimits(); 38c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 39c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru break; 40c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 41b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru default: name = ""; break; 42b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 43b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru} 44b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 45b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 46b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// ***************************************************************************** 47b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// class CalendarLimitTest 48b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// ***************************************************************************** 49b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 50b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// ------------------------------------- 51b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruvoid 52103e9ffba2cba345d0078eb8b8db33249f81840aCraig CorneliusCalendarLimitTest::test(UDate millis, icu::Calendar* cal, icu::DateFormat* fmt) 53b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru{ 54b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru static const UDate kDrift = 1e-10; 55b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UErrorCode exception = U_ZERO_ERROR; 56b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UnicodeString theDate; 57b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UErrorCode status = U_ZERO_ERROR; 58b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru cal->setTime(millis, exception); 59b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if (U_SUCCESS(exception)) { 60b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru fmt->format(millis, theDate); 61b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UDate dt = fmt->parse(theDate, status); 62b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // allow a small amount of error (drift) 63b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if(! withinErr(dt, millis, kDrift)) { 64b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru errln("FAIL:round trip for large milli, got: %.1lf wanted: %.1lf. (delta %.2lf greater than %.2lf)", 65b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru dt, millis, uprv_fabs(millis-dt), uprv_fabs(dt*kDrift)); 66b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru logln(UnicodeString(" ") + theDate + " " + CalendarTest::calToStr(*cal)); 67b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } else { 68b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru logln(UnicodeString("OK: got ") + dt + ", wanted " + millis); 69b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru logln(UnicodeString(" ") + theDate); 70b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 71b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 72b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru} 73b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 74b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// ------------------------------------- 75b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 76b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// bug 986c: deprecate nextDouble/previousDouble 77b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|double 78b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|CalendarLimitTest::nextDouble(double a) 79b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|{ 80b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//| return uprv_nextDouble(a, TRUE); 81b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|} 82b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//| 83b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|double 84b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|CalendarLimitTest::previousDouble(double a) 85b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|{ 86b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//| return uprv_nextDouble(a, FALSE); 87b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru//|} 88b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 89b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste QueruUBool 90b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste QueruCalendarLimitTest::withinErr(double a, double b, double err) 91b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru{ 92b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return ( uprv_fabs(a - b) < uprv_fabs(a * err) ); 93b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru} 94b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 95b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queruvoid 96c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste QueruCalendarLimitTest::TestCalendarExtremeLimit() 97b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru{ 98b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UErrorCode status = U_ZERO_ERROR; 99b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru Calendar *cal = Calendar::createInstance(status); 10050294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho if (failure(status, "Calendar::createInstance", TRUE)) return; 101b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru cal->adoptTimeZone(TimeZone::createTimeZone("GMT")); 102b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru DateFormat *fmt = DateFormat::createDateTimeInstance(); 103b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru if(!fmt || !cal) { 104b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru dataerrln("can't open cal and/or fmt"); 105b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru return; 106b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 107b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru fmt->adoptCalendar(cal); 108b26ce3a7367e4ed2ee7ddddcdc3f3d3377a455c2claireho ((SimpleDateFormat*) fmt)->applyPattern("HH:mm:ss.SSS Z, EEEE, MMMM d, yyyy G"); 109b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 110b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 111b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // This test used to test the algorithmic limits of the dates that 112b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // GregorianCalendar could handle. However, the algorithm has 113b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // been rewritten completely since then and the prior limits no 114b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // longer apply. Instead, we now do basic round-trip testing of 115b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // some extreme (but still manageable) dates. 116b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UDate m; 117b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru logln("checking 1e16..1e17"); 118b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru for ( m = 1e16; m < 1e17; m *= 1.1) { 119b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru test(m, cal, fmt); 120b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 121b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru logln("checking -1e14..-1e15"); 122b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru for ( m = -1e14; m > -1e15; m *= 1.1) { 123b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru test(m, cal, fmt); 124b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru } 125b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 126b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // This is 2^52 - 1, the largest allowable mantissa with a 0 127b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // exponent in a 64-bit double 128b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UDate VERY_EARLY_MILLIS = - 4503599627370495.0; 129b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru UDate VERY_LATE_MILLIS = 4503599627370495.0; 130b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 131b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // I am removing the previousDouble and nextDouble calls below for 132b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // two reasons: 1. As part of jitterbug 986, I am deprecating 133b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // these methods and removing calls to them. 2. This test is a 134b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru // non-critical boundary behavior test. 135b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru test(VERY_EARLY_MILLIS, cal, fmt); 136b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru //test(previousDouble(VERY_EARLY_MILLIS), cal, fmt); 137b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru test(VERY_LATE_MILLIS, cal, fmt); 138b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru //test(nextDouble(VERY_LATE_MILLIS), cal, fmt); 139b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru delete fmt; 140b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru} 141b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 142c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queruvoid 143c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste QueruCalendarLimitTest::TestLimits(void) { 144c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru static const UDate DEFAULT_START = 944006400000.0; // 1999-12-01T00:00Z 14550294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho static const int32_t DEFAULT_END = -120; // Default for non-quick is run 2 minutes 146c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 147c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru static const struct { 148c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru const char *type; 149c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UBool hasLeapMonth; 150c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UDate actualTestStart; 15150294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho int32_t actualTestEnd; 152c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } TestCases[] = { 15350294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"gregorian", FALSE, DEFAULT_START, DEFAULT_END}, 15450294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"japanese", FALSE, 596937600000.0, DEFAULT_END}, // 1988-12-01T00:00Z, Showa 63 15550294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"buddhist", FALSE, DEFAULT_START, DEFAULT_END}, 15650294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"roc", FALSE, DEFAULT_START, DEFAULT_END}, 15750294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"persian", FALSE, DEFAULT_START, DEFAULT_END}, 15850294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"islamic-civil", FALSE, DEFAULT_START, DEFAULT_END}, 15950294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"islamic", FALSE, DEFAULT_START, 800000}, // Approx. 2250 years from now, after which some rounding errors occur in Islamic calendar 16050294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"hebrew", TRUE, DEFAULT_START, DEFAULT_END}, 16150294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"chinese", TRUE, DEFAULT_START, DEFAULT_END}, 1628393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius {"dangi", TRUE, DEFAULT_START, DEFAULT_END}, 16350294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"indian", FALSE, DEFAULT_START, DEFAULT_END}, 16450294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"coptic", FALSE, DEFAULT_START, DEFAULT_END}, 16550294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"ethiopic", FALSE, DEFAULT_START, DEFAULT_END}, 16650294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho {"ethiopic-amete-alem", FALSE, DEFAULT_START, DEFAULT_END}, 16727f654740f2a26ad62a5c155af9199af9e69b889claireho {NULL, FALSE, 0, 0} 168c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru }; 169c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 170c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int16_t i = 0; 171c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru char buf[64]; 172c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 173c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru for (i = 0; TestCases[i].type; i++) { 174c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UErrorCode status = U_ZERO_ERROR; 175c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru uprv_strcpy(buf, "root@calendar="); 176c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru strcat(buf, TestCases[i].type); 177c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru Calendar *cal = Calendar::createInstance(buf, status); 17850294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho if (failure(status, "Calendar::createInstance", TRUE)) { 179c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru continue; 180c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 181c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (uprv_strcmp(cal->getType(), TestCases[i].type) != 0) { 182c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: Wrong calendar type: " + cal->getType() 183c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + " Requested: " + TestCases[i].type); 184c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru delete cal; 185c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru continue; 186c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 187c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Do the test 188c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru doTheoreticalLimitsTest(*cal, TestCases[i].hasLeapMonth); 18950294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho doLimitsTest(*cal, TestCases[i].actualTestStart,TestCases[i].actualTestEnd); 190c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru delete cal; 191c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 192c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru} 193c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 194c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queruvoid 195c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste QueruCalendarLimitTest::doTheoreticalLimitsTest(Calendar& cal, UBool leapMonth) { 196c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru const char* calType = cal.getType(); 197c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 198c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t nDOW = cal.getMaximum(UCAL_DAY_OF_WEEK); 199c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxDOY = cal.getMaximum(UCAL_DAY_OF_YEAR); 200c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t lmaxDOW = cal.getLeastMaximum(UCAL_DAY_OF_YEAR); 201c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxWOY = cal.getMaximum(UCAL_WEEK_OF_YEAR); 202c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t lmaxWOY = cal.getLeastMaximum(UCAL_WEEK_OF_YEAR); 203c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxM = cal.getMaximum(UCAL_MONTH) + 1; 204c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t lmaxM = cal.getLeastMaximum(UCAL_MONTH) + 1; 205c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxDOM = cal.getMaximum(UCAL_DAY_OF_MONTH); 206c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t lmaxDOM = cal.getLeastMaximum(UCAL_DAY_OF_MONTH); 207c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxDOWIM = cal.getMaximum(UCAL_DAY_OF_WEEK_IN_MONTH); 208c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t lmaxDOWIM = cal.getLeastMaximum(UCAL_DAY_OF_WEEK_IN_MONTH); 209c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxWOM = cal.getMaximum(UCAL_WEEK_OF_MONTH); 210c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t lmaxWOM = cal.getLeastMaximum(UCAL_WEEK_OF_MONTH); 211c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t minDaysInFirstWeek = cal.getMinimalDaysInFirstWeek(); 212c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 213c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Day of year 214c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t expected; 215c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (!leapMonth) { 216c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = maxM*maxDOM; 217c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (maxDOY > expected) { 218c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Maximum value of DAY_OF_YEAR is too big: " 219c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + maxDOY + "/expected: <=" + expected); 220c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 221c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = lmaxM*lmaxDOM; 222c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (lmaxDOW < expected) { 223c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Least maximum value of DAY_OF_YEAR is too small: " 224c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + lmaxDOW + "/expected: >=" + expected); 225c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 226c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 227c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 228c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Week of year 229c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = maxDOY/nDOW + 1; 230c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (maxWOY > expected) { 231c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Maximum value of WEEK_OF_YEAR is too big: " 232c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + maxWOY + "/expected: <=" + expected); 233c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 234c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = lmaxDOW/nDOW; 235c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (lmaxWOY < expected) { 236c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Least maximum value of WEEK_OF_YEAR is too small: " 237c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + lmaxWOY + "/expected >=" + expected); 238c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 239c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 240c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Day of week in month 241c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = (maxDOM + nDOW - 1)/nDOW; 242c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (maxDOWIM != expected) { 243c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Maximum value of DAY_OF_WEEK_IN_MONTH is incorrect: " 244c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + maxDOWIM + "/expected: " + expected); 245c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 246c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = (lmaxDOM + nDOW - 1)/nDOW; 247c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (lmaxDOWIM != expected) { 248c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Least maximum value of DAY_OF_WEEK_IN_MONTH is incorrect: " 249c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + lmaxDOWIM + "/expected: " + expected); 250c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 251c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 252c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Week of month 253c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = (maxDOM + (nDOW - 1) + (nDOW - minDaysInFirstWeek)) / nDOW; 254c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (maxWOM != expected) { 255c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Maximum value of WEEK_OF_MONTH is incorrect: " 256c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + maxWOM + "/expected: " + expected); 257c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 258c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru expected = (lmaxDOM + (nDOW - minDaysInFirstWeek)) / nDOW; 259c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (lmaxWOM != expected) { 260c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"FAIL: [" + calType + "] Least maximum value of WEEK_OF_MONTH is incorrect: " 261c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + lmaxWOM + "/expected: " + expected); 262c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 263c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru} 264c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 265c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queruvoid 26650294ead5e5d23f5bbfed76e00e6b510bd41eee1clairehoCalendarLimitTest::doLimitsTest(Calendar& cal, UDate startDate, int32_t endTime) { 26750294ead5e5d23f5bbfed76e00e6b510bd41eee1claireho int32_t testTime = quick ? ( endTime / 40 ) : endTime; 268c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru doLimitsTest(cal, NULL /*default fields*/, startDate, testTime); 269c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru} 270c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 271c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queruvoid 272c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste QueruCalendarLimitTest::doLimitsTest(Calendar& cal, 273c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru const int32_t* fieldsToTest, 274c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UDate startDate, 275c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t testDuration) { 276c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru static const int32_t FIELDS[] = { 277c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_ERA, 278c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_YEAR, 279c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_MONTH, 280c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_WEEK_OF_YEAR, 281c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_WEEK_OF_MONTH, 282c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_DAY_OF_MONTH, 283c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_DAY_OF_YEAR, 284c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_DAY_OF_WEEK_IN_MONTH, 285c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_YEAR_WOY, 286c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCAL_EXTENDED_YEAR, 287c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru -1, 288c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru }; 289c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 290c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru static const char* FIELD_NAME[] = { 291c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "ERA", "YEAR", "MONTH", "WEEK_OF_YEAR", "WEEK_OF_MONTH", 292c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "DAY_OF_MONTH", "DAY_OF_YEAR", "DAY_OF_WEEK", 293c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "DAY_OF_WEEK_IN_MONTH", "AM_PM", "HOUR", "HOUR_OF_DAY", 294c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "MINUTE", "SECOND", "MILLISECOND", "ZONE_OFFSET", 295c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "DST_OFFSET", "YEAR_WOY", "DOW_LOCAL", "EXTENDED_YEAR", 296c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "JULIAN_DAY", "MILLISECONDS_IN_DAY", 297c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru "IS_LEAP_MONTH" 298c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru }; 299c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 300c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UErrorCode status = U_ZERO_ERROR; 301c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t i, j; 302c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UnicodeString ymd; 303c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 304c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru GregorianCalendar greg(status); 305c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (failure(status, "new GregorianCalendar")) { 306c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru return; 307c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 308c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru greg.setTime(startDate, status); 309c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (failure(status, "GregorianCalendar::setTime")) { 310c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru return; 311c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 312c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln((UnicodeString)"Start: " + startDate); 313c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 314c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (fieldsToTest == NULL) { 315c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru fieldsToTest = FIELDS; 316c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 317c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 318c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 319c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Keep a record of minima and maxima that we actually see. 320c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // These are kept in an array of arrays of hashes. 321c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t limits[UCAL_FIELD_COUNT][4]; 322c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru for (j = 0; j < UCAL_FIELD_COUNT; j++) { 323c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][0] = INT32_MAX; 324c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][1] = INT32_MIN; 325c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][2] = INT32_MAX; 326c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][3] = INT32_MIN; 327c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 328c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 329c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // This test can run for a long time; show progress. 330c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UDate millis = ucal_getNow(); 331c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UDate mark = millis + 5000; // 5 sec 332c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru millis -= testDuration * 1000; // stop time if testDuration<0 333c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 334c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru for (i = 0; 335c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru testDuration > 0 ? i < testDuration 336c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru : ucal_getNow() < millis; 337c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ++i) { 338c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (ucal_getNow() >= mark) { 339c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln((UnicodeString)"(" + i + " days)"); 340c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru mark += 5000; // 5 sec 341c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 3428393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius UDate testMillis = greg.getTime(status); 3438393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius cal.setTime(testMillis, status); 344b0ac937921a2c196d8b9da665135bf6ba01a1ccfJean-Baptiste Queru cal.setMinimalDaysInFirstWeek(1); 345c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (failure(status, "Calendar set/getTime")) { 346c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru return; 347c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 348c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru for (j = 0; fieldsToTest[j] >= 0; ++j) { 349c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCalendarDateFields f = (UCalendarDateFields)fieldsToTest[j]; 350c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t v = cal.get(f, status); 351c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t minActual = cal.getActualMinimum(f, status); 352c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxActual = cal.getActualMaximum(f, status); 353c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t minLow = cal.getMinimum(f); 354c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t minHigh = cal.getGreatestMinimum(f); 355c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxLow = cal.getLeastMaximum(f); 356c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t maxHigh = cal.getMaximum(f); 357c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 358c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (limits[j][0] > minActual) { 359c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // the minimum 360c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][0] = minActual; 361c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 362c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (limits[j][1] < minActual) { 363c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // the greatest minimum 364c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][1] = minActual; 365c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 366c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (limits[j][2] > maxActual) { 367c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // the least maximum 368c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][2] = maxActual; 369c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 370c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (limits[j][3] < maxActual) { 371c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // the maximum 372c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru limits[j][3] = maxActual; 373c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 374c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 375c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (minActual < minLow || minActual > minHigh) { 376c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"Fail: [" + cal.getType() + "] " + 377c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ymdToString(cal, ymd) + 378c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru " Range for min of " + FIELD_NAME[f] + "(" + f + 379c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ")=" + minLow + ".." + minHigh + 380c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ", actual_min=" + minActual); 381c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 382c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (maxActual < maxLow || maxActual > maxHigh) { 383c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru errln((UnicodeString)"Fail: [" + cal.getType() + "] " + 384c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ymdToString(cal, ymd) + 385c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru " Range for max of " + FIELD_NAME[f] + "(" + f + 386c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ")=" + maxLow + ".." + maxHigh + 387c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru ", actual_max=" + maxActual); 388c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 389c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (v < minActual || v > maxActual) { 3908393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius // timebomb per #9967, fix with #9972 39159d709d503bab6e2b61931737e662dd293b40578ccornelius if ( uprv_strcmp(cal.getType(), "dangi") == 0 && 39259d709d503bab6e2b61931737e662dd293b40578ccornelius testMillis >= 1865635198000.0 && 39359d709d503bab6e2b61931737e662dd293b40578ccornelius logKnownIssue("9972", "as per #9967")) { // Feb 2029 gregorian, end of dangi 4361 3948393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius logln((UnicodeString)"Fail: [" + cal.getType() + "] " + 3958393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius ymdToString(cal, ymd) + 3968393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius " " + FIELD_NAME[f] + "(" + f + ")=" + v + 3978393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius ", actual=" + minActual + ".." + maxActual + 3988393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius ", allowed=(" + minLow + ".." + minHigh + ")..(" + 3998393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius maxLow + ".." + maxHigh + ")"); 4008393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius } else { 4018393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius errln((UnicodeString)"Fail: [" + cal.getType() + "] " + 4028393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius ymdToString(cal, ymd) + 4038393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius " " + FIELD_NAME[f] + "(" + f + ")=" + v + 4048393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius ", actual=" + minActual + ".." + maxActual + 4058393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius ", allowed=(" + minLow + ".." + minHigh + ")..(" + 4068393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius maxLow + ".." + maxHigh + ")"); 4078393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius } 408c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 409c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 410c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru greg.add(UCAL_DAY_OF_YEAR, 1, status); 411c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (failure(status, "Calendar::add")) { 412c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru return; 413c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 414c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 415c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 416c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Check actual maxima and minima seen against ranges returned 417c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // by API. 418c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UnicodeString buf; 419c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru for (j = 0; fieldsToTest[j] >= 0; ++j) { 420c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru int32_t rangeLow, rangeHigh; 421c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UBool fullRangeSeen = TRUE; 422c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UCalendarDateFields f = (UCalendarDateFields)fieldsToTest[j]; 423c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 424c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru buf.remove(); 425c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru buf.append((UnicodeString)"[" + cal.getType() + "] " + FIELD_NAME[f]); 426c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 427c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Minumum 428c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru rangeLow = cal.getMinimum(f); 429c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru rangeHigh = cal.getGreatestMinimum(f); 430c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (limits[j][0] != rangeLow || limits[j][1] != rangeHigh) { 431c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru fullRangeSeen = FALSE; 432c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 433c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru buf.append((UnicodeString)" minima range=" + rangeLow + ".." + rangeHigh); 434c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru buf.append((UnicodeString)" minima actual=" + limits[j][0] + ".." + limits[j][1]); 435c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 436c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // Maximum 437c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru rangeLow = cal.getLeastMaximum(f); 438c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru rangeHigh = cal.getMaximum(f); 439c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (limits[j][2] != rangeLow || limits[j][3] != rangeHigh) { 440c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru fullRangeSeen = FALSE; 441c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 442c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru buf.append((UnicodeString)" maxima range=" + rangeLow + ".." + rangeHigh); 443c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru buf.append((UnicodeString)" maxima actual=" + limits[j][2] + ".." + limits[j][3]); 444c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 445c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru if (fullRangeSeen) { 446c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln((UnicodeString)"OK: " + buf); 447c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } else { 448c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // This may or may not be an error -- if the range of dates 449c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // we scan over doesn't happen to contain a minimum or 450c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru // maximum, it doesn't mean some other range won't. 451c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln((UnicodeString)"Warning: " + buf); 452c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 453c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru } 454c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 455c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru logln((UnicodeString)"End: " + greg.getTime(status)); 456c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru} 457c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 458c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste QueruUnicodeString& 459c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste QueruCalendarLimitTest::ymdToString(const Calendar& cal, UnicodeString& str) { 460c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru UErrorCode status = U_ZERO_ERROR; 461c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru str.remove(); 462c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru str.append((UnicodeString)"" + cal.get(UCAL_EXTENDED_YEAR, status) 463c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + "/" + (cal.get(UCAL_MONTH, status) + 1) 464c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + (cal.get(UCAL_IS_LEAP_MONTH, status) == 1 ? "(leap)" : "") 465c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru + "/" + cal.get(UCAL_DATE, status) 4668393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius + " " + cal.get(UCAL_HOUR_OF_DAY, status) 4678393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius + ":" + cal.get(UCAL_MINUTE, status) 4688393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius + " zone(hrs) " + cal.get(UCAL_ZONE_OFFSET, status)/(60.0*60.0*1000.0) 4698393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius + " dst(hrs) " + cal.get(UCAL_DST_OFFSET, status)/(60.0*60.0*1000.0) 4708393335b955da7340c9f19b1b4b2d6c0c2c04be7Craig Cornelius + ", time(millis)=" + cal.getTime(status)); 471c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru return str; 472c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru} 473c69afcec261fc345fda8daf46f0ea6b4351dc777Jean-Baptiste Queru 474b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru#endif /* #if !UCONFIG_NO_FORMATTING */ 475b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru 476b13da9df870a61b11249bf741347908dbea0edd8Jean-Baptiste Queru// eof 477