1 /*
   2  * Copyright (c) 2012, 2013, 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  * This file is available under and governed by the GNU General Public
  26  * License version 2 only, as published by the Free Software Foundation.
  27  * However, the following notice accompanied the original version of this
  28  * file:
  29  *
  30  * Copyright (c) 2007-2012, Stephen Colebourne & Michael Nascimento Santos
  31  *
  32  * All rights reserved.
  33  *
  34  * Redistribution and use in source and binary forms, with or without
  35  * modification, are permitted provided that the following conditions are met:
  36  *
  37  *  * Redistributions of source code must retain the above copyright notice,
  38  *    this list of conditions and the following disclaimer.
  39  *
  40  *  * Redistributions in binary form must reproduce the above copyright notice,
  41  *    this list of conditions and the following disclaimer in the documentation
  42  *    and/or other materials provided with the distribution.
  43  *
  44  *  * Neither the name of JSR-310 nor the names of its contributors
  45  *    may be used to endorse or promote products derived from this software
  46  *    without specific prior written permission.
  47  *
  48  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  49  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  50  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  51  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  52  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  53  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  54  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  55  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
  56  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  57  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  58  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  59  */
  60 package tck.java.time;
  61 
  62 import static java.time.temporal.ChronoUnit.DAYS;
  63 import static java.time.temporal.ChronoUnit.HALF_DAYS;
  64 import static java.time.temporal.ChronoUnit.HOURS;
  65 import static java.time.temporal.ChronoUnit.MICROS;
  66 import static java.time.temporal.ChronoUnit.MILLIS;
  67 import static java.time.temporal.ChronoUnit.MINUTES;
  68 import static java.time.temporal.ChronoUnit.NANOS;
  69 import static java.time.temporal.ChronoUnit.SECONDS;
  70 import static java.time.temporal.ChronoUnit.WEEKS;
  71 import static org.testng.Assert.assertEquals;
  72 import static org.testng.Assert.assertTrue;
  73 import static org.testng.Assert.fail;
  74 
  75 import java.io.ByteArrayOutputStream;
  76 import java.io.DataOutputStream;
  77 import java.time.DateTimeException;
  78 import java.time.Duration;
  79 import java.time.Instant;
  80 import java.time.LocalDateTime;
  81 import java.time.LocalTime;
  82 import java.time.Period;
  83 import java.time.ZoneOffset;
  84 import java.time.ZonedDateTime;
  85 import java.time.format.DateTimeParseException;
  86 import java.time.temporal.ChronoUnit;
  87 import java.time.temporal.Temporal;
  88 import java.time.temporal.TemporalAmount;
  89 import java.time.temporal.TemporalUnit;
  90 import java.util.ArrayList;
  91 import java.util.Collections;
  92 import java.util.List;
  93 import java.util.Locale;
  94 
  95 import org.testng.annotations.DataProvider;
  96 import org.testng.annotations.Test;
  97 
  98 /**
  99  * Test Duration.
 100  */
 101 @Test
 102 public class TCKDuration extends AbstractTCKTest {
 103 
 104     private static final long CYCLE_SECS = 146097L * 86400L;
 105 
 106     //-----------------------------------------------------------------------
 107     @Test
 108     public void test_serialization() throws Exception {
 109         assertSerializable(Duration.ofHours(5));
 110         assertSerializable(Duration.ofHours(0));
 111         assertSerializable(Duration.ofHours(-5));
 112     }
 113 
 114     @Test
 115     public void test_serialization_format() throws Exception {
 116         ByteArrayOutputStream baos = new ByteArrayOutputStream();
 117         try (DataOutputStream dos = new DataOutputStream(baos) ) {
 118             dos.writeByte(1);
 119             dos.writeLong(654321);
 120             dos.writeInt(123456789);
 121         }
 122         byte[] bytes = baos.toByteArray();
 123         assertSerializedBySer(Duration.ofSeconds(654321, 123456789), bytes);
 124     }
 125 
 126     //-----------------------------------------------------------------------
 127     // constants
 128     //-----------------------------------------------------------------------
 129     @Test
 130     public void test_zero() {
 131         assertEquals(Duration.ZERO.getSeconds(), 0L);
 132         assertEquals(Duration.ZERO.getNano(), 0);
 133     }
 134 
 135     //-----------------------------------------------------------------------
 136     // ofSeconds(long)
 137     //-----------------------------------------------------------------------
 138     @Test
 139     public void factory_seconds_long() {
 140         for (long i = -2; i <= 2; i++) {
 141             Duration t = Duration.ofSeconds(i);
 142             assertEquals(t.getSeconds(), i);
 143             assertEquals(t.getNano(), 0);
 144         }
 145     }
 146 
 147     //-----------------------------------------------------------------------
 148     // ofSeconds(long,long)
 149     //-----------------------------------------------------------------------
 150     @Test
 151     public void factory_seconds_long_long() {
 152         for (long i = -2; i <= 2; i++) {
 153             for (int j = 0; j < 10; j++) {
 154                 Duration t = Duration.ofSeconds(i, j);
 155                 assertEquals(t.getSeconds(), i);
 156                 assertEquals(t.getNano(), j);
 157             }
 158             for (int j = -10; j < 0; j++) {
 159                 Duration t = Duration.ofSeconds(i, j);
 160                 assertEquals(t.getSeconds(), i - 1);
 161                 assertEquals(t.getNano(), j + 1000000000);
 162             }
 163             for (int j = 999999990; j < 1000000000; j++) {
 164                 Duration t = Duration.ofSeconds(i, j);
 165                 assertEquals(t.getSeconds(), i);
 166                 assertEquals(t.getNano(), j);
 167             }
 168         }
 169     }
 170 
 171     @Test
 172     public void factory_seconds_long_long_nanosNegativeAdjusted() {
 173         Duration test = Duration.ofSeconds(2L, -1);
 174         assertEquals(test.getSeconds(), 1);
 175         assertEquals(test.getNano(), 999999999);
 176     }
 177 
 178     @Test(expectedExceptions=ArithmeticException.class)
 179     public void factory_seconds_long_long_tooBig() {
 180         Duration.ofSeconds(Long.MAX_VALUE, 1000000000);
 181     }
 182 
 183     //-----------------------------------------------------------------------
 184     // ofMillis(long)
 185     //-----------------------------------------------------------------------
 186     @DataProvider(name="MillisDurationNoNanos")
 187     Object[][] provider_factory_millis_long() {
 188         return new Object[][] {
 189             {0, 0, 0},
 190             {1, 0, 1000000},
 191             {2, 0, 2000000},
 192             {999, 0, 999000000},
 193             {1000, 1, 0},
 194             {1001, 1, 1000000},
 195             {-1, -1, 999000000},
 196             {-2, -1, 998000000},
 197             {-999, -1, 1000000},
 198             {-1000, -1, 0},
 199             {-1001, -2, 999000000},
 200         };
 201     }
 202 
 203     @Test(dataProvider="MillisDurationNoNanos")
 204     public void factory_millis_long(long millis, long expectedSeconds, int expectedNanoOfSecond) {
 205         Duration test = Duration.ofMillis(millis);
 206         assertEquals(test.getSeconds(), expectedSeconds);
 207         assertEquals(test.getNano(), expectedNanoOfSecond);
 208     }
 209 
 210     //-----------------------------------------------------------------------
 211     // ofNanos(long)
 212     //-----------------------------------------------------------------------
 213     @Test
 214     public void factory_nanos_nanos() {
 215         Duration test = Duration.ofNanos(1);
 216         assertEquals(test.getSeconds(), 0);
 217         assertEquals(test.getNano(), 1);
 218     }
 219 
 220     @Test
 221     public void factory_nanos_nanosSecs() {
 222         Duration test = Duration.ofNanos(1000000002);
 223         assertEquals(test.getSeconds(), 1);
 224         assertEquals(test.getNano(), 2);
 225     }
 226 
 227     @Test
 228     public void factory_nanos_negative() {
 229         Duration test = Duration.ofNanos(-2000000001);
 230         assertEquals(test.getSeconds(), -3);
 231         assertEquals(test.getNano(), 999999999);
 232     }
 233 
 234     @Test
 235     public void factory_nanos_max() {
 236         Duration test = Duration.ofNanos(Long.MAX_VALUE);
 237         assertEquals(test.getSeconds(), Long.MAX_VALUE / 1000000000);
 238         assertEquals(test.getNano(), Long.MAX_VALUE % 1000000000);
 239     }
 240 
 241     @Test
 242     public void factory_nanos_min() {
 243         Duration test = Duration.ofNanos(Long.MIN_VALUE);
 244         assertEquals(test.getSeconds(), Long.MIN_VALUE / 1000000000 - 1);
 245         assertEquals(test.getNano(), Long.MIN_VALUE % 1000000000 + 1000000000);
 246     }
 247 
 248     //-----------------------------------------------------------------------
 249     // ofMinutes()
 250     //-----------------------------------------------------------------------
 251     @Test
 252     public void factory_minutes() {
 253         Duration test = Duration.ofMinutes(2);
 254         assertEquals(test.getSeconds(), 120);
 255         assertEquals(test.getNano(), 0);
 256     }
 257 
 258     @Test
 259     public void factory_minutes_max() {
 260         Duration test = Duration.ofMinutes(Long.MAX_VALUE / 60);
 261         assertEquals(test.getSeconds(), (Long.MAX_VALUE / 60) * 60);
 262         assertEquals(test.getNano(), 0);
 263     }
 264 
 265     @Test
 266     public void factory_minutes_min() {
 267         Duration test = Duration.ofMinutes(Long.MIN_VALUE / 60);
 268         assertEquals(test.getSeconds(), (Long.MIN_VALUE / 60) * 60);
 269         assertEquals(test.getNano(), 0);
 270     }
 271 
 272     @Test(expectedExceptions=ArithmeticException.class)
 273     public void factory_minutes_tooBig() {
 274         Duration.ofMinutes(Long.MAX_VALUE / 60 + 1);
 275     }
 276 
 277     @Test(expectedExceptions=ArithmeticException.class)
 278     public void factory_minutes_tooSmall() {
 279         Duration.ofMinutes(Long.MIN_VALUE / 60 - 1);
 280     }
 281 
 282     //-----------------------------------------------------------------------
 283     // ofHours()
 284     //-----------------------------------------------------------------------
 285     @Test
 286     public void factory_hours() {
 287         Duration test = Duration.ofHours(2);
 288         assertEquals(test.getSeconds(), 2 * 3600);
 289         assertEquals(test.getNano(), 0);
 290     }
 291 
 292     @Test
 293     public void factory_hours_max() {
 294         Duration test = Duration.ofHours(Long.MAX_VALUE / 3600);
 295         assertEquals(test.getSeconds(), (Long.MAX_VALUE / 3600) * 3600);
 296         assertEquals(test.getNano(), 0);
 297     }
 298 
 299     @Test
 300     public void factory_hours_min() {
 301         Duration test = Duration.ofHours(Long.MIN_VALUE / 3600);
 302         assertEquals(test.getSeconds(), (Long.MIN_VALUE / 3600) * 3600);
 303         assertEquals(test.getNano(), 0);
 304     }
 305 
 306     @Test(expectedExceptions=ArithmeticException.class)
 307     public void factory_hours_tooBig() {
 308         Duration.ofHours(Long.MAX_VALUE / 3600 + 1);
 309     }
 310 
 311     @Test(expectedExceptions=ArithmeticException.class)
 312     public void factory_hours_tooSmall() {
 313         Duration.ofHours(Long.MIN_VALUE / 3600 - 1);
 314     }
 315 
 316     //-----------------------------------------------------------------------
 317     // ofDays()
 318     //-----------------------------------------------------------------------
 319     @Test
 320     public void factory_days() {
 321         Duration test = Duration.ofDays(2);
 322         assertEquals(test.getSeconds(), 2 * 86400);
 323         assertEquals(test.getNano(), 0);
 324     }
 325 
 326     @Test
 327     public void factory_days_max() {
 328         Duration test = Duration.ofDays(Long.MAX_VALUE / 86400);
 329         assertEquals(test.getSeconds(), (Long.MAX_VALUE / 86400) * 86400);
 330         assertEquals(test.getNano(), 0);
 331     }
 332 
 333     @Test
 334     public void factory_days_min() {
 335         Duration test = Duration.ofDays(Long.MIN_VALUE / 86400);
 336         assertEquals(test.getSeconds(), (Long.MIN_VALUE / 86400) * 86400);
 337         assertEquals(test.getNano(), 0);
 338     }
 339 
 340     @Test(expectedExceptions=ArithmeticException.class)
 341     public void factory_days_tooBig() {
 342         Duration.ofDays(Long.MAX_VALUE / 86400 + 1);
 343     }
 344 
 345     @Test(expectedExceptions=ArithmeticException.class)
 346     public void factory_days_tooSmall() {
 347         Duration.ofDays(Long.MIN_VALUE / 86400 - 1);
 348     }
 349 
 350     //-----------------------------------------------------------------------
 351     // of(long,TemporalUnit)
 352     //-----------------------------------------------------------------------
 353     @DataProvider(name="OfTemporalUnit")
 354     Object[][] provider_factory_of_longTemporalUnit() {
 355         return new Object[][] {
 356             {0, NANOS, 0, 0},
 357             {0, MICROS, 0, 0},
 358             {0, MILLIS, 0, 0},
 359             {0, SECONDS, 0, 0},
 360             {0, MINUTES, 0, 0},
 361             {0, HOURS, 0, 0},
 362             {0, HALF_DAYS, 0, 0},
 363             {0, DAYS, 0, 0},
 364             {1, NANOS, 0, 1},
 365             {1, MICROS, 0, 1000},
 366             {1, MILLIS, 0, 1000000},
 367             {1, SECONDS, 1, 0},
 368             {1, MINUTES, 60, 0},
 369             {1, HOURS, 3600, 0},
 370             {1, HALF_DAYS, 43200, 0},
 371             {1, DAYS, 86400, 0},
 372             {3, NANOS, 0, 3},
 373             {3, MICROS, 0, 3000},
 374             {3, MILLIS, 0, 3000000},
 375             {3, SECONDS, 3, 0},
 376             {3, MINUTES, 3 * 60, 0},
 377             {3, HOURS, 3 * 3600, 0},
 378             {3, HALF_DAYS, 3 * 43200, 0},
 379             {3, DAYS, 3 * 86400, 0},
 380             {-1, NANOS, -1, 999999999},
 381             {-1, MICROS, -1, 999999000},
 382             {-1, MILLIS, -1, 999000000},
 383             {-1, SECONDS, -1, 0},
 384             {-1, MINUTES, -60, 0},
 385             {-1, HOURS, -3600, 0},
 386             {-1, HALF_DAYS, -43200, 0},
 387             {-1, DAYS, -86400, 0},
 388             {-3, NANOS, -1, 999999997},
 389             {-3, MICROS, -1, 999997000},
 390             {-3, MILLIS, -1, 997000000},
 391             {-3, SECONDS, -3, 0},
 392             {-3, MINUTES, -3 * 60, 0},
 393             {-3, HOURS, -3 * 3600, 0},
 394             {-3, HALF_DAYS, -3 * 43200, 0},
 395             {-3, DAYS, -3 * 86400, 0},
 396             {Long.MAX_VALUE, NANOS, Long.MAX_VALUE / 1000000000, (int) (Long.MAX_VALUE % 1000000000)},
 397             {Long.MIN_VALUE, NANOS, Long.MIN_VALUE / 1000000000 - 1, (int) (Long.MIN_VALUE % 1000000000 + 1000000000)},
 398             {Long.MAX_VALUE, MICROS, Long.MAX_VALUE / 1000000, (int) ((Long.MAX_VALUE % 1000000) * 1000)},
 399             {Long.MIN_VALUE, MICROS, Long.MIN_VALUE / 1000000 - 1, (int) ((Long.MIN_VALUE % 1000000 + 1000000) * 1000)},
 400             {Long.MAX_VALUE, MILLIS, Long.MAX_VALUE / 1000, (int) ((Long.MAX_VALUE % 1000) * 1000000)},
 401             {Long.MIN_VALUE, MILLIS, Long.MIN_VALUE / 1000 - 1, (int) ((Long.MIN_VALUE % 1000 + 1000) * 1000000)},
 402             {Long.MAX_VALUE, SECONDS, Long.MAX_VALUE, 0},
 403             {Long.MIN_VALUE, SECONDS, Long.MIN_VALUE, 0},
 404             {Long.MAX_VALUE / 60, MINUTES, (Long.MAX_VALUE / 60) * 60, 0},
 405             {Long.MIN_VALUE / 60, MINUTES, (Long.MIN_VALUE / 60) * 60, 0},
 406             {Long.MAX_VALUE / 3600, HOURS, (Long.MAX_VALUE / 3600) * 3600, 0},
 407             {Long.MIN_VALUE / 3600, HOURS, (Long.MIN_VALUE / 3600) * 3600, 0},
 408             {Long.MAX_VALUE / 43200, HALF_DAYS, (Long.MAX_VALUE / 43200) * 43200, 0},
 409             {Long.MIN_VALUE / 43200, HALF_DAYS, (Long.MIN_VALUE / 43200) * 43200, 0},
 410         };
 411     }
 412 
 413     @Test(dataProvider="OfTemporalUnit")
 414     public void factory_of_longTemporalUnit(long amount, TemporalUnit unit, long expectedSeconds, int expectedNanoOfSecond) {
 415         Duration t = Duration.of(amount, unit);
 416         assertEquals(t.getSeconds(), expectedSeconds);
 417         assertEquals(t.getNano(), expectedNanoOfSecond);
 418     }
 419 
 420     @DataProvider(name="OfTemporalUnitOutOfRange")
 421     Object[][] provider_factory_of_longTemporalUnit_outOfRange() {
 422         return new Object[][] {
 423             {Long.MAX_VALUE / 60 + 1, MINUTES},
 424             {Long.MIN_VALUE / 60 - 1, MINUTES},
 425             {Long.MAX_VALUE / 3600 + 1, HOURS},
 426             {Long.MIN_VALUE / 3600 - 1, HOURS},
 427             {Long.MAX_VALUE / 43200 + 1, HALF_DAYS},
 428             {Long.MIN_VALUE / 43200 - 1, HALF_DAYS},
 429         };
 430     }
 431 
 432     @Test(dataProvider="OfTemporalUnitOutOfRange", expectedExceptions=ArithmeticException.class)
 433     public void factory_of_longTemporalUnit_outOfRange(long amount, TemporalUnit unit) {
 434         Duration.of(amount, unit);
 435     }
 436 
 437     @Test(expectedExceptions=DateTimeException.class)
 438     public void factory_of_longTemporalUnit_estimatedUnit() {
 439         Duration.of(2, WEEKS);
 440     }
 441 
 442     @Test(expectedExceptions=NullPointerException.class)
 443     public void factory_of_longTemporalUnit_null() {
 444         Duration.of(1, (TemporalUnit) null);
 445     }
 446 
 447     //-----------------------------------------------------------------------
 448     // from(TemporalAmount)
 449     //-----------------------------------------------------------------------
 450     @Test
 451     public void factory_from_TemporalAmount_Duration() {
 452         TemporalAmount amount = Duration.ofHours(3);
 453         assertEquals(Duration.from(amount), Duration.ofHours(3));
 454     }
 455 
 456     @Test
 457     public void factory_from_TemporalAmount_DaysNanos() {
 458         TemporalAmount amount = new TemporalAmount() {
 459             @Override
 460             public long get(TemporalUnit unit) {
 461                 if (unit == DAYS) {
 462                     return 23;
 463                 } else {
 464                     return 45;
 465                 }
 466             }
 467             @Override
 468             public List<TemporalUnit> getUnits() {
 469                 List<TemporalUnit> list = new ArrayList<>();
 470                 list.add(DAYS);
 471                 list.add(NANOS);
 472                 return list;
 473             }
 474             @Override
 475             public Temporal addTo(Temporal temporal) {
 476                 throw new UnsupportedOperationException();
 477             }
 478             @Override
 479             public Temporal subtractFrom(Temporal temporal) {
 480                 throw new UnsupportedOperationException();
 481             }
 482         };
 483         Duration t = Duration.from(amount);
 484         assertEquals(t.getSeconds(), 23 * 86400);
 485         assertEquals(t.getNano(), 45);
 486     }
 487 
 488     @Test(expectedExceptions = ArithmeticException.class)
 489     public void factory_from_TemporalAmount_Minutes_tooBig() {
 490         TemporalAmount amount = new TemporalAmount() {
 491             @Override
 492             public long get(TemporalUnit unit) {
 493                 return (Long.MAX_VALUE / 60) + 2;
 494             }
 495             @Override
 496             public List<TemporalUnit> getUnits() {
 497                 return Collections.<TemporalUnit>singletonList(MINUTES);
 498             }
 499             @Override
 500             public Temporal addTo(Temporal temporal) {
 501                 throw new UnsupportedOperationException();
 502             }
 503             @Override
 504             public Temporal subtractFrom(Temporal temporal) {
 505                 throw new UnsupportedOperationException();
 506             }
 507         };
 508         Duration.from(amount);
 509     }
 510 
 511     @Test(expectedExceptions = DateTimeException.class)
 512     public void factory_from_TemporalAmount_Period() {
 513         Duration.from(Period.ZERO);
 514     }
 515 
 516     @Test(expectedExceptions = NullPointerException.class)
 517     public void factory_from_TemporalAmount_null() {
 518         Duration.from(null);
 519     }
 520 
 521     //-----------------------------------------------------------------------
 522     // parse(String)
 523     //-----------------------------------------------------------------------
 524     @DataProvider(name="parseSuccess")
 525     Object[][] data_parseSuccess() {
 526         return new Object[][] {
 527                 {"PT0S", 0, 0},
 528                 {"PT1S", 1, 0},
 529                 {"PT12S", 12, 0},
 530                 {"PT123456789S", 123456789, 0},
 531                 {"PT" + Long.MAX_VALUE + "S", Long.MAX_VALUE, 0},
 532 
 533                 {"PT+1S", 1, 0},
 534                 {"PT+12S", 12, 0},
 535                 {"PT+123456789S", 123456789, 0},
 536                 {"PT+" + Long.MAX_VALUE + "S", Long.MAX_VALUE, 0},
 537 
 538                 {"PT-1S", -1, 0},
 539                 {"PT-12S", -12, 0},
 540                 {"PT-123456789S", -123456789, 0},
 541                 {"PT" + Long.MIN_VALUE + "S", Long.MIN_VALUE, 0},
 542 
 543                 {"PT1.1S", 1, 100000000},
 544                 {"PT1.12S", 1, 120000000},
 545                 {"PT1.123S", 1, 123000000},
 546                 {"PT1.1234S", 1, 123400000},
 547                 {"PT1.12345S", 1, 123450000},
 548                 {"PT1.123456S", 1, 123456000},
 549                 {"PT1.1234567S", 1, 123456700},
 550                 {"PT1.12345678S", 1, 123456780},
 551                 {"PT1.123456789S", 1, 123456789},
 552 
 553                 {"PT-1.1S", -2, 1000000000 - 100000000},
 554                 {"PT-1.12S", -2, 1000000000 - 120000000},
 555                 {"PT-1.123S", -2, 1000000000 - 123000000},
 556                 {"PT-1.1234S", -2, 1000000000 - 123400000},
 557                 {"PT-1.12345S", -2, 1000000000 - 123450000},
 558                 {"PT-1.123456S", -2, 1000000000 - 123456000},
 559                 {"PT-1.1234567S", -2, 1000000000 - 123456700},
 560                 {"PT-1.12345678S", -2, 1000000000 - 123456780},
 561                 {"PT-1.123456789S", -2, 1000000000 - 123456789},
 562 
 563                 {"PT" + Long.MAX_VALUE + ".123456789S", Long.MAX_VALUE, 123456789},
 564                 {"PT" + Long.MIN_VALUE + ".000000000S", Long.MIN_VALUE, 0},
 565 
 566                 {"PT01S", 1, 0},
 567                 {"PT001S", 1, 0},
 568                 {"PT000S", 0, 0},
 569                 {"PT+01S", 1, 0},
 570                 {"PT-01S", -1, 0},
 571 
 572                 {"PT1.S", 1, 0},
 573                 {"PT+1.S", 1, 0},
 574                 {"PT-1.S", -1, 0},
 575 
 576                 {"P0D", 0, 0},
 577                 {"P0DT0H", 0, 0},
 578                 {"P0DT0M", 0, 0},
 579                 {"P0DT0S", 0, 0},
 580                 {"P0DT0H0S", 0, 0},
 581                 {"P0DT0M0S", 0, 0},
 582                 {"P0DT0H0M0S", 0, 0},
 583 
 584                 {"P1D", 86400, 0},
 585                 {"P1DT0H", 86400, 0},
 586                 {"P1DT0M", 86400, 0},
 587                 {"P1DT0S", 86400, 0},
 588                 {"P1DT0H0S", 86400, 0},
 589                 {"P1DT0M0S", 86400, 0},
 590                 {"P1DT0H0M0S", 86400, 0},
 591 
 592                 {"P3D", 86400 * 3, 0},
 593                 {"P3DT2H", 86400 * 3 + 3600 * 2, 0},
 594                 {"P3DT2M", 86400 * 3 + 60 * 2, 0},
 595                 {"P3DT2S", 86400 * 3 + 2, 0},
 596                 {"P3DT2H1S", 86400 * 3 + 3600 * 2 + 1, 0},
 597                 {"P3DT2M1S", 86400 * 3 + 60 * 2 + 1, 0},
 598                 {"P3DT2H1M1S", 86400 * 3 + 3600 * 2 + 60 + 1, 0},
 599 
 600                 {"P-3D", -86400 * 3, 0},
 601                 {"P-3DT2H", -86400 * 3 + 3600 * 2, 0},
 602                 {"P-3DT2M", -86400 * 3 + 60 * 2, 0},
 603                 {"P-3DT2S", -86400 * 3 + 2, 0},
 604                 {"P-3DT2H1S", -86400 * 3 + 3600 * 2 + 1, 0},
 605                 {"P-3DT2M1S", -86400 * 3 + 60 * 2 + 1, 0},
 606                 {"P-3DT2H1M1S", -86400 * 3 + 3600 * 2 + 60 + 1, 0},
 607 
 608                 {"P-3DT-2H", -86400 * 3 - 3600 * 2, 0},
 609                 {"P-3DT-2M", -86400 * 3 - 60 * 2, 0},
 610                 {"P-3DT-2S", -86400 * 3 - 2, 0},
 611                 {"P-3DT-2H1S", -86400 * 3 - 3600 * 2 + 1, 0},
 612                 {"P-3DT-2M1S", -86400 * 3 - 60 * 2 + 1, 0},
 613                 {"P-3DT-2H1M1S", -86400 * 3 - 3600 * 2 + 60 + 1, 0},
 614 
 615                 {"PT0H", 0, 0},
 616                 {"PT0H0M", 0, 0},
 617                 {"PT0H0S", 0, 0},
 618                 {"PT0H0M0S", 0, 0},
 619 
 620                 {"PT1H", 3600, 0},
 621                 {"PT3H", 3600 * 3, 0},
 622                 {"PT-1H", -3600, 0},
 623                 {"PT-3H", -3600 * 3, 0},
 624 
 625                 {"PT2H5M", 3600 * 2 + 60 * 5, 0},
 626                 {"PT2H5S", 3600 * 2 + 5, 0},
 627                 {"PT2H5M8S", 3600 * 2 + 60 * 5 + 8, 0},
 628                 {"PT-2H5M", -3600 * 2 + 60 * 5, 0},
 629                 {"PT-2H5S", -3600 * 2 + 5, 0},
 630                 {"PT-2H5M8S", -3600 * 2 + 60 * 5 + 8, 0},
 631                 {"PT-2H-5M", -3600 * 2 - 60 * 5, 0},
 632                 {"PT-2H-5S", -3600 * 2 - 5, 0},
 633                 {"PT-2H-5M8S", -3600 * 2 - 60 * 5 + 8, 0},
 634                 {"PT-2H-5M-8S", -3600 * 2 - 60 * 5 - 8, 0},
 635 
 636                 {"PT0M", 0, 0},
 637                 {"PT1M", 60, 0},
 638                 {"PT3M", 60 * 3, 0},
 639                 {"PT-1M", -60, 0},
 640                 {"PT-3M", -60 * 3, 0},
 641                 {"P0DT3M", 60 * 3, 0},
 642                 {"P0DT-3M", -60 * 3, 0},
 643         };
 644     }
 645 
 646     @Test(dataProvider="parseSuccess")
 647     public void factory_parse(String text, long expectedSeconds, int expectedNanoOfSecond) {
 648         Duration test = Duration.parse(text);
 649         assertEquals(test.getSeconds(), expectedSeconds);
 650         assertEquals(test.getNano(), expectedNanoOfSecond);
 651     }
 652 
 653     @Test(dataProvider="parseSuccess")
 654     public void factory_parse_plus(String text, long expectedSeconds, int expectedNanoOfSecond) {
 655         Duration test = Duration.parse("+" + text);
 656         assertEquals(test.getSeconds(), expectedSeconds);
 657         assertEquals(test.getNano(), expectedNanoOfSecond);
 658     }
 659 
 660     @Test(dataProvider="parseSuccess")
 661     public void factory_parse_minus(String text, long expectedSeconds, int expectedNanoOfSecond) {
 662         Duration test;
 663         try {
 664             test = Duration.parse("-" + text);
 665         } catch (DateTimeParseException ex) {
 666             assertEquals(expectedSeconds == Long.MIN_VALUE, true);
 667             return;
 668         }
 669         // not inside try/catch or it breaks test
 670         assertEquals(test, Duration.ofSeconds(expectedSeconds, expectedNanoOfSecond).negated());
 671     }
 672 
 673     @Test(dataProvider="parseSuccess")
 674     public void factory_parse_comma(String text, long expectedSeconds, int expectedNanoOfSecond) {
 675         text = text.replace('.', ',');
 676         Duration test = Duration.parse(text);
 677         assertEquals(test.getSeconds(), expectedSeconds);
 678         assertEquals(test.getNano(), expectedNanoOfSecond);
 679     }
 680 
 681     @Test(dataProvider="parseSuccess")
 682     public void factory_parse_lowerCase(String text, long expectedSeconds, int expectedNanoOfSecond) {
 683         Duration test = Duration.parse(text.toLowerCase(Locale.ENGLISH));
 684         assertEquals(test.getSeconds(), expectedSeconds);
 685         assertEquals(test.getNano(), expectedNanoOfSecond);
 686     }
 687 
 688     @DataProvider(name="parseFailure")
 689     Object[][] data_parseFailure() {
 690         return new Object[][] {
 691                 {""},
 692                 {"ABCDEF"},
 693                 {" PT0S"},
 694                 {"PT0S "},
 695 
 696                 {"PTS"},
 697                 {"AT0S"},
 698                 {"PA0S"},
 699                 {"PT0A"},
 700 
 701                 {"P0Y"},
 702                 {"P1Y"},
 703                 {"P-2Y"},
 704                 {"P0M"},
 705                 {"P1M"},
 706                 {"P-2M"},
 707                 {"P3Y2D"},
 708                 {"P3M2D"},
 709                 {"P3W"},
 710                 {"P-3W"},
 711                 {"P2YT30S"},
 712                 {"P2MT30S"},
 713 
 714                 {"P1DT"},
 715 
 716                 {"PT+S"},
 717                 {"PT-S"},
 718                 {"PT.S"},
 719                 {"PTAS"},
 720 
 721                 {"PT-.S"},
 722                 {"PT+.S"},
 723 
 724                 {"PT1ABC2S"},
 725                 {"PT1.1ABC2S"},
 726 
 727                 {"PT123456789123456789123456789S"},
 728                 {"PT0.1234567891S"},
 729 
 730                 {"PT2.-3"},
 731                 {"PT-2.-3"},
 732                 {"PT2.+3"},
 733                 {"PT-2.+3"},
 734         };
 735     }
 736 
 737     @Test(dataProvider="parseFailure", expectedExceptions=DateTimeParseException.class)
 738     public void factory_parseFailures(String text) {
 739         Duration.parse(text);
 740     }
 741 
 742     @Test(dataProvider="parseFailure", expectedExceptions=DateTimeParseException.class)
 743     public void factory_parseFailures_comma(String text) {
 744         text = text.replace('.', ',');
 745         Duration.parse(text);
 746     }
 747 
 748     @Test(expectedExceptions=DateTimeParseException.class)
 749     public void factory_parse_tooBig() {
 750         Duration.parse("PT" + Long.MAX_VALUE + "1S");
 751     }
 752 
 753     @Test(expectedExceptions=DateTimeParseException.class)
 754     public void factory_parse_tooBig_decimal() {
 755         Duration.parse("PT" + Long.MAX_VALUE + "1.1S");
 756     }
 757 
 758     @Test(expectedExceptions=DateTimeParseException.class)
 759     public void factory_parse_tooSmall() {
 760         Duration.parse("PT" + Long.MIN_VALUE + "1S");
 761     }
 762 
 763     @Test(expectedExceptions=DateTimeParseException.class)
 764     public void factory_parse_tooSmall_decimal() {
 765         Duration.parse("PT" + Long.MIN_VALUE + ".1S");
 766     }
 767 
 768     @Test(expectedExceptions=NullPointerException.class)
 769     public void factory_parse_nullText() {
 770         Duration.parse(null);
 771     }
 772 
 773     //-----------------------------------------------------------------------
 774     // between()
 775     //-----------------------------------------------------------------------
 776     @DataProvider(name="durationBetweenInstant")
 777     Object[][] data_durationBetweenInstant() {
 778         return new Object[][] {
 779                 {0, 0, 0, 0, 0, 0},
 780                 {3, 0, 7, 0, 4, 0},
 781                 {7, 0, 3, 0, -4, 0},
 782 
 783                 {3, 20, 7, 50, 4, 30},
 784                 {3, 80, 7, 50, 3, 999999970},
 785                 {3, 80, 7, 79, 3, 999999999},
 786                 {3, 80, 7, 80, 4, 0},
 787                 {3, 80, 7, 81, 4, 1},
 788         };
 789     }
 790 
 791     @Test(dataProvider="durationBetweenInstant")
 792     public void factory_between_TemporalTemporal_Instant(long secs1, int nanos1, long secs2, int nanos2, long expectedSeconds, int expectedNanoOfSecond) {
 793         Instant start = Instant.ofEpochSecond(secs1, nanos1);
 794         Instant end = Instant.ofEpochSecond(secs2, nanos2);
 795         Duration t = Duration.between(start, end);
 796         assertEquals(t.getSeconds(), expectedSeconds);
 797         assertEquals(t.getNano(), expectedNanoOfSecond);
 798     }
 799 
 800     @Test(dataProvider="durationBetweenInstant")
 801     public void factory_between_TemporalTemporal_Instant_negated(long secs1, int nanos1, long secs2, int nanos2, long expectedSeconds, int expectedNanoOfSecond) {
 802         Instant start = Instant.ofEpochSecond(secs1, nanos1);
 803         Instant end = Instant.ofEpochSecond(secs2, nanos2);
 804         assertEquals(Duration.between(end, start), Duration.between(start, end).negated());
 805     }
 806 
 807     @DataProvider(name="durationBetweenLocalTime")
 808     Object[][] data_durationBetweenLocalTime() {
 809         return new Object[][] {
 810                 {LocalTime.of(11, 0, 30), LocalTime.of(11, 0, 45), 15L, 0},
 811                 {LocalTime.of(11, 0, 30), LocalTime.of(11, 0, 25), -5L, 0},
 812         };
 813     }
 814 
 815     @Test(dataProvider="durationBetweenLocalTime")
 816     public void factory_between_TemporalTemporal_LT(LocalTime start, LocalTime end, long expectedSeconds, int expectedNanoOfSecond) {
 817         Duration t = Duration.between(start, end);
 818         assertEquals(t.getSeconds(), expectedSeconds);
 819         assertEquals(t.getNano(), expectedNanoOfSecond);
 820     }
 821 
 822     @Test(dataProvider="durationBetweenLocalTime")
 823     public void factory_between_TemporalTemporal_LT_negated(LocalTime start, LocalTime end, long expectedSeconds, int expectedNanoOfSecond) {
 824         assertEquals(Duration.between(end, start), Duration.between(start, end).negated());
 825     }
 826 
 827     @DataProvider(name="durationBetweenLocalDateTime")
 828     Object[][] data_durationBetweenLocalDateTime() {
 829         return new Object[][] {
 830                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 565_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 30, 65_000_000), -2L, 500_000_000},
 831                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 565_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), -1L, 500_000_000},
 832                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 565_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 32, 65_000_000), 0L, 500_000_000},
 833                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 565_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 33, 65_000_000), 1L, 500_000_000},
 834                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 565_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 34, 65_000_000), 2L, 500_000_000},
 835 
 836                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 30, 565_000_000), -1L, 500_000_000},
 837                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 31, 565_000_000), 0L, 500_000_000},
 838                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 32, 565_000_000), 1L, 500_000_000},
 839                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 33, 565_000_000), 2L, 500_000_000},
 840                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 34, 565_000_000), 3L, 500_000_000},
 841 
 842                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 30, 65_000_000), -1L, 0},
 843                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), 0L, 0},
 844                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 32, 65_000_000), 1L, 0},
 845                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 33, 65_000_000), 2L, 0},
 846                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2013, 3, 24, 0, 44, 34, 65_000_000), 3L, 0},
 847 
 848                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2813, 3, 24, 0, 44, 30, 565_000_000), 2 * CYCLE_SECS - 1L, 500_000_000},
 849                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2813, 3, 24, 0, 44, 31, 565_000_000), 2 * CYCLE_SECS + 0L, 500_000_000},
 850                 {LocalDateTime.of(2013, 3, 24, 0, 44, 31, 65_000_000), LocalDateTime.of(2813, 3, 24, 0, 44, 32, 565_000_000), 2 * CYCLE_SECS + 1L, 500_000_000},
 851         };
 852     }
 853 
 854     @Test(dataProvider="durationBetweenLocalDateTime")
 855     public void factory_between_TemporalTemporal_LDT(LocalDateTime start, LocalDateTime end, long expectedSeconds, int expectedNanoOfSecond) {
 856         Duration t = Duration.between(start, end);
 857         assertEquals(t.getSeconds(), expectedSeconds);
 858         assertEquals(t.getNano(), expectedNanoOfSecond);
 859     }
 860 
 861     @Test(dataProvider="durationBetweenLocalDateTime")
 862     public void factory_between_TemporalTemporal_LDT_negated(LocalDateTime start, LocalDateTime end, long expectedSeconds, int expectedNanoOfSecond) {
 863         assertEquals(Duration.between(end, start), Duration.between(start, end).negated());
 864     }
 865 
 866     @Test(expectedExceptions=DateTimeException.class)
 867     public void factory_between_TemporalTemporal_mixedTypes() {
 868         Instant start = Instant.ofEpochSecond(1);
 869         ZonedDateTime end = Instant.ofEpochSecond(4).atZone(ZoneOffset.UTC);
 870         Duration.between(start, end);
 871     }
 872 
 873     @Test(expectedExceptions=NullPointerException.class)
 874     public void factory_between__TemporalTemporal_startNull() {
 875         Instant end = Instant.ofEpochSecond(1);
 876         Duration.between(null, end);
 877     }
 878 
 879     @Test(expectedExceptions=NullPointerException.class)
 880     public void factory_between__TemporalTemporal_endNull() {
 881         Instant start = Instant.ofEpochSecond(1);
 882         Duration.between(start, null);
 883     }
 884 
 885     //-----------------------------------------------------------------------
 886     // isZero(), isPositive(), isPositiveOrZero(), isNegative(), isNegativeOrZero()
 887     //-----------------------------------------------------------------------
 888     @Test
 889     public void test_isZero() {
 890         assertEquals(Duration.ofNanos(0).isZero(), true);
 891         assertEquals(Duration.ofSeconds(0).isZero(), true);
 892         assertEquals(Duration.ofNanos(1).isZero(), false);
 893         assertEquals(Duration.ofSeconds(1).isZero(), false);
 894         assertEquals(Duration.ofSeconds(1, 1).isZero(), false);
 895         assertEquals(Duration.ofNanos(-1).isZero(), false);
 896         assertEquals(Duration.ofSeconds(-1).isZero(), false);
 897         assertEquals(Duration.ofSeconds(-1, -1).isZero(), false);
 898     }
 899 
 900     @Test
 901     public void test_isNegative() {
 902         assertEquals(Duration.ofNanos(0).isNegative(), false);
 903         assertEquals(Duration.ofSeconds(0).isNegative(), false);
 904         assertEquals(Duration.ofNanos(1).isNegative(), false);
 905         assertEquals(Duration.ofSeconds(1).isNegative(), false);
 906         assertEquals(Duration.ofSeconds(1, 1).isNegative(), false);
 907         assertEquals(Duration.ofNanos(-1).isNegative(), true);
 908         assertEquals(Duration.ofSeconds(-1).isNegative(), true);
 909         assertEquals(Duration.ofSeconds(-1, -1).isNegative(), true);
 910     }
 911 
 912     //-----------------------------------------------------------------------
 913     // plus()
 914     //-----------------------------------------------------------------------
 915     @DataProvider(name="Plus")
 916     Object[][] provider_plus() {
 917         return new Object[][] {
 918             {Long.MIN_VALUE, 0, Long.MAX_VALUE, 0, -1, 0},
 919 
 920             {-4, 666666667, -4, 666666667, -7, 333333334},
 921             {-4, 666666667, -3,         0, -7, 666666667},
 922             {-4, 666666667, -2,         0, -6, 666666667},
 923             {-4, 666666667, -1,         0, -5, 666666667},
 924             {-4, 666666667, -1, 333333334, -4,         1},
 925             {-4, 666666667, -1, 666666667, -4, 333333334},
 926             {-4, 666666667, -1, 999999999, -4, 666666666},
 927             {-4, 666666667,  0,         0, -4, 666666667},
 928             {-4, 666666667,  0,         1, -4, 666666668},
 929             {-4, 666666667,  0, 333333333, -3,         0},
 930             {-4, 666666667,  0, 666666666, -3, 333333333},
 931             {-4, 666666667,  1,         0, -3, 666666667},
 932             {-4, 666666667,  2,         0, -2, 666666667},
 933             {-4, 666666667,  3,         0, -1, 666666667},
 934             {-4, 666666667,  3, 333333333,  0,         0},
 935 
 936             {-3, 0, -4, 666666667, -7, 666666667},
 937             {-3, 0, -3,         0, -6,         0},
 938             {-3, 0, -2,         0, -5,         0},
 939             {-3, 0, -1,         0, -4,         0},
 940             {-3, 0, -1, 333333334, -4, 333333334},
 941             {-3, 0, -1, 666666667, -4, 666666667},
 942             {-3, 0, -1, 999999999, -4, 999999999},
 943             {-3, 0,  0,         0, -3,         0},
 944             {-3, 0,  0,         1, -3,         1},
 945             {-3, 0,  0, 333333333, -3, 333333333},
 946             {-3, 0,  0, 666666666, -3, 666666666},
 947             {-3, 0,  1,         0, -2,         0},
 948             {-3, 0,  2,         0, -1,         0},
 949             {-3, 0,  3,         0,  0,         0},
 950             {-3, 0,  3, 333333333,  0, 333333333},
 951 
 952             {-2, 0, -4, 666666667, -6, 666666667},
 953             {-2, 0, -3,         0, -5,         0},
 954             {-2, 0, -2,         0, -4,         0},
 955             {-2, 0, -1,         0, -3,         0},
 956             {-2, 0, -1, 333333334, -3, 333333334},
 957             {-2, 0, -1, 666666667, -3, 666666667},
 958             {-2, 0, -1, 999999999, -3, 999999999},
 959             {-2, 0,  0,         0, -2,         0},
 960             {-2, 0,  0,         1, -2,         1},
 961             {-2, 0,  0, 333333333, -2, 333333333},
 962             {-2, 0,  0, 666666666, -2, 666666666},
 963             {-2, 0,  1,         0, -1,         0},
 964             {-2, 0,  2,         0,  0,         0},
 965             {-2, 0,  3,         0,  1,         0},
 966             {-2, 0,  3, 333333333,  1, 333333333},
 967 
 968             {-1, 0, -4, 666666667, -5, 666666667},
 969             {-1, 0, -3,         0, -4,         0},
 970             {-1, 0, -2,         0, -3,         0},
 971             {-1, 0, -1,         0, -2,         0},
 972             {-1, 0, -1, 333333334, -2, 333333334},
 973             {-1, 0, -1, 666666667, -2, 666666667},
 974             {-1, 0, -1, 999999999, -2, 999999999},
 975             {-1, 0,  0,         0, -1,         0},
 976             {-1, 0,  0,         1, -1,         1},
 977             {-1, 0,  0, 333333333, -1, 333333333},
 978             {-1, 0,  0, 666666666, -1, 666666666},
 979             {-1, 0,  1,         0,  0,         0},
 980             {-1, 0,  2,         0,  1,         0},
 981             {-1, 0,  3,         0,  2,         0},
 982             {-1, 0,  3, 333333333,  2, 333333333},
 983 
 984             {-1, 666666667, -4, 666666667, -4, 333333334},
 985             {-1, 666666667, -3,         0, -4, 666666667},
 986             {-1, 666666667, -2,         0, -3, 666666667},
 987             {-1, 666666667, -1,         0, -2, 666666667},
 988             {-1, 666666667, -1, 333333334, -1,         1},
 989             {-1, 666666667, -1, 666666667, -1, 333333334},
 990             {-1, 666666667, -1, 999999999, -1, 666666666},
 991             {-1, 666666667,  0,         0, -1, 666666667},
 992             {-1, 666666667,  0,         1, -1, 666666668},
 993             {-1, 666666667,  0, 333333333,  0,         0},
 994             {-1, 666666667,  0, 666666666,  0, 333333333},
 995             {-1, 666666667,  1,         0,  0, 666666667},
 996             {-1, 666666667,  2,         0,  1, 666666667},
 997             {-1, 666666667,  3,         0,  2, 666666667},
 998             {-1, 666666667,  3, 333333333,  3,         0},
 999 
1000             {0, 0, -4, 666666667, -4, 666666667},
1001             {0, 0, -3,         0, -3,         0},
1002             {0, 0, -2,         0, -2,         0},
1003             {0, 0, -1,         0, -1,         0},
1004             {0, 0, -1, 333333334, -1, 333333334},
1005             {0, 0, -1, 666666667, -1, 666666667},
1006             {0, 0, -1, 999999999, -1, 999999999},
1007             {0, 0,  0,         0,  0,         0},
1008             {0, 0,  0,         1,  0,         1},
1009             {0, 0,  0, 333333333,  0, 333333333},
1010             {0, 0,  0, 666666666,  0, 666666666},
1011             {0, 0,  1,         0,  1,         0},
1012             {0, 0,  2,         0,  2,         0},
1013             {0, 0,  3,         0,  3,         0},
1014             {0, 0,  3, 333333333,  3, 333333333},
1015 
1016             {0, 333333333, -4, 666666667, -3,         0},
1017             {0, 333333333, -3,         0, -3, 333333333},
1018             {0, 333333333, -2,         0, -2, 333333333},
1019             {0, 333333333, -1,         0, -1, 333333333},
1020             {0, 333333333, -1, 333333334, -1, 666666667},
1021             {0, 333333333, -1, 666666667,  0,         0},
1022             {0, 333333333, -1, 999999999,  0, 333333332},
1023             {0, 333333333,  0,         0,  0, 333333333},
1024             {0, 333333333,  0,         1,  0, 333333334},
1025             {0, 333333333,  0, 333333333,  0, 666666666},
1026             {0, 333333333,  0, 666666666,  0, 999999999},
1027             {0, 333333333,  1,         0,  1, 333333333},
1028             {0, 333333333,  2,         0,  2, 333333333},
1029             {0, 333333333,  3,         0,  3, 333333333},
1030             {0, 333333333,  3, 333333333,  3, 666666666},
1031 
1032             {1, 0, -4, 666666667, -3, 666666667},
1033             {1, 0, -3,         0, -2,         0},
1034             {1, 0, -2,         0, -1,         0},
1035             {1, 0, -1,         0,  0,         0},
1036             {1, 0, -1, 333333334,  0, 333333334},
1037             {1, 0, -1, 666666667,  0, 666666667},
1038             {1, 0, -1, 999999999,  0, 999999999},
1039             {1, 0,  0,         0,  1,         0},
1040             {1, 0,  0,         1,  1,         1},
1041             {1, 0,  0, 333333333,  1, 333333333},
1042             {1, 0,  0, 666666666,  1, 666666666},
1043             {1, 0,  1,         0,  2,         0},
1044             {1, 0,  2,         0,  3,         0},
1045             {1, 0,  3,         0,  4,         0},
1046             {1, 0,  3, 333333333,  4, 333333333},
1047 
1048             {2, 0, -4, 666666667, -2, 666666667},
1049             {2, 0, -3,         0, -1,         0},
1050             {2, 0, -2,         0,  0,         0},
1051             {2, 0, -1,         0,  1,         0},
1052             {2, 0, -1, 333333334,  1, 333333334},
1053             {2, 0, -1, 666666667,  1, 666666667},
1054             {2, 0, -1, 999999999,  1, 999999999},
1055             {2, 0,  0,         0,  2,         0},
1056             {2, 0,  0,         1,  2,         1},
1057             {2, 0,  0, 333333333,  2, 333333333},
1058             {2, 0,  0, 666666666,  2, 666666666},
1059             {2, 0,  1,         0,  3,         0},
1060             {2, 0,  2,         0,  4,         0},
1061             {2, 0,  3,         0,  5,         0},
1062             {2, 0,  3, 333333333,  5, 333333333},
1063 
1064             {3, 0, -4, 666666667, -1, 666666667},
1065             {3, 0, -3,         0,  0,         0},
1066             {3, 0, -2,         0,  1,         0},
1067             {3, 0, -1,         0,  2,         0},
1068             {3, 0, -1, 333333334,  2, 333333334},
1069             {3, 0, -1, 666666667,  2, 666666667},
1070             {3, 0, -1, 999999999,  2, 999999999},
1071             {3, 0,  0,         0,  3,         0},
1072             {3, 0,  0,         1,  3,         1},
1073             {3, 0,  0, 333333333,  3, 333333333},
1074             {3, 0,  0, 666666666,  3, 666666666},
1075             {3, 0,  1,         0,  4,         0},
1076             {3, 0,  2,         0,  5,         0},
1077             {3, 0,  3,         0,  6,         0},
1078             {3, 0,  3, 333333333,  6, 333333333},
1079 
1080             {3, 333333333, -4, 666666667,  0,         0},
1081             {3, 333333333, -3,         0,  0, 333333333},
1082             {3, 333333333, -2,         0,  1, 333333333},
1083             {3, 333333333, -1,         0,  2, 333333333},
1084             {3, 333333333, -1, 333333334,  2, 666666667},
1085             {3, 333333333, -1, 666666667,  3,         0},
1086             {3, 333333333, -1, 999999999,  3, 333333332},
1087             {3, 333333333,  0,         0,  3, 333333333},
1088             {3, 333333333,  0,         1,  3, 333333334},
1089             {3, 333333333,  0, 333333333,  3, 666666666},
1090             {3, 333333333,  0, 666666666,  3, 999999999},
1091             {3, 333333333,  1,         0,  4, 333333333},
1092             {3, 333333333,  2,         0,  5, 333333333},
1093             {3, 333333333,  3,         0,  6, 333333333},
1094             {3, 333333333,  3, 333333333,  6, 666666666},
1095 
1096             {Long.MAX_VALUE, 0, Long.MIN_VALUE, 0, -1, 0},
1097        };
1098     }
1099 
1100     @Test(dataProvider="Plus")
1101     public void plus(long seconds, int nanos, long otherSeconds, int otherNanos, long expectedSeconds, int expectedNanoOfSecond) {
1102        Duration t = Duration.ofSeconds(seconds, nanos).plus(Duration.ofSeconds(otherSeconds, otherNanos));
1103        assertEquals(t.getSeconds(), expectedSeconds);
1104        assertEquals(t.getNano(), expectedNanoOfSecond);
1105     }
1106 
1107     @Test(expectedExceptions=ArithmeticException.class)
1108     public void plusOverflowTooBig() {
1109        Duration t = Duration.ofSeconds(Long.MAX_VALUE, 999999999);
1110        t.plus(Duration.ofSeconds(0, 1));
1111     }
1112 
1113     @Test(expectedExceptions=ArithmeticException.class)
1114     public void plusOverflowTooSmall() {
1115        Duration t = Duration.ofSeconds(Long.MIN_VALUE);
1116        t.plus(Duration.ofSeconds(-1, 999999999));
1117     }
1118 
1119     //-----------------------------------------------------------------------
1120     @Test
1121     public void plus_longTemporalUnit_seconds() {
1122         Duration t = Duration.ofSeconds(1);
1123         t = t.plus(1, SECONDS);
1124         assertEquals(2, t.getSeconds());
1125         assertEquals(0, t.getNano());
1126      }
1127 
1128     @Test
1129     public void plus_longTemporalUnit_millis() {
1130         Duration t = Duration.ofSeconds(1);
1131         t = t.plus(1, MILLIS);
1132         assertEquals(1, t.getSeconds());
1133         assertEquals(1000000, t.getNano());
1134      }
1135 
1136     @Test
1137     public void plus_longTemporalUnit_micros() {
1138         Duration t = Duration.ofSeconds(1);
1139         t = t.plus(1, MICROS);
1140         assertEquals(1, t.getSeconds());
1141         assertEquals(1000, t.getNano());
1142      }
1143 
1144     @Test
1145     public void plus_longTemporalUnit_nanos() {
1146         Duration t = Duration.ofSeconds(1);
1147         t = t.plus(1, NANOS);
1148         assertEquals(1, t.getSeconds());
1149         assertEquals(1, t.getNano());
1150      }
1151 
1152     @Test(expectedExceptions=NullPointerException.class)
1153     public void plus_longTemporalUnit_null() {
1154        Duration t = Duration.ofSeconds(1);
1155        t.plus(1, (TemporalUnit) null);
1156     }
1157 
1158     //-----------------------------------------------------------------------
1159     @DataProvider(name="PlusDays")
1160     Object[][] provider_plusDays_long() {
1161         return new Object[][] {
1162             {0, 0, 0},
1163             {0, 1, 1},
1164             {0, -1, -1},
1165             {Long.MAX_VALUE/3600/24, 0, Long.MAX_VALUE/3600/24},
1166             {Long.MIN_VALUE/3600/24, 0, Long.MIN_VALUE/3600/24},
1167             {1, 0, 1},
1168             {1, 1, 2},
1169             {1, -1, 0},
1170             {1, Long.MIN_VALUE/3600/24, Long.MIN_VALUE/3600/24 + 1},
1171             {1, 0, 1},
1172             {1, 1, 2},
1173             {1, -1, 0},
1174             {-1, 0, -1},
1175             {-1, 1, 0},
1176             {-1, -1, -2},
1177             {-1, Long.MAX_VALUE/3600/24, Long.MAX_VALUE/3600/24 - 1},
1178         };
1179     }
1180 
1181     @Test(dataProvider="PlusDays")
1182     public void plusDays_long(long days, long amount, long expectedDays) {
1183         Duration t = Duration.ofDays(days);
1184         t = t.plusDays(amount);
1185         assertEquals(t.toDays(), expectedDays);
1186     }
1187 
1188     @Test(expectedExceptions = {ArithmeticException.class})
1189     public void plusDays_long_overflowTooBig() {
1190         Duration t = Duration.ofDays(1);
1191         t.plusDays(Long.MAX_VALUE/3600/24);
1192     }
1193 
1194     @Test(expectedExceptions = {ArithmeticException.class})
1195     public void plusDays_long_overflowTooSmall() {
1196         Duration t = Duration.ofDays(-1);
1197         t.plusDays(Long.MIN_VALUE/3600/24);
1198     }
1199 
1200     //-----------------------------------------------------------------------
1201     @DataProvider(name="PlusHours")
1202     Object[][] provider_plusHours_long() {
1203         return new Object[][] {
1204             {0, 0, 0},
1205             {0, 1, 1},
1206             {0, -1, -1},
1207             {Long.MAX_VALUE/3600, 0, Long.MAX_VALUE/3600},
1208             {Long.MIN_VALUE/3600, 0, Long.MIN_VALUE/3600},
1209             {1, 0, 1},
1210             {1, 1, 2},
1211             {1, -1, 0},
1212             {1, Long.MIN_VALUE/3600, Long.MIN_VALUE/3600 + 1},
1213             {1, 0, 1},
1214             {1, 1, 2},
1215             {1, -1, 0},
1216             {-1, 0, -1},
1217             {-1, 1, 0},
1218             {-1, -1, -2},
1219             {-1, Long.MAX_VALUE/3600, Long.MAX_VALUE/3600 - 1},
1220         };
1221     }
1222 
1223     @Test(dataProvider="PlusHours")
1224     public void plusHours_long(long hours, long amount, long expectedHours) {
1225         Duration t = Duration.ofHours(hours);
1226         t = t.plusHours(amount);
1227         assertEquals(t.toHours(), expectedHours);
1228     }
1229 
1230     @Test(expectedExceptions = {ArithmeticException.class})
1231     public void plusHours_long_overflowTooBig() {
1232         Duration t = Duration.ofHours(1);
1233         t.plusHours(Long.MAX_VALUE/3600);
1234     }
1235 
1236     @Test(expectedExceptions = {ArithmeticException.class})
1237     public void plusHours_long_overflowTooSmall() {
1238         Duration t = Duration.ofHours(-1);
1239         t.plusHours(Long.MIN_VALUE/3600);
1240     }
1241 
1242     //-----------------------------------------------------------------------
1243     @DataProvider(name="PlusMinutes")
1244     Object[][] provider_plusMinutes_long() {
1245         return new Object[][] {
1246             {0, 0, 0},
1247             {0, 1, 1},
1248             {0, -1, -1},
1249             {Long.MAX_VALUE/60, 0, Long.MAX_VALUE/60},
1250             {Long.MIN_VALUE/60, 0, Long.MIN_VALUE/60},
1251             {1, 0, 1},
1252             {1, 1, 2},
1253             {1, -1, 0},
1254             {1, Long.MIN_VALUE/60, Long.MIN_VALUE/60 + 1},
1255             {1, 0, 1},
1256             {1, 1, 2},
1257             {1, -1, 0},
1258             {-1, 0, -1},
1259             {-1, 1, 0},
1260             {-1, -1, -2},
1261             {-1, Long.MAX_VALUE/60, Long.MAX_VALUE/60 - 1},
1262         };
1263     }
1264 
1265     @Test(dataProvider="PlusMinutes")
1266     public void plusMinutes_long(long minutes, long amount, long expectedMinutes) {
1267         Duration t = Duration.ofMinutes(minutes);
1268         t = t.plusMinutes(amount);
1269         assertEquals(t.toMinutes(), expectedMinutes);
1270     }
1271 
1272     @Test(expectedExceptions = {ArithmeticException.class})
1273     public void plusMinutes_long_overflowTooBig() {
1274         Duration t = Duration.ofMinutes(1);
1275         t.plusMinutes(Long.MAX_VALUE/60);
1276     }
1277 
1278     @Test(expectedExceptions = {ArithmeticException.class})
1279     public void plusMinutes_long_overflowTooSmall() {
1280         Duration t = Duration.ofMinutes(-1);
1281         t.plusMinutes(Long.MIN_VALUE/60);
1282     }
1283 
1284     //-----------------------------------------------------------------------
1285     @DataProvider(name="PlusSeconds")
1286     Object[][] provider_plusSeconds_long() {
1287         return new Object[][] {
1288             {0, 0, 0, 0, 0},
1289             {0, 0, 1, 1, 0},
1290             {0, 0, -1, -1, 0},
1291             {0, 0, Long.MAX_VALUE, Long.MAX_VALUE, 0},
1292             {0, 0, Long.MIN_VALUE, Long.MIN_VALUE, 0},
1293             {1, 0, 0, 1, 0},
1294             {1, 0, 1, 2, 0},
1295             {1, 0, -1, 0, 0},
1296             {1, 0, Long.MAX_VALUE - 1, Long.MAX_VALUE, 0},
1297             {1, 0, Long.MIN_VALUE, Long.MIN_VALUE + 1, 0},
1298             {1, 1, 0, 1, 1},
1299             {1, 1, 1, 2, 1},
1300             {1, 1, -1, 0, 1},
1301             {1, 1, Long.MAX_VALUE - 1, Long.MAX_VALUE, 1},
1302             {1, 1, Long.MIN_VALUE, Long.MIN_VALUE + 1, 1},
1303             {-1, 1, 0, -1, 1},
1304             {-1, 1, 1, 0, 1},
1305             {-1, 1, -1, -2, 1},
1306             {-1, 1, Long.MAX_VALUE, Long.MAX_VALUE - 1, 1},
1307             {-1, 1, Long.MIN_VALUE + 1, Long.MIN_VALUE, 1},
1308         };
1309     }
1310 
1311     @Test(dataProvider="PlusSeconds")
1312     public void plusSeconds_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
1313         Duration t = Duration.ofSeconds(seconds, nanos);
1314         t = t.plusSeconds(amount);
1315         assertEquals(t.getSeconds(), expectedSeconds);
1316         assertEquals(t.getNano(), expectedNanoOfSecond);
1317     }
1318 
1319     @Test(expectedExceptions = {ArithmeticException.class})
1320     public void plusSeconds_long_overflowTooBig() {
1321         Duration t = Duration.ofSeconds(1, 0);
1322         t.plusSeconds(Long.MAX_VALUE);
1323     }
1324 
1325     @Test(expectedExceptions = {ArithmeticException.class})
1326     public void plusSeconds_long_overflowTooSmall() {
1327         Duration t = Duration.ofSeconds(-1, 0);
1328         t.plusSeconds(Long.MIN_VALUE);
1329     }
1330 
1331     //-----------------------------------------------------------------------
1332     @DataProvider(name="PlusMillis")
1333     Object[][] provider_plusMillis_long() {
1334         return new Object[][] {
1335             {0, 0, 0,       0, 0},
1336             {0, 0, 1,       0, 1000000},
1337             {0, 0, 999,     0, 999000000},
1338             {0, 0, 1000,    1, 0},
1339             {0, 0, 1001,    1, 1000000},
1340             {0, 0, 1999,    1, 999000000},
1341             {0, 0, 2000,    2, 0},
1342             {0, 0, -1,      -1, 999000000},
1343             {0, 0, -999,    -1, 1000000},
1344             {0, 0, -1000,   -1, 0},
1345             {0, 0, -1001,   -2, 999000000},
1346             {0, 0, -1999,   -2, 1000000},
1347 
1348             {0, 1, 0,       0, 1},
1349             {0, 1, 1,       0, 1000001},
1350             {0, 1, 998,     0, 998000001},
1351             {0, 1, 999,     0, 999000001},
1352             {0, 1, 1000,    1, 1},
1353             {0, 1, 1998,    1, 998000001},
1354             {0, 1, 1999,    1, 999000001},
1355             {0, 1, 2000,    2, 1},
1356             {0, 1, -1,      -1, 999000001},
1357             {0, 1, -2,      -1, 998000001},
1358             {0, 1, -1000,   -1, 1},
1359             {0, 1, -1001,   -2, 999000001},
1360 
1361             {0, 1000000, 0,       0, 1000000},
1362             {0, 1000000, 1,       0, 2000000},
1363             {0, 1000000, 998,     0, 999000000},
1364             {0, 1000000, 999,     1, 0},
1365             {0, 1000000, 1000,    1, 1000000},
1366             {0, 1000000, 1998,    1, 999000000},
1367             {0, 1000000, 1999,    2, 0},
1368             {0, 1000000, 2000,    2, 1000000},
1369             {0, 1000000, -1,      0, 0},
1370             {0, 1000000, -2,      -1, 999000000},
1371             {0, 1000000, -999,    -1, 2000000},
1372             {0, 1000000, -1000,   -1, 1000000},
1373             {0, 1000000, -1001,   -1, 0},
1374             {0, 1000000, -1002,   -2, 999000000},
1375 
1376             {0, 999999999, 0,     0, 999999999},
1377             {0, 999999999, 1,     1, 999999},
1378             {0, 999999999, 999,   1, 998999999},
1379             {0, 999999999, 1000,  1, 999999999},
1380             {0, 999999999, 1001,  2, 999999},
1381             {0, 999999999, -1,    0, 998999999},
1382             {0, 999999999, -1000, -1, 999999999},
1383             {0, 999999999, -1001, -1, 998999999},
1384         };
1385     }
1386 
1387     @Test(dataProvider="PlusMillis")
1388     public void plusMillis_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
1389         Duration t = Duration.ofSeconds(seconds, nanos);
1390         t = t.plusMillis(amount);
1391         assertEquals(t.getSeconds(), expectedSeconds);
1392         assertEquals(t.getNano(), expectedNanoOfSecond);
1393     }
1394     @Test(dataProvider="PlusMillis")
1395     public void plusMillis_long_oneMore(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
1396         Duration t = Duration.ofSeconds(seconds + 1, nanos);
1397         t = t.plusMillis(amount);
1398         assertEquals(t.getSeconds(), expectedSeconds + 1);
1399         assertEquals(t.getNano(), expectedNanoOfSecond);
1400     }
1401     @Test(dataProvider="PlusMillis")
1402     public void plusMillis_long_minusOneLess(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
1403         Duration t = Duration.ofSeconds(seconds - 1, nanos);
1404         t = t.plusMillis(amount);
1405         assertEquals(t.getSeconds(), expectedSeconds - 1);
1406         assertEquals(t.getNano(), expectedNanoOfSecond);
1407     }
1408 
1409     @Test
1410     public void plusMillis_long_max() {
1411         Duration t = Duration.ofSeconds(Long.MAX_VALUE, 998999999);
1412         t = t.plusMillis(1);
1413         assertEquals(t.getSeconds(), Long.MAX_VALUE);
1414         assertEquals(t.getNano(), 999999999);
1415     }
1416 
1417     @Test(expectedExceptions = {ArithmeticException.class})
1418     public void plusMillis_long_overflowTooBig() {
1419         Duration t = Duration.ofSeconds(Long.MAX_VALUE, 999000000);
1420         t.plusMillis(1);
1421     }
1422 
1423     @Test
1424     public void plusMillis_long_min() {
1425         Duration t = Duration.ofSeconds(Long.MIN_VALUE, 1000000);
1426         t = t.plusMillis(-1);
1427         assertEquals(t.getSeconds(), Long.MIN_VALUE);
1428         assertEquals(t.getNano(), 0);
1429     }
1430 
1431     @Test(expectedExceptions = {ArithmeticException.class})
1432     public void plusMillis_long_overflowTooSmall() {
1433         Duration t = Duration.ofSeconds(Long.MIN_VALUE, 0);
1434         t.plusMillis(-1);
1435     }
1436 
1437     //-----------------------------------------------------------------------
1438     @DataProvider(name="PlusNanos")
1439     Object[][] provider_plusNanos_long() {
1440         return new Object[][] {
1441             {0, 0, 0,           0, 0},
1442             {0, 0, 1,           0, 1},
1443             {0, 0, 999999999,   0, 999999999},
1444             {0, 0, 1000000000,  1, 0},
1445             {0, 0, 1000000001,  1, 1},
1446             {0, 0, 1999999999,  1, 999999999},
1447             {0, 0, 2000000000,  2, 0},
1448             {0, 0, -1,          -1, 999999999},
1449             {0, 0, -999999999,  -1, 1},
1450             {0, 0, -1000000000, -1, 0},
1451             {0, 0, -1000000001, -2, 999999999},
1452             {0, 0, -1999999999, -2, 1},
1453 
1454             {1, 0, 0,           1, 0},
1455             {1, 0, 1,           1, 1},
1456             {1, 0, 999999999,   1, 999999999},
1457             {1, 0, 1000000000,  2, 0},
1458             {1, 0, 1000000001,  2, 1},
1459             {1, 0, 1999999999,  2, 999999999},
1460             {1, 0, 2000000000,  3, 0},
1461             {1, 0, -1,          0, 999999999},
1462             {1, 0, -999999999,  0, 1},
1463             {1, 0, -1000000000, 0, 0},
1464             {1, 0, -1000000001, -1, 999999999},
1465             {1, 0, -1999999999, -1, 1},
1466 
1467             {-1, 0, 0,           -1, 0},
1468             {-1, 0, 1,           -1, 1},
1469             {-1, 0, 999999999,   -1, 999999999},
1470             {-1, 0, 1000000000,  0, 0},
1471             {-1, 0, 1000000001,  0, 1},
1472             {-1, 0, 1999999999,  0, 999999999},
1473             {-1, 0, 2000000000,  1, 0},
1474             {-1, 0, -1,          -2, 999999999},
1475             {-1, 0, -999999999,  -2, 1},
1476             {-1, 0, -1000000000, -2, 0},
1477             {-1, 0, -1000000001, -3, 999999999},
1478             {-1, 0, -1999999999, -3, 1},
1479 
1480             {1, 1, 0,           1, 1},
1481             {1, 1, 1,           1, 2},
1482             {1, 1, 999999998,   1, 999999999},
1483             {1, 1, 999999999,   2, 0},
1484             {1, 1, 1000000000,  2, 1},
1485             {1, 1, 1999999998,  2, 999999999},
1486             {1, 1, 1999999999,  3, 0},
1487             {1, 1, 2000000000,  3, 1},
1488             {1, 1, -1,          1, 0},
1489             {1, 1, -2,          0, 999999999},
1490             {1, 1, -1000000000, 0, 1},
1491             {1, 1, -1000000001, 0, 0},
1492             {1, 1, -1000000002, -1, 999999999},
1493             {1, 1, -2000000000, -1, 1},
1494 
1495             {1, 999999999, 0,           1, 999999999},
1496             {1, 999999999, 1,           2, 0},
1497             {1, 999999999, 999999999,   2, 999999998},
1498             {1, 999999999, 1000000000,  2, 999999999},
1499             {1, 999999999, 1000000001,  3, 0},
1500             {1, 999999999, -1,          1, 999999998},
1501             {1, 999999999, -1000000000, 0, 999999999},
1502             {1, 999999999, -1000000001, 0, 999999998},
1503             {1, 999999999, -1999999999, 0, 0},
1504             {1, 999999999, -2000000000, -1, 999999999},
1505 
1506             {Long.MAX_VALUE, 0, 999999999, Long.MAX_VALUE, 999999999},
1507             {Long.MAX_VALUE - 1, 0, 1999999999, Long.MAX_VALUE, 999999999},
1508             {Long.MIN_VALUE, 1, -1, Long.MIN_VALUE, 0},
1509             {Long.MIN_VALUE + 1, 1, -1000000001, Long.MIN_VALUE, 0},
1510         };
1511     }
1512 
1513     @Test(dataProvider="PlusNanos")
1514     public void plusNanos_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
1515         Duration t = Duration.ofSeconds(seconds, nanos);
1516         t = t.plusNanos(amount);
1517         assertEquals(t.getSeconds(), expectedSeconds);
1518         assertEquals(t.getNano(), expectedNanoOfSecond);
1519     }
1520 
1521     @Test(expectedExceptions = {ArithmeticException.class})
1522     public void plusNanos_long_overflowTooBig() {
1523         Duration t = Duration.ofSeconds(Long.MAX_VALUE, 999999999);
1524         t.plusNanos(1);
1525     }
1526 
1527     @Test(expectedExceptions = {ArithmeticException.class})
1528     public void plusNanos_long_overflowTooSmall() {
1529         Duration t = Duration.ofSeconds(Long.MIN_VALUE, 0);
1530         t.plusNanos(-1);
1531     }
1532 
1533     //-----------------------------------------------------------------------
1534     @DataProvider(name="Minus")
1535     Object[][] provider_minus() {
1536         return new Object[][] {
1537             {Long.MIN_VALUE, 0, Long.MIN_VALUE + 1, 0, -1, 0},
1538 
1539             {-4, 666666667, -4, 666666667,  0,         0},
1540             {-4, 666666667, -3,         0, -1, 666666667},
1541             {-4, 666666667, -2,         0, -2, 666666667},
1542             {-4, 666666667, -1,         0, -3, 666666667},
1543             {-4, 666666667, -1, 333333334, -3, 333333333},
1544             {-4, 666666667, -1, 666666667, -3,         0},
1545             {-4, 666666667, -1, 999999999, -4, 666666668},
1546             {-4, 666666667,  0,         0, -4, 666666667},
1547             {-4, 666666667,  0,         1, -4, 666666666},
1548             {-4, 666666667,  0, 333333333, -4, 333333334},
1549             {-4, 666666667,  0, 666666666, -4,         1},
1550             {-4, 666666667,  1,         0, -5, 666666667},
1551             {-4, 666666667,  2,         0, -6, 666666667},
1552             {-4, 666666667,  3,         0, -7, 666666667},
1553             {-4, 666666667,  3, 333333333, -7, 333333334},
1554 
1555             {-3, 0, -4, 666666667,  0, 333333333},
1556             {-3, 0, -3,         0,  0,         0},
1557             {-3, 0, -2,         0, -1,         0},
1558             {-3, 0, -1,         0, -2,         0},
1559             {-3, 0, -1, 333333334, -3, 666666666},
1560             {-3, 0, -1, 666666667, -3, 333333333},
1561             {-3, 0, -1, 999999999, -3,         1},
1562             {-3, 0,  0,         0, -3,         0},
1563             {-3, 0,  0,         1, -4, 999999999},
1564             {-3, 0,  0, 333333333, -4, 666666667},
1565             {-3, 0,  0, 666666666, -4, 333333334},
1566             {-3, 0,  1,         0, -4,         0},
1567             {-3, 0,  2,         0, -5,         0},
1568             {-3, 0,  3,         0, -6,         0},
1569             {-3, 0,  3, 333333333, -7, 666666667},
1570 
1571             {-2, 0, -4, 666666667,  1, 333333333},
1572             {-2, 0, -3,         0,  1,         0},
1573             {-2, 0, -2,         0,  0,         0},
1574             {-2, 0, -1,         0, -1,         0},
1575             {-2, 0, -1, 333333334, -2, 666666666},
1576             {-2, 0, -1, 666666667, -2, 333333333},
1577             {-2, 0, -1, 999999999, -2,         1},
1578             {-2, 0,  0,         0, -2,         0},
1579             {-2, 0,  0,         1, -3, 999999999},
1580             {-2, 0,  0, 333333333, -3, 666666667},
1581             {-2, 0,  0, 666666666, -3, 333333334},
1582             {-2, 0,  1,         0, -3,         0},
1583             {-2, 0,  2,         0, -4,         0},
1584             {-2, 0,  3,         0, -5,         0},
1585             {-2, 0,  3, 333333333, -6, 666666667},
1586 
1587             {-1, 0, -4, 666666667,  2, 333333333},
1588             {-1, 0, -3,         0,  2,         0},
1589             {-1, 0, -2,         0,  1,         0},
1590             {-1, 0, -1,         0,  0,         0},
1591             {-1, 0, -1, 333333334, -1, 666666666},
1592             {-1, 0, -1, 666666667, -1, 333333333},
1593             {-1, 0, -1, 999999999, -1,         1},
1594             {-1, 0,  0,         0, -1,         0},
1595             {-1, 0,  0,         1, -2, 999999999},
1596             {-1, 0,  0, 333333333, -2, 666666667},
1597             {-1, 0,  0, 666666666, -2, 333333334},
1598             {-1, 0,  1,         0, -2,         0},
1599             {-1, 0,  2,         0, -3,         0},
1600             {-1, 0,  3,         0, -4,         0},
1601             {-1, 0,  3, 333333333, -5, 666666667},
1602 
1603             {-1, 666666667, -4, 666666667,  3,         0},
1604             {-1, 666666667, -3,         0,  2, 666666667},
1605             {-1, 666666667, -2,         0,  1, 666666667},
1606             {-1, 666666667, -1,         0,  0, 666666667},
1607             {-1, 666666667, -1, 333333334,  0, 333333333},
1608             {-1, 666666667, -1, 666666667,  0,         0},
1609             {-1, 666666667, -1, 999999999, -1, 666666668},
1610             {-1, 666666667,  0,         0, -1, 666666667},
1611             {-1, 666666667,  0,         1, -1, 666666666},
1612             {-1, 666666667,  0, 333333333, -1, 333333334},
1613             {-1, 666666667,  0, 666666666, -1,         1},
1614             {-1, 666666667,  1,         0, -2, 666666667},
1615             {-1, 666666667,  2,         0, -3, 666666667},
1616             {-1, 666666667,  3,         0, -4, 666666667},
1617             {-1, 666666667,  3, 333333333, -4, 333333334},
1618 
1619             {0, 0, -4, 666666667,  3, 333333333},
1620             {0, 0, -3,         0,  3,         0},
1621             {0, 0, -2,         0,  2,         0},
1622             {0, 0, -1,         0,  1,         0},
1623             {0, 0, -1, 333333334,  0, 666666666},
1624             {0, 0, -1, 666666667,  0, 333333333},
1625             {0, 0, -1, 999999999,  0,         1},
1626             {0, 0,  0,         0,  0,         0},
1627             {0, 0,  0,         1, -1, 999999999},
1628             {0, 0,  0, 333333333, -1, 666666667},
1629             {0, 0,  0, 666666666, -1, 333333334},
1630             {0, 0,  1,         0, -1,         0},
1631             {0, 0,  2,         0, -2,         0},
1632             {0, 0,  3,         0, -3,         0},
1633             {0, 0,  3, 333333333, -4, 666666667},
1634 
1635             {0, 333333333, -4, 666666667,  3, 666666666},
1636             {0, 333333333, -3,         0,  3, 333333333},
1637             {0, 333333333, -2,         0,  2, 333333333},
1638             {0, 333333333, -1,         0,  1, 333333333},
1639             {0, 333333333, -1, 333333334,  0, 999999999},
1640             {0, 333333333, -1, 666666667,  0, 666666666},
1641             {0, 333333333, -1, 999999999,  0, 333333334},
1642             {0, 333333333,  0,         0,  0, 333333333},
1643             {0, 333333333,  0,         1,  0, 333333332},
1644             {0, 333333333,  0, 333333333,  0,         0},
1645             {0, 333333333,  0, 666666666, -1, 666666667},
1646             {0, 333333333,  1,         0, -1, 333333333},
1647             {0, 333333333,  2,         0, -2, 333333333},
1648             {0, 333333333,  3,         0, -3, 333333333},
1649             {0, 333333333,  3, 333333333, -3,         0},
1650 
1651             {1, 0, -4, 666666667,  4, 333333333},
1652             {1, 0, -3,         0,  4,         0},
1653             {1, 0, -2,         0,  3,         0},
1654             {1, 0, -1,         0,  2,         0},
1655             {1, 0, -1, 333333334,  1, 666666666},
1656             {1, 0, -1, 666666667,  1, 333333333},
1657             {1, 0, -1, 999999999,  1,         1},
1658             {1, 0,  0,         0,  1,         0},
1659             {1, 0,  0,         1,  0, 999999999},
1660             {1, 0,  0, 333333333,  0, 666666667},
1661             {1, 0,  0, 666666666,  0, 333333334},
1662             {1, 0,  1,         0,  0,         0},
1663             {1, 0,  2,         0, -1,         0},
1664             {1, 0,  3,         0, -2,         0},
1665             {1, 0,  3, 333333333, -3, 666666667},
1666 
1667             {2, 0, -4, 666666667,  5, 333333333},
1668             {2, 0, -3,         0,  5,         0},
1669             {2, 0, -2,         0,  4,         0},
1670             {2, 0, -1,         0,  3,         0},
1671             {2, 0, -1, 333333334,  2, 666666666},
1672             {2, 0, -1, 666666667,  2, 333333333},
1673             {2, 0, -1, 999999999,  2,         1},
1674             {2, 0,  0,         0,  2,         0},
1675             {2, 0,  0,         1,  1, 999999999},
1676             {2, 0,  0, 333333333,  1, 666666667},
1677             {2, 0,  0, 666666666,  1, 333333334},
1678             {2, 0,  1,         0,  1,         0},
1679             {2, 0,  2,         0,  0,         0},
1680             {2, 0,  3,         0, -1,         0},
1681             {2, 0,  3, 333333333, -2, 666666667},
1682 
1683             {3, 0, -4, 666666667,  6, 333333333},
1684             {3, 0, -3,         0,  6,         0},
1685             {3, 0, -2,         0,  5,         0},
1686             {3, 0, -1,         0,  4,         0},
1687             {3, 0, -1, 333333334,  3, 666666666},
1688             {3, 0, -1, 666666667,  3, 333333333},
1689             {3, 0, -1, 999999999,  3,         1},
1690             {3, 0,  0,         0,  3,         0},
1691             {3, 0,  0,         1,  2, 999999999},
1692             {3, 0,  0, 333333333,  2, 666666667},
1693             {3, 0,  0, 666666666,  2, 333333334},
1694             {3, 0,  1,         0,  2,         0},
1695             {3, 0,  2,         0,  1,         0},
1696             {3, 0,  3,         0,  0,         0},
1697             {3, 0,  3, 333333333, -1, 666666667},
1698 
1699             {3, 333333333, -4, 666666667,  6, 666666666},
1700             {3, 333333333, -3,         0,  6, 333333333},
1701             {3, 333333333, -2,         0,  5, 333333333},
1702             {3, 333333333, -1,         0,  4, 333333333},
1703             {3, 333333333, -1, 333333334,  3, 999999999},
1704             {3, 333333333, -1, 666666667,  3, 666666666},
1705             {3, 333333333, -1, 999999999,  3, 333333334},
1706             {3, 333333333,  0,         0,  3, 333333333},
1707             {3, 333333333,  0,         1,  3, 333333332},
1708             {3, 333333333,  0, 333333333,  3,         0},
1709             {3, 333333333,  0, 666666666,  2, 666666667},
1710             {3, 333333333,  1,         0,  2, 333333333},
1711             {3, 333333333,  2,         0,  1, 333333333},
1712             {3, 333333333,  3,         0,  0, 333333333},
1713             {3, 333333333,  3, 333333333,  0,         0},
1714 
1715             {Long.MAX_VALUE, 0, Long.MAX_VALUE, 0, 0, 0},
1716        };
1717     }
1718 
1719     @Test(dataProvider="Minus")
1720     public void minus(long seconds, int nanos, long otherSeconds, int otherNanos, long expectedSeconds, int expectedNanoOfSecond) {
1721        Duration t = Duration.ofSeconds(seconds, nanos).minus(Duration.ofSeconds(otherSeconds, otherNanos));
1722        assertEquals(t.getSeconds(), expectedSeconds);
1723        assertEquals(t.getNano(), expectedNanoOfSecond);
1724     }
1725 
1726     @Test(expectedExceptions=ArithmeticException.class)
1727     public void minusOverflowTooSmall() {
1728        Duration t = Duration.ofSeconds(Long.MIN_VALUE);
1729        t.minus(Duration.ofSeconds(0, 1));
1730     }
1731 
1732     @Test(expectedExceptions=ArithmeticException.class)
1733     public void minusOverflowTooBig() {
1734        Duration t = Duration.ofSeconds(Long.MAX_VALUE, 999999999);
1735        t.minus(Duration.ofSeconds(-1, 999999999));
1736     }
1737 
1738     //-----------------------------------------------------------------------
1739     @Test
1740     public void minus_longTemporalUnit_seconds() {
1741         Duration t = Duration.ofSeconds(1);
1742         t = t.minus(1, SECONDS);
1743         assertEquals(0, t.getSeconds());
1744         assertEquals(0, t.getNano());
1745      }
1746 
1747     @Test
1748     public void minus_longTemporalUnit_millis() {
1749         Duration t = Duration.ofSeconds(1);
1750         t = t.minus(1, MILLIS);
1751         assertEquals(0, t.getSeconds());
1752         assertEquals(999000000, t.getNano());
1753      }
1754 
1755     @Test
1756     public void minus_longTemporalUnit_micros() {
1757         Duration t = Duration.ofSeconds(1);
1758         t = t.minus(1, MICROS);
1759         assertEquals(0, t.getSeconds());
1760         assertEquals(999999000, t.getNano());
1761      }
1762 
1763     @Test
1764     public void minus_longTemporalUnit_nanos() {
1765         Duration t = Duration.ofSeconds(1);
1766         t = t.minus(1, NANOS);
1767         assertEquals(0, t.getSeconds());
1768         assertEquals(999999999, t.getNano());
1769      }
1770 
1771     @Test(expectedExceptions=NullPointerException.class)
1772     public void minus_longTemporalUnit_null() {
1773        Duration t = Duration.ofSeconds(1);
1774        t.minus(1, (TemporalUnit) null);
1775     }
1776 
1777     //-----------------------------------------------------------------------
1778     @DataProvider(name="MinusDays")
1779     Object[][] provider_minusDays_long() {
1780         return new Object[][] {
1781             {0, 0, 0},
1782             {0, 1, -1},
1783             {0, -1, 1},
1784             {Long.MAX_VALUE/3600/24, 0, Long.MAX_VALUE/3600/24},
1785             {Long.MIN_VALUE/3600/24, 0, Long.MIN_VALUE/3600/24},
1786             {1, 0, 1},
1787             {1, 1, 0},
1788             {1, -1, 2},
1789             {Long.MAX_VALUE/3600/24, 1, Long.MAX_VALUE/3600/24 - 1},
1790             {Long.MIN_VALUE/3600/24, -1, Long.MIN_VALUE/3600/24 + 1},
1791             {1, 0, 1},
1792             {1, 1, 0},
1793             {1, -1, 2},
1794             {-1, 0, -1},
1795             {-1, 1, -2},
1796             {-1, -1, 0},
1797         };
1798     }
1799 
1800     @Test(dataProvider="MinusDays")
1801     public void minusDays_long(long days, long amount, long expectedDays) {
1802         Duration t = Duration.ofDays(days);
1803         t = t.minusDays(amount);
1804         assertEquals(t.toDays(), expectedDays);
1805     }
1806 
1807     @Test(expectedExceptions = {ArithmeticException.class})
1808     public void minusDays_long_overflowTooBig() {
1809         Duration t = Duration.ofDays(Long.MAX_VALUE/3600/24);
1810         t.minusDays(-1);
1811     }
1812 
1813     @Test(expectedExceptions = {ArithmeticException.class})
1814     public void minusDays_long_overflowTooSmall() {
1815         Duration t = Duration.ofDays(Long.MIN_VALUE/3600/24);
1816         t.minusDays(1);
1817     }
1818 
1819     //-----------------------------------------------------------------------
1820     @DataProvider(name="MinusHours")
1821     Object[][] provider_minusHours_long() {
1822         return new Object[][] {
1823             {0, 0, 0},
1824             {0, 1, -1},
1825             {0, -1, 1},
1826             {Long.MAX_VALUE/3600, 0, Long.MAX_VALUE/3600},
1827             {Long.MIN_VALUE/3600, 0, Long.MIN_VALUE/3600},
1828             {1, 0, 1},
1829             {1, 1, 0},
1830             {1, -1, 2},
1831             {Long.MAX_VALUE/3600, 1, Long.MAX_VALUE/3600 - 1},
1832             {Long.MIN_VALUE/3600, -1, Long.MIN_VALUE/3600 + 1},
1833             {1, 0, 1},
1834             {1, 1, 0},
1835             {1, -1, 2},
1836             {-1, 0, -1},
1837             {-1, 1, -2},
1838             {-1, -1, 0},
1839         };
1840     }
1841 
1842     @Test(dataProvider="MinusHours")
1843     public void minusHours_long(long hours, long amount, long expectedHours) {
1844         Duration t = Duration.ofHours(hours);
1845         t = t.minusHours(amount);
1846         assertEquals(t.toHours(), expectedHours);
1847     }
1848 
1849     @Test(expectedExceptions = {ArithmeticException.class})
1850     public void minusHours_long_overflowTooBig() {
1851         Duration t = Duration.ofHours(Long.MAX_VALUE/3600);
1852         t.minusHours(-1);
1853     }
1854 
1855     @Test(expectedExceptions = {ArithmeticException.class})
1856     public void minusHours_long_overflowTooSmall() {
1857         Duration t = Duration.ofHours(Long.MIN_VALUE/3600);
1858         t.minusHours(1);
1859     }
1860 
1861     //-----------------------------------------------------------------------
1862     @DataProvider(name="MinusMinutes")
1863     Object[][] provider_minusminutes_long() {
1864         return new Object[][] {
1865             {0, 0, 0},
1866             {0, 1, -1},
1867             {0, -1, 1},
1868             {Long.MAX_VALUE/60, 0, Long.MAX_VALUE/60},
1869             {Long.MIN_VALUE/60, 0, Long.MIN_VALUE/60},
1870             {1, 0, 1},
1871             {1, 1, 0},
1872             {1, -1, 2},
1873             {Long.MAX_VALUE/60, 1, Long.MAX_VALUE/60 - 1},
1874             {Long.MIN_VALUE/60, -1, Long.MIN_VALUE/60 + 1},
1875             {1, 0, 1},
1876             {1, 1, 0},
1877             {1, -1, 2},
1878             {-1, 0, -1},
1879             {-1, 1, -2},
1880             {-1, -1, 0},
1881         };
1882     }
1883 
1884     @Test(dataProvider="MinusMinutes")
1885     public void minusMinutes_long(long minutes, long amount, long expectedMinutes) {
1886         Duration t = Duration.ofMinutes(minutes);
1887         t = t.minusMinutes(amount);
1888         assertEquals(t.toMinutes(), expectedMinutes);
1889     }
1890 
1891     @Test(expectedExceptions = {ArithmeticException.class})
1892     public void minusMinutes_long_overflowTooBig() {
1893         Duration t = Duration.ofMinutes(Long.MAX_VALUE/60);
1894         t.minusMinutes(-1);
1895     }
1896 
1897     @Test(expectedExceptions = {ArithmeticException.class})
1898     public void minusMinutes_long_overflowTooSmall() {
1899         Duration t = Duration.ofMinutes(Long.MIN_VALUE/60);
1900         t.minusMinutes(1);
1901     }
1902 
1903     //-----------------------------------------------------------------------
1904     @DataProvider(name="MinusSeconds")
1905     Object[][] provider_minusSeconds_long() {
1906         return new Object[][] {
1907             {0, 0, 0, 0, 0},
1908             {0, 0, 1, -1, 0},
1909             {0, 0, -1, 1, 0},
1910             {0, 0, Long.MAX_VALUE, -Long.MAX_VALUE, 0},
1911             {0, 0, Long.MIN_VALUE + 1, Long.MAX_VALUE, 0},
1912             {1, 0, 0, 1, 0},
1913             {1, 0, 1, 0, 0},
1914             {1, 0, -1, 2, 0},
1915             {1, 0, Long.MAX_VALUE - 1, -Long.MAX_VALUE + 2, 0},
1916             {1, 0, Long.MIN_VALUE + 2, Long.MAX_VALUE, 0},
1917             {1, 1, 0, 1, 1},
1918             {1, 1, 1, 0, 1},
1919             {1, 1, -1, 2, 1},
1920             {1, 1, Long.MAX_VALUE, -Long.MAX_VALUE + 1, 1},
1921             {1, 1, Long.MIN_VALUE + 2, Long.MAX_VALUE, 1},
1922             {-1, 1, 0, -1, 1},
1923             {-1, 1, 1, -2, 1},
1924             {-1, 1, -1, 0, 1},
1925             {-1, 1, Long.MAX_VALUE, Long.MIN_VALUE, 1},
1926             {-1, 1, Long.MIN_VALUE + 1, Long.MAX_VALUE - 1, 1},
1927         };
1928     }
1929 
1930     @Test(dataProvider="MinusSeconds")
1931     public void minusSeconds_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
1932         Duration t = Duration.ofSeconds(seconds, nanos);
1933         t = t.minusSeconds(amount);
1934         assertEquals(t.getSeconds(), expectedSeconds);
1935         assertEquals(t.getNano(), expectedNanoOfSecond);
1936     }
1937 
1938     @Test(expectedExceptions = {ArithmeticException.class})
1939     public void minusSeconds_long_overflowTooBig() {
1940         Duration t = Duration.ofSeconds(1, 0);
1941         t.minusSeconds(Long.MIN_VALUE + 1);
1942     }
1943 
1944     @Test(expectedExceptions = {ArithmeticException.class})
1945     public void minusSeconds_long_overflowTooSmall() {
1946         Duration t = Duration.ofSeconds(-2, 0);
1947         t.minusSeconds(Long.MAX_VALUE);
1948     }
1949 
1950     //-----------------------------------------------------------------------
1951     @DataProvider(name="MinusMillis")
1952     Object[][] provider_minusMillis_long() {
1953         return new Object[][] {
1954             {0, 0, 0,       0, 0},
1955             {0, 0, 1,      -1, 999000000},
1956             {0, 0, 999,    -1, 1000000},
1957             {0, 0, 1000,   -1, 0},
1958             {0, 0, 1001,   -2, 999000000},
1959             {0, 0, 1999,   -2, 1000000},
1960             {0, 0, 2000,   -2, 0},
1961             {0, 0, -1,      0, 1000000},
1962             {0, 0, -999,    0, 999000000},
1963             {0, 0, -1000,   1, 0},
1964             {0, 0, -1001,   1, 1000000},
1965             {0, 0, -1999,   1, 999000000},
1966 
1967             {0, 1, 0,       0, 1},
1968             {0, 1, 1,      -1, 999000001},
1969             {0, 1, 998,    -1, 2000001},
1970             {0, 1, 999,    -1, 1000001},
1971             {0, 1, 1000,   -1, 1},
1972             {0, 1, 1998,   -2, 2000001},
1973             {0, 1, 1999,   -2, 1000001},
1974             {0, 1, 2000,   -2, 1},
1975             {0, 1, -1,      0, 1000001},
1976             {0, 1, -2,      0, 2000001},
1977             {0, 1, -1000,   1, 1},
1978             {0, 1, -1001,   1, 1000001},
1979 
1980             {0, 1000000, 0,       0, 1000000},
1981             {0, 1000000, 1,       0, 0},
1982             {0, 1000000, 998,    -1, 3000000},
1983             {0, 1000000, 999,    -1, 2000000},
1984             {0, 1000000, 1000,   -1, 1000000},
1985             {0, 1000000, 1998,   -2, 3000000},
1986             {0, 1000000, 1999,   -2, 2000000},
1987             {0, 1000000, 2000,   -2, 1000000},
1988             {0, 1000000, -1,      0, 2000000},
1989             {0, 1000000, -2,      0, 3000000},
1990             {0, 1000000, -999,    1, 0},
1991             {0, 1000000, -1000,   1, 1000000},
1992             {0, 1000000, -1001,   1, 2000000},
1993             {0, 1000000, -1002,   1, 3000000},
1994 
1995             {0, 999999999, 0,     0, 999999999},
1996             {0, 999999999, 1,     0, 998999999},
1997             {0, 999999999, 999,   0, 999999},
1998             {0, 999999999, 1000, -1, 999999999},
1999             {0, 999999999, 1001, -1, 998999999},
2000             {0, 999999999, -1,    1, 999999},
2001             {0, 999999999, -1000, 1, 999999999},
2002             {0, 999999999, -1001, 2, 999999},
2003         };
2004     }
2005 
2006     @Test(dataProvider="MinusMillis")
2007     public void minusMillis_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
2008         Duration t = Duration.ofSeconds(seconds, nanos);
2009         t = t.minusMillis(amount);
2010         assertEquals(t.getSeconds(), expectedSeconds);
2011         assertEquals(t.getNano(), expectedNanoOfSecond);
2012     }
2013     @Test(dataProvider="MinusMillis")
2014     public void minusMillis_long_oneMore(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
2015         Duration t = Duration.ofSeconds(seconds + 1, nanos);
2016         t = t.minusMillis(amount);
2017         assertEquals(t.getSeconds(), expectedSeconds + 1);
2018         assertEquals(t.getNano(), expectedNanoOfSecond);
2019     }
2020     @Test(dataProvider="MinusMillis")
2021     public void minusMillis_long_minusOneLess(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
2022         Duration t = Duration.ofSeconds(seconds - 1, nanos);
2023         t = t.minusMillis(amount);
2024         assertEquals(t.getSeconds(), expectedSeconds - 1);
2025         assertEquals(t.getNano(), expectedNanoOfSecond);
2026     }
2027 
2028     @Test
2029     public void minusMillis_long_max() {
2030         Duration t = Duration.ofSeconds(Long.MAX_VALUE, 998999999);
2031         t = t.minusMillis(-1);
2032         assertEquals(t.getSeconds(), Long.MAX_VALUE);
2033         assertEquals(t.getNano(), 999999999);
2034     }
2035 
2036     @Test(expectedExceptions = {ArithmeticException.class})
2037     public void minusMillis_long_overflowTooBig() {
2038         Duration t = Duration.ofSeconds(Long.MAX_VALUE, 999000000);
2039         t.minusMillis(-1);
2040     }
2041 
2042     @Test
2043     public void minusMillis_long_min() {
2044         Duration t = Duration.ofSeconds(Long.MIN_VALUE, 1000000);
2045         t = t.minusMillis(1);
2046         assertEquals(t.getSeconds(), Long.MIN_VALUE);
2047         assertEquals(t.getNano(), 0);
2048     }
2049 
2050     @Test(expectedExceptions = {ArithmeticException.class})
2051     public void minusMillis_long_overflowTooSmall() {
2052         Duration t = Duration.ofSeconds(Long.MIN_VALUE, 0);
2053         t.minusMillis(1);
2054     }
2055 
2056     //-----------------------------------------------------------------------
2057     @DataProvider(name="MinusNanos")
2058     Object[][] provider_minusNanos_long() {
2059         return new Object[][] {
2060             {0, 0, 0,           0, 0},
2061             {0, 0, 1,          -1, 999999999},
2062             {0, 0, 999999999,  -1, 1},
2063             {0, 0, 1000000000, -1, 0},
2064             {0, 0, 1000000001, -2, 999999999},
2065             {0, 0, 1999999999, -2, 1},
2066             {0, 0, 2000000000, -2, 0},
2067             {0, 0, -1,          0, 1},
2068             {0, 0, -999999999,  0, 999999999},
2069             {0, 0, -1000000000, 1, 0},
2070             {0, 0, -1000000001, 1, 1},
2071             {0, 0, -1999999999, 1, 999999999},
2072 
2073             {1, 0, 0,            1, 0},
2074             {1, 0, 1,            0, 999999999},
2075             {1, 0, 999999999,    0, 1},
2076             {1, 0, 1000000000,   0, 0},
2077             {1, 0, 1000000001,  -1, 999999999},
2078             {1, 0, 1999999999,  -1, 1},
2079             {1, 0, 2000000000,  -1, 0},
2080             {1, 0, -1,           1, 1},
2081             {1, 0, -999999999,   1, 999999999},
2082             {1, 0, -1000000000,  2, 0},
2083             {1, 0, -1000000001,  2, 1},
2084             {1, 0, -1999999999,  2, 999999999},
2085 
2086             {-1, 0, 0,           -1, 0},
2087             {-1, 0, 1,           -2, 999999999},
2088             {-1, 0, 999999999,   -2, 1},
2089             {-1, 0, 1000000000,  -2, 0},
2090             {-1, 0, 1000000001,  -3, 999999999},
2091             {-1, 0, 1999999999,  -3, 1},
2092             {-1, 0, 2000000000,  -3, 0},
2093             {-1, 0, -1,          -1, 1},
2094             {-1, 0, -999999999,  -1, 999999999},
2095             {-1, 0, -1000000000,  0, 0},
2096             {-1, 0, -1000000001,  0, 1},
2097             {-1, 0, -1999999999,  0, 999999999},
2098 
2099             {1, 1, 0,           1, 1},
2100             {1, 1, 1,           1, 0},
2101             {1, 1, 999999998,   0, 3},
2102             {1, 1, 999999999,   0, 2},
2103             {1, 1, 1000000000,  0, 1},
2104             {1, 1, 1999999998, -1, 3},
2105             {1, 1, 1999999999, -1, 2},
2106             {1, 1, 2000000000, -1, 1},
2107             {1, 1, -1,          1, 2},
2108             {1, 1, -2,          1, 3},
2109             {1, 1, -1000000000, 2, 1},
2110             {1, 1, -1000000001, 2, 2},
2111             {1, 1, -1000000002, 2, 3},
2112             {1, 1, -2000000000, 3, 1},
2113 
2114             {1, 999999999, 0,           1, 999999999},
2115             {1, 999999999, 1,           1, 999999998},
2116             {1, 999999999, 999999999,   1, 0},
2117             {1, 999999999, 1000000000,  0, 999999999},
2118             {1, 999999999, 1000000001,  0, 999999998},
2119             {1, 999999999, -1,          2, 0},
2120             {1, 999999999, -1000000000, 2, 999999999},
2121             {1, 999999999, -1000000001, 3, 0},
2122             {1, 999999999, -1999999999, 3, 999999998},
2123             {1, 999999999, -2000000000, 3, 999999999},
2124 
2125             {Long.MAX_VALUE, 0, -999999999, Long.MAX_VALUE, 999999999},
2126             {Long.MAX_VALUE - 1, 0, -1999999999, Long.MAX_VALUE, 999999999},
2127             {Long.MIN_VALUE, 1, 1, Long.MIN_VALUE, 0},
2128             {Long.MIN_VALUE + 1, 1, 1000000001, Long.MIN_VALUE, 0},
2129         };
2130     }
2131 
2132     @Test(dataProvider="MinusNanos")
2133     public void minusNanos_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
2134         Duration t = Duration.ofSeconds(seconds, nanos);
2135         t = t.minusNanos(amount);
2136         assertEquals(t.getSeconds(), expectedSeconds);
2137         assertEquals(t.getNano(), expectedNanoOfSecond);
2138     }
2139 
2140     @Test(expectedExceptions = {ArithmeticException.class})
2141     public void minusNanos_long_overflowTooBig() {
2142         Duration t = Duration.ofSeconds(Long.MAX_VALUE, 999999999);
2143         t.minusNanos(-1);
2144     }
2145 
2146     @Test(expectedExceptions = {ArithmeticException.class})
2147     public void minusNanos_long_overflowTooSmall() {
2148         Duration t = Duration.ofSeconds(Long.MIN_VALUE, 0);
2149         t.minusNanos(1);
2150     }
2151 
2152     //-----------------------------------------------------------------------
2153     // multipliedBy()
2154     //-----------------------------------------------------------------------
2155     @DataProvider(name="MultipliedBy")
2156     Object[][] provider_multipliedBy() {
2157        return new Object[][] {
2158           {-4, 666666667, -3,   9, 999999999},
2159           {-4, 666666667, -2,   6, 666666666},
2160           {-4, 666666667, -1,   3, 333333333},
2161           {-4, 666666667,  0,   0,         0},
2162           {-4, 666666667,  1,  -4, 666666667},
2163           {-4, 666666667,  2,  -7, 333333334},
2164           {-4, 666666667,  3, -10, 000000001},
2165 
2166           {-3, 0, -3,  9, 0},
2167           {-3, 0, -2,  6, 0},
2168           {-3, 0, -1,  3, 0},
2169           {-3, 0,  0,  0, 0},
2170           {-3, 0,  1, -3, 0},
2171           {-3, 0,  2, -6, 0},
2172           {-3, 0,  3, -9, 0},
2173 
2174           {-2, 0, -3,  6, 0},
2175           {-2, 0, -2,  4, 0},
2176           {-2, 0, -1,  2, 0},
2177           {-2, 0,  0,  0, 0},
2178           {-2, 0,  1, -2, 0},
2179           {-2, 0,  2, -4, 0},
2180           {-2, 0,  3, -6, 0},
2181 
2182           {-1, 0, -3,  3, 0},
2183           {-1, 0, -2,  2, 0},
2184           {-1, 0, -1,  1, 0},
2185           {-1, 0,  0,  0, 0},
2186           {-1, 0,  1, -1, 0},
2187           {-1, 0,  2, -2, 0},
2188           {-1, 0,  3, -3, 0},
2189 
2190           {-1, 500000000, -3,  1, 500000000},
2191           {-1, 500000000, -2,  1,         0},
2192           {-1, 500000000, -1,  0, 500000000},
2193           {-1, 500000000,  0,  0,         0},
2194           {-1, 500000000,  1, -1, 500000000},
2195           {-1, 500000000,  2, -1,         0},
2196           {-1, 500000000,  3, -2, 500000000},
2197 
2198           {0, 0, -3, 0, 0},
2199           {0, 0, -2, 0, 0},
2200           {0, 0, -1, 0, 0},
2201           {0, 0,  0, 0, 0},
2202           {0, 0,  1, 0, 0},
2203           {0, 0,  2, 0, 0},
2204           {0, 0,  3, 0, 0},
2205 
2206           {0, 500000000, -3, -2, 500000000},
2207           {0, 500000000, -2, -1,         0},
2208           {0, 500000000, -1, -1, 500000000},
2209           {0, 500000000,  0,  0,         0},
2210           {0, 500000000,  1,  0, 500000000},
2211           {0, 500000000,  2,  1,         0},
2212           {0, 500000000,  3,  1, 500000000},
2213 
2214           {1, 0, -3, -3, 0},
2215           {1, 0, -2, -2, 0},
2216           {1, 0, -1, -1, 0},
2217           {1, 0,  0,  0, 0},
2218           {1, 0,  1,  1, 0},
2219           {1, 0,  2,  2, 0},
2220           {1, 0,  3,  3, 0},
2221 
2222           {2, 0, -3, -6, 0},
2223           {2, 0, -2, -4, 0},
2224           {2, 0, -1, -2, 0},
2225           {2, 0,  0,  0, 0},
2226           {2, 0,  1,  2, 0},
2227           {2, 0,  2,  4, 0},
2228           {2, 0,  3,  6, 0},
2229 
2230           {3, 0, -3, -9, 0},
2231           {3, 0, -2, -6, 0},
2232           {3, 0, -1, -3, 0},
2233           {3, 0,  0,  0, 0},
2234           {3, 0,  1,  3, 0},
2235           {3, 0,  2,  6, 0},
2236           {3, 0,  3,  9, 0},
2237 
2238           {3, 333333333, -3, -10, 000000001},
2239           {3, 333333333, -2,  -7, 333333334},
2240           {3, 333333333, -1,  -4, 666666667},
2241           {3, 333333333,  0,   0,         0},
2242           {3, 333333333,  1,   3, 333333333},
2243           {3, 333333333,  2,   6, 666666666},
2244           {3, 333333333,  3,   9, 999999999},
2245        };
2246     }
2247 
2248     @Test(dataProvider="MultipliedBy")
2249     public void multipliedBy(long seconds, int nanos, int multiplicand, long expectedSeconds, int expectedNanos) {
2250         Duration t = Duration.ofSeconds(seconds, nanos);
2251         t = t.multipliedBy(multiplicand);
2252         assertEquals(t.getSeconds(), expectedSeconds);
2253         assertEquals(t.getNano(), expectedNanos);
2254     }
2255 
2256     @Test
2257     public void multipliedBy_max() {
2258         Duration test = Duration.ofSeconds(1);
2259         assertEquals(test.multipliedBy(Long.MAX_VALUE), Duration.ofSeconds(Long.MAX_VALUE));
2260     }
2261 
2262     @Test
2263     public void multipliedBy_min() {
2264         Duration test = Duration.ofSeconds(1);
2265         assertEquals(test.multipliedBy(Long.MIN_VALUE), Duration.ofSeconds(Long.MIN_VALUE));
2266     }
2267 
2268     @Test(expectedExceptions=ArithmeticException.class)
2269     public void multipliedBy_tooBig() {
2270         Duration test = Duration.ofSeconds(1, 1);
2271         test.multipliedBy(Long.MAX_VALUE);
2272     }
2273 
2274     @Test(expectedExceptions=ArithmeticException.class)
2275     public void multipliedBy_tooBig_negative() {
2276         Duration test = Duration.ofSeconds(1, 1);
2277         test.multipliedBy(Long.MIN_VALUE);
2278     }
2279 
2280     //-----------------------------------------------------------------------
2281     // dividedBy()
2282     //-----------------------------------------------------------------------
2283     @DataProvider(name="DividedBy")
2284     Object[][] provider_dividedBy() {
2285        return new Object[][] {
2286           {-4, 666666667, -3,  1, 111111111},
2287           {-4, 666666667, -2,  1, 666666666},
2288           {-4, 666666667, -1,  3, 333333333},
2289           {-4, 666666667,  1, -4, 666666667},
2290           {-4, 666666667,  2, -2, 333333334},
2291           {-4, 666666667,  3, -2, 888888889},
2292 
2293           {-3, 0, -3,  1, 0},
2294           {-3, 0, -2,  1, 500000000},
2295           {-3, 0, -1,  3, 0},
2296           {-3, 0,  1, -3, 0},
2297           {-3, 0,  2, -2, 500000000},
2298           {-3, 0,  3, -1, 0},
2299 
2300           {-2, 0, -3,  0, 666666666},
2301           {-2, 0, -2,  1,         0},
2302           {-2, 0, -1,  2,         0},
2303           {-2, 0,  1, -2,         0},
2304           {-2, 0,  2, -1,         0},
2305           {-2, 0,  3, -1, 333333334},
2306 
2307           {-1, 0, -3,  0, 333333333},
2308           {-1, 0, -2,  0, 500000000},
2309           {-1, 0, -1,  1,         0},
2310           {-1, 0,  1, -1,         0},
2311           {-1, 0,  2, -1, 500000000},
2312           {-1, 0,  3, -1, 666666667},
2313 
2314           {-1, 500000000, -3,  0, 166666666},
2315           {-1, 500000000, -2,  0, 250000000},
2316           {-1, 500000000, -1,  0, 500000000},
2317           {-1, 500000000,  1, -1, 500000000},
2318           {-1, 500000000,  2, -1, 750000000},
2319           {-1, 500000000,  3, -1, 833333334},
2320 
2321           {0, 0, -3, 0, 0},
2322           {0, 0, -2, 0, 0},
2323           {0, 0, -1, 0, 0},
2324           {0, 0,  1, 0, 0},
2325           {0, 0,  2, 0, 0},
2326           {0, 0,  3, 0, 0},
2327 
2328           {0, 500000000, -3, -1, 833333334},
2329           {0, 500000000, -2, -1, 750000000},
2330           {0, 500000000, -1, -1, 500000000},
2331           {0, 500000000,  1,  0, 500000000},
2332           {0, 500000000,  2,  0, 250000000},
2333           {0, 500000000,  3,  0, 166666666},
2334 
2335           {1, 0, -3, -1, 666666667},
2336           {1, 0, -2, -1, 500000000},
2337           {1, 0, -1, -1,         0},
2338           {1, 0,  1,  1,         0},
2339           {1, 0,  2,  0, 500000000},
2340           {1, 0,  3,  0, 333333333},
2341 
2342           {2, 0, -3, -1, 333333334},
2343           {2, 0, -2, -1,         0},
2344           {2, 0, -1, -2,         0},
2345           {2, 0,  1,  2,         0},
2346           {2, 0,  2,  1,         0},
2347           {2, 0,  3,  0, 666666666},
2348 
2349           {3, 0, -3, -1,         0},
2350           {3, 0, -2, -2, 500000000},
2351           {3, 0, -1, -3,         0},
2352           {3, 0,  1,  3,         0},
2353           {3, 0,  2,  1, 500000000},
2354           {3, 0,  3,  1,         0},
2355 
2356           {3, 333333333, -3, -2, 888888889},
2357           {3, 333333333, -2, -2, 333333334},
2358           {3, 333333333, -1, -4, 666666667},
2359           {3, 333333333,  1,  3, 333333333},
2360           {3, 333333333,  2,  1, 666666666},
2361           {3, 333333333,  3,  1, 111111111},
2362        };
2363     }
2364 
2365     @Test(dataProvider="DividedBy")
2366     public void dividedBy(long seconds, int nanos, int divisor, long expectedSeconds, int expectedNanos) {
2367         Duration t = Duration.ofSeconds(seconds, nanos);
2368         t = t.dividedBy(divisor);
2369         assertEquals(t.getSeconds(), expectedSeconds);
2370         assertEquals(t.getNano(), expectedNanos);
2371     }
2372 
2373     @Test(dataProvider="DividedBy", expectedExceptions=ArithmeticException.class)
2374     public void dividedByZero(long seconds, int nanos, int divisor, long expectedSeconds, int expectedNanos) {
2375        Duration t = Duration.ofSeconds(seconds, nanos);
2376        t.dividedBy(0);
2377        fail(t + " divided by zero did not throw ArithmeticException");
2378     }
2379 
2380     @Test
2381     public void dividedBy_max() {
2382         Duration test = Duration.ofSeconds(Long.MAX_VALUE);
2383         assertEquals(test.dividedBy(Long.MAX_VALUE), Duration.ofSeconds(1));
2384     }
2385 
2386     //-----------------------------------------------------------------------
2387     // negated()
2388     //-----------------------------------------------------------------------
2389     @Test
2390     public void test_negated() {
2391         assertEquals(Duration.ofSeconds(0).negated(), Duration.ofSeconds(0));
2392         assertEquals(Duration.ofSeconds(12).negated(), Duration.ofSeconds(-12));
2393         assertEquals(Duration.ofSeconds(-12).negated(), Duration.ofSeconds(12));
2394         assertEquals(Duration.ofSeconds(12, 20).negated(), Duration.ofSeconds(-12, -20));
2395         assertEquals(Duration.ofSeconds(12, -20).negated(), Duration.ofSeconds(-12, 20));
2396         assertEquals(Duration.ofSeconds(-12, -20).negated(), Duration.ofSeconds(12, 20));
2397         assertEquals(Duration.ofSeconds(-12, 20).negated(), Duration.ofSeconds(12, -20));
2398         assertEquals(Duration.ofSeconds(Long.MAX_VALUE).negated(), Duration.ofSeconds(-Long.MAX_VALUE));
2399     }
2400 
2401     @Test(expectedExceptions=ArithmeticException.class)
2402     public void test_negated_overflow() {
2403         Duration.ofSeconds(Long.MIN_VALUE).negated();
2404     }
2405 
2406     //-----------------------------------------------------------------------
2407     // abs()
2408     //-----------------------------------------------------------------------
2409     @Test
2410     public void test_abs() {
2411         assertEquals(Duration.ofSeconds(0).abs(), Duration.ofSeconds(0));
2412         assertEquals(Duration.ofSeconds(12).abs(), Duration.ofSeconds(12));
2413         assertEquals(Duration.ofSeconds(-12).abs(), Duration.ofSeconds(12));
2414         assertEquals(Duration.ofSeconds(12, 20).abs(), Duration.ofSeconds(12, 20));
2415         assertEquals(Duration.ofSeconds(12, -20).abs(), Duration.ofSeconds(12, -20));
2416         assertEquals(Duration.ofSeconds(-12, -20).abs(), Duration.ofSeconds(12, 20));
2417         assertEquals(Duration.ofSeconds(-12, 20).abs(), Duration.ofSeconds(12, -20));
2418         assertEquals(Duration.ofSeconds(Long.MAX_VALUE).abs(), Duration.ofSeconds(Long.MAX_VALUE));
2419     }
2420 
2421     @Test(expectedExceptions=ArithmeticException.class)
2422     public void test_abs_overflow() {
2423         Duration.ofSeconds(Long.MIN_VALUE).abs();
2424     }
2425 
2426     //-----------------------------------------------------------------------
2427     // toNanos()
2428     //-----------------------------------------------------------------------
2429     @Test
2430     public void test_toNanos() {
2431         Duration test = Duration.ofSeconds(321, 123456789);
2432         assertEquals(test.toNanos(), 321123456789L);
2433     }
2434 
2435     @Test
2436     public void test_toNanos_max() {
2437         Duration test = Duration.ofSeconds(0, Long.MAX_VALUE);
2438         assertEquals(test.toNanos(), Long.MAX_VALUE);
2439     }
2440 
2441     @Test(expectedExceptions=ArithmeticException.class)
2442     public void test_toNanos_tooBig() {
2443         Duration test = Duration.ofSeconds(0, Long.MAX_VALUE).plusNanos(1);
2444         test.toNanos();
2445     }
2446 
2447     //-----------------------------------------------------------------------
2448     // toMillis()
2449     //-----------------------------------------------------------------------
2450     @Test
2451     public void test_toMillis() {
2452         Duration test = Duration.ofSeconds(321, 123456789);
2453         assertEquals(test.toMillis(), 321000 + 123);
2454     }
2455 
2456     @Test
2457     public void test_toMillis_max() {
2458         Duration test = Duration.ofSeconds(Long.MAX_VALUE / 1000, (Long.MAX_VALUE % 1000) * 1000000);
2459         assertEquals(test.toMillis(), Long.MAX_VALUE);
2460     }
2461 
2462     @Test(expectedExceptions=ArithmeticException.class)
2463     public void test_toMillis_tooBig() {
2464         Duration test = Duration.ofSeconds(Long.MAX_VALUE / 1000, ((Long.MAX_VALUE % 1000) + 1) * 1000000);
2465         test.toMillis();
2466     }
2467 
2468     //-----------------------------------------------------------------------
2469     // compareTo()
2470     //-----------------------------------------------------------------------
2471     @Test
2472     public void test_comparisons() {
2473         doTest_comparisons_Duration(
2474             Duration.ofSeconds(-2L, 0),
2475             Duration.ofSeconds(-2L, 999999998),
2476             Duration.ofSeconds(-2L, 999999999),
2477             Duration.ofSeconds(-1L, 0),
2478             Duration.ofSeconds(-1L, 1),
2479             Duration.ofSeconds(-1L, 999999998),
2480             Duration.ofSeconds(-1L, 999999999),
2481             Duration.ofSeconds(0L, 0),
2482             Duration.ofSeconds(0L, 1),
2483             Duration.ofSeconds(0L, 2),
2484             Duration.ofSeconds(0L, 999999999),
2485             Duration.ofSeconds(1L, 0),
2486             Duration.ofSeconds(2L, 0)
2487         );
2488     }
2489 
2490     void doTest_comparisons_Duration(Duration... durations) {
2491         for (int i = 0; i < durations.length; i++) {
2492             Duration a = durations[i];
2493             for (int j = 0; j < durations.length; j++) {
2494                 Duration b = durations[j];
2495                 if (i < j) {
2496                     assertEquals(a.compareTo(b)< 0, true, a + " <=> " + b);
2497                     assertEquals(a.equals(b), false, a + " <=> " + b);
2498                 } else if (i > j) {
2499                     assertEquals(a.compareTo(b) > 0, true, a + " <=> " + b);
2500                     assertEquals(a.equals(b), false, a + " <=> " + b);
2501                 } else {
2502                     assertEquals(a.compareTo(b), 0, a + " <=> " + b);
2503                     assertEquals(a.equals(b), true, a + " <=> " + b);
2504                 }
2505             }
2506         }
2507     }
2508 
2509     @Test(expectedExceptions=NullPointerException.class)
2510     public void test_compareTo_ObjectNull() {
2511         Duration a = Duration.ofSeconds(0L, 0);
2512         a.compareTo(null);
2513     }
2514 
2515     @Test(expectedExceptions=ClassCastException.class)
2516     @SuppressWarnings({ "unchecked", "rawtypes" })
2517     public void compareToNonDuration() {
2518        Comparable c = Duration.ofSeconds(0L);
2519        c.compareTo(new Object());
2520     }
2521 
2522     //-----------------------------------------------------------------------
2523     // equals()
2524     //-----------------------------------------------------------------------
2525     @Test
2526     public void test_equals() {
2527         Duration test5a = Duration.ofSeconds(5L, 20);
2528         Duration test5b = Duration.ofSeconds(5L, 20);
2529         Duration test5n = Duration.ofSeconds(5L, 30);
2530         Duration test6 = Duration.ofSeconds(6L, 20);
2531 
2532         assertEquals(test5a.equals(test5a), true);
2533         assertEquals(test5a.equals(test5b), true);
2534         assertEquals(test5a.equals(test5n), false);
2535         assertEquals(test5a.equals(test6), false);
2536 
2537         assertEquals(test5b.equals(test5a), true);
2538         assertEquals(test5b.equals(test5b), true);
2539         assertEquals(test5b.equals(test5n), false);
2540         assertEquals(test5b.equals(test6), false);
2541 
2542         assertEquals(test5n.equals(test5a), false);
2543         assertEquals(test5n.equals(test5b), false);
2544         assertEquals(test5n.equals(test5n), true);
2545         assertEquals(test5n.equals(test6), false);
2546 
2547         assertEquals(test6.equals(test5a), false);
2548         assertEquals(test6.equals(test5b), false);
2549         assertEquals(test6.equals(test5n), false);
2550         assertEquals(test6.equals(test6), true);
2551     }
2552 
2553     @Test
2554     public void test_equals_null() {
2555         Duration test5 = Duration.ofSeconds(5L, 20);
2556         assertEquals(test5.equals(null), false);
2557     }
2558 
2559     @Test
2560     public void test_equals_otherClass() {
2561         Duration test5 = Duration.ofSeconds(5L, 20);
2562         assertEquals(test5.equals(""), false);
2563     }
2564 
2565     //-----------------------------------------------------------------------
2566     // hashCode()
2567     //-----------------------------------------------------------------------
2568     @Test
2569     public void test_hashCode() {
2570         Duration test5a = Duration.ofSeconds(5L, 20);
2571         Duration test5b = Duration.ofSeconds(5L, 20);
2572         Duration test5n = Duration.ofSeconds(5L, 30);
2573         Duration test6 = Duration.ofSeconds(6L, 20);
2574 
2575         assertEquals(test5a.hashCode() == test5a.hashCode(), true);
2576         assertEquals(test5a.hashCode() == test5b.hashCode(), true);
2577         assertEquals(test5b.hashCode() == test5b.hashCode(), true);
2578 
2579         assertEquals(test5a.hashCode() == test5n.hashCode(), false);
2580         assertEquals(test5a.hashCode() == test6.hashCode(), false);
2581     }
2582 
2583     //-----------------------------------------------------------------------
2584     @DataProvider(name="withNanos")
2585     Object[][] provider_withNanos_int() {
2586         return new Object[][] {
2587             {0, 0, 0,           0, 0},
2588             {0, 0, 1,           0, 1},
2589             {0, 0, 999999999,   0, 999999999},
2590 
2591             {1, 0, 0,           1, 0},
2592             {1, 0, 1,           1, 1},
2593             {1, 0, 999999999,   1, 999999999},
2594 
2595             {-1, 0, 0,           -1, 0},
2596             {-1, 0, 1,           -1, 1},
2597             {-1, 0, 999999999,   -1, 999999999},
2598 
2599             {1, 999999999, 0,           1, 0},
2600             {1, 999999999, 1,           1, 1},
2601             {1, 999999998, 2,           1, 2},
2602 
2603             {Long.MAX_VALUE, 0, 999999999, Long.MAX_VALUE, 999999999},
2604             {Long.MIN_VALUE, 0, 999999999, Long.MIN_VALUE, 999999999},
2605         };
2606     }
2607 
2608     @Test(dataProvider="withNanos")
2609     public void withNanos_long(long seconds, int nanos, int amount, long expectedSeconds, int expectedNanoOfSecond) {
2610         Duration t = Duration.ofSeconds(seconds, nanos);
2611         t = t.withNanos(amount);
2612         assertEquals(t.getSeconds(), expectedSeconds);
2613         assertEquals(t.getNano(), expectedNanoOfSecond);
2614     }
2615 
2616     //-----------------------------------------------------------------------
2617     @DataProvider(name="withSeconds")
2618     Object[][] provider_withSeconds_long() {
2619         return new Object[][] {
2620             {0, 0, 0, 0, 0},
2621             {0, 0, 1, 1, 0},
2622             {0, 0, -1, -1, 0},
2623             {0, 0, Long.MAX_VALUE, Long.MAX_VALUE, 0},
2624             {0, 0, Long.MIN_VALUE, Long.MIN_VALUE, 0},
2625 
2626             {1, 0, 0, 0, 0},
2627             {1, 0, 2, 2, 0},
2628             {1, 0, -1, -1, 0},
2629             {1, 0, Long.MAX_VALUE, Long.MAX_VALUE, 0},
2630             {1, 0, Long.MIN_VALUE, Long.MIN_VALUE, 0},
2631 
2632             {-1, 1, 0, 0, 1},
2633             {-1, 1, 1, 1, 1},
2634             {-1, 1, -1, -1, 1},
2635             {-1, 1, Long.MAX_VALUE, Long.MAX_VALUE, 1},
2636             {-1, 1, Long.MIN_VALUE, Long.MIN_VALUE, 1},
2637         };
2638     }
2639 
2640     @Test(dataProvider="withSeconds")
2641     public void withSeconds_long(long seconds, int nanos, long amount, long expectedSeconds, int expectedNanoOfSecond) {
2642         Duration t = Duration.ofSeconds(seconds, nanos);
2643         t = t.withSeconds(amount);
2644         assertEquals(t.getSeconds(), expectedSeconds);
2645         assertEquals(t.getNano(), expectedNanoOfSecond);
2646     }
2647 
2648     //-----------------------------------------------------------------------
2649     // toString()
2650     //-----------------------------------------------------------------------
2651     @DataProvider(name="toString")
2652     Object[][] provider_toString() {
2653         return new Object[][] {
2654             {0, 0, "PT0S"},
2655             {0, 1, "PT0.000000001S"},
2656             {0, 10, "PT0.00000001S"},
2657             {0, 100, "PT0.0000001S"},
2658             {0, 1000, "PT0.000001S"},
2659             {0, 10000, "PT0.00001S"},
2660             {0, 100000, "PT0.0001S"},
2661             {0, 1000000, "PT0.001S"},
2662             {0, 10000000, "PT0.01S"},
2663             {0, 100000000, "PT0.1S"},
2664             {0, 120000000, "PT0.12S"},
2665             {0, 123000000, "PT0.123S"},
2666             {0, 123400000, "PT0.1234S"},
2667             {0, 123450000, "PT0.12345S"},
2668             {0, 123456000, "PT0.123456S"},
2669             {0, 123456700, "PT0.1234567S"},
2670             {0, 123456780, "PT0.12345678S"},
2671             {0, 123456789, "PT0.123456789S"},
2672             {1, 0, "PT1S"},
2673             {59, 0, "PT59S"},
2674             {60, 0, "PT1M"},
2675             {61, 0, "PT1M1S"},
2676             {3599, 0, "PT59M59S"},
2677             {3600, 0, "PT1H"},
2678             {3601, 0, "PT1H1S"},
2679             {3661, 0, "PT1H1M1S"},
2680             {86399, 0, "PT23H59M59S"},
2681             {86400, 0, "PT24H"},
2682             {59, 0, "PT59S"},
2683             {59, 0, "PT59S"},
2684             {-1, 0, "PT-1S"},
2685             {-1, 1000, "PT-0.999999S"},
2686             {-1, 900000000, "PT-0.1S"},
2687             {Long.MAX_VALUE, 0, "PT" + (Long.MAX_VALUE / 3600) + "H" +
2688                     ((Long.MAX_VALUE % 3600) / 60) + "M" + (Long.MAX_VALUE % 60) + "S"},
2689             {Long.MIN_VALUE, 0, "PT" + (Long.MIN_VALUE / 3600) + "H" +
2690                     ((Long.MIN_VALUE % 3600) / 60) + "M" + (Long.MIN_VALUE % 60) + "S"},
2691         };
2692     }
2693 
2694     @Test(dataProvider="toString")
2695     public void test_toString(long seconds, int nanos, String expected) {
2696         Duration t = Duration.ofSeconds(seconds, nanos);
2697         assertEquals(t.toString(), expected);
2698     }
2699 
2700     //-----------------------------------------------------------------------
2701     @Test(groups="{tck}")
2702     public void test_duration_getUnits() {
2703         Duration duration = Duration.ofSeconds(5000, 1000);
2704         List<TemporalUnit> units = duration.getUnits();
2705         assertEquals(units.size(), 2, "Period.getUnits length");
2706         assertTrue(units.contains(ChronoUnit.SECONDS), "Period.getUnits contains ChronoUnit.SECONDS");
2707         assertTrue(units.contains(ChronoUnit.NANOS), "contains ChronoUnit.NANOS");
2708     }
2709 
2710     @Test()
2711     public void test_getUnit() {
2712         Duration test = Duration.ofSeconds(2000, 1000);
2713         long seconds = test.get(ChronoUnit.SECONDS);
2714         assertEquals(seconds, 2000, "duration.get(SECONDS)");
2715         long nanos = test.get(ChronoUnit.NANOS);
2716         assertEquals(nanos, 1000, "duration.get(NANOS)");
2717     }
2718 
2719     @DataProvider(name="BadTemporalUnit")
2720     Object[][] provider_factory_of_badTemporalUnit() {
2721         return new Object[][] {
2722             {0, MICROS},
2723             {0, MILLIS},
2724             {0, MINUTES},
2725             {0, HOURS},
2726             {0, HALF_DAYS},
2727             {0, DAYS},
2728             {0, ChronoUnit.MONTHS},
2729             {0, ChronoUnit.YEARS},
2730             {0, ChronoUnit.DECADES},
2731             {0, ChronoUnit.CENTURIES},
2732             {0, ChronoUnit.MILLENNIA},
2733         };
2734     }
2735 
2736     @Test(dataProvider="BadTemporalUnit", expectedExceptions=DateTimeException.class)
2737     public void test_bad_getUnit(long amount, TemporalUnit unit) {
2738         Duration t = Duration.of(amount, unit);
2739         t.get(unit);
2740     }
2741 }