Home | History | Annotate | Download | only in intltest
      1 /********************************************************************
      2  * COPYRIGHT:
      3  * Copyright (c) 1997-2009, International Business Machines Corporation
      4  * and others. All Rights Reserved.
      5  ********************************************************************/
      6 
      7 #include "unicode/utypes.h"
      8 
      9 #if !UCONFIG_NO_FORMATTING
     10 
     11 #include "calregts.h"
     12 
     13 #include "unicode/gregocal.h"
     14 #include "unicode/simpletz.h"
     15 #include "unicode/smpdtfmt.h"
     16 #include "unicode/strenum.h"
     17 #include "cmemory.h"
     18 #include "caltest.h"
     19 
     20 #include <float.h>
     21 
     22 // *****************************************************************************
     23 // class CalendarRegressionTest
     24 // *****************************************************************************
     25 
     26 // these numbers correspond to using LONG_MIN and LONG_MAX in Java
     27 // this is 2^52 - 1, the largest allowable mantissa with a 0 exponent in a 64-bit double
     28 const UDate CalendarRegressionTest::EARLIEST_SUPPORTED_MILLIS = - 4503599627370495.0;
     29 const UDate CalendarRegressionTest::LATEST_SUPPORTED_MILLIS    =   4503599627370495.0;
     30 
     31 #define CASE(id,test) case id: name = #test; if (exec) { logln(#test "---"); logln((UnicodeString)""); test(); } break
     32 
     33 void
     34 CalendarRegressionTest::runIndexedTest( int32_t index, UBool exec, const char* &name, char* /*par*/ )
     35 {
     36     // if (exec) logln((UnicodeString)"TestSuite NumberFormatRegressionTest");
     37     switch (index) {
     38         CASE(0,test4100311);
     39         CASE(1,test4074758);
     40         CASE(2,test4028518);
     41         CASE(3,test4031502);
     42         CASE(4,test4035301);
     43         CASE(5,test4040996);
     44         CASE(6,test4051765);
     45         CASE(7,test4061476);
     46         CASE(8,test4070502);
     47         CASE(9,test4071197);
     48         CASE(10,test4071385);
     49         CASE(11,test4073929);
     50         CASE(12,test4083167);
     51         CASE(13,test4086724);
     52         CASE(14,test4095407);
     53         CASE(15,test4096231);
     54         CASE(16,test4096539);
     55         CASE(17,test41003112);
     56         CASE(18,test4103271);
     57         CASE(19,test4106136);
     58         CASE(20,test4108764);
     59         CASE(21,test4114578);
     60         CASE(22,test4118384);
     61         CASE(23,test4125881);
     62         CASE(24,test4125892);
     63         CASE(25,test4141665);
     64         CASE(26,test4142933);
     65         CASE(27,test4145158);
     66         CASE(28,test4145983);
     67         CASE(29,test4147269);
     68 
     69         CASE(30,Test4149677);
     70         CASE(31,Test4162587);
     71         CASE(32,Test4165343);
     72         CASE(33,Test4166109);
     73         CASE(34,Test4167060);
     74         CASE(35,Test4197699);
     75         CASE(36,TestJ81);
     76         CASE(37,TestJ438);
     77         CASE(38,TestLeapFieldDifference);
     78         CASE(39,TestMalaysianInstance);
     79         CASE(40,test4059654);
     80         CASE(41,test4092362);
     81         CASE(42,TestWeekShift);
     82         CASE(43,TestTimeZoneTransitionAdd);
     83         CASE(44,TestDeprecates);
     84         CASE(45,TestT5555);
     85         CASE(46,TestT6745);
     86     default: name = ""; break;
     87     }
     88 }
     89 
     90 const char* CalendarRegressionTest::FIELD_NAME [] = {
     91     "ERA",
     92     "YEAR",
     93     "MONTH",
     94     "WEEK_OF_YEAR",
     95     "WEEK_OF_MONTH",
     96     "DAY_OF_MONTH",
     97     "DAY_OF_YEAR",
     98     "DAY_OF_WEEK",
     99     "DAY_OF_WEEK_IN_MONTH",
    100     "AM_PM",
    101     "HOUR",
    102     "HOUR_OF_DAY",
    103     "MINUTE",
    104     "SECOND",
    105     "MILLISECOND",
    106     "ZONE_OFFSET",
    107     "DST_OFFSET",
    108     "YEAR_WOY",
    109     "DOW_LOCAL"
    110 };
    111 
    112 UBool
    113 CalendarRegressionTest::failure(UErrorCode status, const char* msg)
    114 {
    115     if(U_FAILURE(status)) {
    116         errcheckln(status, UnicodeString("FAIL: ") + msg + " failed, error " + u_errorName(status));
    117         return TRUE;
    118     }
    119 
    120     return FALSE;
    121 }
    122 
    123 /*
    124  * bug 4100311
    125  */
    126 void
    127 CalendarRegressionTest::test4100311()
    128 {
    129     UErrorCode status = U_ZERO_ERROR;
    130     GregorianCalendar *cal = (GregorianCalendar*)Calendar::createInstance(status);
    131     if(U_FAILURE(status)) {
    132       errln("Error creating Calendar: %s", u_errorName(status));
    133       delete cal;
    134       return;
    135     }
    136     failure(status, "Calendar::createInstance(status)");
    137     cal->set(UCAL_YEAR, 1997);
    138     cal->set(UCAL_DAY_OF_YEAR, 1);
    139     UDate d = cal->getTime(status);             // Should be Jan 1
    140     failure(status, "cal->getTime");
    141     logln(UnicodeString("") + d);
    142     delete cal;
    143 }
    144 
    145 
    146 /**
    147  * @bug 4074758
    148  */
    149 void
    150 CalendarRegressionTest::test4074758()
    151 {       //Set system time to between 12-1 (am or pm) and then run
    152     UErrorCode status = U_ZERO_ERROR;
    153     GregorianCalendar *cal = new GregorianCalendar(status);
    154     if(U_FAILURE(status)) {
    155       errln("Error creating Calendar: %s", u_errorName(status));
    156       delete cal;
    157       return;
    158     }
    159     failure(status, "new GregorianCalendar");
    160     for (int32_t h=0; h<25; ++h) {
    161         cal->set(97, UCAL_JANUARY, 1, h, 34);
    162         //System.out.print(d);
    163         logln(UnicodeString("HOUR=") + cal->get(UCAL_HOUR, status)); //prints 0
    164         failure(status, "cal->get");
    165         logln(UnicodeString("HOUR_OF_DAY=") + cal->get(UCAL_HOUR_OF_DAY, status));
    166         failure(status, "cal->get");
    167     }
    168 
    169     delete cal;
    170 }
    171 
    172 void
    173 CalendarRegressionTest::test4028518()
    174 {
    175     UErrorCode status = U_ZERO_ERROR;
    176     GregorianCalendar *cal1 = new GregorianCalendar(status) ;
    177     if(U_FAILURE(status)) {
    178       errln("Error creating Calendar: %s", u_errorName(status));
    179       delete cal1;
    180       return;
    181     }
    182     failure(status, "new GregorianCalendar");
    183     GregorianCalendar *cal2 = (GregorianCalendar*) cal1->clone() ;
    184 
    185     printdate(cal1, "cal1: ") ;
    186     printdate(cal2, "cal2 - cloned(): ") ;
    187     cal1->add(UCAL_DATE, 1, status) ;
    188     failure(status, "cal1->add");
    189     printdate(cal1, "cal1 after adding 1 day:") ;
    190     printdate(cal2, "cal2 should be unmodified:") ;
    191     delete cal1;
    192     delete cal2;
    193 }
    194 
    195 void
    196 CalendarRegressionTest::printdate(GregorianCalendar *cal, const char *string)
    197 {
    198     UErrorCode status = U_ZERO_ERROR;
    199     logln(UnicodeString(string, ""));
    200     log(UnicodeString("") + cal->get(UCAL_MONTH, status)) ;
    201     failure(status, "cal->get");
    202     int32_t date = cal->get(UCAL_DATE, status) + 1 ;
    203     failure(status, "cal->get");
    204     log(UnicodeString("/") + date) ;
    205     logln(UnicodeString("/") + cal->get(UCAL_YEAR, status)) ;
    206     failure(status, "cal->get");
    207 }
    208 
    209 /**
    210  * @bug 4031502
    211  */
    212 void
    213 CalendarRegressionTest::test4031502()
    214 {
    215     // This bug actually occurs on Windows NT as well, and doesn't
    216     // require the host zone to be set; it can be set in Java.
    217     UErrorCode status = U_ZERO_ERROR;
    218     StringEnumeration* ids = TimeZone::createEnumeration();
    219     UBool bad = FALSE;
    220     TimeZone* tz =TimeZone::createTimeZone("Asia/Riyadh87");
    221     failure(status, "new TimeZone");
    222     GregorianCalendar *cl = new GregorianCalendar(tz, status);
    223     failure(status, "new GregorianCalendar");
    224     cl->clear();
    225     cl->set(1900, 15, 5, 5, 8, 13);
    226     cl->get(UCAL_HOUR, status);
    227     failure(status, "cl->get(UCAL_HOUR, status)");
    228     status = U_ZERO_ERROR;
    229     delete cl;
    230     for (int32_t i=0; i<ids->count(status); ++i) {
    231         TimeZone *zone = TimeZone::createTimeZone(*ids->snext(status));
    232         GregorianCalendar *cal = new GregorianCalendar(zone, status);
    233         failure(status, "new GregorianCalendar");
    234         cal->clear();
    235         cal->set(1900, 15, 5, 5, 8, 13);
    236         if (cal->get(UCAL_HOUR, status) != 5 || U_FAILURE(status)) {
    237             UnicodeString temp;
    238             logln(zone->getID(temp) + " " +
    239                                //zone.useDaylightTime() + " " +
    240                                cal->get(UCAL_DST_OFFSET,status) / (60*60*1000) + " " +
    241                                zone->getRawOffset() / (60*60*1000) +
    242                                ": HOUR = " + cal->get(UCAL_HOUR,status));
    243             bad = TRUE;
    244         }
    245         delete cal;
    246     }
    247     if (bad)
    248         errln("TimeZone problems with GC");
    249     // delete [] ids;  // TODO: bad APIs
    250     delete ids;
    251 }
    252 
    253 /**
    254  * @bug 4035301
    255  */
    256 void CalendarRegressionTest::test4035301()
    257 {
    258     UErrorCode status = U_ZERO_ERROR;
    259     GregorianCalendar *c = new GregorianCalendar(98, 8, 7,status);
    260     GregorianCalendar *d = new GregorianCalendar(98, 8, 7,status);
    261     if (c->after(*d,status) ||
    262         c->after(*c,status) ||
    263         c->before(*d,status) ||
    264         c->before(*c,status) ||
    265         *c != *c ||
    266         *c != *d)
    267         errln("Fail");
    268     delete c;
    269     delete d;
    270 }
    271 
    272 /**
    273  * @bug 4040996
    274  */
    275 void CalendarRegressionTest::test4040996()
    276 {
    277     int32_t count = 0;
    278     StringEnumeration* ids = TimeZone::createEnumeration(-8 * 60 * 60 * 1000);
    279     UErrorCode status = U_ZERO_ERROR;
    280     count = ids->count(status);
    281     SimpleTimeZone *pdt = new SimpleTimeZone(-8 * 60 * 60 * 1000, *ids->snext(status));
    282     pdt->setStartRule(UCAL_APRIL, 1, UCAL_SUNDAY, 2 * 60 * 60 * 1000, status);
    283     pdt->setEndRule(UCAL_OCTOBER, -1, UCAL_SUNDAY, 2 * 60 * 60 * 1000, status);
    284     Calendar *calendar = new GregorianCalendar(pdt, status);
    285 
    286     calendar->set(UCAL_MONTH,3);
    287     calendar->set(UCAL_DATE,18);
    288     calendar->set(UCAL_SECOND, 30);
    289 
    290     logln(UnicodeString("MONTH: ") + calendar->get(UCAL_MONTH, status));
    291     logln(UnicodeString("DAY_OF_MONTH: ") +
    292                        calendar->get(UCAL_DATE, status));
    293     logln(UnicodeString("MINUTE: ") + calendar->get(UCAL_MINUTE, status));
    294     logln(UnicodeString("SECOND: ") + calendar->get(UCAL_SECOND, status));
    295 
    296     calendar->add(UCAL_SECOND,6, status);
    297     //This will print out todays date for MONTH and DAY_OF_MONTH
    298     //instead of the date it was set to.
    299     //This happens when adding MILLISECOND or MINUTE also
    300     logln(UnicodeString("MONTH: ") + calendar->get(UCAL_MONTH, status));
    301     logln(UnicodeString("DAY_OF_MONTH: ") +
    302                        calendar->get(UCAL_DATE, status));
    303     logln(UnicodeString("MINUTE: ") + calendar->get(UCAL_MINUTE, status));
    304     logln(UnicodeString("SECOND: ") + calendar->get(UCAL_SECOND, status));
    305     if (calendar->get(UCAL_MONTH, status) != 3 ||
    306         calendar->get(UCAL_DATE, status) != 18 ||
    307         calendar->get(UCAL_SECOND, status) != 36)
    308         errln(UnicodeString("Fail: Calendar::add misbehaves"));
    309 
    310     delete calendar;
    311     delete ids;
    312     // delete ids;   // TODO:  BAD API
    313 }
    314 
    315 /**
    316  * @bug 4051765
    317  */
    318 void CalendarRegressionTest::test4051765()
    319 {
    320     UErrorCode status = U_ZERO_ERROR;
    321     Calendar *cal = Calendar::createInstance(status);
    322     if(U_FAILURE(status)) {
    323       errln("Error creating Calendar: %s", u_errorName(status));
    324       delete cal;
    325       return;
    326     }
    327     cal->setLenient(FALSE);
    328     cal->set(UCAL_DAY_OF_WEEK, 0);
    329     //try {
    330         cal->getTime(status);
    331         if( ! U_FAILURE(status))
    332             errln("Fail: DAY_OF_WEEK 0 should be disallowed");
    333     /*}
    334     catch (IllegalArgumentException e) {
    335         return;
    336     }*/
    337 
    338     delete cal;
    339 }
    340 
    341 /* User error - no bug here
    342 void CalendarRegressionTest::test4059524() {
    343     // Create calendar for April 10, 1997
    344     GregorianCalendar calendar  = new GregorianCalendar(status);
    345     // print out a bunch of interesting things
    346     logln("ERA: " + Calendar::get(Calendar::ERA));
    347     logln("YEAR: " + Calendar::get(Calendar::YEAR));
    348     logln("MONTH: " + Calendar::get(Calendar::MONTH));
    349     logln("WEEK_OF_YEAR: " +
    350                        Calendar::get(Calendar::WEEK_OF_YEAR));
    351     logln("WEEK_OF_MONTH: " +
    352                        Calendar::get(Calendar::WEEK_OF_MONTH));
    353     logln("DATE: " + Calendar::get(Calendar::DATE));
    354     logln("DAY_OF_MONTH: " +
    355                        Calendar::get(Calendar::DAY_OF_MONTH));
    356     logln("DAY_OF_YEAR: " + Calendar::get(Calendar::DAY_OF_YEAR));
    357     logln("DAY_OF_WEEK: " + Calendar::get(Calendar::DAY_OF_WEEK));
    358     logln("DAY_OF_WEEK_IN_MONTH: " +
    359                        Calendar::get(Calendar::DAY_OF_WEEK_IN_MONTH));
    360     logln("AM_PM: " + Calendar::get(Calendar::AM_PM));
    361     logln("HOUR: " + Calendar::get(Calendar::HOUR));
    362     logln("HOUR_OF_DAY: " + Calendar::get(Calendar::HOUR_OF_DAY));
    363     logln("MINUTE: " + Calendar::get(Calendar::MINUTE));
    364     logln("SECOND: " + Calendar::get(Calendar::SECOND));
    365     logln("MILLISECOND: " + Calendar::get(Calendar::MILLISECOND));
    366     logln("ZONE_OFFSET: "
    367                        + (Calendar::get(Calendar::ZONE_OFFSET)/(60*60*1000)));
    368     logln("DST_OFFSET: "
    369                        + (Calendar::get(Calendar::DST_OFFSET)/(60*60*1000)));
    370     calendar  = new GregorianCalendar(1997,3,10);
    371     Calendar::getTime();
    372     logln("April 10, 1997");
    373     logln("ERA: " + Calendar::get(Calendar::ERA));
    374     logln("YEAR: " + Calendar::get(Calendar::YEAR));
    375     logln("MONTH: " + Calendar::get(Calendar::MONTH));
    376     logln("WEEK_OF_YEAR: " +
    377                        Calendar::get(Calendar::WEEK_OF_YEAR));
    378     logln("WEEK_OF_MONTH: " +
    379                        Calendar::get(Calendar::WEEK_OF_MONTH));
    380     logln("DATE: " + Calendar::get(Calendar::DATE));
    381     logln("DAY_OF_MONTH: " +
    382                        Calendar::get(Calendar::DAY_OF_MONTH));
    383     logln("DAY_OF_YEAR: " + Calendar::get(Calendar::DAY_OF_YEAR));
    384     logln("DAY_OF_WEEK: " + Calendar::get(Calendar::DAY_OF_WEEK));
    385     logln("DAY_OF_WEEK_IN_MONTH: " + Calendar::get(Calendar::DAY_OF_WEEK_IN_MONTH));
    386     logln("AM_PM: " + Calendar::get(Calendar::AM_PM));
    387     logln("HOUR: " + Calendar::get(Calendar::HOUR));
    388     logln("HOUR_OF_DAY: " + Calendar::get(Calendar::HOUR_OF_DAY));
    389     logln("MINUTE: " + Calendar::get(Calendar::MINUTE));
    390     logln("SECOND: " + Calendar::get(Calendar::SECOND));
    391     logln("MILLISECOND: " + Calendar::get(Calendar::MILLISECOND));
    392     logln("ZONE_OFFSET: "
    393                        + (Calendar::get(Calendar::ZONE_OFFSET)/(60*60*1000))); // in hours
    394     logln("DST_OFFSET: "
    395                        + (Calendar::get(Calendar::DST_OFFSET)/(60*60*1000))); // in hours
    396 }
    397 */
    398 
    399 /**
    400  * @bug 4059654
    401  */
    402 void CalendarRegressionTest::test4059654() {
    403     UErrorCode status = U_ZERO_ERROR;
    404     GregorianCalendar *gc = new GregorianCalendar(status);
    405     if(U_FAILURE(status)) {
    406       errln("Error creating Calendar: %s", u_errorName(status));
    407       delete gc;
    408       return;
    409     }
    410 
    411     gc->set(1997, 3, 1, 15, 16, 17); // April 1, 1997
    412 
    413     gc->set(UCAL_HOUR, 0);
    414     gc->set(UCAL_AM_PM, UCAL_AM);
    415     gc->set(UCAL_MINUTE, 0);
    416     gc->set(UCAL_SECOND, 0);
    417     gc->set(UCAL_MILLISECOND, 0);
    418 
    419     UDate cd = gc->getTime(status);
    420     GregorianCalendar *exp = new GregorianCalendar(1997, 3, 1, 0, 0, 0, status);
    421     if (cd != exp->getTime(status))
    422         errln(UnicodeString("Fail: Calendar::set broken. Got ") + cd + " Want " + exp->getTime(status));
    423 
    424     delete gc;
    425     delete exp;
    426 }
    427 
    428 /**
    429  * @bug 4061476
    430  */
    431 void CalendarRegressionTest::test4061476()
    432 {
    433     UErrorCode status = U_ZERO_ERROR;
    434     SimpleDateFormat *fmt = new SimpleDateFormat(UnicodeString("ddMMMyy"), Locale::getUK(),status);
    435     Calendar *cal = Calendar::createInstance(TimeZone::createTimeZone("GMT"),
    436                                     Locale::getUK(),status);
    437     if(U_FAILURE(status)) {
    438       errcheckln(status, "Error creating Calendar: %s", u_errorName(status));
    439       delete cal;
    440       delete fmt;
    441       return;
    442     }
    443     fmt->adoptCalendar(cal);
    444     // try {
    445             UDate date = fmt->parse("29MAY97", status);
    446             failure(status, "fmt->parse");
    447             cal->setTime(date, status);
    448             failure(status, "cal->setTime");
    449      //   }
    450     //catch (Exception e) {;}
    451     cal->set(UCAL_HOUR_OF_DAY, 13);
    452     logln(UnicodeString("Hour: ")+cal->get(UCAL_HOUR_OF_DAY, status));
    453     cal->add(UCAL_HOUR_OF_DAY, 6,status);
    454     logln(UnicodeString("Hour: ")+cal->get(UCAL_HOUR_OF_DAY, status));
    455     if (cal->get(UCAL_HOUR_OF_DAY, status) != 19)
    456         errln(UnicodeString("Fail: Want 19 Got ") + cal->get(UCAL_HOUR_OF_DAY, status));
    457 
    458     delete fmt;
    459 }
    460 
    461 /**
    462  * @bug 4070502
    463  */
    464 void CalendarRegressionTest::test4070502()
    465 {
    466     UErrorCode status = U_ZERO_ERROR;
    467     Calendar *cal = new GregorianCalendar(status);
    468     if(status == U_USING_FALLBACK_WARNING) {
    469       dataerrln("Error creating Calendar: %s", u_errorName(status));
    470       delete cal;
    471       return;
    472     }
    473     UDate d = getAssociatedDate(makeDate(1998,0,30), status);
    474     cal->setTime(d,status);
    475     if (cal->get(UCAL_DAY_OF_WEEK,status) == UCAL_SATURDAY ||
    476         cal->get(UCAL_DAY_OF_WEEK,status) == UCAL_SUNDAY)
    477         errln(UnicodeString("Fail: Want weekday Got ") + d);
    478 
    479     delete cal;
    480 }
    481 
    482 /**
    483  * Get the associated date starting from a specified date
    484  * NOTE: the unnecessary "getTime()'s" below are a work-around for a
    485  * bug in jdk 1.1.3 (and probably earlier versions also)
    486  * <p>
    487  * @param date The date to start from
    488  */
    489 UDate
    490 CalendarRegressionTest::getAssociatedDate(UDate d, UErrorCode& status)
    491 {
    492     GregorianCalendar *cal = new GregorianCalendar(status);
    493     cal->setTime(d,status);
    494     //cal.add(field, amount); //<-- PROBLEM SEEN WITH field = DATE,MONTH
    495     // cal.getTime();  // <--- REMOVE THIS TO SEE BUG
    496     for (;;) {
    497         int32_t wd = cal->get(UCAL_DAY_OF_WEEK, status);
    498         if (wd == UCAL_SATURDAY || wd == UCAL_SUNDAY) {
    499             cal->add(UCAL_DATE, 1, status);
    500             // cal.getTime();
    501         }
    502         else
    503             break;
    504     }
    505 
    506     UDate dd = cal->getTime(status);
    507     delete cal;
    508     return dd;
    509 }
    510 
    511 /**
    512  * @bug 4071197
    513  */
    514 void CalendarRegressionTest::test4071197()
    515 {
    516     dowTest(FALSE);
    517     dowTest(TRUE);
    518 }
    519 
    520 void CalendarRegressionTest::dowTest(UBool lenient)
    521 {
    522     UErrorCode status = U_ZERO_ERROR;
    523     GregorianCalendar *cal = new GregorianCalendar(status);
    524     if(U_FAILURE(status)) {
    525       errln("Error creating Calendar: %s", u_errorName(status));
    526       delete cal;
    527       return;
    528     }
    529     cal->set(1997, UCAL_AUGUST, 12); // Wednesday
    530     // cal.getTime(); // Force update
    531     cal->setLenient(lenient);
    532     cal->set(1996, UCAL_DECEMBER, 1); // Set the date to be December 1, 1996
    533     int32_t dow = cal->get(UCAL_DAY_OF_WEEK, status);
    534     int32_t min = cal->getMinimum(UCAL_DAY_OF_WEEK);
    535     int32_t max = cal->getMaximum(UCAL_DAY_OF_WEEK);
    536     //logln(cal.getTime().toString());
    537     if (min != UCAL_SUNDAY || max != UCAL_SATURDAY)
    538         errln("FAIL: Min/max bad");
    539     if (dow < min || dow > max)
    540         errln("FAIL: Day of week %d out of range [%d,%d]\n", dow, min, max);
    541     if (dow != UCAL_SUNDAY)
    542         errln("FAIL: Day of week should be SUNDAY Got " + dow);
    543 
    544     if(U_FAILURE(status)) {
    545       errln("Error checking Calendar: %s", u_errorName(status));
    546       delete cal;
    547       return;
    548     }
    549 
    550     if(cal->getActualMinimum(UCAL_DAY_OF_WEEK, status) != min) {
    551         errln("FAIL: actual minimum differs from minimum");
    552     }
    553     if(cal->getActualMinimum(Calendar::DAY_OF_WEEK, status) != min) {
    554         errln("FAIL: actual minimum (Calendar::DAY_OF_WEEK, status) differs from minimum");
    555     }
    556     if(cal->getActualMinimum(Calendar::DAY_OF_WEEK) != min) {
    557         errln("FAIL: actual minimum (Calendar::DAY_OF_WEEK) differs from minimum");
    558     }
    559     if(((Calendar*)cal)->getActualMinimum(UCAL_DAY_OF_WEEK, status) != min) {
    560         errln("FAIL: actual minimum (UCAL_DAY_OF_WEEK, status) differs from minimum");
    561     }
    562 // NOTE: This function does not exist!  jitterbug #3016
    563 //    if(((Calendar*)cal)->getActualMinimum(Calendar::DAY_OF_WEEK, status) != min) {
    564 //        errln("FAIL: actual minimum (Calendar::DAY_OF_WEEK, status) differs from minimum");
    565 //    }
    566     if(U_FAILURE(status)) {
    567       errln("Error getting actual minimum: %s", u_errorName(status));
    568       return;
    569     }
    570 
    571     delete cal;
    572 }
    573 
    574 /**
    575  * @bug 4071385
    576  */
    577 void CalendarRegressionTest::test4071385()
    578 {
    579     UErrorCode status = U_ZERO_ERROR;
    580     Calendar *cal = Calendar::createInstance(status);
    581     if(U_FAILURE(status)) {
    582       errln("Error creating Calendar: %s", u_errorName(status));
    583       delete cal;
    584       return;
    585     }
    586     cal->setTime(makeDate(1998, UCAL_JUNE, 24),status);
    587     cal->set(UCAL_MONTH, UCAL_NOVEMBER); // change a field
    588     //logln(cal.getTime().toString());
    589     if (cal->getTime(status) != makeDate(1998, UCAL_NOVEMBER, 24))
    590         errln("Fail");
    591 
    592     delete cal;
    593 }
    594 
    595 /**
    596  * @bug 4073929
    597  */
    598 void CalendarRegressionTest::test4073929()
    599 {
    600     UErrorCode status = U_ZERO_ERROR;
    601     GregorianCalendar *foo1 = new GregorianCalendar(1997, 8, 27,status);
    602     if(U_FAILURE(status)) {
    603       errln("Error creating Calendar: %s", u_errorName(status));
    604       delete foo1;
    605       return;
    606     }
    607     logln("foo1@%.0f - %d-%d-%d %d:%d:%d.%ds\n", foo1->getTime(status),
    608           foo1->get(UCAL_YEAR, status),
    609           foo1->get(UCAL_MONTH, status),
    610           foo1->get(UCAL_DATE, status),
    611           foo1->get(UCAL_HOUR, status),
    612           foo1->get(UCAL_MINUTE, status),
    613           foo1->get(UCAL_SECOND, status),
    614           foo1->get(UCAL_MILLISECOND,status));
    615     foo1->add(UCAL_DATE, + 1, status);
    616     logln("foo1@%.0f - %d-%d-%d %d:%d:%d.%ds after +\n", foo1->getTime(status),
    617           foo1->get(UCAL_YEAR, status),
    618           foo1->get(UCAL_MONTH, status),
    619           foo1->get(UCAL_DATE, status),
    620           foo1->get(UCAL_HOUR, status),
    621           foo1->get(UCAL_MINUTE, status),
    622           foo1->get(UCAL_SECOND, status),
    623           foo1->get(UCAL_MILLISECOND ,status));
    624     foo1->add(UCAL_DATE, - 1, status);
    625     logln("foo1@%.0f - %d-%d-%d %d:%d:%d.%ds after -\n", foo1->getTime(status),
    626           foo1->get(UCAL_YEAR, status),
    627           foo1->get(UCAL_MONTH, status),
    628           foo1->get(UCAL_DATE, status),
    629           foo1->get(UCAL_HOUR, status),
    630           foo1->get(UCAL_MINUTE, status),
    631           foo1->get(UCAL_SECOND, status),
    632           foo1->get(UCAL_MILLISECOND, status));
    633 
    634     foo1->add(UCAL_DATE, + 1, status);
    635     int32_t testyear = foo1->get(UCAL_YEAR, status);
    636     int32_t testmonth = foo1->get(UCAL_MONTH, status);
    637     int32_t testday = foo1->get(UCAL_DATE, status);
    638     if (testyear != 1997 ||
    639         testmonth != 8 ||
    640         testday != 28)
    641         errln("Fail: Calendar not initialized");
    642 
    643     delete foo1;
    644 }
    645 
    646 /**
    647  * @bug 4083167
    648  */
    649 void CalendarRegressionTest::test4083167()
    650 {
    651     UErrorCode status = U_ZERO_ERROR;
    652     TimeZone *saveZone = TimeZone::createDefault();
    653     //try {
    654     TimeZone *newZone = TimeZone::createTimeZone("UTC");
    655     TimeZone::setDefault(*newZone);
    656     UDate firstDate = Calendar::getNow();
    657         Calendar *cal = new GregorianCalendar(status);
    658         if(U_FAILURE(status)) {
    659           errln("Error creating Calendar: %s", u_errorName(status));
    660           delete cal;
    661           return;
    662         }
    663         cal->setTime(firstDate,status);
    664         int32_t hr        = cal->get(UCAL_HOUR_OF_DAY, status);
    665         int32_t min        = cal->get(UCAL_MINUTE, status);
    666         int32_t sec        = cal->get(UCAL_SECOND, status);
    667         int32_t msec    = cal->get(UCAL_MILLISECOND, status);
    668         double firstMillisInDay = hr * 3600000 + min * 60000 + sec * 1000 + msec;
    669 
    670         //logln("Current time: " + firstDate.toString());
    671 
    672         for (int32_t validity=0; validity<30; validity++) {
    673             UDate lastDate = firstDate + validity*1000*24*60*60.0;
    674             cal->setTime(lastDate, status);
    675             hr        = cal->get(UCAL_HOUR_OF_DAY, status);
    676             min        = cal->get(UCAL_MINUTE, status);
    677             sec        = cal->get(UCAL_SECOND, status);
    678             msec    = cal->get(UCAL_MILLISECOND, status);
    679             double millisInDay = hr * 3600000.0 + min * 60000.0 + sec * 1000.0 + msec;
    680             if (firstMillisInDay != millisInDay)
    681                 errln(UnicodeString("Day has shifted ") + lastDate);
    682         }
    683     //}
    684     //finally {
    685         TimeZone::setDefault(*saveZone);
    686     //}
    687 
    688     delete saveZone;
    689     delete newZone;
    690     delete cal;
    691 }
    692 
    693 /**
    694  * @bug 4086724
    695  */
    696 void CalendarRegressionTest::test4086724()
    697 {
    698     UErrorCode status = U_ZERO_ERROR;
    699     SimpleDateFormat *date;
    700     TimeZone *saveZone = TimeZone::createDefault();
    701     Locale saveLocale = Locale::getDefault();
    702     //try {
    703     Locale::setDefault(Locale::getUK(),status);
    704     TimeZone *newZone = TimeZone::createTimeZone("GMT");
    705     TimeZone::setDefault(*newZone);
    706         date = new SimpleDateFormat(UnicodeString("dd MMM yyy (zzzz) 'is in week' ww"),status);
    707         Calendar *cal = Calendar::createInstance(status);
    708         if(U_FAILURE(status)) {
    709           errcheckln(status, "Error creating Calendar: %s", u_errorName(status));
    710           delete cal;
    711           delete newZone;
    712           delete date;
    713           return;
    714         }
    715         cal->set(1997,UCAL_SEPTEMBER,30);
    716         UDate now = cal->getTime(status);
    717         UnicodeString temp;
    718         FieldPosition pos(FieldPosition::DONT_CARE);
    719         logln(date->format(now, temp, pos));
    720         cal->set(1997,UCAL_JANUARY,1);
    721         now=cal->getTime(status);
    722         logln(date->format(now,temp, pos));
    723         cal->set(1997,UCAL_JANUARY,8);
    724         now=cal->getTime(status);
    725         logln(date->format(now,temp, pos));
    726         cal->set(1996,UCAL_DECEMBER,31);
    727         now=cal->getTime(status);
    728         logln(date->format(now,temp, pos));
    729     //}
    730     //finally {
    731         Locale::setDefault(saveLocale,status);
    732         TimeZone::setDefault(*saveZone);
    733     //}
    734     logln("*** THE RESULTS OF THIS TEST MUST BE VERIFIED MANUALLY ***");
    735 
    736 delete newZone;
    737 delete cal;
    738 delete date;
    739 delete saveZone;
    740 }
    741 
    742 /**
    743  * @bug 4092362
    744  */
    745 void CalendarRegressionTest::test4092362() {
    746     UErrorCode status = U_ZERO_ERROR;
    747     GregorianCalendar *cal1 = new GregorianCalendar(1997, 10, 11, 10, 20, 40,status);
    748     /*cal1.set( Calendar::YEAR, 1997 );
    749     cal1.set( Calendar::MONTH, 10 );
    750     cal1.set( Calendar::DATE, 11 );
    751     cal1.set( Calendar::HOUR, 10 );
    752     cal1.set( Calendar::MINUTE, 20 );
    753     cal1.set( Calendar::SECOND, 40 ); */
    754 
    755     logln( UnicodeString(" Cal1 = ") + cal1->getTime(status) );
    756     logln( UnicodeString(" Cal1 time in ms = ") + cal1->get(UCAL_MILLISECOND,status) );
    757     for( int32_t k = 0; k < 100 ; k++ );
    758 
    759     GregorianCalendar *cal2 = new GregorianCalendar(1997, 10, 11, 10, 20, 40,status);
    760     /*cal2.set( Calendar::YEAR, 1997 );
    761     cal2.set( Calendar::MONTH, 10 );
    762     cal2.set( Calendar::DATE, 11 );
    763     cal2.set( Calendar::HOUR, 10 );
    764     cal2.set( Calendar::MINUTE, 20 );
    765     cal2.set( Calendar::SECOND, 40 ); */
    766 
    767     logln( UnicodeString(" Cal2 = ") + cal2->getTime(status) );
    768     logln( UnicodeString(" Cal2 time in ms = ") + cal2->get(UCAL_MILLISECOND,status) );
    769     if( *cal1 != *cal2 )
    770         errln("Fail: Milliseconds randomized");
    771 
    772     delete cal1;
    773     delete cal2;
    774 }
    775 
    776 /**
    777  * @bug 4095407
    778  */
    779 void CalendarRegressionTest::test4095407()
    780 {
    781     UErrorCode status = U_ZERO_ERROR;
    782     GregorianCalendar *a = new GregorianCalendar(1997,UCAL_NOVEMBER, 13,status);
    783     int32_t dow = a->get(UCAL_DAY_OF_WEEK, status);
    784     if (dow != UCAL_THURSDAY)
    785         errln("Fail: Want THURSDAY Got " + dow);
    786 
    787     delete a;
    788 }
    789 
    790 /**
    791  * @bug 4096231
    792  */
    793 void CalendarRegressionTest::test4096231()
    794 {
    795     UErrorCode status = U_ZERO_ERROR;
    796     TimeZone *GMT = TimeZone::createTimeZone("GMT");
    797     TimeZone *PST = TimeZone::createTimeZone("PST");
    798     int32_t sec = 0, min = 0, hr = 0, day = 1, month = 10, year = 1997;
    799 
    800     Calendar *cal1 = new GregorianCalendar(*PST,status);
    801     cal1->setTime(880698639000.0,status);
    802     // Issue 1: Changing the timezone doesn't change the
    803     //          represented time.  The old API, pre 1.2.2a requires
    804     // setTime to be called in order to update the time fields after the time
    805     // zone has been set.
    806     int32_t h1,h2;
    807     logln(UnicodeString("PST 1 is: ") + (h1=cal1->get(UCAL_HOUR_OF_DAY, status)));
    808     cal1->setTimeZone(*GMT);
    809     logln(UnicodeString("GMT 2 is: ") + (h2=cal1->get(UCAL_HOUR_OF_DAY, status)));
    810     if ((*GMT != *PST) && (h1 == h2))
    811         errln("Fail: Hour same in different zones");
    812 
    813     Calendar *cal2 = new GregorianCalendar(*GMT,status);
    814     Calendar *cal3 = new GregorianCalendar(*PST,status);
    815     cal2->set(UCAL_MILLISECOND, 0);
    816     cal3->set(UCAL_MILLISECOND, 0);
    817 
    818     cal2->set(cal1->get(UCAL_YEAR,status),
    819              cal1->get(UCAL_MONTH,status),
    820              cal1->get(UCAL_DATE,status),
    821              cal1->get(UCAL_HOUR_OF_DAY,status),
    822              cal1->get(UCAL_MINUTE,status),
    823              cal1->get(UCAL_SECOND,status));
    824 
    825     double t1,t2,t3,t4;
    826     logln(UnicodeString("RGMT 1 is: ") + (t1=cal2->getTime(status)));
    827     cal3->set(year, month, day, hr, min, sec);
    828     logln(UnicodeString("RPST 1 is: ") + (t2=cal3->getTime(status)));
    829     cal3->setTimeZone(*GMT);
    830     logln(UnicodeString("RGMT 2 is: ") + (t3=cal3->getTime(status)));
    831     cal3->set(cal1->get(UCAL_YEAR,status),
    832              cal1->get(UCAL_MONTH,status),
    833              cal1->get(UCAL_DATE,status),
    834              cal1->get(UCAL_HOUR_OF_DAY,status),
    835              cal1->get(UCAL_MINUTE,status),
    836              cal1->get(UCAL_SECOND,status));
    837     // Issue 2: Calendar continues to use the timezone in its
    838     //          constructor for set() conversions, regardless
    839     //          of calls to setTimeZone()
    840     logln(UnicodeString("RGMT 3 is: ") + (t4=cal3->getTime(status)));
    841     if (t1 == t2 ||
    842         t1 != t4 ||
    843         t2 != t3)
    844         errln("Fail: Calendar zone behavior faulty");
    845 
    846     delete cal1;
    847     delete cal2;
    848     delete cal3;
    849     delete GMT;
    850     delete PST;
    851 }
    852 
    853 /**
    854  * @bug 4096539
    855  */
    856 void CalendarRegressionTest::test4096539()
    857 {
    858     UErrorCode status = U_ZERO_ERROR;
    859     int32_t y [] = {31,28,31,30,31,30,31,31,30,31,30,31};
    860 
    861     for (int32_t x=0;x<12;x++) {
    862         GregorianCalendar *gc = new
    863             GregorianCalendar(1997,x,y[x], status);
    864         int32_t m1,m2;
    865         log(UnicodeString("") + (m1=gc->get(UCAL_MONTH,status)+1)+UnicodeString("/")+
    866                          gc->get(UCAL_DATE,status)+"/"+gc->get(UCAL_YEAR,status)+
    867                          " + 1mo = ");
    868 
    869         gc->add(UCAL_MONTH, 1,status);
    870         logln(UnicodeString("") + (m2=gc->get(UCAL_MONTH,status)+1)+UnicodeString("/")+
    871                            gc->get(UCAL_DATE,status)+"/"+gc->get(UCAL_YEAR,status)
    872                            );
    873         int32_t m = (m1 % 12) + 1;
    874         if (m2 != m)
    875             errln(UnicodeString("Fail: Want ") + m + " Got " + m2);
    876         delete gc;
    877     }
    878 
    879 }
    880 
    881 /**
    882  * @bug 4100311
    883  */
    884 void CalendarRegressionTest::test41003112()
    885 {
    886     UErrorCode status = U_ZERO_ERROR;
    887     GregorianCalendar *cal = (GregorianCalendar*)Calendar::createInstance(status);
    888     if(U_FAILURE(status)) {
    889       errln("Error creating calendar: %s", u_errorName(status));
    890       delete cal;
    891       return;
    892     }
    893     cal->set(UCAL_YEAR, 1997);
    894     cal->set(UCAL_DAY_OF_YEAR, 1);
    895     //UDate d = cal->getTime(status);             // Should be Jan 1
    896     //logln(d.toString());
    897     if (cal->get(UCAL_DAY_OF_YEAR, status) != 1)
    898         errln("Fail: DAY_OF_YEAR not set");
    899     delete cal;
    900 }
    901 
    902 /**
    903  * @bug 4103271
    904  */
    905 void CalendarRegressionTest::test4103271()
    906 {
    907     UErrorCode status = U_ZERO_ERROR;
    908     SimpleDateFormat sdf(status);
    909     int32_t numYears=40, startYear=1997, numDays=15;
    910     UnicodeString output, testDesc, str, str2;
    911     GregorianCalendar *testCal = (GregorianCalendar*)Calendar::createInstance(status);
    912     if(U_FAILURE(status)) {
    913       errcheckln(status, "Error creating calendar: %s", u_errorName(status));
    914       delete testCal;
    915       return;
    916     }
    917     testCal->clear();
    918     sdf.adoptCalendar(testCal);
    919     sdf.applyPattern("EEE dd MMM yyyy 'WOY'ww'-'YYYY 'DOY'DDD");
    920     UBool fail = FALSE;
    921     for (int32_t firstDay=1; firstDay<=2; firstDay++) {
    922         for (int32_t minDays=1; minDays<=7; minDays++) {
    923             testCal->setMinimalDaysInFirstWeek((uint8_t)minDays);
    924             testCal->setFirstDayOfWeek((UCalendarDaysOfWeek)firstDay);
    925             testDesc = (UnicodeString("Test") + firstDay + minDays);
    926             logln(testDesc + " => 1st day of week=" +
    927                                firstDay +
    928                                ", minimum days in first week=" +
    929                                minDays);
    930             for (int32_t j=startYear; j<=startYear+numYears; j++) {
    931                 testCal->set(j,11,25);
    932                 for(int32_t i=0; i<numDays; i++) {
    933                     testCal->add(UCAL_DATE,1,status);
    934                     UnicodeString calWOY;
    935                     int32_t actWOY = testCal->get(UCAL_WEEK_OF_YEAR,status);
    936                     if (actWOY < 1 || actWOY > 53) {
    937                         UDate d = testCal->getTime(status);
    938                         //calWOY = String.valueOf(actWOY);
    939                         UnicodeString temp;
    940                         FieldPosition pos(FieldPosition::DONT_CARE);
    941                         output = testDesc + " - " + sdf.format(d,temp,pos) + "\t";
    942                         output = output + "\t" + actWOY;
    943                         logln(output);
    944                         fail = TRUE;
    945                     }
    946                 }
    947             }
    948         }
    949     }
    950 
    951     int32_t DATA [] = {
    952         3, 52, 52, 52, 52, 52, 52, 52,
    953             1,  1,  1,  1,  1,  1,  1,
    954             2,  2,  2,  2,  2,  2,  2,
    955         4, 52, 52, 52, 52, 52, 52, 52,
    956            53, 53, 53, 53, 53, 53, 53,
    957             1,  1,  1,  1,  1,  1,  1,
    958     };
    959     testCal->setFirstDayOfWeek(UCAL_SUNDAY);
    960     for (int32_t j=0; j<44; j+=22) {
    961         logln(UnicodeString("Minimal days in first week = ") + DATA[j] +
    962                            "  Week starts on Sunday");
    963         testCal->setMinimalDaysInFirstWeek((uint8_t)DATA[j]);
    964         testCal->set(1997, UCAL_DECEMBER, 21);
    965         for (int32_t i=0; i<21; ++i) {
    966             int32_t woy = testCal->get(UCAL_WEEK_OF_YEAR,status);
    967             str.remove();
    968             log(UnicodeString("") + sdf.format(testCal->getTime(status), str) +
    969                 UnicodeString(" ") + woy);
    970             if (woy != DATA[j + 1 + i]) {
    971                 log(" ERROR");
    972                 fail = TRUE;
    973             }
    974             logln("");
    975 
    976             // Now compute the time from the fields, and make sure we
    977             // get the same answer back.  This is a round-trip test.
    978             UDate save = testCal->getTime(status);
    979             testCal->clear();
    980             testCal->set(UCAL_YEAR_WOY, DATA[j+1+i] < 25 ? 1998 : 1997);
    981             testCal->set(UCAL_WEEK_OF_YEAR, DATA[j+1+i]);
    982             testCal->set(UCAL_DAY_OF_WEEK, (i%7) + UCAL_SUNDAY);
    983             if (testCal->getTime(status) != save) {
    984                 str.remove();
    985                 logln(UnicodeString("  Parse failed: ") +
    986                       sdf.format(testCal->getTime(status), str));
    987                 fail= TRUE;
    988             }
    989 
    990             testCal->setTime(save,status);
    991             testCal->add(UCAL_DATE, 1,status);
    992         }
    993     }
    994     // Test field disambiguation with a few special hard-coded cases.
    995     // This shouldn't fail if the above cases aren't failing.
    996     int32_t DISAM_int [] = {
    997         // y y_woy woy dow
    998         1997, 1998, 1, UCAL_SUNDAY,
    999         (1998), (1998), (2), (UCAL_SATURDAY),
   1000         (1998), (1998), (53), (UCAL_THURSDAY),
   1001         (1999), (1998), (53), (UCAL_FRIDAY)
   1002     };
   1003 
   1004     UDate DISAM_date [] = {
   1005             makeDate(1997, UCAL_DECEMBER, 28),
   1006             makeDate(1998, UCAL_JANUARY, 10),
   1007             makeDate(1998, UCAL_DECEMBER, 31),
   1008             makeDate(1999, UCAL_JANUARY, 1)
   1009     };
   1010 
   1011     testCal->setMinimalDaysInFirstWeek(3);
   1012     testCal->setFirstDayOfWeek(UCAL_SUNDAY);
   1013     int32_t i = 0;
   1014 
   1015     /* Enable this code to display various WOY values
   1016     testCal->clear();
   1017     for (i=25; i<38; ++i) {
   1018         testCal->set(1996, Calendar::DECEMBER, i);
   1019         UDate got = testCal->getTime(status);
   1020         str.remove();
   1021         logln(UnicodeString("") + sdf.format(got, str));
   1022     }
   1023     for (i=25; i<38; ++i) {
   1024         testCal->set(1997, Calendar::DECEMBER, i);
   1025         UDate got = testCal->getTime(status);
   1026         str.remove();
   1027         logln(UnicodeString("") + sdf.format(got, str));
   1028     }
   1029     for (i=25; i<38; ++i) {
   1030         testCal->set(1998, UCAL_DECEMBER, i);
   1031         UDate got = testCal->getTime(status);
   1032         str.remove();
   1033         logln(UnicodeString("") + sdf.format(got, str));
   1034     }
   1035     */
   1036 
   1037     for (i=0; i < 16; i += 4) {
   1038         int32_t y = DISAM_int[i];
   1039         int32_t ywoy = DISAM_int[i+1];
   1040         int32_t woy = DISAM_int[i+2];
   1041         int32_t dow = DISAM_int[i+3];
   1042         UDate exp = DISAM_date[i/4];
   1043         testCal->clear();
   1044         testCal->set(UCAL_YEAR, y);
   1045         testCal->set(UCAL_WEEK_OF_YEAR, woy);
   1046         testCal->set(UCAL_DAY_OF_WEEK, dow);
   1047         UDate got = testCal->getTime(status);
   1048         str.remove();
   1049         str2.remove();
   1050         log(UnicodeString("Y") + y + "-W" + woy +
   1051                          "-DOW" + dow + " expect:" + sdf.format(exp, str) +
   1052                          " got:" + sdf.format(got, str2));
   1053         if (got != exp) {
   1054             log("  FAIL (%s:%d, i=%d)", __FILE__, __LINE__, i);
   1055             logln(CalendarTest::calToStr(*testCal));
   1056             testCal->setTime(exp, status);
   1057             logln(CalendarTest::calToStr(*testCal) + UnicodeString( " <<< expected "));
   1058             fail = TRUE;
   1059         }
   1060         logln("");
   1061 
   1062         testCal->clear();
   1063         testCal->set(UCAL_YEAR_WOY, ywoy);
   1064         testCal->set(UCAL_WEEK_OF_YEAR, woy);
   1065         testCal->set(UCAL_DAY_OF_WEEK, dow);
   1066         got = testCal->getTime(status);
   1067         str.remove();
   1068         str2.remove();
   1069         log(UnicodeString("YWOY") + ywoy + "-W" + woy +
   1070                          "-DOW" + dow + " expect:" + sdf.format(exp, str) +
   1071                          " got:" + sdf.format(got, str2));
   1072         if (got != exp) {
   1073             log("  FAIL");
   1074             fail = TRUE;
   1075         }
   1076         logln("");
   1077     }
   1078     // Now try adding and rolling
   1079     UDate ADDROLL_date [] = {
   1080         makeDate(1998, UCAL_DECEMBER, 25), makeDate(1999, UCAL_JANUARY, 1),
   1081         makeDate(1997, UCAL_DECEMBER, 28), makeDate(1998, UCAL_JANUARY, 4),
   1082         makeDate(1998, UCAL_DECEMBER, 27), makeDate(1997, UCAL_DECEMBER, 28),
   1083         makeDate(1999, UCAL_JANUARY, 2), makeDate(1998, UCAL_JANUARY, 3),
   1084     };
   1085 
   1086     int32_t ADDROLL_int []= {
   1087         (1),
   1088         (1),
   1089         (1),
   1090         (1)
   1091     };
   1092 
   1093 
   1094     UBool ADDROLL_bool [] = {
   1095         TRUE,//ADD,
   1096         TRUE,
   1097         FALSE,
   1098         FALSE
   1099     };
   1100 
   1101     testCal->setMinimalDaysInFirstWeek(3);
   1102     testCal->setFirstDayOfWeek(UCAL_SUNDAY);
   1103     for (i=0; i<8; i += 2) {
   1104         int32_t amount = ADDROLL_int[i/2];
   1105         UDate before = ADDROLL_date[i];
   1106         UDate after = ADDROLL_date[i+1];
   1107 
   1108         testCal->setTime(before,status);
   1109         if (ADDROLL_bool[i/2])
   1110             testCal->add(UCAL_WEEK_OF_YEAR, amount,status);
   1111         else
   1112             testCal->roll(UCAL_WEEK_OF_YEAR, amount,status);
   1113         UDate got = testCal->getTime(status);
   1114         str.remove();
   1115         str2.remove();
   1116         UnicodeString opTypeStr;
   1117         if (ADDROLL_bool[i/2]) {
   1118             opTypeStr = UnicodeString("add(WOY,", "");
   1119         } else {
   1120             opTypeStr = UnicodeString("roll(WOY,", "");
   1121         }
   1122         log(opTypeStr + amount + ") " + sdf.format(before, str) + " => " +
   1123                     sdf.format(got, str2));
   1124         if (after != got) {
   1125             str.remove();
   1126             logln(UnicodeString("  exp:") + sdf.format(after, str) + "  FAIL");
   1127             fail = TRUE;
   1128         }
   1129         else logln(" ok");
   1130 
   1131         testCal->setTime(after,status);
   1132         if (ADDROLL_bool[i/2])
   1133             testCal->add(UCAL_WEEK_OF_YEAR, -amount,status);
   1134         else
   1135             testCal->roll(UCAL_WEEK_OF_YEAR, -amount,status);
   1136         got = testCal->getTime(status);
   1137         str.remove();
   1138         str2.remove();
   1139         log(opTypeStr + (-amount) + ") " + sdf.format(after, str) + " => " +
   1140                 sdf.format(got, str2));
   1141         if (before != got) {
   1142             str.remove();
   1143             logln(UnicodeString("  exp:") + sdf.format(before, str) + "  FAIL");
   1144             fail = TRUE;
   1145         }
   1146         else logln(" ok");
   1147     }
   1148     if (fail)
   1149         errln("Fail: Week of year misbehaving");
   1150 }
   1151 
   1152 /**
   1153  * @bug 4106136
   1154  */
   1155 void CalendarRegressionTest::test4106136()
   1156 {
   1157     UErrorCode status = U_ZERO_ERROR;
   1158     Locale saveLocale = Locale::getDefault();
   1159     //try {
   1160     Locale locales [] = { Locale::getChinese(), Locale::getChina() };
   1161         for (int32_t i=0; i<2; ++i) {
   1162             Locale::setDefault(locales[i], status);
   1163             failure(status, "Locale::setDefault");
   1164             int32_t count1, count2, count3;
   1165             Calendar::getAvailableLocales(count1);
   1166             DateFormat::getAvailableLocales(count2);
   1167             NumberFormat::getAvailableLocales(count3);
   1168             int32_t n [] = {
   1169                 count1, count2, count3
   1170             };
   1171             for (int32_t j=0; j<3; ++j) {
   1172                 UnicodeString temp;
   1173                 if (n[j] == 0)
   1174                     dataerrln(UnicodeString("Fail: No locales for ") + locales[i].getName());
   1175             }
   1176         }
   1177     //}
   1178     //finally {
   1179         Locale::setDefault(saveLocale,status);
   1180     //}
   1181 }
   1182 
   1183 /**
   1184  * @bug 4108764
   1185  */
   1186 void CalendarRegressionTest::test4108764()
   1187 {
   1188     UErrorCode status = U_ZERO_ERROR;
   1189     Calendar *cal = Calendar::createInstance(status);
   1190     if(U_FAILURE(status)) {
   1191       errln("Error creating calendar %s", u_errorName(status));
   1192       delete cal;
   1193       return;
   1194     }
   1195     UDate d00 = makeDate(1997, UCAL_MARCH, 15, 12, 00, 00);
   1196     UDate d01 = makeDate(1997, UCAL_MARCH, 15, 12, 00, 56);
   1197     UDate d10 = makeDate(1997, UCAL_MARCH, 15, 12, 34, 00);
   1198     UDate d11 = makeDate(1997, UCAL_MARCH, 15, 12, 34, 56);
   1199     UDate epoch = makeDate(1970, UCAL_JANUARY, 1);
   1200 
   1201     cal->setTime(d11,status);
   1202 
   1203     cal->clear( UCAL_MINUTE );
   1204     logln(UnicodeString("") + cal->getTime(status));
   1205     if (cal->getTime(status)  != d01)
   1206         errln("Fail: clear(MINUTE) broken");
   1207 
   1208     cal->set( UCAL_SECOND, 0 );
   1209     logln(UnicodeString("") + cal->getTime(status));
   1210     if (cal->getTime(status)  != d00)
   1211         errln("Fail: set(SECOND, 0) broken");
   1212 
   1213     cal->setTime(d11,status);
   1214     cal->set( UCAL_SECOND, 0 );
   1215     logln(UnicodeString("") + cal->getTime(status));
   1216     if (cal->getTime(status)  != d10)
   1217         errln("Fail: set(SECOND, 0) broken #2");
   1218 
   1219     cal->clear( UCAL_MINUTE );
   1220     logln(UnicodeString("") + cal->getTime(status));
   1221     if (cal->getTime(status)  != d00)
   1222         errln("Fail: clear(MINUTE) broken #2");
   1223 
   1224     cal->clear();
   1225     logln(UnicodeString("") + cal->getTime(status));
   1226     if (cal->getTime(status)  != epoch)
   1227         errln(UnicodeString("Fail: clear() broken Want ") + epoch);
   1228 
   1229     delete cal;
   1230 }
   1231 
   1232 /**
   1233  * @bug 4114578
   1234  */
   1235 void CalendarRegressionTest::test4114578()
   1236 {
   1237     UErrorCode status = U_ZERO_ERROR;
   1238     int32_t ONE_HOUR = 60*60*1000;
   1239     Calendar *cal = Calendar::createInstance(status);
   1240     if(U_FAILURE(status)) {
   1241       errln("Error creating calendar %s", u_errorName(status));
   1242       delete cal;
   1243       return;
   1244     }
   1245     cal->adoptTimeZone(TimeZone::createTimeZone("PST"));
   1246     UDate onset = makeDate(1998, UCAL_APRIL, 5, 1, 0) + ONE_HOUR;
   1247     UDate cease = makeDate(1998, UCAL_OCTOBER, 25, 0, 0) + 2*ONE_HOUR;
   1248 
   1249     UBool fail = FALSE;
   1250 
   1251     const int32_t ADD = 1;
   1252     const int32_t ROLL = 2;
   1253 
   1254     double DATA []= {
   1255         // Start            Action   Amt    Expected_change
   1256         onset - ONE_HOUR,   ADD,      1,     ONE_HOUR,
   1257         onset,              ADD,     -1,    -ONE_HOUR,
   1258         onset - ONE_HOUR,   ROLL,     1,     ONE_HOUR,
   1259         onset,              ROLL,    -1,    -ONE_HOUR,
   1260         cease - ONE_HOUR,   ADD,      1,     ONE_HOUR,
   1261         cease,              ADD,     -1,    -ONE_HOUR,
   1262         cease - ONE_HOUR,   ROLL,     1,     ONE_HOUR,
   1263         cease,              ROLL,    -1,    -ONE_HOUR,
   1264     };
   1265 
   1266     for (int32_t i=0; i<32; i+=4) {
   1267         UDate date = DATA[i];
   1268         int32_t amt = (int32_t) DATA[i+2];
   1269         double expectedChange = DATA[i+3];
   1270 
   1271         log(UnicodeString("") + date);
   1272         cal->setTime(date,status);
   1273 
   1274         switch ((int32_t) DATA[i+1]) {
   1275         case ADD:
   1276             log(UnicodeString(" add (HOUR,") + (amt<0?"":"+")+amt + ")= ");
   1277             cal->add(UCAL_HOUR, amt,status);
   1278             break;
   1279         case ROLL:
   1280             log(UnicodeString(" roll(HOUR,") + (amt<0?"":"+")+amt + ")= ");
   1281             cal->roll(UCAL_HOUR, amt,status);
   1282             break;
   1283         }
   1284 
   1285         log(UnicodeString("") + cal->getTime(status));
   1286 
   1287         double change = cal->getTime(status) - date;
   1288         if (change != expectedChange) {
   1289             fail = TRUE;
   1290             logln(" FAIL");
   1291         }
   1292         else logln(" OK");
   1293     }
   1294 
   1295     if (fail) errln("Fail: roll/add misbehaves around DST onset/cease");
   1296 
   1297     delete cal;
   1298 }
   1299 
   1300 /**
   1301  * @bug 4118384
   1302  * Make sure maximum for HOUR field is 11, not 12.
   1303  */
   1304 void CalendarRegressionTest::test4118384()
   1305 {
   1306     UErrorCode status = U_ZERO_ERROR;
   1307     Calendar *cal = Calendar::createInstance(status);
   1308     if(U_FAILURE(status)) {
   1309       errln("Error creating calendar %s", u_errorName(status));
   1310       delete cal;
   1311       return;
   1312     }
   1313     if (cal->getMaximum(UCAL_HOUR) != 11 ||
   1314         cal->getLeastMaximum(UCAL_HOUR) != 11 ||
   1315         cal->getActualMaximum(UCAL_HOUR,status) != 11)
   1316         errln("Fail: maximum of HOUR field should be 11");
   1317 
   1318     // test deprecated functions
   1319     if (cal->getLeastMaximum(Calendar::HOUR) != 11 ||
   1320         cal->getMaximum(Calendar::HOUR) != 11) {
   1321         errln("Fail: [deprecated functions] maximum of HOUR field should be 11\n");
   1322     }
   1323 
   1324     if (cal->getGreatestMinimum(Calendar::HOUR) != 0 ||
   1325         cal->getMinimum(Calendar::HOUR) != 0) {
   1326         errln("Fail: [deprecated functions] minimum of HOUR field should be 1\n");
   1327     }
   1328 
   1329     delete cal;
   1330     cal = Calendar::createInstance(Locale("th_TH@calendar=buddhist"),status);
   1331     // test deprecated functions
   1332     if (cal->getLeastMaximum(Calendar::HOUR) != 11 ||
   1333         cal->getMaximum(Calendar::HOUR) != 11) {
   1334         errln("Fail: Buddhist:[deprecated functions] maximum of HOUR field should be 11\n");
   1335     }
   1336 
   1337     if (cal->getGreatestMinimum(Calendar::HOUR) != 0 ||
   1338         cal->getMinimum(Calendar::HOUR) != 0) {
   1339         errln("Fail: Buddhist:[deprecated functions] minimum of HOUR field should be 1\n");
   1340     }
   1341 
   1342     delete cal;
   1343     // test deprecated functions
   1344     cal = Calendar::createInstance(Locale("ja_JP@calendar=japanese"),status);
   1345     if (cal->getLeastMaximum(Calendar::HOUR) != 11 ||
   1346         cal->getMaximum(Calendar::HOUR) != 11) {
   1347         errln("Fail: Japanese:[deprecated functions] maximum of HOUR field should be 11\n");
   1348     }
   1349 
   1350     if (cal->getGreatestMinimum(Calendar::HOUR) != 0 ||
   1351         cal->getMinimum(Calendar::HOUR) != 0) {
   1352         errln("Fail: Japanese:[deprecated functions] minimum of HOUR field should be 1\n");
   1353     }
   1354 
   1355     delete cal;
   1356 }
   1357 
   1358 /**
   1359  * @bug 4125881
   1360  * Check isLeapYear for BC years.
   1361  */
   1362 void CalendarRegressionTest::test4125881()
   1363 {
   1364     UErrorCode status = U_ZERO_ERROR;
   1365     GregorianCalendar *cal = (GregorianCalendar*) Calendar::createInstance(status);
   1366     if(U_FAILURE(status)) {
   1367       errln("Error creating calendar %s", u_errorName(status));
   1368       delete cal;
   1369       return;
   1370     }
   1371     DateFormat *fmt = new SimpleDateFormat(UnicodeString("MMMM d, yyyy G"),status);
   1372     if(!assertSuccess("trying to construct", status))return;
   1373     cal->clear();
   1374     for (int32_t y=-20; y<=10; ++y) {
   1375         cal->set(UCAL_ERA, y < 1 ? GregorianCalendar::BC : GregorianCalendar::AD);
   1376         cal->set(UCAL_YEAR, y < 1 ? 1 - y : y);
   1377         UnicodeString temp;
   1378         logln(UnicodeString("") + y + UnicodeString(" = ") + fmt->format(cal->getTime(status), temp) + " " +
   1379                            cal->isLeapYear(y));
   1380         if (cal->isLeapYear(y) != ((y+40)%4 == 0))
   1381             errln("Leap years broken");
   1382     }
   1383 
   1384     delete cal;
   1385     delete fmt;
   1386 }
   1387 
   1388 /**
   1389  * @bug 4125892
   1390  * Prove that GregorianCalendar is proleptic (it used to cut off
   1391  * at 45 BC, and not have leap years before then).
   1392  */
   1393 void CalendarRegressionTest::test4125892() {
   1394     UErrorCode status = U_ZERO_ERROR;
   1395     GregorianCalendar *cal = (GregorianCalendar*) Calendar::createInstance(status);
   1396     if(U_FAILURE(status)) {
   1397       errln("Error creating calendar %s", u_errorName(status));
   1398       delete cal;
   1399       return;
   1400     }
   1401     DateFormat *fmt = new SimpleDateFormat(UnicodeString("MMMM d, yyyy G"),status);
   1402     if(!assertSuccess("trying to construct", status))return;
   1403     cal->clear();
   1404     cal->set(UCAL_ERA, GregorianCalendar::BC);
   1405     cal->set(UCAL_YEAR, 81); // 81 BC is a leap year (proleptically)
   1406     cal->set(UCAL_MONTH, UCAL_FEBRUARY);
   1407     cal->set(UCAL_DATE, 28);
   1408     cal->add(UCAL_DATE, 1,status);
   1409     if(U_FAILURE(status))
   1410         errln("add(DATE,1) failed");
   1411     if (cal->get(UCAL_DATE,status) != 29 ||
   1412         !cal->isLeapYear(-80)) // -80 == 81 BC
   1413         errln("Calendar not proleptic");
   1414 
   1415     delete cal;
   1416     delete fmt;
   1417 }
   1418 
   1419 /**
   1420  * @bug 4141665
   1421  * GregorianCalendar::equals() ignores cutover date
   1422  */
   1423 void CalendarRegressionTest::test4141665()
   1424 {
   1425     UErrorCode status = U_ZERO_ERROR;
   1426     GregorianCalendar *cal = new GregorianCalendar(status);
   1427     if(U_FAILURE(status)) {
   1428       errln("Error creating calendar %s", u_errorName(status));
   1429       delete cal;
   1430       return;
   1431     }
   1432     GregorianCalendar *cal2 = (GregorianCalendar*)cal->clone();
   1433     UDate cut = cal->getGregorianChange();
   1434     UDate cut2 = cut + 100*24*60*60*1000.0; // 100 days later
   1435     if (*cal != *cal2) {
   1436         errln("Cloned GregorianCalendars not equal");
   1437     }
   1438     cal2->setGregorianChange(cut2,status);
   1439     if ( *cal == *cal2) {
   1440         errln("GregorianCalendar::equals() ignores cutover");
   1441     }
   1442 
   1443     delete cal;
   1444     delete cal2;
   1445 }
   1446 
   1447 /**
   1448  * @bug 4142933
   1449  * Bug states that ArrayIndexOutOfBoundsException is thrown by GregorianCalendar::roll()
   1450  * when IllegalArgumentException should be.
   1451  */
   1452 void CalendarRegressionTest::test4142933()
   1453 {
   1454     UErrorCode status = U_ZERO_ERROR;
   1455     GregorianCalendar *calendar = new GregorianCalendar(status);
   1456     if(U_FAILURE(status)) {
   1457       errln("Error creating calendar %s", u_errorName(status));
   1458       delete calendar;
   1459       return;
   1460     }
   1461     //try {
   1462     calendar->roll((UCalendarDateFields)-1, TRUE, status);
   1463         if(U_SUCCESS(status))
   1464             errln("Test failed, no exception thrown");
   1465     //}
   1466     //catch (IllegalArgumentException e) {
   1467         // OK: Do nothing
   1468         // logln("Test passed");
   1469     //}
   1470     //catch (Exception e) {
   1471         //errln("Test failed. Unexpected exception is thrown: " + e);
   1472         //e.printStackTrace();
   1473     //}
   1474 
   1475     delete calendar;
   1476 }
   1477 
   1478 /**
   1479  * @bug 4145158
   1480  * GregorianCalendar handling of Dates Long.MIN_VALUE and Long.MAX_VALUE is
   1481  * confusing; unless the time zone has a raw offset of zero, one or the
   1482  * other of these will wrap.  We've modified the test given in the bug
   1483  * report to therefore only check the behavior of a calendar with a zero raw
   1484  * offset zone.
   1485  */
   1486 void CalendarRegressionTest::test4145158()
   1487 {
   1488     UErrorCode status = U_ZERO_ERROR;
   1489     GregorianCalendar *calendar = new GregorianCalendar(status);
   1490     if(status == U_USING_FALLBACK_WARNING || U_FAILURE(status)) {
   1491       dataerrln("Error creating calendar %s", u_errorName(status));
   1492       delete calendar;
   1493       return;
   1494     }
   1495 
   1496     calendar->adoptTimeZone(TimeZone::createTimeZone("GMT"));
   1497 
   1498     calendar->setTime(makeDate(INT32_MIN),status);
   1499     int32_t year1 = calendar->get(UCAL_YEAR,status);
   1500     int32_t era1 = calendar->get(UCAL_ERA,status);
   1501 
   1502     calendar->setTime(makeDate(INT32_MAX),status);
   1503     int32_t year2 = calendar->get(UCAL_YEAR,status);
   1504     int32_t era2 = calendar->get(UCAL_ERA,status);
   1505 
   1506     if (year1 == year2 && era1 == era2) {
   1507         errln("Fail: Long.MIN_VALUE or Long.MAX_VALUE wrapping around");
   1508     }
   1509 
   1510     delete calendar;
   1511 }
   1512 
   1513 /**
   1514  * @bug 4145983
   1515  * Maximum value for YEAR field wrong.
   1516  */
   1517 // {sfb} this is not directly applicable in C++, since all
   1518 // possible doubles are not representable by our Calendar.
   1519 // In Java, all longs are representable.
   1520 // We can determine limits programmatically
   1521 // Using DBL_MAX is a bit of a hack, since for large doubles
   1522 // Calendar gets squirrely and doesn't behave in any sort
   1523 // of linear fashion (ie years jump around, up/down, etc) for a
   1524 // small change in millis.
   1525 void CalendarRegressionTest::test4145983()
   1526 {
   1527     UErrorCode status = U_ZERO_ERROR;
   1528     GregorianCalendar *calendar = new GregorianCalendar(status);
   1529     if(U_FAILURE(status)) {
   1530       errln("Error creating calendar %s", u_errorName(status));
   1531       delete calendar;
   1532       return;
   1533     }
   1534     calendar->adoptTimeZone(TimeZone::createTimeZone("GMT"));
   1535     UDate DATES [] = { LATEST_SUPPORTED_MILLIS, EARLIEST_SUPPORTED_MILLIS };
   1536     for (int32_t i=0; i<2; ++i) {
   1537         calendar->setTime(DATES[i], status);
   1538         int32_t year = calendar->get(UCAL_YEAR,status);
   1539         int32_t maxYear = calendar->getMaximum(UCAL_YEAR);
   1540         if (year > maxYear) {
   1541             errln(UnicodeString("Failed for ")+DATES[i]+" ms: year=" +
   1542                   year + ", maxYear=" + maxYear);
   1543         }
   1544     }
   1545 
   1546     delete calendar;
   1547 }
   1548 
   1549 /**
   1550  * @bug 4147269
   1551  * This is a bug in the validation code of GregorianCalendar::  As reported,
   1552  * the bug seems worse than it really is, due to a bug in the way the bug
   1553  * report test was written.  In reality the bug is restricted to the DAY_OF_YEAR
   1554  * field. - liu 6/29/98
   1555  */
   1556 void CalendarRegressionTest::test4147269()
   1557 {
   1558     UErrorCode status = U_ZERO_ERROR;
   1559     GregorianCalendar *calendar = new GregorianCalendar(status);
   1560     if(status == U_USING_FALLBACK_WARNING || U_FAILURE(status)) {
   1561       dataerrln("Error creating calendar %s", u_errorName(status));
   1562       delete calendar;
   1563       return;
   1564     }
   1565     calendar->setLenient(FALSE);
   1566     UDate date = makeDate(1996, UCAL_JANUARY, 3); // Arbitrary date
   1567     for (int32_t field = 0; field < UCAL_FIELD_COUNT; field++) {
   1568         calendar->setTime(date,status);
   1569         // Note: In the bug report, getActualMaximum() was called instead
   1570         // of getMaximum() -- this was an error.  The validation code doesn't
   1571         // use getActualMaximum(), since that's too costly.
   1572         int32_t max = calendar->getMaximum((UCalendarDateFields)field);
   1573         int32_t value = max+1;
   1574         calendar->set((UCalendarDateFields)field, value);
   1575         //try {
   1576             calendar->getTime(status); // Force time computation
   1577             // We expect an exception to be thrown. If we fall through
   1578             // to the next line, then we have a bug.
   1579             if(U_SUCCESS(status))
   1580             errln(UnicodeString("Test failed with field ") + FIELD_NAME[field] +
   1581                   ", date before: " + date +
   1582                   ", date after: " + calendar->getTime(status) +
   1583                   ", value: " + value + " (max = " + max +")");
   1584         //} catch (IllegalArgumentException e) {}
   1585     }
   1586 
   1587     delete calendar;
   1588 }
   1589 
   1590 /**
   1591  * @bug 4149677
   1592  * Reported bug is that a GregorianCalendar with a cutover of Date(Long.MAX_VALUE)
   1593  * doesn't behave as a pure Julian calendar.
   1594  * CANNOT REPRODUCE THIS BUG
   1595  */
   1596 void
   1597 CalendarRegressionTest::Test4149677()
   1598 {
   1599     UErrorCode status = U_ZERO_ERROR;
   1600 
   1601     TimeZone *zones [] = {
   1602         TimeZone::createTimeZone("GMT"),
   1603         TimeZone::createTimeZone("PST"),
   1604         TimeZone::createTimeZone("EAT")
   1605     };
   1606     if(U_FAILURE(status)) {
   1607         errln("Couldn't create zones");
   1608         return;
   1609         // could leak memory
   1610     }
   1611 
   1612     for (int32_t i=0; i < 3; ++i) {
   1613         GregorianCalendar *calendar = new GregorianCalendar(zones[i], status);
   1614         if(U_FAILURE(status)) {
   1615             errln("Couldnt' create calendar.");
   1616             return;
   1617         }
   1618 
   1619         // Make sure extreme values don't wrap around
   1620         calendar->setTime(EARLIEST_SUPPORTED_MILLIS, status);
   1621         if(U_FAILURE(status))
   1622             errln("setTime failed");
   1623         if (calendar->get(UCAL_ERA, status) != GregorianCalendar::BC || U_FAILURE(status)) {
   1624             errln("Fail: Date(EARLIEST_SUPPORTED_MILLIS) has an AD year");
   1625         }
   1626         calendar->setTime(LATEST_SUPPORTED_MILLIS, status);
   1627         if(U_FAILURE(status))
   1628             errln("setTime failed");
   1629         if (calendar->get(UCAL_ERA, status) != GregorianCalendar::AD || U_FAILURE(status)) {
   1630             errln("Fail: Date(LATEST_SUPPORTED_MILLIS) has a BC year");
   1631         }
   1632 
   1633         calendar->setGregorianChange(LATEST_SUPPORTED_MILLIS, status);
   1634         if(U_FAILURE(status))
   1635             errln("setGregorianChange failed");
   1636         // to obtain a pure Julian calendar
   1637 
   1638         UBool is100Leap = calendar->isLeapYear(100);
   1639         if (!is100Leap) {
   1640             UnicodeString temp;
   1641             errln("test failed with zone " + zones[i]->getID(temp));
   1642             errln(" cutover date is Date(Long.MAX_VALUE)");
   1643             errln(" isLeapYear(100) returns: " + is100Leap);
   1644         }
   1645         delete calendar;
   1646     }
   1647 
   1648     // no need for cleanup- zones were adopted
   1649 }
   1650 
   1651 /**
   1652  * @bug 4162587
   1653  * Calendar and Date HOUR broken.  If HOUR is out-of-range, Calendar
   1654  * and Date classes will misbehave.
   1655  */
   1656 void
   1657 CalendarRegressionTest::Test4162587()
   1658 {
   1659     UErrorCode status = U_ZERO_ERROR;
   1660     TimeZone *savedef = TimeZone::createDefault();
   1661     TimeZone *tz = TimeZone::createTimeZone("PST");
   1662     //TimeZone::adoptDefault(tz);
   1663     TimeZone::setDefault(*tz);
   1664 
   1665     GregorianCalendar *cal = new GregorianCalendar(tz, status);
   1666     if(U_FAILURE(status)) {
   1667         errln("Couldn't create calendar");
   1668         return;
   1669     }
   1670     UDate d0, dPlus, dMinus;
   1671 
   1672     for(int32_t i=0; i<5; ++i) {
   1673         if (i>0) logln("---");
   1674 
   1675         cal->clear();
   1676         cal->set(1998, UCAL_APRIL, 5, i, 0);
   1677         d0 = cal->getTime(status);
   1678         if(U_FAILURE(status))
   1679             errln("Coudln't get time (1)");
   1680         //String s0 = d.toString();
   1681         logln(UnicodeString("0 ") + i + ": " + d0/*s0*/);
   1682 
   1683         cal->clear();
   1684         cal->set(1998, UCAL_APRIL, 4, i+24, 0);
   1685         dPlus = cal->getTime(status);
   1686         if(U_FAILURE(status))
   1687             errln("Coudln't get time (2)");
   1688         //String sPlus = d.toString();
   1689         logln(UnicodeString("+ ") + i + ": " + dPlus/*sPlus*/);
   1690 
   1691         cal->clear();
   1692         cal->set(1998, UCAL_APRIL, 6, i-24, 0);
   1693         dMinus = cal->getTime(status);
   1694         if(U_FAILURE(status))
   1695             errln("Coudln't get time (3)");
   1696         //String sMinus = d.toString();
   1697         logln(UnicodeString("- ") + i + ": " + dMinus/*sMinus*/);
   1698 
   1699         if (d0 != dPlus || d0 != dMinus) {
   1700             errln("Fail: All three lines must match");
   1701         }
   1702     }
   1703     TimeZone::setDefault(*savedef);
   1704     //delete tz;
   1705     delete cal;
   1706     delete savedef;
   1707 }
   1708 
   1709 /**
   1710  * @bug 4165343
   1711  * Adding 12 months behaves differently from adding 1 year
   1712  */
   1713 void
   1714 CalendarRegressionTest::Test4165343()
   1715 {
   1716     UErrorCode status = U_ZERO_ERROR;
   1717     GregorianCalendar *calendar = new GregorianCalendar(1996, UCAL_FEBRUARY, 29, status);
   1718     if(U_FAILURE(status)) {
   1719         errln("Couldn't create calendar");
   1720         return;
   1721     }
   1722     UDate start = calendar->getTime(status);
   1723     if(U_FAILURE(status))
   1724         errln("Couldn't getTime (1)");
   1725     logln(UnicodeString("init date: ") + start);
   1726     calendar->add(UCAL_MONTH, 12, status);
   1727     if(U_FAILURE(status))
   1728         errln("Couldn't add(MONTH, 12)");
   1729     UDate date1 = calendar->getTime(status);
   1730     if(U_FAILURE(status))
   1731         errln("Couldn't getTime (2)");
   1732     logln(UnicodeString("after adding 12 months: ") + date1);
   1733     calendar->setTime(start, status);
   1734     if(U_FAILURE(status))
   1735         errln("Couldn't setTime");
   1736     calendar->add(UCAL_YEAR, 1, status);
   1737     if(U_FAILURE(status))
   1738         errln("Couldn't add(YEAR, 1)");
   1739     UDate date2 = calendar->getTime(status);
   1740     if(U_FAILURE(status))
   1741         errln("Couldn't getTime (3)");
   1742     logln(UnicodeString("after adding one year : ") + date2);
   1743     if (date1 == date2) {
   1744         logln("Test passed");
   1745     } else {
   1746         errln("Test failed");
   1747     }
   1748     delete calendar;
   1749 }
   1750 
   1751 /**
   1752  * @bug 4166109
   1753  * GregorianCalendar.getActualMaximum() does not account for first day of week.
   1754  */
   1755 void
   1756 CalendarRegressionTest::Test4166109()
   1757 {
   1758     /* Test month:
   1759      *
   1760      *      March 1998
   1761      * Su Mo Tu We Th Fr Sa
   1762      *  1  2  3  4  5  6  7
   1763      *  8  9 10 11 12 13 14
   1764      * 15 16 17 18 19 20 21
   1765      * 22 23 24 25 26 27 28
   1766      * 29 30 31
   1767      */
   1768     UBool passed = TRUE;
   1769     UErrorCode status = U_ZERO_ERROR;
   1770     UCalendarDateFields field = UCAL_WEEK_OF_MONTH;
   1771 
   1772     GregorianCalendar *calendar = new GregorianCalendar(Locale::getUS(), status);
   1773     if(U_FAILURE(status)) {
   1774         errln("Couldn't create calendar");
   1775         return;
   1776     }
   1777     calendar->set(1998, UCAL_MARCH, 1);
   1778     calendar->setMinimalDaysInFirstWeek(1);
   1779     logln(UnicodeString("Date:  ") + calendar->getTime(status)); // 888817448000
   1780 
   1781     int32_t firstInMonth = calendar->get(UCAL_DATE, status);
   1782     if(U_FAILURE(status))
   1783         errln("get(D_O_M) failed");
   1784 
   1785     for(int32_t firstInWeek = UCAL_SUNDAY; firstInWeek <= UCAL_SATURDAY; firstInWeek++) {
   1786         calendar->setFirstDayOfWeek((UCalendarDaysOfWeek)firstInWeek);
   1787         int32_t returned = calendar->getActualMaximum(field, status);
   1788         int32_t expected = (31 + ((firstInMonth - firstInWeek + 7)% 7) + 6) / 7;
   1789 
   1790         logln(UnicodeString("First day of week = ") + firstInWeek +
   1791               "  getActualMaximum(WEEK_OF_MONTH, status) = " + returned +
   1792               "  expected = " + expected +
   1793               ((returned == expected) ? "  ok" : "  FAIL"));
   1794 
   1795         if (returned != expected) {
   1796             passed = FALSE;
   1797         }
   1798     }
   1799     if (!passed) {
   1800         errln("Test failed");
   1801     }
   1802 
   1803     delete calendar;
   1804 }
   1805 
   1806 /**
   1807  * @bug 4167060
   1808  * Calendar.getActualMaximum(YEAR) works wrong.
   1809  */
   1810 void
   1811 CalendarRegressionTest::Test4167060()
   1812 {
   1813     UErrorCode status = U_ZERO_ERROR;
   1814     UCalendarDateFields field = UCAL_YEAR;
   1815     DateFormat *format = new SimpleDateFormat(UnicodeString("EEE MMM dd HH:mm:ss zzz yyyy G"),
   1816         Locale::getUS(), status);
   1817     if(U_FAILURE(status)) {
   1818         errcheckln(status, "Couldn't create SimpleDateFormat - %s", u_errorName(status));
   1819         return;
   1820     }
   1821 
   1822     GregorianCalendar *calendars [] = {
   1823         new GregorianCalendar(100, UCAL_NOVEMBER, 1, status),
   1824         new GregorianCalendar(-99 /*100BC*/, UCAL_JANUARY, 1, status),
   1825         new GregorianCalendar(1996, UCAL_FEBRUARY, 29, status),
   1826     };
   1827     if(U_FAILURE(status)) {
   1828         errln("Couldn't create GregorianCalendars");
   1829         return;
   1830         // could leak
   1831     }
   1832 
   1833     UnicodeString id [] = { "Hybrid", "Gregorian", "Julian" };
   1834 
   1835     for (int32_t k=0; k<3; ++k) {
   1836         logln("--- " + id[k] + " ---");
   1837 
   1838         for (int32_t j=0; j < 3; ++j) {
   1839             GregorianCalendar *calendar = calendars[j];
   1840             if (k == 1) {
   1841                 calendar->setGregorianChange(EARLIEST_SUPPORTED_MILLIS, status);
   1842             }
   1843             else if (k == 2) {
   1844                 calendar->setGregorianChange(LATEST_SUPPORTED_MILLIS, status);
   1845             }
   1846 
   1847             if(U_FAILURE(status))
   1848                 errln("setGregorianChange() failed");
   1849             format->adoptCalendar((Calendar*)calendar->clone());
   1850 
   1851             UDate dateBefore = calendar->getTime(status);
   1852             if(U_FAILURE(status))
   1853                 errln("getTime() failed");
   1854 
   1855             int32_t maxYear = calendar->getActualMaximum(field, status);
   1856             UnicodeString temp;
   1857             logln(UnicodeString("maxYear: ") + maxYear + " for " + format->format(calendar->getTime(status), temp));
   1858             temp.remove();
   1859             logln("date before: " + format->format(dateBefore, temp));
   1860 
   1861             int32_t years[] = {2000, maxYear-1, maxYear, maxYear+1};
   1862 
   1863             for (int32_t i = 0; i < 4; i++) {
   1864                 UBool valid = years[i] <= maxYear;
   1865                 calendar->set(field, years[i]);
   1866                 UDate dateAfter = calendar->getTime(status);
   1867                 if(U_FAILURE(status))
   1868                     errln("getTime() failed");
   1869                 int32_t newYear = calendar->get(field, status);
   1870                 if(U_FAILURE(status))
   1871                     errln(UnicodeString("get(") + (int32_t)field + ") failed");
   1872                 calendar->setTime(dateBefore, status); // restore calendar for next use
   1873                 if(U_FAILURE(status))
   1874                     errln("setTime() failed");
   1875 
   1876                 temp.remove();
   1877                 logln(UnicodeString(" Year ") + years[i] + (valid? " ok " : " bad") +
   1878                       " => " + format->format(dateAfter, temp));
   1879                 if (valid && newYear != years[i]) {
   1880                     errln(UnicodeString("  FAIL: ") + newYear + " should be valid; date, month and time shouldn't change");
   1881                 }
   1882                 // {sfb} this next line is a hack, but it should work since if a
   1883                 // double has an exponent, adding 1 should not yield the same double
   1884                 else if (!valid && /*newYear == years[i]*/ dateAfter + 1.0 == dateAfter)  {
   1885                     errln(UnicodeString("  FAIL: ") + newYear + " should be invalid");
   1886                 }
   1887             }
   1888         }
   1889     }
   1890 
   1891     delete format;
   1892     delete calendars[0];
   1893     delete calendars[1];
   1894     delete calendars[2];
   1895 }
   1896 
   1897 /**
   1898  * Week of year is wrong at the start and end of the year.
   1899  */
   1900 void CalendarRegressionTest::Test4197699() {
   1901     UErrorCode status = U_ZERO_ERROR;
   1902     GregorianCalendar cal(status);
   1903     cal.setFirstDayOfWeek(UCAL_MONDAY);
   1904     cal.setMinimalDaysInFirstWeek(4);
   1905     SimpleDateFormat fmt("E dd MMM yyyy  'DOY='D 'WOY='w",
   1906                          Locale::getUS(), status);
   1907     fmt.setCalendar(cal);
   1908     if (U_FAILURE(status)) {
   1909         errcheckln(status, "Couldn't initialize test - %s", u_errorName(status));
   1910         return;
   1911     }
   1912 
   1913     int32_t DATA[] = {
   1914         2000,  UCAL_JANUARY,   1,   52,
   1915         2001,  UCAL_DECEMBER,  31,  1,
   1916     };
   1917     int32_t DATA_length = (int32_t)(sizeof(DATA) / sizeof(DATA[0]));
   1918 
   1919     UnicodeString str;
   1920     DateFormat& dfmt = *(DateFormat*)&fmt;
   1921     for (int32_t i=0; i<DATA_length; ) {
   1922         cal.clear();
   1923         cal.set(DATA[i], DATA[i+1], DATA[i+2]);
   1924         i += 3;
   1925         int32_t expWOY = DATA[i++];
   1926         int32_t actWOY = cal.get(UCAL_WEEK_OF_YEAR, status);
   1927         if (expWOY == actWOY) {
   1928             logln(UnicodeString("Ok: ") + dfmt.format(cal.getTime(status), str.remove()));
   1929         } else {
   1930             errln(UnicodeString("FAIL: ") + dfmt.format(cal.getTime(status), str.remove())
   1931                   + ", expected WOY=" + expWOY);
   1932             cal.add(UCAL_DATE, -8, status);
   1933             for (int j=0; j<14; ++j) {
   1934                 cal.add(UCAL_DATE, 1, status);
   1935                 logln(dfmt.format(cal.getTime(status), str.remove()));
   1936             }
   1937         }
   1938         if (U_FAILURE(status)) {
   1939             errln("FAIL: Unexpected error from Calendar");
   1940             return;
   1941         }
   1942     }
   1943 }
   1944 
   1945     enum Action { ADD=1, ROLL=2 };
   1946     enum Sign { PLUS=1, MINUS=2 };
   1947 
   1948 #define     ONE_HOUR (60*60*1000)
   1949 #define ONE_DAY (24*ONE_HOUR)
   1950 
   1951     typedef struct {
   1952         UCalendarDateFields field;
   1953         int8_t actionMask; // ADD or ROLL or both
   1954         int8_t signMask; // PLUS or MINUS or both
   1955         int32_t amount;
   1956         int32_t before; // ms before cutover
   1957         int32_t after;  // ms after cutover
   1958     } J81_DATA;
   1959 
   1960 /**
   1961  * Rolling and adding across the Gregorian cutover should work as expected.
   1962  * Jitterbug 81.
   1963  */
   1964 void CalendarRegressionTest::TestJ81() {
   1965     UErrorCode status = U_ZERO_ERROR;
   1966     UnicodeString temp, temp2, temp3;
   1967     int32_t i;
   1968     GregorianCalendar cal(TimeZone::createTimeZone("GMT"), Locale::getUS(), status);
   1969     SimpleDateFormat fmt("HH:mm 'w'w 'd'D E d MMM yyyy", Locale::getUS(), status);
   1970     if (U_FAILURE(status)) {
   1971         errcheckln(status, "Error: Cannot create calendar or format - %s", u_errorName(status));
   1972         return;
   1973     }
   1974     fmt.setCalendar(cal);
   1975     // Get the Gregorian cutover
   1976     UDate cutover = cal.getGregorianChange();
   1977     UDate days = ONE_DAY;
   1978     days = cutover/days;
   1979     logln(UnicodeString("Cutover: {") +
   1980           fmt.format(cutover, temp) + "}(epoch days-" + (int)days + ", jd" + (2440588 + days) +")");
   1981 
   1982     // Check woy and doy handling.  Reference data:
   1983     /* w40 d274 Mon 1 Oct 1582
   1984        w40 d275 Tue 2 Oct 1582
   1985        w40 d276 Wed 3 Oct 1582
   1986        w40 d277 Thu 4 Oct 1582
   1987        w40 d278 Fri 15 Oct 1582
   1988        w40 d279 Sat 16 Oct 1582
   1989        w41 d280 Sun 17 Oct 1582
   1990        w41 d281 Mon 18 Oct 1582
   1991        w41 d282 Tue 19 Oct 1582
   1992        w41 d283 Wed 20 Oct 1582
   1993        w41 d284 Thu 21 Oct 1582
   1994        w41 d285 Fri 22 Oct 1582
   1995        w41 d286 Sat 23 Oct 1582
   1996        w42 d287 Sun 24 Oct 1582
   1997        w42 d288 Mon 25 Oct 1582
   1998        w42 d289 Tue 26 Oct 1582
   1999        w42 d290 Wed 27 Oct 1582
   2000        w42 d291 Thu 28 Oct 1582
   2001        w42 d292 Fri 29 Oct 1582
   2002        w42 d293 Sat 30 Oct 1582
   2003        w43 d294 Sun 31 Oct 1582
   2004        w43 d295 Mon 1 Nov 1582 */
   2005     int32_t DOY_DATA[] = {
   2006         // dom, woy, doy
   2007         1, 40, 274, UCAL_MONDAY,
   2008         4, 40, 277, UCAL_THURSDAY,
   2009         15, 40, 278, UCAL_FRIDAY,
   2010         17, 41, 280, UCAL_SUNDAY,
   2011         24, 42, 287, UCAL_SUNDAY,
   2012         25, 42, 288, UCAL_MONDAY,
   2013         26, 42, 289, UCAL_TUESDAY,
   2014         27, 42, 290, UCAL_WEDNESDAY,
   2015         28, 42, 291, UCAL_THURSDAY,
   2016         29, 42, 292, UCAL_FRIDAY,
   2017         30, 42, 293, UCAL_SATURDAY,
   2018         31, 43, 294, UCAL_SUNDAY
   2019     };
   2020     int32_t DOY_DATA_length = (int32_t)(sizeof(DOY_DATA) / sizeof(DOY_DATA[0]));
   2021 
   2022     for (i=0; i<DOY_DATA_length; i+=4) {
   2023         // Test time->fields
   2024         cal.set(1582, UCAL_OCTOBER, DOY_DATA[i]);
   2025         int32_t woy = cal.get(UCAL_WEEK_OF_YEAR, status);
   2026         int32_t doy = cal.get(UCAL_DAY_OF_YEAR, status);
   2027         int32_t dow = cal.get(UCAL_DAY_OF_WEEK, status);
   2028         if (U_FAILURE(status)) {
   2029             errln("Error: get() failed");
   2030             break;
   2031         }
   2032         if (woy != DOY_DATA[i+1] || doy != DOY_DATA[i+2] || dow != DOY_DATA[i+3]) {
   2033             errln((UnicodeString)"Fail: expect woy=" + DOY_DATA[i+1] +
   2034                   ", doy=" + DOY_DATA[i+2] + ", dow=" + DOY_DATA[i+3] + " on " +
   2035                   fmt.format(cal.getTime(status), temp.remove()) +
   2036                   " set(1582,OCTOBER, " + DOY_DATA[i] + ")");
   2037             logln(CalendarTest::calToStr(cal));
   2038             status = U_ZERO_ERROR;
   2039         }  else {
   2040           logln((UnicodeString)"PASS: expect woy=" + DOY_DATA[i+1] +
   2041                 ", doy=" + DOY_DATA[i+2] + ", dow=" + DOY_DATA[i+3] + " on " +
   2042                 fmt.format(cal.getTime(status), temp.remove()));
   2043           logln(CalendarTest::calToStr(cal));
   2044           status = U_ZERO_ERROR;
   2045         }
   2046         // Test fields->time for WOY
   2047         cal.clear();
   2048         cal.set(UCAL_YEAR, 1582);
   2049         cal.set(UCAL_WEEK_OF_YEAR, DOY_DATA[i+1]);
   2050         cal.set(UCAL_DAY_OF_WEEK, DOY_DATA[i+3]);
   2051         int32_t dom = cal.get(UCAL_DATE, status);
   2052         if (U_FAILURE(status)) {
   2053             errln("Error: get() failed");
   2054             break;
   2055         }
   2056         if (dom != DOY_DATA[i]) {
   2057             errln((UnicodeString)"Fail: set woy=" + DOY_DATA[i+1] +
   2058                   " dow=" + DOY_DATA[i+3] + " => " +
   2059                   fmt.format(cal.getTime(status), temp.remove()) +
   2060                   ", expected 1582 Oct " + DOY_DATA[i]);
   2061             logln(CalendarTest::calToStr(cal));
   2062             status = U_ZERO_ERROR;
   2063         }
   2064 
   2065         // Test fields->time for DOY
   2066         cal.clear();
   2067         cal.set(UCAL_YEAR, 1582);
   2068         cal.set(UCAL_DAY_OF_YEAR, DOY_DATA[i+2]);
   2069         dom = cal.get(UCAL_DATE, status);
   2070         if (U_FAILURE(status)) {
   2071             errln("Error: get() failed");
   2072             break;
   2073         }
   2074         if (dom != DOY_DATA[i]) {
   2075             errln((UnicodeString)"Fail: set doy=" + DOY_DATA[i+2] +
   2076                   " => " +
   2077                   fmt.format(cal.getTime(status), temp.remove()) +
   2078                   ", expected 1582 Oct " + DOY_DATA[i]);
   2079             status = U_ZERO_ERROR;
   2080         }
   2081     }
   2082     status = U_ZERO_ERROR;
   2083 
   2084 #define ADD_ROLL  ADD|ROLL
   2085 #define PLUS_MINUS PLUS|MINUS
   2086     // Test cases
   2087     J81_DATA DATA[] = {
   2088         { UCAL_WEEK_OF_YEAR, ADD_ROLL, PLUS_MINUS, 1, -ONE_DAY, +6*ONE_DAY },
   2089         { UCAL_WEEK_OF_YEAR, ADD_ROLL, PLUS_MINUS, 1, -ONE_DAY, +6*ONE_DAY },
   2090         { UCAL_WEEK_OF_MONTH, ADD|ROLL, PLUS|MINUS, 1, -ONE_DAY, +6*ONE_DAY },
   2091         { UCAL_DATE, ADD|ROLL, PLUS|MINUS, 2, -ONE_DAY, +1*ONE_DAY },
   2092         { UCAL_DATE, ROLL, PLUS, -6, -ONE_DAY, +14*ONE_DAY },
   2093         { UCAL_DATE, ROLL, PLUS, -7, 0, +14*ONE_DAY },
   2094         { UCAL_DATE, ROLL, PLUS, -7, +ONE_DAY, +15*ONE_DAY },
   2095         { UCAL_DATE, ROLL, PLUS, +18, -ONE_DAY, -4*ONE_DAY },
   2096         { UCAL_DAY_OF_YEAR, ADD|ROLL, PLUS|MINUS, 2, -ONE_DAY, +1*ONE_DAY },
   2097         { UCAL_DAY_OF_WEEK, ADD|ROLL, PLUS|MINUS, 2, -ONE_DAY, +1*ONE_DAY },
   2098         { UCAL_DAY_OF_WEEK_IN_MONTH, ADD|ROLL, PLUS|MINUS, 1, -ONE_DAY, +6*ONE_DAY },
   2099         { UCAL_AM_PM, ADD, PLUS|MINUS, 4, -12*ONE_HOUR, +36*ONE_HOUR },
   2100         { UCAL_HOUR, ADD, PLUS|MINUS, 48, -12*ONE_HOUR, +36*ONE_HOUR },
   2101         { UCAL_HOUR_OF_DAY, ADD, PLUS|MINUS, 48, -12*ONE_HOUR, +36*ONE_HOUR },
   2102         { UCAL_MINUTE, ADD, PLUS|MINUS, 48*60, -12*ONE_HOUR, +36*ONE_HOUR },
   2103         { UCAL_SECOND, ADD, PLUS|MINUS, 48*60*60, -12*ONE_HOUR, +36*ONE_HOUR },
   2104         { UCAL_MILLISECOND, ADD, PLUS|MINUS, 48*ONE_HOUR, -12*ONE_HOUR, +36*ONE_HOUR },
   2105         // NOTE: These are not supported yet.  See jitterbug 180.
   2106         // Uncomment these lines when add/roll supported on these fields.
   2107         // { Calendar::YEAR_WOY, ADD|ROLL, 1, -ONE_DAY, +6*ONE_DAY },
   2108         // { Calendar::DOW_LOCAL, ADD|ROLL, 2, -ONE_DAY, +1*ONE_DAY }
   2109     };
   2110     int32_t DATA_length = (int32_t)(sizeof(DATA) / sizeof(DATA[0]));
   2111 
   2112     // Now run the tests
   2113     for (i=0; i<DATA_length; ++i) {
   2114         for (Action action=ADD; action<=ROLL; action=(Action)(action+1)) {
   2115             if (!(DATA[i].actionMask & action)) {
   2116                 continue;
   2117             }
   2118             for (Sign sign=PLUS; sign<=MINUS; sign=(Sign)(sign+1)) {
   2119                 if (!(DATA[i].signMask & sign)) {
   2120                     continue;
   2121                 }
   2122                 status = U_ZERO_ERROR;
   2123                 int32_t amount = DATA[i].amount * (sign==MINUS?-1:1);
   2124                 UDate date = cutover +
   2125                     (sign==PLUS ? DATA[i].before : DATA[i].after);
   2126                 UDate expected = cutover +
   2127                     (sign==PLUS ? DATA[i].after : DATA[i].before);
   2128                 cal.setTime(date, status);
   2129                 if (U_FAILURE(status)) {
   2130                     errln((UnicodeString)"FAIL: setTime returned error code " + u_errorName(status));
   2131                     continue;
   2132                 }
   2133                 if (action == ADD) {
   2134                     cal.add(DATA[i].field, amount, status);
   2135                 } else {
   2136                     cal.roll(DATA[i].field, amount, status);
   2137                 }
   2138                 if (U_FAILURE(status)) {
   2139                     errln((UnicodeString)"FAIL: " +
   2140                           (action==ADD?"add ":"roll ") + FIELD_NAME[DATA[i].field] +
   2141                           " returned error code " + u_errorName(status));
   2142                     continue;
   2143                 }
   2144                 UDate result = cal.getTime(status);
   2145                 if (U_FAILURE(status)) {
   2146                     errln((UnicodeString)"FAIL: getTime returned error code " + u_errorName(status));
   2147                     continue;
   2148                 }
   2149                 if (result == expected) {
   2150                     logln((UnicodeString)"Ok: {" +
   2151                           fmt.format(date, temp.remove()) +
   2152                           "}(" + date/ONE_DAY +
   2153                           (action==ADD?") add ":") roll ") +
   2154                           amount + " " + FIELD_NAME[DATA[i].field] + " -> {" +
   2155                           fmt.format(result, temp2.remove()) +
   2156                           "}(" + result/ONE_DAY + ")");
   2157                 } else {
   2158                     errln((UnicodeString)"FAIL: {" +
   2159                           fmt.format(date, temp.remove()) +
   2160                           "}(" + date/ONE_DAY +
   2161                           (action==ADD?") add ":") roll ") +
   2162                           amount + " " + FIELD_NAME[DATA[i].field] + " -> {" +
   2163                           fmt.format(result, temp2.remove()) +
   2164                           "}(" + result/ONE_DAY + "), expect {" +
   2165                           fmt.format(expected, temp3.remove()) +
   2166                           "}(" + expected/ONE_DAY + ")");
   2167                 }
   2168             }
   2169         }
   2170     }
   2171 }
   2172 
   2173 /**
   2174  * Test fieldDifference().
   2175  */
   2176 void CalendarRegressionTest::TestJ438(void) {
   2177     UErrorCode ec = U_ZERO_ERROR;
   2178     int32_t DATA[] = {
   2179         2000, UCAL_JANUARY, 20,   2010, UCAL_JUNE, 15,
   2180         2010, UCAL_JUNE, 15,      2000, UCAL_JANUARY, 20,
   2181         1964, UCAL_SEPTEMBER, 7,  1999, UCAL_JUNE, 4,
   2182         1999, UCAL_JUNE, 4,       1964, UCAL_SEPTEMBER, 7,
   2183     };
   2184     int32_t DATA_length = (int32_t)(sizeof(DATA)/sizeof(DATA[0]));
   2185     Calendar* pcal = Calendar::createInstance(Locale::getUS(), ec);
   2186     if(U_FAILURE(ec)) {
   2187       errcheckln(ec, "Error creating calendar %s", u_errorName(ec));
   2188       delete pcal;
   2189       return;
   2190     }
   2191     Calendar& cal = *pcal;
   2192     int32_t i;
   2193     SimpleDateFormat fmt(UnicodeString("MMM dd yyyy",""), ec);
   2194     fmt.setCalendar(cal);
   2195     UnicodeString s, t, u;
   2196     if (!failure(ec, "setup")) {
   2197         for (i=0; i<DATA_length; i+=6) {
   2198             int32_t y1 = DATA[i];
   2199             int32_t m1 = DATA[i+1];
   2200             int32_t d1 = DATA[i+2];
   2201             int32_t y2 = DATA[i+3];
   2202             int32_t m2 = DATA[i+4];
   2203             int32_t d2 = DATA[i+5];
   2204 
   2205             cal.clear();
   2206             cal.set(y1, m1, d1);
   2207             UDate date1 = cal.getTime(ec);
   2208             if (failure(ec, "getTime"))
   2209                 break;
   2210             cal.set(y2, m2, d2);
   2211             UDate date2 = cal.getTime(ec);
   2212             if (failure(ec, "getTime"))
   2213                 break;
   2214 
   2215             cal.setTime(date1, ec);
   2216             if (failure(ec, "setTime"))
   2217                 break;
   2218             int32_t dy = cal.fieldDifference(date2, UCAL_YEAR, ec);
   2219             int32_t dm = cal.fieldDifference(date2, UCAL_MONTH, ec);
   2220             int32_t dd = cal.fieldDifference(date2, UCAL_DATE, ec);
   2221             if (failure(ec, "fieldDifference"))
   2222                 break;
   2223 
   2224             {
   2225                 Calendar *cal2 = cal.clone();
   2226                 UErrorCode ec2 = U_ZERO_ERROR;
   2227 
   2228                 cal2->setTime(date1, ec2);
   2229 
   2230                 int32_t dy2 = cal2->fieldDifference(date2, Calendar::YEAR, ec2);
   2231                 int32_t dm2 = cal2->fieldDifference(date2, Calendar::MONTH, ec2);
   2232                 int32_t dd2 = cal2->fieldDifference(date2, Calendar::DATE, ec2);
   2233                 if (failure(ec2, "fieldDifference(date, Calendar::DATE, ec)"))
   2234                     break;
   2235                 if( (dd2 != dd) ||
   2236                     (dm2 != dm) ||
   2237                     (dy2 != dy)){
   2238                     errln("fieldDifference(UCAL_...) and fieldDifference(Calendar::...) give different results!\n");
   2239                 }
   2240                 delete cal2;
   2241             }
   2242 
   2243 
   2244             logln(UnicodeString("") +
   2245                   fmt.format(date2, s.remove()) + " - " +
   2246                   fmt.format(date1, t.remove()) + " = " +
   2247                   dy + "y " + dm + "m " + dd + "d");
   2248 
   2249             cal.setTime(date1, ec);
   2250             if (failure(ec, "setTime"))
   2251                 break;
   2252             cal.add(UCAL_YEAR, dy, ec);
   2253             cal.add(UCAL_MONTH, dm, ec);
   2254             cal.add(UCAL_DATE, dd, ec);
   2255             if (failure(ec, "add"))
   2256                 break;
   2257             UDate date22 = cal.getTime(ec);
   2258             if (failure(ec, "getTime"))
   2259                 break;
   2260             if (date2 != date22) {
   2261                 errln(UnicodeString("FAIL: ") +
   2262                       fmt.format(date1, s.remove()) + " + " +
   2263                       dy + "y " + dm + "m " + dd + "d = " +
   2264                       fmt.format(date22, t.remove()) + ", exp " +
   2265                       fmt.format(date2, u.remove()));
   2266             } else {
   2267                 logln(UnicodeString("Ok: ") +
   2268                       fmt.format(date1, s.remove()) + " + " +
   2269                       dy + "y " + dm + "m " + dd + "d = " +
   2270                       fmt.format(date22, t.remove()));
   2271             }
   2272         }
   2273     }
   2274     delete pcal;
   2275 }
   2276 
   2277 void CalendarRegressionTest::TestT5555()
   2278 {
   2279     UErrorCode ec = U_ZERO_ERROR;
   2280     Calendar *cal = Calendar::createInstance(ec);
   2281 
   2282     if (cal == NULL || U_FAILURE(ec)) {
   2283         errln("FAIL: Calendar::createInstance()");
   2284         delete cal;
   2285         return;
   2286     }
   2287 
   2288     // Set to Wednesday, February 21, 2007
   2289     cal->set(2007, UCAL_FEBRUARY, 21);
   2290 
   2291     // Advance three years
   2292     cal->add(UCAL_MONTH, 36, ec);
   2293 
   2294     // Set to last Wednesday of the month
   2295     cal->set(UCAL_DAY_OF_WEEK_IN_MONTH, -1);
   2296 
   2297     cal->getTime(ec);
   2298 
   2299     int32_t yy, mm, dd, ee;
   2300 
   2301     yy = cal->get(UCAL_YEAR, ec);
   2302     mm = cal->get(UCAL_MONTH, ec);
   2303     dd = cal->get(UCAL_DATE, ec);
   2304     ee = cal->get(UCAL_DAY_OF_WEEK, ec);
   2305 
   2306     // Should be set to Wednesday, February 24, 2010
   2307     if (U_FAILURE(ec) || yy != 2010 || mm != UCAL_FEBRUARY || dd != 24 || ee != UCAL_WEDNESDAY) {
   2308         errln("FAIL: got date %4d/%02d/%02d, expected 210/02/24: ", yy, mm + 1, dd);
   2309     }
   2310     delete cal;
   2311 }
   2312 
   2313 typedef struct {
   2314     int32_t             startYear;
   2315     int32_t             startMonth; // 0-based
   2316     int32_t             startDay;   // 1-based
   2317     UCalendarDateFields fieldToChange;
   2318     int32_t             fieldDelta;
   2319     int32_t             endYear;
   2320     int32_t             endMonth;   // 0-based
   2321     int32_t             endDay;     // 1-based
   2322 } CoptEthCalTestItem;
   2323 
   2324 // year 1724 in coptic calendar =
   2325 // year 2000 in ethiopic calendar (276 more than coptic) =
   2326 // year 7500 in ethiopic-amete-alem calendar (5776 more than coptic)
   2327 // (2007-2008 in gregorian calendar depending on month)
   2328 static const CoptEthCalTestItem coptEthCalTestItems[] = {
   2329     { 1724, 12, 1, UCAL_MONTH, +1, 1725,  0, 1 },
   2330     { 1724, 12, 1, UCAL_MONTH, +9, 1725,  8, 1 },
   2331     { 1723, 12, 2, UCAL_MONTH, +1, 1724,  0, 2 }, // 1723 is a leap year
   2332     { 1723, 12, 2, UCAL_MONTH, +9, 1724,  8, 2 },
   2333     { 1725,  0, 1, UCAL_MONTH, -1, 1724, 12, 1 },
   2334     { 1725,  0, 1, UCAL_MONTH, -6, 1724,  7, 1 },
   2335     { 1724, 12, 1, UCAL_DATE,  +8, 1725,  0, 4 },
   2336     { 1723, 12, 1, UCAL_DATE,  +8, 1724,  0, 3 }, // 1723 is a leap year
   2337     { 1724,  0, 1, UCAL_DATE,  -1, 1723, 12, 6 }, // 1723 is a leap year
   2338     { 0, 0, 0, (UCalendarDateFields)0, 0, 0, 0, 0 } // terminator
   2339 };
   2340 
   2341 typedef struct {
   2342     const char * locale;
   2343     int32_t      yearOffset;
   2344 } CoptEthCalLocale;
   2345 
   2346 static const CoptEthCalLocale copEthCalLocales[] = {
   2347     { "en@calendar=coptic",   0    },
   2348     { "en@calendar=ethiopic", 276  },
   2349     { NULL,                   0    } // terminator
   2350 };
   2351 
   2352 void CalendarRegressionTest::TestT6745()
   2353 {
   2354     const CoptEthCalLocale * testLocalePtr;
   2355     for ( testLocalePtr = copEthCalLocales; testLocalePtr->locale != NULL; ++testLocalePtr) {
   2356         UErrorCode status = U_ZERO_ERROR;
   2357         Calendar *cal = Calendar::createInstance(Locale(testLocalePtr->locale), status);
   2358         if ( U_FAILURE(status) ) {
   2359             errln((UnicodeString)"FAIL: Calendar::createInstance, locale " + testLocalePtr->locale + ", status " + u_errorName(status));
   2360             continue;
   2361         }
   2362         const CoptEthCalTestItem * testItemPtr;
   2363         for (testItemPtr = coptEthCalTestItems; testItemPtr->fieldDelta != 0; ++testItemPtr) {
   2364             status = U_ZERO_ERROR;
   2365             cal->set( testItemPtr->startYear + testLocalePtr->yearOffset, testItemPtr->startMonth, testItemPtr->startDay, 9, 0 );
   2366             cal->add( testItemPtr->fieldToChange, testItemPtr->fieldDelta, status );
   2367             if ( U_FAILURE(status) ) {
   2368                 errln((UnicodeString)"FAIL: Calendar::add, locale " + testLocalePtr->locale + ", field/delta " +
   2369                         testItemPtr->fieldToChange + "/" + testItemPtr->fieldDelta + ", status " + u_errorName(status));
   2370                 continue;
   2371             }
   2372             int32_t endYear = testItemPtr->endYear + testLocalePtr->yearOffset;
   2373             int32_t year  = cal->get(UCAL_YEAR, status);
   2374             int32_t month = cal->get(UCAL_MONTH, status);
   2375             int32_t day   = cal->get(UCAL_DATE, status);
   2376             if ( U_FAILURE(status) || year != endYear || month != testItemPtr->endMonth || day != testItemPtr->endDay ) {
   2377                 errln((UnicodeString)"ERROR: Calendar::add, locale " + testLocalePtr->locale + ", field/delta " +
   2378                         testItemPtr->fieldToChange + "/" + testItemPtr->fieldDelta + ", status " + u_errorName(status) +
   2379                         ", expected " + endYear + "/" + testItemPtr->endMonth + "/" + testItemPtr->endDay +
   2380                         ", got " + year + "/" + month + "/" + day );
   2381             }
   2382         }
   2383         delete cal;
   2384     }
   2385 }
   2386 
   2387 /**
   2388  * Test behavior of fieldDifference around leap years.  Also test a large
   2389  * field difference to check binary search.
   2390  */
   2391 void CalendarRegressionTest::TestLeapFieldDifference() {
   2392     UErrorCode ec = U_ZERO_ERROR;
   2393     Calendar* cal = Calendar::createInstance(ec);
   2394     if (cal == NULL || U_FAILURE(ec)) {
   2395         errln("FAIL: Calendar::createInstance()");
   2396         delete cal;
   2397         return;
   2398     }
   2399     cal->set(2004, UCAL_FEBRUARY, 29);
   2400     UDate date2004 = cal->getTime(ec);
   2401     cal->set(2000, UCAL_FEBRUARY, 29);
   2402     UDate date2000 = cal->getTime(ec);
   2403     if (U_FAILURE(ec)) {
   2404         errln("FAIL: getTime()");
   2405         delete cal;
   2406         return;
   2407     }
   2408     int32_t y = cal->fieldDifference(date2004, UCAL_YEAR, ec);
   2409     int32_t d = cal->fieldDifference(date2004, UCAL_DAY_OF_YEAR, ec);
   2410     if (U_FAILURE(ec)) {
   2411         errln("FAIL: fieldDifference()");
   2412         delete cal;
   2413         return;
   2414     }
   2415     if (d == 0) {
   2416         logln((UnicodeString)"Ok: 2004/Feb/29 - 2000/Feb/29 = " + y + " years, " + d + " days");
   2417     } else {
   2418         errln((UnicodeString)"FAIL: 2004/Feb/29 - 2000/Feb/29 = " + y + " years, " + d + " days");
   2419     }
   2420     cal->setTime(date2004, ec);
   2421     y = cal->fieldDifference(date2000, UCAL_YEAR, ec);
   2422     d = cal->fieldDifference(date2000, UCAL_DAY_OF_YEAR, ec);
   2423     if (U_FAILURE(ec)) {
   2424         errln("FAIL: setTime() / fieldDifference()");
   2425         delete cal;
   2426         return;
   2427     }
   2428     if (d == 0) {
   2429         logln((UnicodeString)"Ok: 2000/Feb/29 - 2004/Feb/29 = " + y + " years, " + d + " days");
   2430     } else {
   2431         errln((UnicodeString)"FAIL: 2000/Feb/29 - 2004/Feb/29 = " + y + " years, " + d + " days");
   2432     }
   2433     // Test large difference
   2434     cal->set(2001, UCAL_APRIL, 5); // 2452005
   2435     UDate ayl = cal->getTime(ec);
   2436     cal->set(1964, UCAL_SEPTEMBER, 7); // 2438646
   2437     UDate asl = cal->getTime(ec);
   2438     if (U_FAILURE(ec)) {
   2439         errln("FAIL: getTime()");
   2440         delete cal;
   2441         return;
   2442     }
   2443     d = cal->fieldDifference(ayl, UCAL_DATE, ec);
   2444     cal->setTime(ayl, ec);
   2445     int32_t d2 = cal->fieldDifference(asl, UCAL_DATE, ec);
   2446     if (U_FAILURE(ec)) {
   2447         errln("FAIL: setTime() / fieldDifference()");
   2448         delete cal;
   2449         return;
   2450     }
   2451     if (d == -d2 && d == 13359) {
   2452         logln((UnicodeString)"Ok: large field difference symmetrical " + d);
   2453     } else {
   2454         logln((UnicodeString)"FAIL: large field difference incorrect " + d + ", " + d2 +
   2455               ", expect +/- 13359");
   2456     }
   2457     delete cal;
   2458 }
   2459 
   2460 /**
   2461  * Test ms_MY "Malay (Malaysia)" locale.  Bug 1543.
   2462  */
   2463 void CalendarRegressionTest::TestMalaysianInstance() {
   2464     Locale loc("ms", "MY");  // Malay (Malaysia)
   2465     UErrorCode ec = U_ZERO_ERROR;
   2466     Calendar* cal = Calendar::createInstance(loc, ec);
   2467     if (U_FAILURE(ec)) {
   2468         errln("FAIL: Can't construct calendar for ms_MY");
   2469     }
   2470     delete cal;
   2471 }
   2472 
   2473 /**
   2474  * setFirstDayOfWeek and setMinimalDaysInFirstWeek may change the
   2475  * field <=> time mapping, since they affect the interpretation of
   2476  * the WEEK_OF_MONTH or WEEK_OF_YEAR fields.
   2477  */
   2478 void CalendarRegressionTest::TestWeekShift() {
   2479     UErrorCode ec = U_ZERO_ERROR;
   2480     GregorianCalendar cal(TimeZone::createTimeZone("America/Los_Angeles"),
   2481                           Locale("en", "US"), ec);
   2482     cal.setTime(UDate(997257600000.0), ec); // Wed Aug 08 01:00:00 PDT 2001
   2483     // In pass one, change the first day of week so that the weeks
   2484     // shift in August 2001.  In pass two, change the minimal days
   2485     // in the first week so that the weeks shift in August 2001.
   2486     //     August 2001
   2487     // Su Mo Tu We Th Fr Sa
   2488     //           1  2  3  4
   2489     //  5  6  7  8  9 10 11
   2490     // 12 13 14 15 16 17 18
   2491     // 19 20 21 22 23 24 25
   2492     // 26 27 28 29 30 31
   2493     for (int32_t pass=0; pass<2; ++pass) {
   2494         if (pass==0) {
   2495             cal.setFirstDayOfWeek(UCAL_WEDNESDAY);
   2496             cal.setMinimalDaysInFirstWeek(4);
   2497         } else {
   2498             cal.setFirstDayOfWeek(UCAL_SUNDAY);
   2499             cal.setMinimalDaysInFirstWeek(4);
   2500         }
   2501         cal.add(UCAL_DATE, 1, ec); // Force recalc
   2502         cal.add(UCAL_DATE, -1, ec);
   2503 
   2504         UDate time1 = cal.getTime(ec); // Get time -- should not change
   2505 
   2506         // Now change a week parameter and then force a recalc.
   2507         // The bug is that the recalc should not be necessary --
   2508         // calendar should do so automatically.
   2509         if (pass==0) {
   2510             cal.setFirstDayOfWeek(UCAL_THURSDAY);
   2511         } else {
   2512             cal.setMinimalDaysInFirstWeek(5);
   2513         }
   2514 
   2515         int32_t woy1 = cal.get(UCAL_WEEK_OF_YEAR, ec);
   2516         int32_t wom1 = cal.get(UCAL_WEEK_OF_MONTH, ec);
   2517 
   2518         cal.add(UCAL_DATE, 1, ec); // Force recalc
   2519         cal.add(UCAL_DATE, -1, ec);
   2520 
   2521         int32_t woy2 = cal.get(UCAL_WEEK_OF_YEAR, ec);
   2522         int32_t wom2 = cal.get(UCAL_WEEK_OF_MONTH, ec);
   2523 
   2524         UDate time2 = cal.getTime(ec);
   2525 
   2526         if (U_FAILURE(ec)) {
   2527             errln("FAIL: internal test error");
   2528             return;
   2529         }
   2530 
   2531         if (time1 != time2) {
   2532             errln("FAIL: shifting week should not alter time");
   2533         } else {
   2534             // logln(time1);
   2535         }
   2536         if (woy1 == woy2 && wom1 == wom2) {
   2537             logln((UnicodeString)"Ok: WEEK_OF_YEAR: " + woy1 +
   2538                   ", WEEK_OF_MONTH: " + wom1);
   2539         } else {
   2540             errln((UnicodeString)"FAIL: WEEK_OF_YEAR: " + woy1 + " => " + woy2 +
   2541                   ", WEEK_OF_MONTH: " + wom1 + " => " + wom2 +
   2542                   " after week shift");
   2543         }
   2544     }
   2545 }
   2546 
   2547 /**
   2548  * Make sure that when adding a day, we actually wind up in a
   2549  * different day.  The DST adjustments we use to keep the hour
   2550  * constant across DST changes can backfire and change the day.
   2551  */
   2552 void CalendarRegressionTest::TestTimeZoneTransitionAdd() {
   2553     UErrorCode ec = U_ZERO_ERROR;
   2554     Locale locale(Locale::getUS()); // could also be CHINA
   2555     SimpleDateFormat dateFormat("MM/dd/yyyy HH:mm z", locale, ec);
   2556 
   2557     StringEnumeration *tz = TimeZone::createEnumeration();
   2558     if (tz == NULL) {
   2559         errln("FAIL: TimeZone::createEnumeration");
   2560         return;
   2561     }
   2562 
   2563     UnicodeString buf1, buf2;
   2564 
   2565     const UChar* id;
   2566     while ((id = tz->unext(NULL, ec)) != NULL && U_SUCCESS(ec)) {
   2567         if (U_FAILURE(ec)) {
   2568             errln("FAIL: StringEnumeration::unext");
   2569             break;
   2570         }
   2571 
   2572         TimeZone *t = TimeZone::createTimeZone(id);
   2573         if (t == NULL) {
   2574             errln("FAIL: TimeZone::createTimeZone");
   2575             break;
   2576         }
   2577         dateFormat.setTimeZone(*t);
   2578 
   2579         Calendar *cal = Calendar::createInstance(t, locale, ec);
   2580         if (cal == NULL || U_FAILURE(ec)) {
   2581             errln("FAIL: Calendar::createTimeZone");
   2582             delete cal;
   2583             break;
   2584         }
   2585 
   2586         cal->clear();
   2587         // Scan the year 2003, overlapping the edges of the year
   2588         cal->set(UCAL_YEAR, 2002);
   2589         cal->set(UCAL_MONTH, UCAL_DECEMBER);
   2590         cal->set(UCAL_DATE, 25);
   2591 
   2592         for (int32_t i=0; i<365+10 && U_SUCCESS(ec); ++i) {
   2593             UDate yesterday = cal->getTime(ec);
   2594             int32_t yesterday_day = cal->get(UCAL_DATE, ec);
   2595             cal->add(UCAL_DATE, 1, ec);
   2596             if (yesterday_day == cal->get(UCAL_DATE, ec)) {
   2597                 errln(UnicodeString(id) + " " +
   2598                       dateFormat.format(yesterday, buf1) + " +1d= " +
   2599                       dateFormat.format(cal->getTime(ec), buf2));
   2600                 buf1.truncate(0);
   2601                 buf2.truncate(0);
   2602             }
   2603         }
   2604         delete cal;
   2605     }
   2606 
   2607     if (U_FAILURE(ec)) {
   2608         errcheckln(ec, "FAIL: %s", u_errorName(ec));
   2609     }
   2610 
   2611     delete tz;
   2612 }
   2613 
   2614 UDate
   2615 CalendarRegressionTest::makeDate(int32_t y, int32_t m, int32_t d,
   2616                                     int32_t hr, int32_t min, int32_t sec)
   2617 {
   2618     UDate result;
   2619 
   2620     UErrorCode status = U_ZERO_ERROR;
   2621     Calendar *cal = Calendar::createInstance(status);
   2622     cal->clear();
   2623 
   2624     cal->set(UCAL_YEAR, y);
   2625 
   2626     if(m != 0)        cal->set(UCAL_MONTH, m);
   2627     if(d != 0)        cal->set(UCAL_DATE, d);
   2628     if(hr != 0)        cal->set(UCAL_HOUR, hr);
   2629     if(min != 0)    cal->set(UCAL_MINUTE, min);
   2630     if(sec != 0)    cal->set(UCAL_SECOND, sec);
   2631 
   2632     result = cal->getTime(status);
   2633 
   2634     delete cal;
   2635 
   2636     return result;
   2637 }
   2638 
   2639 void CalendarRegressionTest::TestDeprecates(void)
   2640 {
   2641     UErrorCode status = U_ZERO_ERROR;
   2642     Calendar *c1 = Calendar::createInstance("ja_JP@calendar=japanese",status);
   2643     Calendar *c2 = Calendar::createInstance("ja_JP_TRADITIONAL",status);
   2644 
   2645     if(!c1 || !c2 || U_FAILURE(status)) {
   2646         errln("Couldn't create calendars for roll of HOUR");
   2647         return;
   2648     }
   2649 
   2650     c2->set(UCAL_HOUR,2);
   2651     c1->setTime(c2->getTime(status),status);
   2652     // *c1 = *c2;
   2653 
   2654     c1->roll(Calendar::HOUR,(int32_t)3,status);
   2655     c2->roll(UCAL_HOUR,(int32_t)3,status);
   2656 
   2657     if(U_FAILURE(status)) {
   2658         errln("Error code when trying to roll");
   2659     } else if(*c1 != *c2) {
   2660         errln("roll(EDateField, int32_t) had different effect than roll(UCalendarField, int32_t)");
   2661     }
   2662 
   2663     c1->setTime(c2->getTime(status),status);
   2664     c1->roll(Calendar::HOUR,(UBool)FALSE,status);
   2665     c2->roll(UCAL_HOUR,(UBool)FALSE,status);
   2666 
   2667     if(U_FAILURE(status)) {
   2668         errln("Error code when trying to roll(UBool)");
   2669     } else if(*c1 != *c2) {
   2670         errln("roll(EDateField, UBool) had different effect than roll(UCalendarField, UBool)");
   2671     }
   2672 
   2673     delete c1;
   2674     delete c2;
   2675 
   2676     status = U_ZERO_ERROR;
   2677 
   2678     c1 = Calendar::createInstance("th_TH_TRADITIONAL",status);
   2679     c2 = Calendar::createInstance("th_TH@calendar=buddhist",status);
   2680 
   2681     if(!c1 || !c2 || U_FAILURE(status)) {
   2682         errln("Couldn't create calendars for add of HOUR");
   2683         return;
   2684     }
   2685 
   2686     c2->set(UCAL_HOUR,2);
   2687     c1->setTime(c2->getTime(status),status);
   2688     //*c1 = *c2;
   2689 
   2690     c1->add(Calendar::HOUR,(int32_t)1,status);
   2691 
   2692     if(U_FAILURE(status)) {
   2693         errln("Error code when trying to add Calendar::HOUR - %s", u_errorName(status));
   2694     }
   2695 
   2696     c2->add(UCAL_HOUR,(int32_t)1,status);
   2697 
   2698     if(U_FAILURE(status)) {
   2699         errln("Error code when trying to add - UCAL_HOUR %s", u_errorName(status));
   2700     } else if(*c1 != *c2) {
   2701         errln("add(EDateField) had different effect than add(UCalendarField)");
   2702     }
   2703 
   2704     delete c1;
   2705     delete c2;
   2706 
   2707     status = U_ZERO_ERROR;
   2708 
   2709     c1 = Calendar::createInstance("es_ES",status);
   2710     c2 = Calendar::createInstance("es_ES",status);
   2711 
   2712     if(!c1 || !c2 || U_FAILURE(status)) {
   2713         errln("Couldn't create calendars for add of YEAR");
   2714         return;
   2715     }
   2716 
   2717     c2->set(UCAL_YEAR,1900);
   2718     c1->setTime(c2->getTime(status),status);
   2719     //*c1 = *c2;
   2720 
   2721     c1->add(Calendar::YEAR,(int32_t)9,status);
   2722     c2->add(UCAL_YEAR,(int32_t)9,status);
   2723 
   2724     if(U_FAILURE(status)) {
   2725         errln("Error code when trying to add YEARs");
   2726     } else if(*c1 != *c2) {
   2727         errln("add(EDateField YEAR) had different effect than add(UCalendarField YEAR)");
   2728     }
   2729 
   2730     delete c1;
   2731     delete c2;
   2732 }
   2733 
   2734 
   2735 #endif /* #if !UCONFIG_NO_FORMATTING */
   2736