1 /* 2 * Copyright (c) 1998, 2016, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 24 /* 25 * @test 26 * @bug 4031502 4035301 4040996 4051765 4059654 4061476 4070502 4071197 4071385 27 * 4073929 4083167 4086724 4092362 4095407 4096231 4096539 4100311 4103271 28 * 4106136 4108764 4114578 4118384 4125881 4125892 4136399 4141665 4142933 29 * 4145158 4145983 4147269 4149677 4162587 4165343 4166109 4167060 4173516 30 * 4174361 4177484 4197699 4209071 4288792 4328747 4413980 4546637 4623997 31 * 4685354 4655637 4683492 4080631 4080631 4167995 4340146 4639407 32 * 4652815 4652830 4740554 4936355 4738710 4633646 4846659 4822110 4960642 33 * 4973919 4980088 4965624 5013094 5006864 8152077 34 * @library /java/text/testlib 35 */ 36 37 import java.lang.reflect.*; 38 import java.io.*; 39 import java.util.*; 40 import java.text.*; 41 42 public class CalendarRegression extends IntlTest { 43 main(String[] args)44 public static void main(String[] args) throws Exception { 45 new CalendarRegression().run(args); 46 } 47 48 /* 49 Synopsis: java.sql.Timestamp constructor works wrong on Windows 95 50 51 ==== Here is the test ==== 52 public static void main (String args[]) { 53 java.sql.Timestamp t= new java.sql.Timestamp(0,15,5,5,8,13,123456700); 54 logln("expected=1901-04-05 05:08:13.1234567"); 55 logln(" result="+t); 56 } 57 58 ==== Here is the output of the test on Solaris or NT ==== 59 expected=1901-04-05 05:08:13.1234567 60 result=1901-04-05 05:08:13.1234567 61 62 ==== Here is the output of the test on Windows95 ==== 63 expected=1901-04-05 05:08:13.1234567 64 result=1901-04-05 06:08:13.1234567 65 */ 66 Test4031502()67 public void Test4031502() { 68 // This bug actually occurs on Windows NT as well, and doesn't 69 // require the host zone to be set; it can be set in Java. 70 String[] ids = TimeZone.getAvailableIDs(); 71 boolean bad = false; 72 for (int i=0; i<ids.length; ++i) { 73 TimeZone zone = TimeZone.getTimeZone(ids[i]); 74 GregorianCalendar cal = new GregorianCalendar(zone); 75 cal.clear(); 76 cal.set(1900, 15, 5, 5, 8, 13); 77 if (cal.get(Calendar.HOUR) != 5) { 78 logln(zone.getID() + " " + 79 //zone.useDaylightTime() + " " + 80 cal.get(Calendar.DST_OFFSET) / (60*60*1000) + " " + 81 zone.getRawOffset() / (60*60*1000) + 82 ": HOUR = " + cal.get(Calendar.HOUR)); 83 bad = true; 84 } 85 } 86 if (bad) errln("TimeZone problems with GC"); 87 } 88 Test4035301()89 public void Test4035301() { 90 GregorianCalendar c = new GregorianCalendar(98, 8, 7); 91 GregorianCalendar d = new GregorianCalendar(98, 8, 7); 92 if (c.after(d) || 93 c.after(c) || 94 c.before(d) || 95 c.before(c) || 96 !c.equals(c) || 97 !c.equals(d)) 98 errln("Fail"); 99 } 100 Test4040996()101 public void Test4040996() { 102 String[] ids = TimeZone.getAvailableIDs(-8 * 60 * 60 * 1000); 103 SimpleTimeZone pdt = new SimpleTimeZone(-8 * 60 * 60 * 1000, ids[0]); 104 pdt.setStartRule(Calendar.APRIL, 1, Calendar.SUNDAY, 2 * 60 * 60 * 1000); 105 pdt.setEndRule(Calendar.OCTOBER, -1, Calendar.SUNDAY, 2 * 60 * 60 * 1000); 106 Calendar calendar = new GregorianCalendar(pdt); 107 108 calendar.set(Calendar.MONTH,3); 109 calendar.set(Calendar.DAY_OF_MONTH,18); 110 calendar.set(Calendar.SECOND, 30); 111 112 logln("MONTH: " + calendar.get(Calendar.MONTH)); 113 logln("DAY_OF_MONTH: " + 114 calendar.get(Calendar.DAY_OF_MONTH)); 115 logln("MINUTE: " + calendar.get(Calendar.MINUTE)); 116 logln("SECOND: " + calendar.get(Calendar.SECOND)); 117 118 calendar.add(Calendar.SECOND,6); 119 //This will print out todays date for MONTH and DAY_OF_MONTH 120 //instead of the date it was set to. 121 //This happens when adding MILLISECOND or MINUTE also 122 logln("MONTH: " + calendar.get(Calendar.MONTH)); 123 logln("DAY_OF_MONTH: " + 124 calendar.get(Calendar.DAY_OF_MONTH)); 125 logln("MINUTE: " + calendar.get(Calendar.MINUTE)); 126 logln("SECOND: " + calendar.get(Calendar.SECOND)); 127 if (calendar.get(Calendar.MONTH) != 3 || 128 calendar.get(Calendar.DAY_OF_MONTH) != 18 || 129 calendar.get(Calendar.SECOND) != 36) 130 errln("Fail: Calendar.add misbehaves"); 131 } 132 Test4051765()133 public void Test4051765() { 134 Calendar cal = Calendar.getInstance(); 135 cal.setLenient(false); 136 cal.set(Calendar.DAY_OF_WEEK, 0); 137 try { 138 cal.getTime(); 139 errln("Fail: DAY_OF_WEEK 0 should be disallowed"); 140 } 141 catch (IllegalArgumentException e) { 142 return; 143 } 144 } 145 146 /* User error - no bug here 147 public void Test4059524() { 148 // Create calendar for April 10, 1997 149 GregorianCalendar calendar = new GregorianCalendar(); 150 // print out a bunch of interesting things 151 logln("ERA: " + calendar.get(calendar.ERA)); 152 logln("YEAR: " + calendar.get(calendar.YEAR)); 153 logln("MONTH: " + calendar.get(calendar.MONTH)); 154 logln("WEEK_OF_YEAR: " + 155 calendar.get(calendar.WEEK_OF_YEAR)); 156 logln("WEEK_OF_MONTH: " + 157 calendar.get(calendar.WEEK_OF_MONTH)); 158 logln("DATE: " + calendar.get(calendar.DATE)); 159 logln("DAY_OF_MONTH: " + 160 calendar.get(calendar.DAY_OF_MONTH)); 161 logln("DAY_OF_YEAR: " + calendar.get(calendar.DAY_OF_YEAR)); 162 logln("DAY_OF_WEEK: " + calendar.get(calendar.DAY_OF_WEEK)); 163 logln("DAY_OF_WEEK_IN_MONTH: " + 164 calendar.get(calendar.DAY_OF_WEEK_IN_MONTH)); 165 logln("AM_PM: " + calendar.get(calendar.AM_PM)); 166 logln("HOUR: " + calendar.get(calendar.HOUR)); 167 logln("HOUR_OF_DAY: " + calendar.get(calendar.HOUR_OF_DAY)); 168 logln("MINUTE: " + calendar.get(calendar.MINUTE)); 169 logln("SECOND: " + calendar.get(calendar.SECOND)); 170 logln("MILLISECOND: " + calendar.get(calendar.MILLISECOND)); 171 logln("ZONE_OFFSET: " 172 + (calendar.get(calendar.ZONE_OFFSET)/(60*60*1000))); 173 logln("DST_OFFSET: " 174 + (calendar.get(calendar.DST_OFFSET)/(60*60*1000))); 175 calendar = new GregorianCalendar(1997,3,10); 176 calendar.getTime(); 177 logln("April 10, 1997"); 178 logln("ERA: " + calendar.get(calendar.ERA)); 179 logln("YEAR: " + calendar.get(calendar.YEAR)); 180 logln("MONTH: " + calendar.get(calendar.MONTH)); 181 logln("WEEK_OF_YEAR: " + 182 calendar.get(calendar.WEEK_OF_YEAR)); 183 logln("WEEK_OF_MONTH: " + 184 calendar.get(calendar.WEEK_OF_MONTH)); 185 logln("DATE: " + calendar.get(calendar.DATE)); 186 logln("DAY_OF_MONTH: " + 187 calendar.get(calendar.DAY_OF_MONTH)); 188 logln("DAY_OF_YEAR: " + calendar.get(calendar.DAY_OF_YEAR)); 189 logln("DAY_OF_WEEK: " + calendar.get(calendar.DAY_OF_WEEK)); 190 logln("DAY_OF_WEEK_IN_MONTH: " + calendar.get(calendar.DAY_OF_WEEK_IN_MONTH)); 191 logln("AM_PM: " + calendar.get(calendar.AM_PM)); 192 logln("HOUR: " + calendar.get(calendar.HOUR)); 193 logln("HOUR_OF_DAY: " + calendar.get(calendar.HOUR_OF_DAY)); 194 logln("MINUTE: " + calendar.get(calendar.MINUTE)); 195 logln("SECOND: " + calendar.get(calendar.SECOND)); 196 logln("MILLISECOND: " + calendar.get(calendar.MILLISECOND)); 197 logln("ZONE_OFFSET: " 198 + (calendar.get(calendar.ZONE_OFFSET)/(60*60*1000))); // in hours 199 logln("DST_OFFSET: " 200 + (calendar.get(calendar.DST_OFFSET)/(60*60*1000))); // in hours 201 } 202 */ 203 Test4059654()204 public void Test4059654() { 205 GregorianCalendar gc = new GregorianCalendar(); 206 207 gc.set(1997, 3, 1, 15, 16, 17); // April 1, 1997 208 209 gc.set(Calendar.HOUR, 0); 210 gc.set(Calendar.AM_PM, Calendar.AM); 211 gc.set(Calendar.MINUTE, 0); 212 gc.set(Calendar.SECOND, 0); 213 gc.set(Calendar.MILLISECOND, 0); 214 215 Date cd = gc.getTime(); 216 Date exp = new Date(97, 3, 1, 0, 0, 0); 217 if (!cd.equals(exp)) 218 errln("Fail: Calendar.set broken. Got " + cd + " Want " + exp); 219 } 220 Test4061476()221 public void Test4061476() { 222 SimpleDateFormat fmt = new SimpleDateFormat("ddMMMyy", Locale.UK); 223 Calendar cal = GregorianCalendar.getInstance(TimeZone.getTimeZone("GMT"), 224 Locale.UK); 225 fmt.setCalendar(cal); 226 try 227 { 228 Date date = fmt.parse("29MAY97"); 229 cal.setTime(date); 230 } 231 catch (Exception e) {;} 232 cal.set(Calendar.HOUR_OF_DAY, 13); 233 logln("Hour: "+cal.get(Calendar.HOUR_OF_DAY)); 234 cal.add(Calendar.HOUR_OF_DAY, 6); 235 logln("Hour: "+cal.get(Calendar.HOUR_OF_DAY)); 236 if (cal.get(Calendar.HOUR_OF_DAY) != 19) 237 errln("Fail: Want 19 Got " + cal.get(Calendar.HOUR_OF_DAY)); 238 } 239 Test4070502()240 public void Test4070502() { 241 Date d = getAssociatedDate(new Date(98, 0, 30)); 242 Calendar cal = new GregorianCalendar(); 243 cal.setTime(d); 244 if (cal.get(Calendar.DAY_OF_WEEK) == Calendar.SATURDAY || 245 cal.get(Calendar.DAY_OF_WEEK) == Calendar.SUNDAY) 246 errln("Fail: Want weekday Got " + d); 247 } 248 249 /** 250 * Get the associated date starting from a specified date 251 * NOTE: the unnecessary "getTime()'s" below are a work-around for a 252 * bug in jdk 1.1.3 (and probably earlier versions also) 253 * <p> 254 * @param date The date to start from 255 */ getAssociatedDate(Date d)256 public static Date getAssociatedDate(Date d) { 257 GregorianCalendar cal = new GregorianCalendar(); 258 cal.setTime(d); 259 //cal.add(field, amount); //<-- PROBLEM SEEN WITH field = DATE,MONTH 260 // cal.getTime(); // <--- REMOVE THIS TO SEE BUG 261 while (true) { 262 int wd = cal.get(Calendar.DAY_OF_WEEK); 263 if (wd == Calendar.SATURDAY || wd == Calendar.SUNDAY) { 264 cal.add(Calendar.DATE, 1); 265 // cal.getTime(); 266 } 267 else 268 break; 269 } 270 return cal.getTime(); 271 } 272 Test4071197()273 public void Test4071197() { 274 dowTest(false); 275 dowTest(true); 276 } 277 dowTest(boolean lenient)278 void dowTest(boolean lenient) { 279 GregorianCalendar cal = new GregorianCalendar(); 280 cal.set(1997, Calendar.AUGUST, 12); // Wednesday 281 // cal.getTime(); // Force update 282 cal.setLenient(lenient); 283 cal.set(1996, Calendar.DECEMBER, 1); // Set the date to be December 1, 1996 284 int dow = cal.get(Calendar.DAY_OF_WEEK); 285 int min = cal.getMinimum(Calendar.DAY_OF_WEEK); 286 int max = cal.getMaximum(Calendar.DAY_OF_WEEK); 287 logln(cal.getTime().toString()); 288 if (min != Calendar.SUNDAY || max != Calendar.SATURDAY) 289 errln("FAIL: Min/max bad"); 290 if (dow < min || dow > max) 291 errln("FAIL: Day of week " + dow + " out of range"); 292 if (dow != Calendar.SUNDAY) 293 errln("FAIL: Day of week should be SUNDAY Got " + dow); 294 } 295 Test4071385()296 public void Test4071385() { 297 Calendar cal = Calendar.getInstance(); 298 cal.setTime(new Date(98, Calendar.JUNE, 24)); 299 cal.set(Calendar.MONTH, Calendar.NOVEMBER); // change a field 300 logln(cal.getTime().toString()); 301 if (!cal.getTime().equals(new Date(98, Calendar.NOVEMBER, 24))) 302 errln("Fail"); 303 } 304 Test4073929()305 public void Test4073929() { 306 GregorianCalendar foo1 = new GregorianCalendar(1997, 8, 27); 307 foo1.add(Calendar.DAY_OF_MONTH, +1); 308 int testyear = foo1.get(Calendar.YEAR); 309 int testmonth = foo1.get(Calendar.MONTH); 310 int testday = foo1.get(Calendar.DAY_OF_MONTH); 311 if (testyear != 1997 || 312 testmonth != 8 || 313 testday != 28) 314 errln("Fail: Calendar not initialized"); 315 } 316 Test4083167()317 public void Test4083167() { 318 TimeZone saveZone = TimeZone.getDefault(); 319 try { 320 TimeZone.setDefault(TimeZone.getTimeZone("UTC")); 321 Date firstDate = new Date(); 322 Calendar cal = new GregorianCalendar(); 323 cal.setTime(firstDate); 324 long firstMillisInDay = cal.get(Calendar.HOUR_OF_DAY) * 3600000L + 325 cal.get(Calendar.MINUTE) * 60000L + 326 cal.get(Calendar.SECOND) * 1000L + 327 cal.get(Calendar.MILLISECOND); 328 329 logln("Current time: " + firstDate.toString()); 330 331 for (int validity=0; validity<30; validity++) { 332 Date lastDate = new Date(firstDate.getTime() + 333 (long)validity*1000*24*60*60); 334 cal.setTime(lastDate); 335 long millisInDay = cal.get(Calendar.HOUR_OF_DAY) * 3600000L + 336 cal.get(Calendar.MINUTE) * 60000L + 337 cal.get(Calendar.SECOND) * 1000L + 338 cal.get(Calendar.MILLISECOND); 339 if (firstMillisInDay != millisInDay) { 340 errln("Day has shifted " + lastDate); 341 } 342 } 343 } 344 finally { 345 TimeZone.setDefault(saveZone); 346 } 347 } 348 Test4086724()349 public void Test4086724() { 350 SimpleDateFormat date; 351 TimeZone saveZone = TimeZone.getDefault(); 352 Locale saveLocale = Locale.getDefault(); 353 354 String summerTime = "British Summer Time"; 355 String standardTime = "Greenwich Mean Time"; 356 try { 357 Locale.setDefault(Locale.UK); 358 TimeZone.setDefault(TimeZone.getTimeZone("Europe/London")); 359 date = new SimpleDateFormat("zzzz"); 360 361 Calendar cal=Calendar.getInstance(); 362 cal.set(1997,Calendar.SEPTEMBER,30); 363 Date now=cal.getTime(); 364 String formattedDate = date.format(now); 365 if (!formattedDate.equals(summerTime)) { 366 errln("Wrong display name \"" + formattedDate 367 + "\" for <" + now + ">"); 368 } 369 int weekOfYear = cal.get(Calendar.WEEK_OF_YEAR); 370 if (weekOfYear != 40) { 371 errln("Wrong week-of-year " + weekOfYear 372 + " for <" + now + ">"); 373 } 374 375 cal.set(1996,Calendar.DECEMBER,31); 376 now=cal.getTime(); 377 formattedDate = date.format(now); 378 if (!formattedDate.equals(standardTime)) { 379 errln("Wrong display name \"" + formattedDate 380 + "\" for <" + now + ">"); 381 } 382 weekOfYear = cal.get(Calendar.WEEK_OF_YEAR); 383 if (weekOfYear != 1) { 384 errln("Wrong week-of-year " + weekOfYear 385 + " for <" + now + ">"); 386 } 387 388 cal.set(1997,Calendar.JANUARY,1); 389 now=cal.getTime(); 390 formattedDate = date.format(now); 391 if (!formattedDate.equals(standardTime)) { 392 errln("Wrong display name \"" + formattedDate 393 + "\" for <" + now + ">"); 394 } 395 weekOfYear = cal.get(Calendar.WEEK_OF_YEAR); 396 if (weekOfYear != 1) { 397 errln("Wrong week-of-year " + weekOfYear 398 + " for <" + now + ">"); 399 } 400 401 cal.set(1997,Calendar.JANUARY,8); 402 now=cal.getTime(); 403 formattedDate = date.format(now); 404 if (!formattedDate.equals(standardTime)) { 405 errln("Wrong display name \"" + formattedDate 406 + "\" for <" + now + ">"); 407 } 408 weekOfYear = cal.get(Calendar.WEEK_OF_YEAR); 409 if (weekOfYear != 2) { 410 errln("Wrong week-of-year " + weekOfYear 411 + " for <" + now + ">"); 412 } 413 414 } 415 finally { 416 Locale.setDefault(saveLocale); 417 TimeZone.setDefault(saveZone); 418 } 419 } 420 Test4092362()421 public void Test4092362() { 422 GregorianCalendar cal1 = new GregorianCalendar(1997, 10, 11, 10, 20, 40); 423 /*cal1.set( Calendar.YEAR, 1997 ); 424 cal1.set( Calendar.MONTH, 10 ); 425 cal1.set( Calendar.DATE, 11 ); 426 cal1.set( Calendar.HOUR, 10 ); 427 cal1.set( Calendar.MINUTE, 20 ); 428 cal1.set( Calendar.SECOND, 40 ); */ 429 430 logln( " Cal1 = " + cal1.getTime().getTime() ); 431 logln( " Cal1 time in ms = " + cal1.get(Calendar.MILLISECOND) ); 432 for( int k = 0; k < 100 ; k++ ); 433 434 GregorianCalendar cal2 = new GregorianCalendar(1997, 10, 11, 10, 20, 40); 435 /*cal2.set( Calendar.YEAR, 1997 ); 436 cal2.set( Calendar.MONTH, 10 ); 437 cal2.set( Calendar.DATE, 11 ); 438 cal2.set( Calendar.HOUR, 10 ); 439 cal2.set( Calendar.MINUTE, 20 ); 440 cal2.set( Calendar.SECOND, 40 ); */ 441 442 logln( " Cal2 = " + cal2.getTime().getTime() ); 443 logln( " Cal2 time in ms = " + cal2.get(Calendar.MILLISECOND) ); 444 if( !cal1.equals( cal2 ) ) 445 errln("Fail: Milliseconds randomized"); 446 } 447 Test4095407()448 public void Test4095407() { 449 GregorianCalendar a = new GregorianCalendar(1997,Calendar.NOVEMBER, 13); 450 int dow = a.get(Calendar.DAY_OF_WEEK); 451 if (dow != Calendar.THURSDAY) 452 errln("Fail: Want THURSDAY Got " + dow); 453 } 454 Test4096231()455 public void Test4096231() { 456 TimeZone GMT = TimeZone.getTimeZone("GMT"); 457 TimeZone PST = TimeZone.getTimeZone("PST"); 458 int sec = 0, min = 0, hr = 0, day = 1, month = 10, year = 1997; 459 460 Calendar cal1 = new GregorianCalendar(PST); 461 cal1.setTime(new Date(880698639000L)); 462 int p; 463 logln("PST 1 is: " + (p=cal1.get(cal1.HOUR_OF_DAY))); 464 cal1.setTimeZone(GMT); 465 // Issue 1: Changing the timezone doesn't change the 466 // represented time. 467 int h1,h2; 468 logln("GMT 1 is: " + (h1=cal1.get(cal1.HOUR_OF_DAY))); 469 cal1.setTime(new Date(880698639000L)); 470 logln("GMT 2 is: " + (h2=cal1.get(cal1.HOUR_OF_DAY))); 471 // Note: This test had a bug in it. It wanted h1!=h2, when 472 // what was meant was h1!=p. Fixed this concurrent with fix 473 // to 4177484. 474 if (p == h1 || h1 != h2) 475 errln("Fail: Hour same in different zones"); 476 477 Calendar cal2 = new GregorianCalendar(GMT); 478 Calendar cal3 = new GregorianCalendar(PST); 479 cal2.set(Calendar.MILLISECOND, 0); 480 cal3.set(Calendar.MILLISECOND, 0); 481 482 cal2.set(cal1.get(cal1.YEAR), 483 cal1.get(cal1.MONTH), 484 cal1.get(cal1.DAY_OF_MONTH), 485 cal1.get(cal1.HOUR_OF_DAY), 486 cal1.get(cal1.MINUTE), 487 cal1.get(cal1.SECOND)); 488 489 long t1,t2,t3,t4; 490 logln("RGMT 1 is: " + (t1=cal2.getTime().getTime())); 491 cal3.set(year, month, day, hr, min, sec); 492 logln("RPST 1 is: " + (t2=cal3.getTime().getTime())); 493 cal3.setTimeZone(GMT); 494 logln("RGMT 2 is: " + (t3=cal3.getTime().getTime())); 495 cal3.set(cal1.get(cal1.YEAR), 496 cal1.get(cal1.MONTH), 497 cal1.get(cal1.DAY_OF_MONTH), 498 cal1.get(cal1.HOUR_OF_DAY), 499 cal1.get(cal1.MINUTE), 500 cal1.get(cal1.SECOND)); 501 // Issue 2: Calendar continues to use the timezone in its 502 // constructor for set() conversions, regardless 503 // of calls to setTimeZone() 504 logln("RGMT 3 is: " + (t4=cal3.getTime().getTime())); 505 if (t1 == t2 || 506 t1 != t4 || 507 t2 != t3) 508 errln("Fail: Calendar zone behavior faulty"); 509 } 510 Test4096539()511 public void Test4096539() { 512 int[] y = {31,28,31,30,31,30,31,31,30,31,30,31}; 513 514 for (int x=0;x<12;x++) { 515 GregorianCalendar gc = new 516 GregorianCalendar(1997,x,y[x]); 517 int m1,m2; 518 log((m1=gc.get(Calendar.MONTH)+1)+"/"+ 519 gc.get(Calendar.DATE)+"/"+gc.get(Calendar.YEAR)+ 520 " + 1mo = "); 521 522 gc.add(Calendar.MONTH, 1); 523 logln((m2=gc.get(Calendar.MONTH)+1)+"/"+ 524 gc.get(Calendar.DATE)+"/"+gc.get(Calendar.YEAR) 525 ); 526 int m = (m1 % 12) + 1; 527 if (m2 != m) 528 errln("Fail: Want " + m + " Got " + m2); 529 } 530 531 } 532 Test4100311()533 public void Test4100311() { 534 GregorianCalendar cal = (GregorianCalendar)Calendar.getInstance(); 535 cal.set(Calendar.YEAR, 1997); 536 cal.set(Calendar.DAY_OF_YEAR, 1); 537 Date d = cal.getTime(); // Should be Jan 1 538 logln(d.toString()); 539 if (cal.get(Calendar.DAY_OF_YEAR) != 1) 540 errln("Fail: DAY_OF_YEAR not set"); 541 } 542 Test4103271()543 public void Test4103271() { 544 if (Locale.getDefault().equals(new Locale("th", "TH"))) { 545 return; 546 } 547 548 SimpleDateFormat sdf = new SimpleDateFormat(); 549 int numYears=40, startYear=1997, numDays=15; 550 String output, testDesc; 551 GregorianCalendar testCal = (GregorianCalendar)Calendar.getInstance(); 552 testCal.clear(); 553 sdf.setCalendar(testCal); 554 sdf.applyPattern("d MMM yyyy"); 555 boolean fail = false; 556 for (int firstDay=1; firstDay<=2; firstDay++) { 557 for (int minDays=1; minDays<=7; minDays++) { 558 testCal.setMinimalDaysInFirstWeek(minDays); 559 testCal.setFirstDayOfWeek(firstDay); 560 testDesc = ("Test" + String.valueOf(firstDay) + String.valueOf(minDays)); 561 logln(testDesc + " => 1st day of week=" + 562 String.valueOf(firstDay) + 563 ", minimum days in first week=" + 564 String.valueOf(minDays)); 565 for (int j=startYear; j<=startYear+numYears; j++) { 566 testCal.set(j,11,25); 567 for(int i=0; i<numDays; i++) { 568 testCal.add(Calendar.DATE,1); 569 String calWOY; 570 int actWOY = testCal.get(Calendar.WEEK_OF_YEAR); 571 if (actWOY < 1 || actWOY > 53) { 572 Date d = testCal.getTime(); 573 calWOY = String.valueOf(actWOY); 574 output = testDesc + " - " + sdf.format(d) + "\t"; 575 output = output + "\t" + calWOY; 576 logln(output); 577 fail = true; 578 } 579 } 580 } 581 } 582 } 583 584 int[] DATA = { 585 3, 52, 52, 52, 52, 52, 52, 52, 586 1, 1, 1, 1, 1, 1, 1, 587 2, 2, 2, 2, 2, 2, 2, 588 4, 52, 52, 52, 52, 52, 52, 52, 589 53, 53, 53, 53, 53, 53, 53, 590 1, 1, 1, 1, 1, 1, 1, 591 }; 592 testCal.setFirstDayOfWeek(Calendar.SUNDAY); 593 for (int j=0; j<DATA.length; j+=22) { 594 logln("Minimal days in first week = " + DATA[j] + 595 " Week starts on Sunday"); 596 testCal.setMinimalDaysInFirstWeek(DATA[j]); 597 testCal.set(1997, Calendar.DECEMBER, 21); 598 for (int i=0; i<21; ++i) { 599 int woy = testCal.get(Calendar.WEEK_OF_YEAR); 600 log("\t" + testCal.getTime() + " " + woy); 601 if (woy != DATA[j + 1 + i]) { 602 log(" ERROR"); 603 fail = true; 604 } else { 605 logln(" OK"); 606 } 607 608 // Now compute the time from the fields, and make sure we 609 // get the same answer back. This is a round-trip test. 610 Date save = testCal.getTime(); 611 testCal.clear(); 612 testCal.set(Calendar.YEAR, DATA[j+1+i] < 25 ? 1998 : 1997); 613 testCal.set(Calendar.WEEK_OF_YEAR, DATA[j+1+i]); 614 testCal.set(Calendar.DAY_OF_WEEK, (i%7) + Calendar.SUNDAY); 615 if (!testCal.getTime().equals(save)) { 616 logln(" Parse failed: " + testCal.getTime()); 617 fail= true; 618 } else { 619 logln(" Passed"); 620 } 621 622 testCal.setTime(save); 623 testCal.add(Calendar.DAY_OF_MONTH, 1); 624 } 625 } 626 627 // Test field disambiguation with a few special hard-coded cases. 628 // This shouldn't fail if the above cases aren't failing. 629 Object[] DISAM = { 630 new Integer(1998), new Integer(1), new Integer(Calendar.SUNDAY), 631 new Date(97, Calendar.DECEMBER, 28), 632 new Integer(1998), new Integer(2), new Integer(Calendar.SATURDAY), 633 new Date(98, Calendar.JANUARY, 10), 634 new Integer(1998), new Integer(53), new Integer(Calendar.THURSDAY), 635 new Date(98, Calendar.DECEMBER, 31), 636 new Integer(1998), new Integer(53), new Integer(Calendar.FRIDAY), 637 new Date(99, Calendar.JANUARY, 1), 638 }; 639 testCal.setMinimalDaysInFirstWeek(3); 640 testCal.setFirstDayOfWeek(Calendar.SUNDAY); 641 for (int i=0; i<DISAM.length; i+=4) { 642 int y = ((Integer)DISAM[i]).intValue(); 643 int woy = ((Integer)DISAM[i+1]).intValue(); 644 int dow = ((Integer)DISAM[i+2]).intValue(); 645 Date exp = (Date)DISAM[i+3]; 646 testCal.clear(); 647 testCal.set(Calendar.YEAR, y); 648 testCal.set(Calendar.WEEK_OF_YEAR, woy); 649 testCal.set(Calendar.DAY_OF_WEEK, dow); 650 log(y + "-W" + woy + "-DOW" + dow); 651 if (!testCal.getTime().equals(exp)) { 652 logln(" FAILED expect: " + exp + "\n got: " +testCal.getTime()); 653 fail = true; 654 } else { 655 logln(" OK"); 656 } 657 } 658 659 // Now try adding and rolling 660 Object ADD = new Object(); 661 Object ROLL = new Object(); 662 Object[] ADDROLL = { 663 ADD, new Integer(1), new Date(98, Calendar.DECEMBER, 25), new Date(99, Calendar.JANUARY, 1), 664 ADD, new Integer(1), new Date(97, Calendar.DECEMBER, 28), new Date(98, Calendar.JANUARY, 4), 665 ROLL, new Integer(1), new Date(98, Calendar.DECEMBER, 27), new Date(98, Calendar.JANUARY, 4), 666 ROLL, new Integer(1), new Date(99, Calendar.DECEMBER, 24), new Date(99, Calendar.DECEMBER, 31), 667 ROLL, new Integer(1), new Date(99, Calendar.DECEMBER, 25), new Date(99, Calendar.JANUARY, 9), 668 }; 669 testCal.setMinimalDaysInFirstWeek(3); 670 testCal.setFirstDayOfWeek(Calendar.SUNDAY); 671 for (int i=0; i<ADDROLL.length; i+=4) { 672 int amount = ((Integer)ADDROLL[i+1]).intValue(); 673 Date before = (Date)ADDROLL[i+2]; 674 Date after = (Date)ADDROLL[i+3]; 675 676 testCal.setTime(before); 677 if (ADDROLL[i] == ADD) 678 testCal.add(Calendar.WEEK_OF_YEAR, amount); 679 else 680 testCal.roll(Calendar.WEEK_OF_YEAR, amount); 681 log((ADDROLL[i]==ADD ? "add(WOY," : "roll(WOY,") + 682 amount + ")\t " + before + 683 "\n\t\t => " + testCal.getTime()); 684 if (!after.equals(testCal.getTime())) { 685 logln("\tFAIL\n\t\texp: " + after); 686 fail = true; 687 } else 688 logln(" OK"); 689 690 testCal.setTime(after); 691 if (ADDROLL[i] == ADD) 692 testCal.add(Calendar.WEEK_OF_YEAR, -amount); 693 else 694 testCal.roll(Calendar.WEEK_OF_YEAR, -amount); 695 log((ADDROLL[i]==ADD ? "add(WOY," : "roll(WOY,") + 696 (-amount) + ") " + after + 697 "\n\t\t => " + testCal.getTime()); 698 if (!before.equals(testCal.getTime())) { 699 logln("\tFAIL\n\t\texp: " + before); 700 fail = true; 701 } 702 else logln("\tOK"); 703 } 704 705 if (fail) { 706 errln("Fail: Week of year misbehaving"); 707 } 708 } 709 Test4106136()710 public void Test4106136() { 711 Locale saveLocale = Locale.getDefault(); 712 try { 713 Locale[] locales = { Locale.CHINESE, Locale.CHINA }; 714 for (int i=0; i<locales.length; ++i) { 715 Locale.setDefault(locales[i]); 716 int[] n = { 717 Calendar.getAvailableLocales().length, 718 DateFormat.getAvailableLocales().length, 719 NumberFormat.getAvailableLocales().length 720 }; 721 for (int j=0; j<n.length; ++j) { 722 if (n[j] == 0) { 723 errln("Fail: No locales for " + locales[i]); 724 } 725 } 726 } 727 } 728 finally { 729 Locale.setDefault(saveLocale); 730 } 731 } 732 Test4108764()733 public void Test4108764() { 734 Date d00 = new Date(97, Calendar.MARCH, 15, 12, 00, 00); 735 Date d01 = new Date(97, Calendar.MARCH, 15, 12, 00, 56); 736 Date d10 = new Date(97, Calendar.MARCH, 15, 12, 34, 00); 737 Date d11 = new Date(97, Calendar.MARCH, 15, 12, 34, 56); 738 Date epoch = new Date(70, Calendar.JANUARY, 1); 739 740 Calendar cal = Calendar.getInstance(); 741 cal.setTime(d11); 742 743 cal.clear( Calendar.MINUTE ); 744 logln(cal.getTime().toString()); 745 if (!cal.getTime().equals(d01)) 746 errln("Fail: clear(MINUTE) broken"); 747 748 cal.set( Calendar.SECOND, 0 ); 749 logln(cal.getTime().toString()); 750 if (!cal.getTime().equals(d00)) 751 errln("Fail: set(SECOND, 0) broken"); 752 753 cal.setTime(d11); 754 cal.set( Calendar.SECOND, 0 ); 755 logln(cal.getTime().toString()); 756 if (!cal.getTime().equals(d10)) 757 errln("Fail: set(SECOND, 0) broken #2"); 758 759 cal.clear( Calendar.MINUTE ); 760 logln(cal.getTime().toString()); 761 if (!cal.getTime().equals(d00)) 762 errln("Fail: clear(MINUTE) broken #2"); 763 764 cal.clear(); 765 logln(cal.getTime().toString()); 766 if (!cal.getTime().equals(epoch)) 767 errln("Fail: clear() broken Want " + epoch); 768 } 769 Test4114578()770 public void Test4114578() { 771 int ONE_HOUR = 60*60*1000; 772 TimeZone saveZone = TimeZone.getDefault(); 773 boolean fail = false; 774 try { 775 TimeZone.setDefault(TimeZone.getTimeZone("PST")); 776 Calendar cal = Calendar.getInstance(); 777 long onset = new Date(98, Calendar.APRIL, 5, 1, 0).getTime() + ONE_HOUR; 778 long cease = new Date(98, Calendar.OCTOBER, 25, 0, 0).getTime() + 2*ONE_HOUR; 779 780 final int ADD = 1; 781 final int ROLL = 2; 782 783 long[] DATA = { 784 // Start Action Amt Expected_change 785 onset - ONE_HOUR, ADD, 1, ONE_HOUR, 786 onset, ADD, -1, -ONE_HOUR, 787 onset - ONE_HOUR, ROLL, 1, ONE_HOUR, 788 onset, ROLL, -1, -ONE_HOUR, 789 cease - ONE_HOUR, ADD, 1, ONE_HOUR, 790 cease, ADD, -1, -ONE_HOUR, 791 // roll() was changed to support wall-clock-based roll (JDK-8152077). The 792 // time value may jump 2 hours by skipping non-existent wall-clock time. 793 // Note that JDK-4114578 was a problem of add(), not roll(). 794 cease - ONE_HOUR, ROLL, 1, ONE_HOUR * 2, 795 cease, ROLL, -1, -ONE_HOUR * 2, 796 }; 797 798 for (int i=0; i<DATA.length; i+=4) { 799 Date date = new Date(DATA[i]); 800 int amt = (int) DATA[i+2]; 801 long expectedChange = DATA[i+3]; 802 803 log(date.toString()); 804 cal.setTime(date); 805 806 switch ((int) DATA[i+1]) { 807 case ADD: 808 log(" add (HOUR," + (amt<0?"":"+")+amt + ")= "); 809 cal.add(Calendar.HOUR, amt); 810 break; 811 case ROLL: 812 log(" roll(HOUR," + (amt<0?"":"+")+amt + ")= "); 813 cal.roll(Calendar.HOUR, amt); 814 break; 815 } 816 817 log(cal.getTime().toString()); 818 819 long change = cal.getTime().getTime() - date.getTime(); 820 if (change != expectedChange) { 821 fail = true; 822 logln(" FAIL"); 823 } 824 else logln(" OK"); 825 } 826 } finally { 827 TimeZone.setDefault(saveZone); 828 } 829 830 if (fail) { 831 errln("Fail: roll/add misbehaves around DST onset/cease"); 832 } 833 } 834 835 /** 836 * Make sure maximum for HOUR field is 11, not 12. 837 */ Test4118384()838 public void Test4118384() { 839 Calendar cal = Calendar.getInstance(); 840 if (cal.getMaximum(Calendar.HOUR) != 11 || 841 cal.getLeastMaximum(Calendar.HOUR) != 11 || 842 cal.getActualMaximum(Calendar.HOUR) != 11) 843 errln("Fail: maximum of HOUR field should be 11"); 844 } 845 846 /** 847 * Check isLeapYear for BC years. 848 */ Test4125881()849 public void Test4125881() { 850 GregorianCalendar cal = (GregorianCalendar) Calendar.getInstance(); 851 DateFormat fmt = new SimpleDateFormat("MMMM d, yyyy G"); 852 cal.clear(); 853 for (int y=-20; y<=10; ++y) { 854 cal.set(Calendar.ERA, y < 1 ? GregorianCalendar.BC : GregorianCalendar.AD); 855 cal.set(Calendar.YEAR, y < 1 ? 1 - y : y); 856 logln(y + " = " + fmt.format(cal.getTime()) + " " + 857 cal.isLeapYear(y)); 858 if (cal.isLeapYear(y) != ((y+40)%4 == 0)) 859 errln("Leap years broken"); 860 } 861 } 862 863 /** 864 * Prove that GregorianCalendar is proleptic (it used to cut off 865 * at 45 BC, and not have leap years before then). 866 */ Test4125892()867 public void Test4125892() { 868 if (Locale.getDefault().equals(new Locale("th", "TH"))) { 869 return; 870 } 871 872 GregorianCalendar cal = (GregorianCalendar) Calendar.getInstance(); 873 DateFormat fmt = new SimpleDateFormat("MMMM d, yyyy G"); 874 cal.clear(); 875 cal.set(Calendar.ERA, GregorianCalendar.BC); 876 cal.set(Calendar.YEAR, 81); // 81 BC is a leap year (proleptically) 877 cal.set(Calendar.MONTH, Calendar.FEBRUARY); 878 cal.set(Calendar.DATE, 28); 879 cal.add(Calendar.DATE, 1); 880 if (cal.get(Calendar.DATE) != 29 || 881 !cal.isLeapYear(-80)) // -80 == 81 BC 882 errln("Calendar not proleptic"); 883 } 884 885 /** 886 * Calendar and GregorianCalendar hashCode() methods need improvement. 887 * Calendar needs a good implementation that subclasses can override, 888 * and GregorianCalendar should use that implementation. 889 */ Test4136399()890 public void Test4136399() { 891 /* Note: This test is actually more strict than it has to be. 892 * Technically, there is no requirement that unequal objects have 893 * unequal hashes. We only require equal objects to have equal hashes. 894 * It is desirable for unequal objects to have distributed hashes, but 895 * there is no hard requirement here. 896 * 897 * In this test we make assumptions about certain attributes of calendar 898 * objects getting represented in the hash, which need not always be the 899 * case (although it does work currently with the given test). */ 900 Calendar a = Calendar.getInstance(); 901 Calendar b = (Calendar)a.clone(); 902 if (a.hashCode() != b.hashCode()) { 903 errln("Calendar hash code unequal for cloned objects"); 904 } 905 906 b.setMinimalDaysInFirstWeek(7 - a.getMinimalDaysInFirstWeek()); 907 if (a.hashCode() == b.hashCode()) { 908 errln("Calendar hash code ignores minimal days in first week"); 909 } 910 b.setMinimalDaysInFirstWeek(a.getMinimalDaysInFirstWeek()); 911 912 b.setFirstDayOfWeek((a.getFirstDayOfWeek() % 7) + 1); // Next day 913 if (a.hashCode() == b.hashCode()) { 914 errln("Calendar hash code ignores first day of week"); 915 } 916 b.setFirstDayOfWeek(a.getFirstDayOfWeek()); 917 918 b.setLenient(!a.isLenient()); 919 if (a.hashCode() == b.hashCode()) { 920 errln("Calendar hash code ignores lenient setting"); 921 } 922 b.setLenient(a.isLenient()); 923 924 // Assume getTimeZone() returns a reference, not a clone 925 // of a reference -- this is true as of this writing 926 b.getTimeZone().setRawOffset(a.getTimeZone().getRawOffset() + 60*60*1000); 927 if (a.hashCode() == b.hashCode()) { 928 errln("Calendar hash code ignores zone"); 929 } 930 b.getTimeZone().setRawOffset(a.getTimeZone().getRawOffset()); 931 932 GregorianCalendar c = new GregorianCalendar(); 933 GregorianCalendar d = (GregorianCalendar)c.clone(); 934 if (c.hashCode() != d.hashCode()) { 935 errln("GregorianCalendar hash code unequal for clones objects"); 936 } 937 Date cutover = c.getGregorianChange(); 938 d.setGregorianChange(new Date(cutover.getTime() + 24*60*60*1000)); 939 if (c.hashCode() == d.hashCode()) { 940 errln("GregorianCalendar hash code ignores cutover"); 941 } 942 } 943 944 /** 945 * GregorianCalendar.equals() ignores cutover date 946 */ Test4141665()947 public void Test4141665() { 948 GregorianCalendar cal = new GregorianCalendar(); 949 GregorianCalendar cal2 = (GregorianCalendar)cal.clone(); 950 Date cut = cal.getGregorianChange(); 951 Date cut2 = new Date(cut.getTime() + 100*24*60*60*1000L); // 100 days later 952 if (!cal.equals(cal2)) { 953 errln("Cloned GregorianCalendars not equal"); 954 } 955 cal2.setGregorianChange(cut2); 956 if (cal.equals(cal2)) { 957 errln("GregorianCalendar.equals() ignores cutover"); 958 } 959 } 960 961 /** 962 * Bug states that ArrayIndexOutOfBoundsException is thrown by GregorianCalendar.roll() 963 * when IllegalArgumentException should be. 964 */ Test4142933()965 public void Test4142933() { 966 GregorianCalendar calendar = new GregorianCalendar(); 967 try { 968 calendar.roll(-1, true); 969 errln("Test failed, no exception trown"); 970 } 971 catch (IllegalArgumentException e) { 972 // OK: Do nothing 973 // logln("Test passed"); 974 } 975 catch (Exception e) { 976 errln("Test failed. Unexpected exception is thrown: " + e); 977 e.printStackTrace(); 978 } 979 } 980 981 /** 982 * GregorianCalendar handling of Dates Long.MIN_VALUE and Long.MAX_VALUE is 983 * confusing; unless the time zone has a raw offset of zero, one or the 984 * other of these will wrap. We've modified the test given in the bug 985 * report to therefore only check the behavior of a calendar with a zero raw 986 * offset zone. 987 */ Test4145158()988 public void Test4145158() { 989 GregorianCalendar calendar = new GregorianCalendar(); 990 991 calendar.setTimeZone(TimeZone.getTimeZone("GMT")); 992 993 calendar.setTime(new Date(Long.MIN_VALUE)); 994 int year1 = calendar.get(Calendar.YEAR); 995 int era1 = calendar.get(Calendar.ERA); 996 997 calendar.setTime(new Date(Long.MAX_VALUE)); 998 int year2 = calendar.get(Calendar.YEAR); 999 int era2 = calendar.get(Calendar.ERA); 1000 1001 if (year1 == year2 && era1 == era2) { 1002 errln("Fail: Long.MIN_VALUE or Long.MAX_VALUE wrapping around"); 1003 } 1004 } 1005 1006 /** 1007 * Maximum value for YEAR field wrong. 1008 */ Test4145983()1009 public void Test4145983() { 1010 GregorianCalendar calendar = new GregorianCalendar(); 1011 calendar.setTimeZone(TimeZone.getTimeZone("GMT")); 1012 Date[] DATES = { new Date(Long.MAX_VALUE), new Date(Long.MIN_VALUE) }; 1013 for (int i=0; i<DATES.length; ++i) { 1014 calendar.setTime(DATES[i]); 1015 int year = calendar.get(Calendar.YEAR); 1016 int maxYear = calendar.getMaximum(Calendar.YEAR); 1017 if (year > maxYear) { 1018 errln("Failed for "+DATES[i].getTime()+" ms: year=" + 1019 year + ", maxYear=" + maxYear); 1020 } 1021 } 1022 } 1023 1024 /** 1025 * This is a bug in the validation code of GregorianCalendar. As reported, 1026 * the bug seems worse than it really is, due to a bug in the way the bug 1027 * report test was written. In reality the bug is restricted to the DAY_OF_YEAR 1028 * field. - liu 6/29/98 1029 */ Test4147269()1030 public void Test4147269() { 1031 final String[] fieldName = { 1032 "ERA", 1033 "YEAR", 1034 "MONTH", 1035 "WEEK_OF_YEAR", 1036 "WEEK_OF_MONTH", 1037 "DAY_OF_MONTH", 1038 "DAY_OF_YEAR", 1039 "DAY_OF_WEEK", 1040 "DAY_OF_WEEK_IN_MONTH", 1041 "AM_PM", 1042 "HOUR", 1043 "HOUR_OF_DAY", 1044 "MINUTE", 1045 "SECOND", 1046 "MILLISECOND", 1047 "ZONE_OFFSET", 1048 "DST_OFFSET" 1049 }; 1050 GregorianCalendar calendar = new GregorianCalendar(); 1051 calendar.setLenient(false); 1052 Date date = new Date(1996-1900, Calendar.JANUARY, 3); // Arbitrary date 1053 for (int field = 0; field < Calendar.FIELD_COUNT; field++) { 1054 calendar.setTime(date); 1055 // Note: In the bug report, getActualMaximum() was called instead 1056 // of getMaximum() -- this was an error. The validation code doesn't 1057 // use getActualMaximum(), since that's too costly. 1058 int max = calendar.getMaximum(field); 1059 int value = max+1; 1060 calendar.set(field, value); 1061 try { 1062 calendar.getTime(); // Force time computation 1063 // We expect an exception to be thrown. If we fall through 1064 // to the next line, then we have a bug. 1065 errln("Test failed with field " + fieldName[field] + 1066 ", date before: " + date + 1067 ", date after: " + calendar.getTime() + 1068 ", value: " + value + " (max = " + max +")"); 1069 } catch (IllegalArgumentException e) {} 1070 } 1071 } 1072 1073 /** 1074 * Reported bug is that a GregorianCalendar with a cutover of Date(Long.MAX_VALUE) 1075 * doesn't behave as a pure Julian calendar. 1076 * CANNOT REPRODUCE THIS BUG 1077 */ Test4149677()1078 public void Test4149677() { 1079 TimeZone[] zones = { TimeZone.getTimeZone("GMT"), 1080 TimeZone.getTimeZone("PST"), 1081 TimeZone.getTimeZone("EAT") }; 1082 for (int i=0; i<zones.length; ++i) { 1083 GregorianCalendar calendar = new GregorianCalendar(zones[i]); 1084 1085 // Make sure extreme values don't wrap around 1086 calendar.setTime(new Date(Long.MIN_VALUE)); 1087 if (calendar.get(Calendar.ERA) != GregorianCalendar.BC) { 1088 errln("Fail: Date(Long.MIN_VALUE) has an AD year in " + zones[i]); 1089 } 1090 calendar.setTime(new Date(Long.MAX_VALUE)); 1091 if (calendar.get(Calendar.ERA) != GregorianCalendar.AD) { 1092 errln("Fail: Date(Long.MAX_VALUE) has a BC year in " + zones[i]); 1093 } 1094 1095 calendar.setGregorianChange(new Date(Long.MAX_VALUE)); 1096 // to obtain a pure Julian calendar 1097 1098 boolean is100Leap = calendar.isLeapYear(100); 1099 if (!is100Leap) { 1100 errln("test failed with zone " + zones[i].getID()); 1101 errln(" cutover date is Date(Long.MAX_VALUE)"); 1102 errln(" isLeapYear(100) returns: " + is100Leap); 1103 } 1104 } 1105 } 1106 1107 /** 1108 * Calendar and Date HOUR broken. If HOUR is out-of-range, Calendar 1109 * and Date classes will misbehave. 1110 */ Test4162587()1111 public void Test4162587() { 1112 TimeZone savedTz = TimeZone.getDefault(); 1113 TimeZone tz = TimeZone.getTimeZone("PST"); 1114 TimeZone.setDefault(tz); 1115 GregorianCalendar cal = new GregorianCalendar(tz); 1116 Date d; 1117 1118 try { 1119 for (int i=0; i<5; ++i) { 1120 if (i>0) logln("---"); 1121 1122 cal.clear(); 1123 cal.set(1998, Calendar.APRIL, 5, i, 0); 1124 d = cal.getTime(); 1125 String s0 = d.toString(); 1126 logln("0 " + i + ": " + s0); 1127 1128 cal.clear(); 1129 cal.set(1998, Calendar.APRIL, 4, i+24, 0); 1130 d = cal.getTime(); 1131 String sPlus = d.toString(); 1132 logln("+ " + i + ": " + sPlus); 1133 1134 cal.clear(); 1135 cal.set(1998, Calendar.APRIL, 6, i-24, 0); 1136 d = cal.getTime(); 1137 String sMinus = d.toString(); 1138 logln("- " + i + ": " + sMinus); 1139 1140 if (!s0.equals(sPlus) || !s0.equals(sMinus)) { 1141 errln("Fail: All three lines must match"); 1142 } 1143 } 1144 } 1145 finally { 1146 TimeZone.setDefault(savedTz); 1147 } 1148 } 1149 1150 /** 1151 * Adding 12 months behaves differently from adding 1 year 1152 */ Test4165343()1153 public void Test4165343() { 1154 GregorianCalendar calendar = new GregorianCalendar(1996, Calendar.FEBRUARY, 29); 1155 Date start = calendar.getTime(); 1156 logln("init date: " + start); 1157 calendar.add(Calendar.MONTH, 12); 1158 Date date1 = calendar.getTime(); 1159 logln("after adding 12 months: " + date1); 1160 calendar.setTime(start); 1161 calendar.add(Calendar.YEAR, 1); 1162 Date date2 = calendar.getTime(); 1163 logln("after adding one year : " + date2); 1164 if (date1.equals(date2)) { 1165 logln("Test passed"); 1166 } else { 1167 errln("Test failed"); 1168 } 1169 } 1170 1171 /** 1172 * GregorianCalendar.getActualMaximum() does not account for first day of week. 1173 */ Test4166109()1174 public void Test4166109() { 1175 /* Test month: 1176 * 1177 * March 1998 1178 * Su Mo Tu We Th Fr Sa 1179 * 1 2 3 4 5 6 7 1180 * 8 9 10 11 12 13 14 1181 * 15 16 17 18 19 20 21 1182 * 22 23 24 25 26 27 28 1183 * 29 30 31 1184 */ 1185 boolean passed = true; 1186 int field = Calendar.WEEK_OF_MONTH; 1187 1188 GregorianCalendar calendar = new GregorianCalendar(Locale.US); 1189 calendar.set(1998, Calendar.MARCH, 1); 1190 calendar.setMinimalDaysInFirstWeek(1); 1191 logln("Date: " + calendar.getTime()); 1192 1193 int firstInMonth = calendar.get(Calendar.DAY_OF_MONTH); 1194 1195 for (int firstInWeek = Calendar.SUNDAY; firstInWeek <= Calendar.SATURDAY; firstInWeek++) { 1196 calendar.setFirstDayOfWeek(firstInWeek); 1197 int returned = calendar.getActualMaximum(field); 1198 int expected = (31 + ((firstInMonth - firstInWeek + 7)% 7) + 6) / 7; 1199 1200 logln("First day of week = " + firstInWeek + 1201 " getActualMaximum(WEEK_OF_MONTH) = " + returned + 1202 " expected = " + expected + 1203 ((returned == expected) ? " ok" : " FAIL")); 1204 1205 if (returned != expected) { 1206 passed = false; 1207 } 1208 } 1209 if (!passed) { 1210 errln("Test failed"); 1211 } 1212 } 1213 1214 /** 1215 * Calendar.getActualMaximum(YEAR) works wrong. 1216 * 1217 * Note: Before 1.5, this test case assumed that 1218 * setGregorianChange didn't change object's date. But it was 1219 * changed. See 4928615. 1220 */ Test4167060()1221 public void Test4167060() { 1222 int field = Calendar.YEAR; 1223 DateFormat format = new SimpleDateFormat("EEE MMM dd HH:mm:ss zzz yyyy G", 1224 Locale.US); 1225 1226 int[][] dates = { 1227 // year, month, day of month 1228 { 100, Calendar.NOVEMBER, 1 }, 1229 { -99 /*100BC*/, Calendar.JANUARY, 1 }, 1230 { 1996, Calendar.FEBRUARY, 29 }}; 1231 1232 String[] id = { "Hybrid", "Gregorian", "Julian" }; 1233 1234 for (int k=0; k<3; ++k) { 1235 logln("--- " + id[k] + " ---"); 1236 1237 for (int j = 0; j < dates.length; ++j) { 1238 GregorianCalendar calendar = new GregorianCalendar(); 1239 if (k == 1) { 1240 calendar.setGregorianChange(new Date(Long.MIN_VALUE)); 1241 } else if (k == 2) { 1242 calendar.setGregorianChange(new Date(Long.MAX_VALUE)); 1243 } 1244 calendar.set(dates[j][0], dates[j][1], dates[j][2]); 1245 format.setCalendar((Calendar)calendar.clone()); 1246 1247 Date dateBefore = calendar.getTime(); 1248 1249 int maxYear = calendar.getActualMaximum(field); 1250 logln("maxYear: " + maxYear + " for " + format.format(calendar.getTime())); 1251 logln("date before: " + format.format(dateBefore)); 1252 1253 int years[] = {2000, maxYear-1, maxYear, maxYear+1}; 1254 1255 for (int i = 0; i < years.length; i++) { 1256 boolean valid = years[i] <= maxYear; 1257 calendar.set(field, years[i]); 1258 Date dateAfter = calendar.getTime(); 1259 int newYear = calendar.get(field); 1260 calendar.setTime(dateBefore); // restore calendar for next use 1261 1262 logln(" Year " + years[i] + (valid? " ok " : " bad") + 1263 " => " + format.format(dateAfter)); 1264 if (valid && newYear != years[i]) { 1265 errln(" FAIL: " + newYear + " should be valid; date, month and time shouldn't change"); 1266 } else if (!valid && newYear == years[i]) { 1267 errln(" FAIL: " + newYear + " should be invalid"); 1268 } 1269 } 1270 } 1271 } 1272 } 1273 1274 /** 1275 * Calendar.roll broken 1276 * This bug relies on the TimeZone bug 4173604 to also be fixed. 1277 */ Test4173516()1278 public void Test4173516() { 1279 if (Locale.getDefault().equals(new Locale("th", "TH"))) { 1280 return; 1281 } 1282 1283 int fieldsList[][] = { 1284 { 1997, Calendar.FEBRUARY, 1, 10, 45, 15, 900 }, 1285 { 1999, Calendar.DECEMBER, 22, 23, 59, 59, 999 }, 1286 // test case for 4960642 with default cutover 1287 { 1582, Calendar.OCTOBER, 4, 23, 59, 59, 999 }, 1288 }; 1289 String[] fieldNames = { 1290 "ERA", "YEAR", "MONTH", "WEEK_OF_YEAR", "WEEK_OF_MONTH", 1291 "DAY_OF_MONTH", "DAY_OF_YEAR", "DAY_OF_WEEK", "DAY_OF_WEEK_IN_MONTH", 1292 "AM_PM", "HOUR", "HOUR_OF_DAY", "MINUTE", "SECOND", "MILLISECOND", 1293 "ZONE_OFFSET", "DST_OFFSET" 1294 }; 1295 1296 Locale savedLocale = Locale.getDefault(); 1297 Locale.setDefault(Locale.US); 1298 int limit = 40; 1299 1300 try { 1301 GregorianCalendar cal = new GregorianCalendar(); 1302 1303 cal.setTime(new Date(0)); 1304 cal.roll(Calendar.HOUR, 0x7F000000); 1305 cal.roll(Calendar.HOUR, -0x7F000000); 1306 if (cal.getTime().getTime() != 0) { 1307 errln("Hour rolling broken. expected 0, got "+cal.getTime().getTime()); 1308 } 1309 1310 for (int op=0; op<2; ++op) { 1311 logln("Testing GregorianCalendar " + (op==0 ? "add" : "roll")); 1312 1313 for (int field=0; field < Calendar.FIELD_COUNT; ++field) { 1314 if (field != Calendar.ZONE_OFFSET && 1315 field != Calendar.DST_OFFSET) { 1316 for (int j=0; j<fieldsList.length; ++j) { 1317 int fields[] = fieldsList[j]; 1318 cal.clear(); 1319 cal.set(fields[0], fields[1], fields[2], 1320 fields[3], fields[4], fields[5]); 1321 cal.set(Calendar.MILLISECOND, fields[6]); 1322 for (int i = 0; i < 2*limit; i++) { 1323 if (op == 0) { 1324 cal.add(field, i < limit ? 1 : -1); 1325 } else { 1326 cal.roll(field, i < limit ? 1 : -1); 1327 } 1328 } 1329 1330 if (cal.get(Calendar.YEAR) != fields[0] || 1331 cal.get(Calendar.MONTH) != fields[1] || 1332 cal.get(Calendar.DATE) != fields[2] || 1333 cal.get(Calendar.HOUR_OF_DAY) != fields[3] || 1334 cal.get(Calendar.MINUTE) != fields[4] || 1335 cal.get(Calendar.SECOND) != fields[5] || 1336 cal.get(Calendar.MILLISECOND) != fields[6]) { 1337 errln("Field " + field + 1338 " (" + fieldNames[field] + 1339 ") FAIL, expected " + 1340 fields[0] + 1341 "/" + (fields[1] + 1) + 1342 "/" + fields[2] + 1343 " " + fields[3] + 1344 ":" + fields[4] + 1345 ":" + fields[5] + 1346 "." + fields[6] + 1347 ", got " + cal.get(Calendar.YEAR) + 1348 "/" + (cal.get(Calendar.MONTH) + 1) + 1349 "/" + cal.get(Calendar.DATE) + 1350 " " + cal.get(Calendar.HOUR_OF_DAY) + 1351 ":" + cal.get(Calendar.MINUTE) + 1352 ":" + cal.get(Calendar.SECOND) + 1353 "." + cal.get(Calendar.MILLISECOND)); 1354 1355 cal.clear(); 1356 cal.set(fields[0], fields[1], fields[2], 1357 fields[3], fields[4], fields[5]); 1358 cal.set(Calendar.MILLISECOND, fields[6]); 1359 errln(cal.get(Calendar.YEAR) + 1360 "/" + (cal.get(Calendar.MONTH) + 1) + 1361 "/" + cal.get(Calendar.DATE) + 1362 " " + cal.get(Calendar.HOUR_OF_DAY) + 1363 ":" + cal.get(Calendar.MINUTE) + 1364 ":" + cal.get(Calendar.SECOND) + 1365 "." + cal.get(Calendar.MILLISECOND)); 1366 1367 long prev = cal.getTime().getTime(); 1368 for (int i = 0; i < 2*limit; i++) { 1369 if (op == 0) { 1370 cal.add(field, i < limit ? 1 : -1); 1371 } else { 1372 cal.roll(field, i < limit ? 1 : -1); 1373 } 1374 long t = cal.getTime().getTime(); 1375 long delta = t - prev; 1376 prev = t; 1377 errln((op == 0 ? "add(" : "roll(") + 1378 fieldNames[field] + ", " + 1379 (i < limit ? "+" : "-") + "1) => " + 1380 cal.get(Calendar.YEAR) + 1381 "/" + (cal.get(Calendar.MONTH) + 1) + 1382 "/" + cal.get(Calendar.DATE) + 1383 " " + cal.get(Calendar.HOUR_OF_DAY) + 1384 ":" + cal.get(Calendar.MINUTE) + 1385 ":" + cal.get(Calendar.SECOND) + 1386 "." + cal.get(Calendar.MILLISECOND) + 1387 " d=" + delta); 1388 } 1389 } 1390 } 1391 } 1392 } 1393 } 1394 } 1395 finally { 1396 Locale.setDefault(savedLocale); 1397 } 1398 } 1399 Test4174361()1400 public void Test4174361() { 1401 GregorianCalendar calendar = new GregorianCalendar(1996, 1, 29); 1402 1403 calendar.add(Calendar.MONTH, 10); 1404 Date date1 = calendar.getTime(); 1405 int d1 = calendar.get(Calendar.DAY_OF_MONTH); 1406 1407 calendar = new GregorianCalendar(1996, 1, 29); 1408 calendar.add(Calendar.MONTH, 11); 1409 Date date2 = calendar.getTime(); 1410 int d2 = calendar.get(Calendar.DAY_OF_MONTH); 1411 1412 if (d1 != d2) { 1413 errln("adding months to Feb 29 broken"); 1414 } 1415 } 1416 1417 /** 1418 * Calendar does not update field values when setTimeZone is called. 1419 */ Test4177484()1420 public void Test4177484() { 1421 TimeZone PST = TimeZone.getTimeZone("PST"); 1422 TimeZone EST = TimeZone.getTimeZone("EST"); 1423 1424 Calendar cal = Calendar.getInstance(PST, Locale.US); 1425 cal.clear(); 1426 cal.set(1999, 3, 21, 15, 5, 0); // Arbitrary 1427 int h1 = cal.get(Calendar.HOUR_OF_DAY); 1428 cal.setTimeZone(EST); 1429 int h2 = cal.get(Calendar.HOUR_OF_DAY); 1430 if (h1 == h2) { 1431 errln("FAIL: Fields not updated after setTimeZone"); 1432 } 1433 1434 // getTime() must NOT change when time zone is changed. 1435 // getTime() returns zone-independent time in ms. 1436 cal.clear(); 1437 cal.setTimeZone(PST); 1438 cal.set(Calendar.HOUR_OF_DAY, 10); 1439 Date pst10 = cal.getTime(); 1440 cal.setTimeZone(EST); 1441 Date est10 = cal.getTime(); 1442 if (!pst10.equals(est10)) { 1443 errln("FAIL: setTimeZone changed time"); 1444 } 1445 } 1446 1447 /** 1448 * Week of year is wrong at the start and end of the year. 1449 */ Test4197699()1450 public void Test4197699() { 1451 GregorianCalendar cal = new GregorianCalendar(); 1452 cal.setFirstDayOfWeek(Calendar.MONDAY); 1453 cal.setMinimalDaysInFirstWeek(4); 1454 DateFormat fmt = new SimpleDateFormat("E dd MMM yyyy 'DOY='D 'WOY='w"); 1455 fmt.setCalendar(cal); 1456 1457 int[] DATA = { 1458 2000, Calendar.JANUARY, 1, 52, 1459 2001, Calendar.DECEMBER, 31, 1, 1460 }; 1461 1462 for (int i=0; i<DATA.length; ) { 1463 cal.set(DATA[i++], DATA[i++], DATA[i++]); 1464 int expWOY = DATA[i++]; 1465 int actWOY = cal.get(Calendar.WEEK_OF_YEAR); 1466 if (expWOY == actWOY) { 1467 logln("Ok: " + fmt.format(cal.getTime())); 1468 } else { 1469 errln("FAIL: " + fmt.format(cal.getTime()) 1470 + ", expected WOY=" + expWOY); 1471 cal.add(Calendar.DATE, -8); 1472 for (int j=0; j<14; ++j) { 1473 cal.add(Calendar.DATE, 1); 1474 logln(fmt.format(cal.getTime())); 1475 } 1476 } 1477 } 1478 } 1479 1480 /** 1481 * Calendar DAY_OF_WEEK_IN_MONTH fields->time broken. The problem 1482 * is in the field disambiguation code in GregorianCalendar. This 1483 * code is supposed to choose the most recent set of fields 1484 * among the following: 1485 * 1486 * MONTH + DAY_OF_MONTH 1487 * MONTH + WEEK_OF_MONTH + DAY_OF_WEEK 1488 * MONTH + DAY_OF_WEEK_IN_MONTH + DAY_OF_WEEK 1489 * DAY_OF_YEAR 1490 * WEEK_OF_YEAR + DAY_OF_WEEK 1491 */ Test4209071()1492 public void Test4209071() { 1493 Calendar cal = Calendar.getInstance(Locale.US); 1494 1495 // General field setting test 1496 int Y = 1995 - 1900; 1497 1498 Object[] FIELD_DATA = { 1499 // Add new test cases as needed. 1500 1501 // 0 1502 new int[] {}, new Date(Y, Calendar.JANUARY, 1), 1503 // 1 1504 new int[] { Calendar.MONTH, Calendar.MARCH }, 1505 new Date(Y, Calendar.MARCH, 1), 1506 // 2 1507 new int[] { Calendar.DAY_OF_WEEK, Calendar.WEDNESDAY }, 1508 new Date(Y, Calendar.JANUARY, 4), 1509 // 3 1510 new int[] { Calendar.DAY_OF_WEEK, Calendar.THURSDAY, 1511 Calendar.DAY_OF_MONTH, 18, }, 1512 new Date(Y, Calendar.JANUARY, 18), 1513 // 4 1514 new int[] { Calendar.DAY_OF_MONTH, 18, 1515 Calendar.DAY_OF_WEEK, Calendar.THURSDAY, }, 1516 new Date(Y, Calendar.JANUARY, 18), 1517 // 5 (WOM -1 is in previous month) 1518 new int[] { Calendar.DAY_OF_MONTH, 18, 1519 Calendar.WEEK_OF_MONTH, -1, 1520 Calendar.DAY_OF_WEEK, Calendar.THURSDAY, }, 1521 new Date(Y-1, Calendar.DECEMBER, 22), 1522 // 6 1523 new int[] { Calendar.DAY_OF_MONTH, 18, 1524 Calendar.WEEK_OF_MONTH, 4, 1525 Calendar.DAY_OF_WEEK, Calendar.THURSDAY, }, 1526 new Date(Y, Calendar.JANUARY, 26), 1527 // 7 (DIM -1 is in same month) 1528 new int[] { Calendar.DAY_OF_MONTH, 18, 1529 Calendar.DAY_OF_WEEK_IN_MONTH, -1, 1530 Calendar.DAY_OF_WEEK, Calendar.THURSDAY, }, 1531 new Date(Y, Calendar.JANUARY, 26), 1532 // 8 1533 new int[] { Calendar.WEEK_OF_YEAR, 9, 1534 Calendar.DAY_OF_WEEK, Calendar.WEDNESDAY, }, 1535 new Date(Y, Calendar.MARCH, 1), 1536 // 9 1537 new int[] { Calendar.MONTH, Calendar.OCTOBER, 1538 Calendar.DAY_OF_WEEK_IN_MONTH, 1, 1539 Calendar.DAY_OF_WEEK, Calendar.FRIDAY, }, 1540 new Date(Y, Calendar.OCTOBER, 6), 1541 // 10 1542 new int[] { Calendar.MONTH, Calendar.OCTOBER, 1543 Calendar.WEEK_OF_MONTH, 2, 1544 Calendar.DAY_OF_WEEK, Calendar.FRIDAY, }, 1545 new Date(Y, Calendar.OCTOBER, 13), 1546 // 11 1547 new int[] { Calendar.MONTH, Calendar.OCTOBER, 1548 Calendar.DAY_OF_MONTH, 15, 1549 Calendar.DAY_OF_YEAR, 222, }, 1550 new Date(Y, Calendar.AUGUST, 10), 1551 // 12 1552 new int[] { Calendar.DAY_OF_WEEK, Calendar.THURSDAY, 1553 Calendar.MONTH, Calendar.DECEMBER, }, 1554 new Date(Y, Calendar.DECEMBER, 7), 1555 }; 1556 1557 for (int i=0; i<FIELD_DATA.length; i+=2) { 1558 int[] fields = (int[]) FIELD_DATA[i]; 1559 Date exp = (Date) FIELD_DATA[i+1]; 1560 1561 cal.clear(); 1562 cal.set(Calendar.YEAR, Y + 1900); 1563 for (int j=0; j<fields.length; j+=2) { 1564 cal.set(fields[j], fields[j+1]); 1565 } 1566 1567 Date act = cal.getTime(); 1568 if (!act.equals(exp)) { 1569 errln("FAIL: Test " + (i/2) + " got " + act + 1570 ", want " + exp + 1571 " (see test/java/util/Calendar/CalendarRegression.java"); 1572 } 1573 } 1574 1575 // Test specific failure reported in bug 1576 Object[] DATA = { 1577 new Integer(1), new Date(1997-1900, Calendar.JANUARY, 5), 1578 new Integer(4), new Date(1997-1900, Calendar.JANUARY, 26), 1579 new Integer(8), new Date(1997-1900, Calendar.FEBRUARY, 23), 1580 new Integer(-1), new Date(1997-1900, Calendar.JANUARY, 26), 1581 new Integer(-4), new Date(1997-1900, Calendar.JANUARY, 5), 1582 new Integer(-8), new Date(1996-1900, Calendar.DECEMBER, 8), 1583 }; 1584 for (int i=0; i<DATA.length; i+=2) { 1585 cal.clear(); 1586 cal.set(Calendar.DAY_OF_WEEK_IN_MONTH, 1587 ((Number) DATA[i]).intValue()); 1588 cal.set(Calendar.DAY_OF_WEEK, Calendar.SUNDAY); 1589 cal.set(Calendar.MONTH, Calendar.JANUARY); 1590 cal.set(Calendar.YEAR, 1997); 1591 Date actual = cal.getTime(); 1592 if (!actual.equals(DATA[i+1])) { 1593 errln("FAIL: Sunday " + DATA[i] + 1594 " of Jan 1997 -> " + actual + 1595 ", want " + DATA[i+1]); 1596 } 1597 } 1598 } 1599 Test4288792()1600 public void Test4288792() throws Exception 1601 { 1602 TimeZone savedTZ = TimeZone.getDefault(); 1603 TimeZone.setDefault(TimeZone.getTimeZone("GMT")); 1604 GregorianCalendar cal = new GregorianCalendar(); 1605 try { 1606 for (int i = 1900; i < 2100; i++) { 1607 for (int j1 = 1; j1 <= 7; j1++) { 1608 // Loop for MinimalDaysInFirstWeek: 1..7 1609 for (int j = Calendar.SUNDAY; j <= Calendar.SATURDAY; j++) { 1610 // Loop for FirstDayOfWeek: SUNDAY..SATURDAY 1611 cal.clear(); 1612 cal.setMinimalDaysInFirstWeek(j1); 1613 cal.setFirstDayOfWeek(j); 1614 cal.set(Calendar.YEAR, i); 1615 int maxWeek = cal.getActualMaximum(Calendar.WEEK_OF_YEAR); 1616 cal.set(Calendar.WEEK_OF_YEAR, maxWeek); 1617 cal.set(Calendar.DAY_OF_WEEK, j); 1618 1619 for (int k = 1; k < 7; k++) { 1620 cal.add(Calendar.DATE, 1); 1621 int WOY = cal.get(Calendar.WEEK_OF_YEAR); 1622 if (WOY != maxWeek) { 1623 errln(cal.getTime() + ",got=" + WOY 1624 + ",expected=" + maxWeek 1625 + ",min=" + j1 + ",first=" + j); 1626 } 1627 } 1628 1629 cal.add(Calendar.DATE, 1); 1630 int WOY = cal.get(Calendar.WEEK_OF_YEAR); 1631 if (WOY != 1) { 1632 errln(cal.getTime() + ",got=" + WOY 1633 + ",expected=1,min=" + j1 + ",first" + j); 1634 } 1635 } 1636 } 1637 } 1638 } 1639 finally { 1640 TimeZone.setDefault(savedTZ); 1641 } 1642 } 1643 Test4328747()1644 public void Test4328747() throws Exception { 1645 Calendar c = (Calendar)Calendar.getInstance(Locale.US); 1646 c.clear(); 1647 c.set(1966,0,1); // 1 jan 1966 1648 1649 // serialize 1650 ByteArrayOutputStream out = new ByteArrayOutputStream(); 1651 ObjectOutputStream s = new ObjectOutputStream(out); 1652 s.writeObject(c); 1653 s.flush(); 1654 1655 // deserialize 1656 ObjectInputStream t = new ObjectInputStream(new ByteArrayInputStream(out.toByteArray())); 1657 Calendar result = (Calendar)t.readObject(); 1658 1659 // let recalculate fields with the same UTC time 1660 result.setTime(result.getTime()); 1661 // Bug gives 1965 11 19 1662 if ((result.get(c.YEAR) != 1966) || (result.get(c.MONTH) != 0) 1663 || (result.get(c.DATE) != 1)) { 1664 errln("deserialized Calendar returned wrong date field(s): " 1665 + result.get(c.YEAR) + "/" + result.get(c.MONTH) + "/" + result.get(c.DATE) 1666 + ", expected 1966/0/1"); 1667 } 1668 } 1669 1670 /** 1671 * Test whether Calendar can be serialized/deserialized correctly 1672 * even if invalid/customized TimeZone is used. 1673 */ Test4413980()1674 public void Test4413980() { 1675 TimeZone savedTimeZone = TimeZone.getDefault(); 1676 try { 1677 boolean pass = true; 1678 String[] IDs = new String[] {"Undefined", "PST", "US/Pacific", 1679 "GMT+3:00", "GMT-01:30"}; 1680 for (int i = 0; i < IDs.length; i++) { 1681 TimeZone tz = TimeZone.getTimeZone(IDs[i]); 1682 TimeZone.setDefault(tz); 1683 1684 Calendar c = (Calendar)Calendar.getInstance(); 1685 1686 // serialize 1687 ByteArrayOutputStream out = new ByteArrayOutputStream(); 1688 ObjectOutputStream s = new ObjectOutputStream(out); 1689 s.writeObject(c); 1690 s.flush(); 1691 1692 // deserialize 1693 ObjectInputStream t = new ObjectInputStream(new ByteArrayInputStream(out.toByteArray())); 1694 1695 if (!c.equals(t.readObject())) { 1696 pass = false; 1697 logln("Calendar instance which uses TimeZone <" + 1698 IDs[i] + "> is incorrectly serialized/deserialized."); 1699 } else { 1700 logln("Calendar instance which uses TimeZone <" + 1701 IDs[i] + "> is correctly serialized/deserialized."); 1702 } 1703 } 1704 if (!pass) { 1705 errln("Fail: Calendar serialization/equality bug"); 1706 } 1707 } 1708 catch (IOException e) { 1709 errln("Fail: " + e); 1710 e.printStackTrace(); 1711 } 1712 catch (ClassNotFoundException e) { 1713 errln("Fail: " + e); 1714 e.printStackTrace(); 1715 } 1716 finally { 1717 TimeZone.setDefault(savedTimeZone); 1718 } 1719 } 1720 1721 /** 1722 * 4546637: Incorrect WEEK_OF_MONTH after changing First Day Of Week 1723 */ Test4546637()1724 public void Test4546637() { 1725 GregorianCalendar day = new GregorianCalendar (2001, Calendar.NOVEMBER, 04); 1726 day.setMinimalDaysInFirstWeek(1); 1727 int wom = day.get(Calendar.WEEK_OF_MONTH); 1728 1729 day.setFirstDayOfWeek(Calendar.MONDAY); 1730 if (day.get(Calendar.WEEK_OF_MONTH) != 1) { 1731 errln("Fail: 2001/11/4 must be the first week of the month."); 1732 } 1733 } 1734 1735 /** 1736 * 4623997: GregorianCalendar returns bad WEEK_OF_YEAR 1737 */ Test4623997()1738 public void Test4623997() { 1739 GregorianCalendar cal = new GregorianCalendar(2000, GregorianCalendar.JANUARY, 1); 1740 1741 int dow = cal.get(GregorianCalendar.DAY_OF_WEEK); 1742 1743 cal.setFirstDayOfWeek(GregorianCalendar.MONDAY); 1744 cal.setMinimalDaysInFirstWeek(4); 1745 1746 if (cal.get(GregorianCalendar.WEEK_OF_YEAR) != 52) { 1747 errln("Fail: 2000/1/1 must be the 52nd week of the year."); 1748 } 1749 } 1750 1751 /** 1752 * 4685354: Handling of Calendar fields setting state is broken 1753 * 1754 * <p>Need to use SimpleDateFormat to test because a call to 1755 * get(int) changes internal states of a Calendar. 1756 */ Test4685354()1757 public void Test4685354() { 1758 if (Locale.getDefault().equals(new Locale("hi", "IN"))) { 1759 return; 1760 } 1761 1762 Calendar calendar = Calendar.getInstance(Locale.US); 1763 DateFormat df = new SimpleDateFormat("yyyy/MM/dd", Locale.US); 1764 String expected = "1999/12/31"; 1765 Date t; 1766 String s; 1767 1768 try { 1769 calendar.setTime(df.parse(expected)); 1770 } catch (Exception e) { 1771 throw new RuntimeException("Unexpected parse exception", e); 1772 } 1773 1774 t = calendar.getTime(); 1775 calendar.set(Calendar.DAY_OF_MONTH, 33); 1776 t = calendar.getTime(); 1777 calendar.set(Calendar.DAY_OF_MONTH, 0); 1778 s = df.format(calendar.getTime()); 1779 if (!expected.equals(s)) { 1780 errln("DAY_OF_MONTH w/o ZONE_OFFSET: expected: " + expected + ", got: " + s); 1781 } 1782 1783 // The same thing must work with ZONE_OFFSET set 1784 try { 1785 calendar.setTime(df.parse(expected)); 1786 } catch (Exception e) { 1787 throw new RuntimeException("Unexpected parse exception", e); 1788 } 1789 t = calendar.getTime(); 1790 calendar.set(calendar.ZONE_OFFSET, calendar.get(calendar.ZONE_OFFSET)); 1791 calendar.set(Calendar.DAY_OF_MONTH, 33); 1792 t = calendar.getTime(); 1793 calendar.set(Calendar.DAY_OF_MONTH, 0); 1794 s = df.format(calendar.getTime()); 1795 if (!expected.equals(s)) { 1796 errln("DAY_OF_MONTH: expected: " + expected + ", got: " + s); 1797 } 1798 1799 expected = "1999/12/24"; // 0th week of 2000 1800 calendar.clear(); 1801 Date initialDate = null; 1802 try { 1803 initialDate = df.parse(expected); 1804 calendar.setTime(initialDate); 1805 } catch (Exception e) { 1806 throw new RuntimeException("Unexpected parse exception", e); 1807 } 1808 t = calendar.getTime(); 1809 calendar.set(calendar.ZONE_OFFSET, calendar.get(calendar.ZONE_OFFSET)); 1810 // jump to the next year 1811 calendar.set(Calendar.WEEK_OF_YEAR, 100); 1812 t = calendar.getTime(); 1813 calendar.set(Calendar.WEEK_OF_YEAR, 0); 1814 s = df.format(calendar.getTime()); 1815 if (!expected.equals(s)) { 1816 errln("WEEK_OF_YEAR: expected: " + expected + ", got: " + s); 1817 } 1818 // change the state back 1819 calendar.clear(); 1820 calendar.setTime(initialDate); 1821 calendar.set(calendar.ZONE_OFFSET, calendar.get(calendar.ZONE_OFFSET)); 1822 // jump to next month 1823 calendar.set(Calendar.WEEK_OF_MONTH, 7); 1824 t = calendar.getTime(); 1825 calendar.set(Calendar.WEEK_OF_MONTH, 0); 1826 s = df.format(calendar.getTime()); 1827 if (!expected.equals(s)) { 1828 errln("WEEK_OF_MONTH: expected: " + expected + ", got: " + s); 1829 } 1830 1831 // Make sure the time fields work correctly. 1832 calendar.clear(); 1833 df = new SimpleDateFormat("HH:mm:ss"); 1834 TimeZone tz = TimeZone.getTimeZone("GMT"); 1835 df.setTimeZone(tz); 1836 calendar.setTimeZone(tz); 1837 expected = "22:59:59"; 1838 try { 1839 calendar.setTime(df.parse(expected)); 1840 } catch (Exception e) { 1841 throw new RuntimeException("Unexpected parse exception", e); 1842 } 1843 t = calendar.getTime(); 1844 // time should be 22:59:59. 1845 calendar.set(Calendar.MINUTE, 61); 1846 // time should be 23:01:59. 1847 t = calendar.getTime(); 1848 calendar.set(Calendar.MINUTE, -1); 1849 // time should be back to 22:59:59. 1850 s = df.format(calendar.getTime()); 1851 if (!expected.equals(s)) { 1852 errln("MINUTE: expected: " + expected + ", got: " + s); 1853 } 1854 } 1855 1856 /** 1857 * 4655637: Calendar.set() for DAY_OF_WEEK does not return the right value 1858 * 1859 * <p>Need to use SimpleDateFormat to test because a call to 1860 * get(int) changes internal states of a Calendar. 1861 */ Test4655637()1862 public void Test4655637() { 1863 // Skip this test case if it's Thai locale 1864 if (Locale.getDefault().equals(new Locale("th", "TH"))) { 1865 return; 1866 } 1867 1868 Calendar cal = Calendar.getInstance(); 1869 cal.setTime(new Date(1029814211523L)); 1870 cal.set(Calendar.YEAR, 2001); 1871 Date t = cal.getTime(); 1872 cal.set(Calendar.MONTH, Calendar.JANUARY); 1873 t = cal.getTime(); 1874 1875 cal.set(Calendar.DAY_OF_MONTH, 8); 1876 t = cal.getTime(); 1877 1878 cal.set(Calendar.DAY_OF_WEEK, Calendar.MONDAY); 1879 DateFormat df = new SimpleDateFormat("yyyy/MM/dd", Locale.US); 1880 String expected = "2001/01/08"; 1881 String s = df.format(cal.getTime()); 1882 if (!expected.equals(s)) { 1883 errln("expected: " + expected + ", got: " + s); 1884 } 1885 } 1886 1887 /** 1888 * 4683492: Invalid value for MONTH in GregorianCalendar causes exception in getTime(). 1889 * 1890 * <p>Need to use SimpleDateFormat to test because a call to 1891 * get(int) changes internal states of a Calendar. 1892 * 1893 * <p>This test case throws ArrayIndexOutOfBoundsException without the fix. 1894 */ Test4683492()1895 public void Test4683492() { 1896 Calendar cal = new GregorianCalendar(2002, 3, 29, 10, 0, 0); 1897 cal.set(Calendar.DAY_OF_WEEK, Calendar.FRIDAY); 1898 cal.set(Calendar.DAY_OF_WEEK_IN_MONTH, -1); 1899 cal.set(Calendar.MONTH, 12); 1900 DateFormat df = new SimpleDateFormat("yyyy/MM/dd", Locale.US); 1901 String expected = "2003/01/31"; 1902 String s = df.format(cal.getTime()); 1903 if (!expected.equals(s)) { 1904 errln("expected: " + expected + ", got: " + s); 1905 } 1906 } 1907 1908 /** 1909 * 4080631: Calendar.hashCode is amazingly bad 1910 */ Test4080631()1911 public void Test4080631() { 1912 Calendar cal = Calendar.getInstance(); 1913 int h1 = cal.hashCode(); 1914 cal.add(cal.SECOND, +1); 1915 int h2 = cal.hashCode(); 1916 Calendar cal2 = (Calendar) cal.clone(); 1917 cal.add(cal.MILLISECOND, +1); 1918 int h3 = cal.hashCode(); 1919 logln("hash code: h1="+h1+", h2="+h2+", h3="+h3); 1920 if (h1 == h2 || h1 == h3 || h2 == h3) { 1921 errln("hash code is poor: hashCode="+h1); 1922 } 1923 h2 = cal2.hashCode(); 1924 cal.add(cal.MILLISECOND, -1); 1925 int h4 = cal.hashCode(); 1926 logln("hash code: h2="+h2+", h4="+h4); 1927 if (cal.equals(cal2) && h2 != h4) { 1928 errln("broken hash code: h2="+h2+", h4="+h4); 1929 } 1930 int x = cal.getFirstDayOfWeek() + 3; 1931 if (x > cal.SATURDAY) { 1932 x -= 7; 1933 } 1934 cal.setFirstDayOfWeek(x); 1935 int h5 = cal.hashCode(); 1936 logln("hash code: h4="+h4+", h5="+h5); 1937 if (h4 == h5) { 1938 errln("has code is poor with first day of week param: hashCode="+h4); 1939 } 1940 } 1941 1942 /** 1943 * 4125161: RFE: GregorianCalendar needs more era names (BCE and CE) 1944 */ 1945 /* 1946 public void Test4125161() throws Exception { 1947 Class gc = GregorianCalendar.class; 1948 Field f; 1949 int mod; 1950 f = gc.getDeclaredField("BCE"); 1951 mod = f.getModifiers(); 1952 if (!Modifier.isStatic(mod) || !Modifier.isFinal(mod)) { 1953 errln("BCE: wrong modifiers: " + mod); 1954 } 1955 f = gc.getDeclaredField("CE"); 1956 mod = f.getModifiers(); 1957 if (!Modifier.isStatic(mod) || !Modifier.isFinal(mod)) { 1958 errln("CE: wrong modifiers: " + mod); 1959 } 1960 if (GregorianCalendar.BCE != GregorianCalendar.BC 1961 || GregorianCalendar.CE != GregorianCalendar.AD) { 1962 errln("Wrong BCE and/or CE values"); 1963 } 1964 } 1965 */ 1966 1967 /** 1968 * 4167995: GregorianCalendar.setGregorianChange() not to spec 1969 */ Test4167995()1970 public void Test4167995() { 1971 Koyomi gc = new Koyomi(TimeZone.getTimeZone("GMT")); 1972 logln("Hybrid: min date"); 1973 gc.setTime(new Date(Long.MIN_VALUE)); 1974 if (!gc.checkDate(292269055, gc.DECEMBER, 2, gc.SUNDAY) 1975 || !gc.checkFieldValue(gc.ERA, gc.BC)) { 1976 errln(gc.getMessage()); 1977 } 1978 logln("Hybrid: max date"); 1979 gc.setTime(new Date(Long.MAX_VALUE)); 1980 if (!gc.checkDate(292278994, gc.AUGUST, 17, gc.SUNDAY) 1981 || !gc.checkFieldValue(gc.ERA, gc.AD)) { 1982 errln(gc.getMessage()); 1983 } 1984 1985 gc.setGregorianChange(new Date(Long.MIN_VALUE)); 1986 logln("Gregorian: min date"); 1987 gc.setTime(new Date(Long.MIN_VALUE)); 1988 if (!gc.checkDate(292275056, gc.MAY, 16, gc.SUNDAY) 1989 || !gc.checkFieldValue(gc.ERA, gc.BC)) { 1990 errln(gc.getMessage()); 1991 } 1992 logln("Gregorian: max date"); 1993 gc.setTime(new Date(Long.MAX_VALUE)); 1994 if (!gc.checkDate(292278994, gc.AUGUST, 17, gc.SUNDAY) 1995 || !gc.checkFieldValue(gc.ERA, gc.AD)) { 1996 errln(gc.getMessage()); 1997 } 1998 1999 gc.setGregorianChange(new Date(Long.MAX_VALUE)); 2000 logln("Julian: min date"); 2001 gc.setTime(new Date(Long.MIN_VALUE)); 2002 if (!gc.checkDate(292269055, gc.DECEMBER, 2, gc.SUNDAY) 2003 || !gc.checkFieldValue(gc.ERA, gc.BC)) { 2004 errln(gc.getMessage()); 2005 } 2006 logln("Julian: max date"); 2007 gc.setTime(new Date(Long.MAX_VALUE)); 2008 if (!gc.checkDate(292272993, gc.JANUARY, 4, gc.SUNDAY) 2009 || !gc.checkFieldValue(gc.ERA, gc.AD)) { 2010 errln(gc.getMessage()); 2011 } 2012 } 2013 2014 /** 2015 * 4340146: Calendar.equals modifies state 2016 */ Test4340146()2017 public void Test4340146() { 2018 Koyomi cal = new Koyomi(); 2019 cal.clear(); 2020 cal.set(2003, cal.OCTOBER, 32); 2021 cal.equals(new Koyomi()); 2022 if (!cal.checkInternalDate(2003, cal.OCTOBER, 32)) { 2023 errln(cal.getMessage()); 2024 } 2025 new Koyomi().equals(cal); 2026 if (!cal.checkInternalDate(2003, cal.OCTOBER, 32)) { 2027 errln(cal.getMessage()); 2028 } 2029 } 2030 2031 /** 2032 * 4639407: GregorianCalendar doesn't work in non-lenient due to timezone bounds checking 2033 */ Test4639407()2034 public void Test4639407() { 2035 // The following operations in non-lenient mode shouldn't 2036 // throw IllegalArgumentException. 2037 Koyomi cal = new Koyomi(TimeZone.getTimeZone("Pacific/Kiritimati")); 2038 cal.setLenient(false); 2039 cal.set(2003, cal.OCTOBER, 10); 2040 cal.getTime(); 2041 cal.setTimeZone(TimeZone.getTimeZone("Pacific/Tongatapu")); 2042 cal.set(2003, cal.OCTOBER, 10); 2043 cal.getTime(); 2044 } 2045 2046 /** 2047 * 4652815: rolling week-of-year back hundreds of weeks changes year 2048 */ Test4652815()2049 public void Test4652815() { 2050 Koyomi cal = new Koyomi(Locale.US); 2051 testRoll(cal, 2003, cal.SEPTEMBER, 29); 2052 testRoll(cal, 2003, cal.DECEMBER, 24); 2053 testRoll(cal, 1582, cal.DECEMBER, 19); 2054 testRoll(cal, 1582, cal.DECEMBER, 20); 2055 } 2056 testRoll(Koyomi cal, int year, int month, int dayOfMonth)2057 private void testRoll(Koyomi cal, int year, int month, int dayOfMonth) { 2058 cal.clear(); 2059 cal.set(year, month, dayOfMonth); 2060 cal.getTime(); // normalize fields 2061 logln("Roll backwards from " + cal.toDateString()); 2062 for (int i = 0; i < 1000; i++) { 2063 cal.roll(cal.WEEK_OF_YEAR, -i); 2064 if (!cal.checkFieldValue(cal.YEAR, year)) { 2065 errln(cal.getMessage()); 2066 } 2067 } 2068 logln("Roll forewards from " + cal.toDateString()); 2069 for (int i = 0; i < 1000; i++) { 2070 cal.roll(cal.WEEK_OF_YEAR, +i); 2071 if (!cal.checkFieldValue(cal.YEAR, year)) { 2072 errln(cal.getMessage()); 2073 } 2074 } 2075 } 2076 2077 /** 2078 * 4652830: GregorianCalendar roll behaves unexpectedly for dates in BC era 2079 */ Test4652830()2080 public void Test4652830() { 2081 Koyomi cal = new Koyomi(Locale.US); 2082 cal.clear(); 2083 logln("BCE 9-2-28 (leap year) roll DAY_OF_MONTH++ twice"); 2084 cal.set(cal.ERA, cal.BC); 2085 cal.set(9, cal.FEBRUARY, 28); 2086 if (cal.getActualMaximum(cal.DAY_OF_YEAR) != 366) { 2087 errln(" wrong actual max of DAY_OF_YEAR: got " 2088 + cal.getActualMaximum(cal.DAY_OF_YEAR) + " expected " + 366); 2089 } 2090 cal.roll(cal.DAY_OF_MONTH, +1); 2091 if (!cal.checkFieldValue(cal.ERA, cal.BC) 2092 || !cal.checkDate(9, cal.FEBRUARY, 29)) { 2093 errln(cal.getMessage()); 2094 } 2095 cal.roll(cal.DAY_OF_MONTH, +1); 2096 if (!cal.checkFieldValue(cal.ERA, cal.BC) 2097 || !cal.checkDate(9, cal.FEBRUARY, 1)) { 2098 errln(cal.getMessage()); 2099 } 2100 } 2101 2102 /** 2103 * 4740554: GregorianCalendar.getActualMaximum is inconsistent with normalization 2104 */ Test4740554()2105 public void Test4740554() { 2106 logln("1999/(Feb+12)/1 should be normalized to 2000/Feb/1 for getActualMaximum"); 2107 Koyomi cal = new Koyomi(Locale.US); 2108 cal.clear(); 2109 cal.set(1999, cal.FEBRUARY + 12, 1); 2110 if (!cal.checkActualMaximum(cal.DAY_OF_YEAR, 366)) { 2111 errln(cal.getMessage()); 2112 } 2113 if (!cal.checkActualMaximum(cal.DAY_OF_MONTH, 29)) { 2114 errln(cal.getMessage()); 2115 } 2116 } 2117 2118 /** 2119 * 4936355: GregorianCalendar causes overflow/underflow with time of day calculation 2120 */ Test4936355()2121 public void Test4936355() { 2122 Koyomi cal = new Koyomi(TimeZone.getTimeZone("GMT")); 2123 cal.clear(); 2124 cal.set(1970, cal.JANUARY, 1); 2125 checkTimeCalculation(cal, cal.HOUR_OF_DAY, Integer.MAX_VALUE, 2126 (long)Integer.MAX_VALUE * 60 * 60 * 1000); 2127 2128 cal.clear(); 2129 cal.set(1970, cal.JANUARY, 1); 2130 checkTimeCalculation(cal, cal.HOUR, Integer.MAX_VALUE, 2131 (long)Integer.MAX_VALUE * 60 * 60 * 1000); 2132 2133 cal.clear(); 2134 cal.set(1970, cal.JANUARY, 1); 2135 checkTimeCalculation(cal, cal.MINUTE, Integer.MAX_VALUE, 2136 (long)Integer.MAX_VALUE * 60 * 1000); 2137 2138 cal.clear(); 2139 // Make sure to use Gregorian dates (before and after the 2140 // set() call) for testing 2141 cal.set(250000, cal.JANUARY, 1); 2142 checkTimeCalculation(cal, cal.HOUR_OF_DAY, Integer.MIN_VALUE, 2143 (long)Integer.MIN_VALUE * 60 * 60 * 1000); 2144 2145 cal.clear(); 2146 cal.set(250000, cal.JANUARY, 1); 2147 checkTimeCalculation(cal, cal.HOUR, Integer.MIN_VALUE, 2148 (long)Integer.MIN_VALUE * 60 * 60 * 1000); 2149 2150 cal.clear(); 2151 cal.set(250000, cal.JANUARY, 1); 2152 checkTimeCalculation(cal, cal.MINUTE, Integer.MIN_VALUE, 2153 (long)Integer.MIN_VALUE * 60 * 1000); 2154 } 2155 checkTimeCalculation(Koyomi cal, int field, int value, long expectedDelta)2156 private void checkTimeCalculation(Koyomi cal, int field, int value, long expectedDelta) { 2157 long time = cal.getTimeInMillis(); 2158 cal.set(field, value); 2159 long time2 = cal.getTimeInMillis(); 2160 if ((time + expectedDelta) != time2) { 2161 String s = value == Integer.MAX_VALUE ? "Integer.MAX_VALUE" : "Integer.MIN_VALUE"; 2162 errln("set(" + Koyomi.getFieldName(field) + ", " + s + ") failed." + " got " + time2 2163 + ", expected " + (time+expectedDelta)); 2164 } 2165 } 2166 2167 /** 2168 * 4722650: Calendar.equals can throw an exception in non-lenient 2169 * (piggy-back tests for compareTo() which is new in 1.5) 2170 */ Test4722650()2171 public void Test4722650() { 2172 Calendar cal1 = new GregorianCalendar(); 2173 cal1.clear(); 2174 Calendar cal2 = new GregorianCalendar(); 2175 cal2.clear(); 2176 cal2.setLenient(false); 2177 2178 cal1.set(2003, Calendar.OCTOBER, 31); 2179 cal2.set(2003, Calendar.OCTOBER, 31); 2180 try { 2181 if (cal1.equals(cal2)) { 2182 errln("lenient and non-lenient shouldn't be equal. (2003/10/31)"); 2183 } 2184 if (cal1.compareTo(cal2) != 0) { 2185 errln("cal1 and cal2 should represent the same time. (2003/10/31)"); 2186 } 2187 } catch (IllegalArgumentException e) { 2188 errln("equals threw IllegalArugumentException with non-lenient"); 2189 } 2190 2191 cal1.set(2003, Calendar.OCTOBER, 32); 2192 cal2.set(2003, Calendar.OCTOBER, 32); 2193 try { 2194 if (cal1.equals(cal2)) { 2195 errln("lenient and non-lenient shouldn't be equal. (2003/10/32)"); 2196 } 2197 if (cal1.compareTo(cal2) != 0) { 2198 errln("cal1 and cal2 should represent the same time. (2003/10/32)"); 2199 } 2200 } catch (IllegalArgumentException e) { 2201 errln("equals threw IllegalArugumentException with non-lenient"); 2202 } 2203 2204 cal1 = Calendar.getInstance(new Locale("th", "TH")); 2205 cal1.setTimeInMillis(0L); 2206 cal2 = Calendar.getInstance(Locale.US); 2207 cal2.setTimeInMillis(0L); 2208 if (cal1.equals(cal2)) { 2209 errln("Buddhist.equals(Gregorian) shouldn't be true. (millis=0)"); 2210 } 2211 if (cal1.compareTo(cal2) != 0) { 2212 errln("cal1 (Buddhist) and cal2 (Gregorian) should represent the same time. (millis=0)"); 2213 } 2214 } 2215 2216 /** 2217 * 4738710: API: Calendar comparison methods should be improved 2218 */ Test4738710()2219 public void Test4738710() { 2220 Calendar cal0 = new GregorianCalendar(2003, Calendar.SEPTEMBER, 30); 2221 Comparable<Calendar> cal1 = new GregorianCalendar(2003, Calendar.OCTOBER, 1); 2222 Calendar cal2 = new GregorianCalendar(2003, Calendar.OCTOBER, 2); 2223 if (!(cal1.compareTo(cal0) > 0)) { 2224 errln("!(cal1 > cal0)"); 2225 } 2226 if (!(cal1.compareTo(cal2) < 0)) { 2227 errln("!(cal1 < cal2)"); 2228 } 2229 if (cal1.compareTo(new GregorianCalendar(2003, Calendar.OCTOBER, 1)) != 0) { 2230 errln("cal1 != new GregorianCalendar(2003, Calendar.OCTOBER, 1)"); 2231 } 2232 2233 if (cal0.after(cal2)) { 2234 errln("cal0 shouldn't be after cal2"); 2235 } 2236 if (cal2.before(cal0)) { 2237 errln("cal2 shouldn't be before cal0"); 2238 } 2239 2240 if (cal0.after(new Integer(0))) { 2241 errln("cal0.after() returned true with an Integer."); 2242 } 2243 if (cal0.before(new Integer(0))) { 2244 errln("cal0.before() returned true with an Integer."); 2245 } 2246 if (cal0.after(null)) { 2247 errln("cal0.after() returned true with null."); 2248 } 2249 if (cal0.before(null)) { 2250 errln("cal0.before() returned true with null."); 2251 } 2252 } 2253 2254 /** 2255 * 4633646: Setting WEEK_OF_MONTH to 1 results in incorrect date 2256 */ Test4633646()2257 public void Test4633646() { 2258 Koyomi cal = new Koyomi(Locale.US); 2259 cal.setTime(new Date(2002-1900, 1-1, 28)); 2260 sub4633646(cal); 2261 2262 cal.setLenient(false); 2263 cal.setTime(new Date(2002-1900, 1-1, 28)); 2264 sub4633646(cal); 2265 2266 cal = new Koyomi(Locale.US); 2267 cal.clear(); 2268 cal.set(2002, cal.JANUARY, 28); 2269 sub4633646(cal); 2270 2271 cal.clear(); 2272 cal.setLenient(false); 2273 cal.set(2002, cal.JANUARY, 28); 2274 sub4633646(cal); 2275 } 2276 sub4633646(Koyomi cal)2277 void sub4633646(Koyomi cal) { 2278 cal.getTime(); 2279 cal.set(cal.WEEK_OF_MONTH, 1); 2280 if (cal.isLenient()) { 2281 if (!cal.checkDate(2001, cal.DECEMBER, 31)) { 2282 errln(cal.getMessage()); 2283 } 2284 if (!cal.checkFieldValue(cal.WEEK_OF_MONTH, 6)) { 2285 errln(cal.getMessage()); 2286 } 2287 } else { 2288 try { 2289 Date d = cal.getTime(); 2290 errln("didn't throw IllegalArgumentException in non-lenient"); 2291 } catch (IllegalArgumentException e) { 2292 } 2293 } 2294 } 2295 2296 /** 2297 * 4846659: Calendar: Both set() and roll() don't work for AM_PM time field 2298 * (Partially fixed only roll as of 1.5) 2299 */ Test4846659()2300 public void Test4846659() { 2301 Koyomi cal = new Koyomi(); 2302 cal.clear(); 2303 cal.set(2003, cal.OCTOBER, 31, 10, 30, 30); 2304 cal.getTime(); 2305 // Test roll() 2306 cal.roll(cal.AM_PM, +1); // should turn to PM 2307 if (!cal.checkFieldValue(cal.HOUR_OF_DAY, 10+12)) { 2308 errln("roll: AM_PM didn't change to PM"); 2309 } 2310 2311 cal.clear(); 2312 cal.set(2003, cal.OCTOBER, 31, 10, 30, 30); 2313 cal.getTime(); 2314 // Test set() 2315 cal.set(cal.AM_PM, cal.PM); // should turn to PM 2316 if (!cal.checkFieldValue(cal.HOUR_OF_DAY, 10+12)) { 2317 errln("set: AM_PM didn't change to PM"); 2318 } 2319 2320 cal.clear(); 2321 cal.set(2003, cal.OCTOBER, 31, 10, 30, 30); 2322 cal.getTime(); 2323 cal.set(cal.AM_PM, cal.PM); 2324 cal.set(cal.HOUR, 9); 2325 if (!cal.checkFieldValue(cal.HOUR_OF_DAY, 9+12)) { 2326 errln("set: both AM_PM and HOUT didn't change to PM"); 2327 } 2328 } 2329 2330 /** 2331 * 4822110: GregorianCalendar.get() returns an incorrect date after setFirstDayOfWeek() 2332 */ Test4822110()2333 public void Test4822110() { 2334 Koyomi cal = new Koyomi(Locale.US); 2335 // June 2003 2336 // S M Tu W Th F S 2337 // 1 2 3 4 5 6 7 2338 // 8 9 10 11 12 13 14 2339 // 15 16 17 18 19 20 21 2340 // 22 23 24 25 26 27 28 2341 // 29 30 2342 cal.clear(); 2343 // 6/1 to 6/7 should be the 1st week of June. 2344 cal.set(2003, cal.JUNE, 2); 2345 cal.getTime(); // Let cal calculate time. 2346 cal.setFirstDayOfWeek(cal.MONDAY); 2347 // Now 6/2 to 6/8 should be the 2nd week of June. Sunday of 2348 // that week is 6/8. 2349 logln("1: " +cal.get(cal.WEEK_OF_MONTH)+", "+cal.get(cal.DAY_OF_MONTH)); 2350 cal.set(cal.DAY_OF_WEEK, cal.SUNDAY); 2351 logln("1st Sunday of June 2003 with FirstDayOfWeek=MONDAY"); 2352 if (!cal.checkDate(2003, cal.JUNE, 8)) { 2353 errln(cal.getMessage()); 2354 } 2355 } 2356 2357 /** 2358 * 4973919: Inconsistent GregorianCalendar hashCode before and after serialization 2359 */ Test4966499()2360 public void Test4966499() throws Exception { 2361 GregorianCalendar date1 = new GregorianCalendar(2004, Calendar.JANUARY, 7); 2362 2363 // Serialize date1 2364 ByteArrayOutputStream baos = new ByteArrayOutputStream(); 2365 ObjectOutputStream oos = new ObjectOutputStream(baos); 2366 oos.writeObject(date1); 2367 2368 byte[] buffer = baos.toByteArray(); 2369 2370 // Deserialize it 2371 ByteArrayInputStream bais = new ByteArrayInputStream(buffer); 2372 ObjectInputStream ois = new ObjectInputStream(bais); 2373 GregorianCalendar date2 = (GregorianCalendar)ois.readObject(); 2374 2375 if (!date1.equals(date2)) { 2376 errln("date1.equals(date2) != true"); 2377 } 2378 if (date1.hashCode() != date2.hashCode()) { 2379 errln("inconsistent hashCode() value (before=0x" 2380 +Integer.toHexString(date1.hashCode())+ 2381 ", after=0x"+Integer.toHexString(date2.hashCode())+")"); 2382 } 2383 } 2384 2385 /** 2386 * 4980088: GregorianCalendar.getActualMaximum doesn't throw exception 2387 */ Test4980088()2388 public void Test4980088() { 2389 GregorianCalendar cal = new GregorianCalendar(); 2390 try { 2391 int x = cal.getMaximum(100); 2392 errln("getMaximum(100) didn't throw an exception."); 2393 } catch (IndexOutOfBoundsException e) { 2394 logln("getMaximum: " + e.getClass().getName() + ": " + e.getMessage()); 2395 } 2396 2397 try { 2398 int x = cal.getLeastMaximum(100); 2399 errln("getLeastMaximum(100) didn't throw an exception."); 2400 } catch (IndexOutOfBoundsException e) { 2401 logln("getLeastMaximum: " + e.getClass().getName() + ": " + e.getMessage()); 2402 } 2403 2404 try { 2405 int x = cal.getActualMaximum(100); 2406 errln("getActualMaximum(100) didn't throw an exception."); 2407 } catch (IndexOutOfBoundsException e) { 2408 logln("getActualMaximum: " + e.getClass().getName() + ": " + e.getMessage()); 2409 } 2410 2411 try { 2412 int x = cal.getMinimum(100); 2413 errln("getMinimum(100) didn't throw an exception."); 2414 } catch (IndexOutOfBoundsException e) { 2415 logln("getMinimum: " + e.getClass().getName() + ": " + e.getMessage()); 2416 } 2417 2418 try { 2419 int x = cal.getGreatestMinimum(100); 2420 errln("getGreatestMinimum(100) didn't throw an exception."); 2421 } catch (IndexOutOfBoundsException e) { 2422 logln("getGreatestMinimum: " + e.getClass().getName() + ": " + e.getMessage()); 2423 } 2424 2425 try { 2426 int x = cal.getActualMinimum(100); 2427 errln("getActualMinimum(100) didn't throw an exception."); 2428 } catch (IndexOutOfBoundsException e) { 2429 logln("getActualMinimum: " + e.getClass().getName() + ": " + e.getMessage()); 2430 } 2431 } 2432 2433 /** 2434 * 4965624: GregorianCalendar.isLeapYear(1000) returns incorrect value 2435 */ Test4965624()2436 public void Test4965624() { 2437 // 5013094: This test case needs to use "GMT" to specify 2438 // Gregorian cutover dates. 2439 TimeZone savedZone = TimeZone.getDefault(); 2440 TimeZone.setDefault(TimeZone.getTimeZone("GMT")); 2441 try { 2442 Map<Date, Boolean> data = new HashMap<Date, Boolean>(); 2443 data.put(getGregorianDate(999, Calendar.OCTOBER, 1), Boolean.FALSE); 2444 data.put(getGregorianDate(1000, Calendar.JANUARY, 1), Boolean.FALSE); 2445 data.put(getGregorianDate(1000, Calendar.FEBRUARY, 1), Boolean.FALSE); 2446 data.put(getGregorianDate(1000, Calendar.FEBRUARY, 28), Boolean.FALSE); 2447 data.put(getGregorianDate(1000, Calendar.MARCH, 1), Boolean.TRUE); 2448 data.put(getGregorianDate(1001, Calendar.JANUARY, 1), Boolean.TRUE); 2449 data.put(getGregorianDate(1001, Calendar.JANUARY, 6), Boolean.TRUE); 2450 data.put(getGregorianDate(1001, Calendar.MARCH, 1), Boolean.TRUE); 2451 2452 Iterator<Date> itr = data.keySet().iterator(); 2453 while (itr.hasNext()) { 2454 Date d = itr.next(); 2455 boolean expected = data.get(d).booleanValue(); 2456 GregorianCalendar cal = new GregorianCalendar(); 2457 cal.setGregorianChange(d); 2458 if (cal.isLeapYear(1000) != expected) { 2459 errln("isLeapYear(1000) returned " + cal.isLeapYear(1000) + 2460 " with cutover date (Julian) " + d); 2461 } 2462 } 2463 } 2464 finally { 2465 TimeZone.setDefault(savedZone); 2466 } 2467 } 2468 2469 // Note that we can't use Date to produce Gregorian calendar dates 2470 // before the default cutover date. getGregorianDate(int year, int month, int dayOfMonth)2471 static Date getGregorianDate(int year, int month, int dayOfMonth) { 2472 GregorianCalendar g = new GregorianCalendar(); 2473 // Make g a pure Gregorian calendar 2474 g.setGregorianChange(new Date(Long.MIN_VALUE)); 2475 g.clear(); 2476 g.set(year, month, dayOfMonth); 2477 return g.getTime(); 2478 } 2479 2480 /** 2481 * 5006864: Define the minimum value of DAY_OF_WEEK_IN_MONTH as 1 2482 */ Test5006864()2483 public void Test5006864() { 2484 GregorianCalendar cal = new GregorianCalendar(); 2485 int min = cal.getMinimum(cal.DAY_OF_WEEK_IN_MONTH); 2486 if (min != 1) { 2487 errln("GregorianCalendar.getMinimum(DAY_OF_WEEK_IN_MONTH) returned " 2488 + min + ", expected 1."); 2489 } 2490 min = cal.getGreatestMinimum(cal.DAY_OF_WEEK_IN_MONTH); 2491 if (min != 1) { 2492 errln("GregorianCalendar.getGreatestMinimum(DAY_OF_WEEK_IN_MONTH) returned " 2493 + min + ", expected 1."); 2494 } 2495 } 2496 } 2497