1 /*
   2  * Copyright (c) 2013, 1025, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  */
  23 
  24 /*
  25  * @test
  26  * @ignore This test has huge memory requirements
  27  * @library ..
  28  * @run main/timeout=180/othervm -Xmx8g SymmetricRangeTests
  29  * @bug 6910473 8021204 8021203 9005933 8074460
  30  * @summary Test range of BigInteger values (use -Dseed=X to set PRNG seed)
  31  * @author Dmitry Nadezhin
  32  */
  33 import java.io.ByteArrayInputStream;
  34 import java.io.ByteArrayOutputStream;
  35 import java.io.IOException;
  36 import java.io.ObjectInputStream;
  37 import java.io.ObjectOutputStream;
  38 import java.util.Arrays;
  39 import java.math.BigInteger;
  40 
  41 public class SymmetricRangeTests {
  42 
  43     private static final BigInteger MAX_VALUE = makeMaxValue();
  44     private static final BigInteger MIN_VALUE = MAX_VALUE.negate();
  45 
  46     private static BigInteger makeMaxValue() {
  47         byte[] ba = new byte[1 << 28];
  48         Arrays.fill(ba, (byte) 0xFF);
  49         ba[0] = (byte) 0x7F;
  50         return new BigInteger(ba);
  51     }
  52 
  53     private static void check(String msg, BigInteger actual, BigInteger expected) {
  54         if (!actual.equals(expected)) {
  55             throw new RuntimeException(msg + ".bitLength()=" + actual.bitLength());
  56         }
  57     }
  58 
  59     private static void check(String msg, double actual, double expected) {
  60         if (actual != expected) {
  61             throw new RuntimeException(msg + "=" + actual);
  62         }
  63     }
  64 
  65     private static void check(String msg, float actual, float expected) {
  66         if (actual != expected) {
  67             throw new RuntimeException(msg + "=" + actual);
  68         }
  69     }
  70 
  71     private static void check(String msg, long actual, long expected) {
  72         if (actual != expected) {
  73             throw new RuntimeException(msg + "=" + actual);
  74         }
  75     }
  76 
  77     private static void check(String msg, int actual, int expected) {
  78         if (actual != expected) {
  79             throw new RuntimeException(msg + "=" + actual);
  80         }
  81     }
  82 
  83     private static void testOverflowInMakePositive() {
  84         System.out.println("Testing overflow in BigInteger.makePositive");
  85         byte[] ba = new byte[Integer.MAX_VALUE - 2];
  86         ba[0] = (byte) 0x80;
  87         try {
  88             BigInteger actual = new BigInteger(ba);
  89             throw new RuntimeException("new BigInteger(ba).bitLength()=" + actual.bitLength());
  90         } catch (ArithmeticException e) {
  91             // expected
  92         }
  93     }
  94 
  95     private static void testBug8021204() {
  96         System.out.println("Testing Bug 8021204");
  97         StringBuilder sb = new StringBuilder();
  98         sb.append('1');
  99         for (int i = 0; i < (1 << 30) - 1; i++) {
 100             sb.append('0');
 101         }
 102         sb.append('1');
 103         String s = sb.toString();
 104         sb = null;
 105         try {
 106             BigInteger actual = new BigInteger(s, 16);
 107             throw new RuntimeException("new BigInteger(\"1000...001\").bitLength()=" + actual.bitLength());
 108         } catch (ArithmeticException e) {
 109             // expected
 110         }
 111     }
 112 
 113     private static void testOverflowInBitSieve() {
 114         System.out.println("Testing overflow in BitSieve.sieveSingle");
 115         int bitLength = (5 << 27) - 1;
 116         try {
 117             RandomSeed rndSeed = new RandomSeed(false);
 118             System.out.println("Random number generator seed = " + rndSeed.getSeed());
 119             BigInteger actual = new BigInteger(bitLength, 0, rndSeed.getRandom());
 120             throw new RuntimeException("new BigInteger(bitLength, 0, null).bitLength()=" + actual.bitLength());
 121         } catch (ArithmeticException e) {
 122             // expected
 123         }
 124         try {
 125             BigInteger bi = BigInteger.ONE.shiftLeft(bitLength - 1).subtract(BigInteger.ONE);
 126             BigInteger actual = bi.nextProbablePrime();
 127             throw new RuntimeException("bi.nextActualPrime().bitLength()=" + actual.bitLength());
 128         } catch (ArithmeticException e) {
 129             // expected
 130         }
 131     }
 132 
 133     private static void testAdd() {
 134         System.out.println("Testing BigInteger.add");
 135         try {
 136             BigInteger actual = MAX_VALUE.add(BigInteger.ONE);
 137             throw new RuntimeException("BigInteger.MAX_VALUE.add(BigInteger.ONE).bitLength()=" + actual.bitLength());
 138         } catch (ArithmeticException e) {
 139             // expected
 140         }
 141     }
 142 
 143     private static void testSubtract() {
 144         System.out.println("Testing BigInteger.subtract");
 145         try {
 146             BigInteger actual = MIN_VALUE.subtract(BigInteger.ONE);
 147             throw new RuntimeException("BigInteger.MIN_VALUE.subtract(BigInteger.ONE).bitLength()=" + actual.bitLength());
 148         } catch (ArithmeticException e) {
 149             // expected
 150         }
 151     }
 152 
 153     private static void testMultiply() {
 154         System.out.println("Testing BigInteger.multiply");
 155         int py = 2000;
 156         int px = Integer.MAX_VALUE - py;
 157         BigInteger x = BigInteger.ONE.shiftLeft(px);
 158         BigInteger y = BigInteger.ONE.shiftLeft(py);
 159         try {
 160             BigInteger actual = x.multiply(y);
 161             throw new RuntimeException("(1 << " + px + " ) * (1 << " + py + ").bitLength()=" + actual.bitLength());
 162         } catch (ArithmeticException e) {
 163             // expected
 164         }
 165     }
 166 
 167     private static void testDivide() {
 168         System.out.println("Testing BigInteger.divide");
 169         check("BigInteger.MIN_VALUE.divide(BigInteger.valueOf(-1))",
 170                 MIN_VALUE.divide(BigInteger.valueOf(-1)), MAX_VALUE);
 171         check("BigInteger.MIN_VALUE.divide(BigInteger.ONE)",
 172                 MIN_VALUE.divide(BigInteger.ONE), MIN_VALUE);
 173     }
 174 
 175     private static void testDivideAndRemainder(String msg, BigInteger dividend, BigInteger divisor,
 176             BigInteger expectedQuotent, BigInteger expectedRemainder) {
 177         BigInteger[] qr = dividend.divideAndRemainder(divisor);
 178         check(msg + "[0]", qr[0], expectedQuotent);
 179         check(msg + "[1]", qr[1], expectedRemainder);
 180     }
 181 
 182     private static void testDivideAndRemainder() {
 183         System.out.println("Testing BigInteger.divideAndRemainder");
 184         testDivideAndRemainder("BigInteger.MIN_VALUE.divideAndRemainder(BigInteger.valueOf(-1))",
 185                 MIN_VALUE, BigInteger.valueOf(-1),
 186                 MAX_VALUE,
 187                 BigInteger.ZERO);
 188     }
 189 
 190     private static void testBug9005933() {
 191         System.out.println("Testing Bug 9005933");
 192         int dividendPow = 2147483646;
 193         int divisorPow = 1568;
 194         BigInteger dividend = BigInteger.ONE.shiftLeft(dividendPow);
 195         BigInteger divisor = BigInteger.ONE.shiftLeft(divisorPow);
 196         testDivideAndRemainder("(1 << " + dividendPow + ").divideAndRemainder(1 << " + divisorPow + ")",
 197                 dividend, divisor,
 198                 BigInteger.ONE.shiftLeft(dividendPow - divisorPow),
 199                 BigInteger.ZERO);
 200     }
 201 
 202     private static void testRemainder() {
 203         System.out.println("Testing BigInteger.remainder");
 204         check("BigInteger.MIN_VALUE.remainder(BigInteger.valueOf(-1))",
 205                 MIN_VALUE.remainder(BigInteger.valueOf(-1)), BigInteger.ZERO);
 206     }
 207 
 208     private static void testPow() {
 209         System.out.println("Testing BigInteger.pow");
 210         check("BigInteger.MIN_VALUE.pow(1)",
 211                 MIN_VALUE.pow(1), MIN_VALUE);
 212         try {
 213             BigInteger actual = BigInteger.valueOf(4).pow(Integer.MAX_VALUE);
 214             throw new RuntimeException("BigInteger.valueOf(4).pow(Integer.MAX_VALUE).bitLength()=" + actual.bitLength());
 215         } catch (ArithmeticException e) {
 216             // expected
 217         }
 218     }
 219 
 220     private static void testGcd() {
 221         System.out.println("Testing BigInteger.gcd");
 222         check("BigInteger.MIN_VALUE.gcd(BigInteger.MIN_VALUE)",
 223                 MIN_VALUE.gcd(MIN_VALUE), MAX_VALUE);
 224         check("BigInteger.MIN_VALUE.gcd(BigInteger.ZERO)",
 225                 MIN_VALUE.gcd(BigInteger.ZERO), MAX_VALUE);
 226         check("BigInteger.ZERO.gcd(MIN_VALUE)",
 227                 BigInteger.ZERO.gcd(MIN_VALUE), MAX_VALUE);
 228     }
 229 
 230     private static void testAbs() {
 231         System.out.println("Testing BigInteger.abs");
 232         check("BigInteger.MIN_VALUE.abs()",
 233                 MIN_VALUE.abs(), MAX_VALUE);
 234         check("BigInteger.MAX_VALUE.abs()",
 235                 MAX_VALUE.abs(), MAX_VALUE);
 236     }
 237 
 238     private static void testNegate() {
 239         System.out.println("Testing BigInteger.negate");
 240         check("BigInteger.MIN_VALUE.negate()",
 241                 MIN_VALUE.negate(), MAX_VALUE);
 242         check("BigInteger.MAX_VALUE.negate()",
 243                 MAX_VALUE.negate(), MIN_VALUE);
 244     }
 245 
 246     private static void testMod() {
 247         System.out.println("Testing BigInteger.mod");
 248         check("BigInteger.MIN_VALUE.mod(BigInteger.MAX_VALUE)",
 249                 MIN_VALUE.mod(MAX_VALUE), BigInteger.ZERO);
 250         check("BigInteger.MAX_VALUE.mod(BigInteger.MAX_VALUE)",
 251                 MIN_VALUE.mod(MAX_VALUE), BigInteger.ZERO);
 252     }
 253 
 254     private static void testModPow() {
 255         System.out.println("Testing BigInteger.modPow");
 256         BigInteger x = BigInteger.valueOf(3);
 257         BigInteger m = BigInteger.valueOf(-4).subtract(MIN_VALUE);
 258         check("BigInteger.valueOf(3).modPow(BigInteger.ONE, m)",
 259                 x.modPow(BigInteger.ONE, m), x);
 260     }
 261 
 262     // slow test
 263     private static void testModInverse() {
 264         System.out.println("Testing BigInteger.modInverse");
 265         check("BigInteger.MIN_VALUE.modInverse(BigInteger.MAX_VALUE)",
 266                 MIN_VALUE.modInverse(MAX_VALUE), MAX_VALUE.subtract(BigInteger.ONE));
 267     }
 268 
 269     private static void testShiftLeft() {
 270         System.out.println("Testing BigInteger.shiftLeft");
 271         try {
 272             BigInteger actual = MIN_VALUE.shiftLeft(1);
 273             throw new RuntimeException("BigInteger.MIN_VALUE.shiftLeft(1).bitLength()=" + actual.bitLength());
 274         } catch (ArithmeticException e) {
 275             // expected
 276         }
 277         try {
 278             BigInteger actual = MAX_VALUE.shiftLeft(1);
 279             throw new RuntimeException("BigInteger.MAX_VALUE.shiftLeft(1).bitLength()=" + actual.bitLength());
 280         } catch (ArithmeticException e) {
 281             // expected
 282         }
 283     }
 284 
 285     private static void testShiftRight() {
 286         System.out.println("Testing BigInteger.shiftRight");
 287         try {
 288             BigInteger actual = MIN_VALUE.shiftRight(-1);
 289             throw new RuntimeException("BigInteger.MIN_VALUE.shiftRight(-1).bitLength()=" + actual.bitLength());
 290         } catch (ArithmeticException e) {
 291             // expected
 292         }
 293         try {
 294             BigInteger actual = MAX_VALUE.shiftRight(-1);
 295             throw new RuntimeException("BigInteger.MAX_VALUE.shiftRight(-1).bitLength()=" + actual.bitLength());
 296         } catch (ArithmeticException e) {
 297             // expected
 298         }
 299     }
 300 
 301     private static void testAnd() {
 302         System.out.println("Testing BigInteger.and");
 303         check("BigInteger.MIN_VALUE.and(BigInteger.MIN_VALUE)",
 304                 MIN_VALUE.and(MIN_VALUE), MIN_VALUE);
 305         check("BigInteger.MAX_VALUE.and(BigInteger.MAX_VALUE)",
 306                 MAX_VALUE.and(MAX_VALUE), MAX_VALUE);
 307         check("BigInteger.MIN_VALUE.and(BigInteger.MAX_VALUE)",
 308                 MIN_VALUE.and(MAX_VALUE), BigInteger.ONE);
 309         try {
 310             BigInteger actual = MIN_VALUE.and(BigInteger.valueOf(-2));
 311             throw new RuntimeException("BigInteger.MIN_VALUE.and(-2)).bitLength()=" + actual.bitLength());
 312         } catch (ArithmeticException e) {
 313             // expected
 314         }
 315     }
 316 
 317     private static void testOr() {
 318         System.out.println("Testing BigInteger.or");
 319         check("BigInteger.MIN_VALUE.or(BigInteger.MIN_VALUE)",
 320                 MIN_VALUE.or(MIN_VALUE), MIN_VALUE);
 321         check("BigInteger.MAX_VALUE.or(BigInteger.MAX_VALUE)",
 322                 MAX_VALUE.or(MAX_VALUE), MAX_VALUE);
 323         check("BigInteger.MIN_VALUE.and(BigInteger.MAX_VALUE)",
 324                 MIN_VALUE.or(MAX_VALUE), BigInteger.valueOf(-1));
 325     }
 326 
 327     private static void testXor() {
 328         System.out.println("Testing BigInteger.xor");
 329         check("BigInteger.MIN_VALUE.xor(BigInteger.MIN_VALUE)",
 330                 MIN_VALUE.xor(MIN_VALUE), BigInteger.ZERO);
 331         check("BigInteger.MAX_VALUE.xor(BigInteger.MAX_VALUE)",
 332                 MAX_VALUE.xor(MAX_VALUE), BigInteger.ZERO);
 333         check("BigInteger.MIN_VALUE.xor(BigInteger.MAX_VALUE)",
 334                 MIN_VALUE.xor(MAX_VALUE), BigInteger.valueOf(-2));
 335         try {
 336             BigInteger actual = MIN_VALUE.xor(BigInteger.ONE);
 337             throw new RuntimeException("BigInteger.MIN_VALUE.xor(BigInteger.ONE)).bitLength()=" + actual.bitLength());
 338         } catch (ArithmeticException e) {
 339             // expected
 340         }
 341     }
 342 
 343     private static void testNot() {
 344         System.out.println("Testing BigInteger.not");
 345         check("BigInteger.MIN_VALUE.not()",
 346                 MIN_VALUE.not(), MAX_VALUE.subtract(BigInteger.ONE));
 347         try {
 348             BigInteger actual = MAX_VALUE.not();
 349             throw new RuntimeException("BigInteger.MAX_VALUE.not()).bitLength()=" + actual.bitLength());
 350         } catch (ArithmeticException e) {
 351             // expected
 352         }
 353     }
 354 
 355     private static void testSetBit() {
 356         System.out.println("Testing BigInteger.setBit");
 357         check("BigInteger.MIN_VALUE.setBit(" + Integer.MAX_VALUE + ")",
 358                 MIN_VALUE.setBit(Integer.MAX_VALUE), MIN_VALUE);
 359         try {
 360             BigInteger actual = MAX_VALUE.setBit(Integer.MAX_VALUE);
 361             throw new RuntimeException("BigInteger.MAX_VALUE.setBit(" + Integer.MAX_VALUE + ").bitLength()=" + actual.bitLength());
 362         } catch (ArithmeticException e) {
 363             // expected
 364         }
 365     }
 366 
 367     private static void testClearBit() {
 368         System.out.println("Testing BigInteger.clearBit");
 369         check("BigInteger.MAX_VALUE.clearBit(" + Integer.MAX_VALUE + ")",
 370                 MAX_VALUE.clearBit(Integer.MAX_VALUE), MAX_VALUE);
 371         try {
 372             BigInteger actual = MIN_VALUE.clearBit(Integer.MAX_VALUE);
 373             throw new RuntimeException("BigInteger.MIN_VALUE.clearBit(" + Integer.MAX_VALUE + ").bitLength()=" + actual.bitLength());
 374         } catch (ArithmeticException e) {
 375             // expected
 376         }
 377         try {
 378             BigInteger actual = MIN_VALUE.clearBit(0);
 379             throw new RuntimeException("BigInteger.MIN_VALUE.clearBit(0).bitLength()=" + actual.bitLength());
 380         } catch (ArithmeticException e) {
 381             // expected
 382         }
 383     }
 384 
 385     private static void testFlipBit() {
 386         System.out.println("Testing BigInteger.flipBit");
 387         try {
 388             BigInteger actual = MIN_VALUE.flipBit(Integer.MAX_VALUE);
 389             throw new RuntimeException("BigInteger.MIN_VALUE.flipBit(" + Integer.MAX_VALUE + ").bitLength()=" + actual.bitLength());
 390         } catch (ArithmeticException e) {
 391             // expected
 392         }
 393         try {
 394             BigInteger actual = MIN_VALUE.flipBit(0);
 395             throw new RuntimeException("BigInteger.MIN_VALUE.flipBit(0).bitLength()=" + actual.bitLength());
 396         } catch (ArithmeticException e) {
 397             // expected
 398         }
 399         try {
 400             BigInteger actual = MAX_VALUE.flipBit(Integer.MAX_VALUE);
 401             throw new RuntimeException("BigInteger.MAX_VALUE.flipBit(" + Integer.MAX_VALUE + ").bitLength()=" + actual.bitLength());
 402         } catch (ArithmeticException e) {
 403             // expected
 404         }
 405     }
 406 
 407     private static void testGetLowestSetBit() {
 408         System.out.println("Testing BigInteger.getLowestSetBit");
 409         check("BigInteger.MIN_VALUE.getLowestSetBit()",
 410                 MIN_VALUE.getLowestSetBit(), 0);
 411         check("BigInteger.MAX_VALUE.getLowestSetBit()",
 412                 MAX_VALUE.getLowestSetBit(), 0);
 413     }
 414 
 415     private static void testBitLength() {
 416         System.out.println("Testing BigInteger.bitLength");
 417         check("BigInteger.MIN_NEXT.bitLength()",
 418                 MIN_VALUE.bitLength(), Integer.MAX_VALUE);
 419         check("BigInteger.MAX_VALUE.bitLength()",
 420                 MAX_VALUE.bitLength(), Integer.MAX_VALUE);
 421     }
 422 
 423     private static void testBitCount() {
 424         System.out.println("Testing BigInteger.bitCount");
 425         check("BigInteger.MIN_VALUE.bitCount()",
 426                 MIN_VALUE.bitCount(), Integer.MAX_VALUE - 1);
 427         check("BigInteger.MAX_VALUE.bitCount()",
 428                 MAX_VALUE.bitCount(), Integer.MAX_VALUE);
 429     }
 430 
 431     private static void testToString(String msg, int radix, BigInteger bi, int length, String startsWith, char c) {
 432         String s = bi.toString(radix);
 433         if (s.length() != length) {
 434             throw new RuntimeException(msg + ".length=" + s.length());
 435         }
 436         if (!s.startsWith(startsWith)) {
 437             throw new RuntimeException(msg + "[0]=" + s.substring(0, startsWith.length()));
 438         }
 439         for (int i = startsWith.length(); i < s.length(); i++) {
 440             if (s.charAt(i) != c) {
 441                 throw new RuntimeException(msg + "[" + i + "]='" + s.charAt(i) + "'");
 442             }
 443         }
 444     }
 445 
 446     private static void testToString() {
 447         System.out.println("Testing BigInteger.toString");
 448         testToString("BigInteger.MIN_VALUE.toString(16)=", 16,
 449                 BigInteger.valueOf(-1).shiftLeft(Integer.MAX_VALUE - 1),
 450                 (1 << 29) + 1, "-4", '0');
 451     }
 452 
 453     private static void testToByteArrayWithConstructor(String msg, BigInteger bi, int length, byte msb, byte b, byte lsb) {
 454         byte[] ba = bi.toByteArray();
 455         if (ba.length != length) {
 456             throw new RuntimeException(msg + ".length=" + ba.length);
 457         }
 458         if (ba[0] != msb) {
 459             throw new RuntimeException(msg + "[0]=" + ba[0]);
 460         }
 461         for (int i = 1; i < ba.length - 1; i++) {
 462             if (ba[i] != b) {
 463                 throw new RuntimeException(msg + "[" + i + "]=" + ba[i]);
 464             }
 465         }
 466         if (ba[ba.length - 1] != lsb) {
 467             throw new RuntimeException(msg + "[" + (ba.length - 1) + "]=" + ba[ba.length - 1]);
 468         }
 469         BigInteger actual = new BigInteger(ba);
 470         if (!actual.equals(bi)) {
 471             throw new RuntimeException(msg + ".bitLength()=" + actual.bitLength());
 472         }
 473     }
 474 
 475     private static void testToByteArrayWithConstructor() {
 476         System.out.println("Testing BigInteger.toByteArray with constructor");
 477         testToByteArrayWithConstructor("BigInteger.MIN_VALUE.toByteArray()",
 478                 MIN_VALUE, (1 << 28), (byte) 0x80, (byte) 0x00, (byte) 0x01);
 479         testToByteArrayWithConstructor("BigInteger.MAX_VALUE.toByteArray()",
 480                 MAX_VALUE, (1 << 28), (byte) 0x7f, (byte) 0xff, (byte) 0xff);
 481 
 482         byte[] ba = new byte[1 << 28];
 483         ba[0] = (byte) 0x80;
 484         try {
 485             BigInteger actual = new BigInteger(-1, ba);
 486             throw new RuntimeException("new BigInteger(-1, ba).bitLength()=" + actual.bitLength());
 487         } catch (ArithmeticException e) {
 488             // expected
 489         }
 490         try {
 491             BigInteger actual = new BigInteger(1, ba);
 492             throw new RuntimeException("new BigInteger(1, ba).bitLength()=" + actual.bitLength());
 493         } catch (ArithmeticException e) {
 494             // expected
 495         }
 496     }
 497 
 498     private static void testIntValue() {
 499         System.out.println("Testing BigInteger.intValue");
 500         check("BigInteger.MIN_VALUE.intValue()",
 501                 MIN_VALUE.intValue(), 1);
 502         check("BigInteger.MAX_VALUE.floatValue()",
 503                 MAX_VALUE.intValue(), -1);
 504     }
 505 
 506     private static void testLongValue() {
 507         System.out.println("Testing BigInteger.longValue");
 508         check("BigInteger.MIN_VALUE.longValue()",
 509                 MIN_VALUE.longValue(), 1L);
 510         check("BigInteger.MAX_VALUE.longValue()",
 511                 MAX_VALUE.longValue(), -1L);
 512     }
 513 
 514     private static void testFloatValue() {
 515         System.out.println("Testing BigInteger.floatValue, Bug 8021203");
 516         check("BigInteger.MIN_VALUE_.floatValue()",
 517                 MIN_VALUE.floatValue(), Float.NEGATIVE_INFINITY);
 518         check("BigInteger.MAX_VALUE.floatValue()",
 519                 MAX_VALUE.floatValue(), Float.POSITIVE_INFINITY);
 520     }
 521 
 522     private static void testDoubleValue() {
 523         System.out.println("Testing BigInteger.doubleValue, Bug 8021203");
 524         check("BigInteger.MIN_VALUE.doubleValue()",
 525                 MIN_VALUE.doubleValue(), Double.NEGATIVE_INFINITY);
 526         check("BigInteger.MAX_VALUE.doubleValue()",
 527                 MAX_VALUE.doubleValue(), Double.POSITIVE_INFINITY);
 528     }
 529 
 530     private static void testSerialization(String msg, BigInteger bi) {
 531         try {
 532             ByteArrayOutputStream baOut = new ByteArrayOutputStream((1 << 28) + 1000);
 533             ObjectOutputStream out = new ObjectOutputStream(baOut);
 534             out.writeObject(bi);
 535             out.close();
 536             out = null;
 537             byte[] ba = baOut.toByteArray();
 538             baOut = null;
 539             ObjectInputStream in = new ObjectInputStream(new ByteArrayInputStream(ba));
 540             BigInteger actual = (BigInteger) in.readObject();
 541             if (!actual.equals(bi)) {
 542                 throw new RuntimeException(msg + ".bitLength()=" + actual.bitLength());
 543             }
 544         } catch (IOException | ClassNotFoundException e) {
 545             throw new RuntimeException(msg + " raised exception ", e);
 546         }
 547     }
 548 
 549     private static void testSerialization() {
 550         System.out.println("Testing BigInteger serialization");
 551         testSerialization("BigInteger.MIN_VALUE.intValue()",
 552                 MIN_VALUE);
 553         testSerialization("BigInteger.MAX_VALUE.floatValue()",
 554                 MAX_VALUE);
 555     }
 556 
 557     private static void testLongValueExact() {
 558         System.out.println("Testing BigInteger.longValueExact");
 559         try {
 560             long actual = MIN_VALUE.longValueExact();
 561             throw new RuntimeException("BigInteger.MIN_VALUE.longValueExact()= " + actual);
 562         } catch (ArithmeticException e) {
 563             // excpected
 564         }
 565         try {
 566             long actual = MAX_VALUE.longValueExact();
 567             throw new RuntimeException("BigInteger.MAX_VALUE.longValueExact()= " + actual);
 568         } catch (ArithmeticException e) {
 569             // excpected
 570         }
 571     }
 572 
 573     private static void testIntValueExact() {
 574         System.out.println("Testing BigInteger.intValueExact");
 575         try {
 576             long actual = MIN_VALUE.intValueExact();
 577             throw new RuntimeException("BigInteger.MIN_VALUE.intValueExact()= " + actual);
 578         } catch (ArithmeticException e) {
 579             // excpected
 580         }
 581         try {
 582             long actual = MAX_VALUE.intValueExact();
 583             throw new RuntimeException("BigInteger.MAX_VALUE.intValueExact()= " + actual);
 584         } catch (ArithmeticException e) {
 585             // excpected
 586         }
 587     }
 588 
 589     private static void testShortValueExact() {
 590         System.out.println("Testing BigInteger.shortValueExact");
 591         try {
 592             long actual = MIN_VALUE.shortValueExact();
 593             throw new RuntimeException("BigInteger.MIN_VALUE.shortValueExact()= " + actual);
 594         } catch (ArithmeticException e) {
 595             // excpected
 596         }
 597         try {
 598             long actual = MAX_VALUE.shortValueExact();
 599             throw new RuntimeException("BigInteger.MAX_VALUE.shortValueExact()= " + actual);
 600         } catch (ArithmeticException e) {
 601             // excpected
 602         }
 603     }
 604 
 605     private static void testByteValueExact() {
 606         System.out.println("Testing BigInteger.byteValueExact");
 607         try {
 608             long actual = MIN_VALUE.byteValueExact();
 609             throw new RuntimeException("BigInteger.MIN_VALUE.byteValueExact()= " + actual);
 610         } catch (ArithmeticException e) {
 611             // excpected
 612         }
 613         try {
 614             long actual = MAX_VALUE.byteValueExact();
 615             throw new RuntimeException("BigInteger.MAX_VALUE.byteValueExact()= " + actual);
 616         } catch (ArithmeticException e) {
 617             // excpected
 618         }
 619     }
 620 
 621     public static void main(String... args) {
 622         testOverflowInMakePositive();
 623         testBug8021204();
 624         testOverflowInBitSieve();
 625         testAdd();
 626         testSubtract();
 627         testMultiply();
 628         testDivide();
 629         testDivideAndRemainder();
 630         testBug9005933();
 631         testRemainder();
 632         testPow();
 633         testGcd();
 634         testAbs();
 635         testNegate();
 636         testMod();
 637         testModPow();
 638 //        testModInverse();
 639         testShiftLeft();
 640         testShiftRight();
 641         testAnd();
 642         testOr();
 643         testXor();
 644         testNot();
 645         testSetBit();
 646         testClearBit();
 647         testFlipBit();
 648         testGetLowestSetBit();
 649         testBitLength();
 650         testBitCount();
 651         testToString();
 652         testToByteArrayWithConstructor();
 653         testIntValue();
 654         testLongValue();
 655         testFloatValue();
 656         testDoubleValue();
 657         testSerialization();
 658         testLongValueExact();
 659         testIntValueExact();
 660         testShortValueExact();
 661         testByteValueExact();
 662     }
 663 }