blob: e9c33ca4f98079f5f0209f988b307487404ba3f6 [file] [log] [blame]
clementbera0bdd90f2019-07-06 11:15:23 +02001// Copyright (c) 2019, the R8 project authors. Please see the AUTHORS file
2// for details. All rights reserved. Use of this source code is governed by a
3// BSD-style license that can be found in the LICENSE file.
4
5package backport;
6
Jake Wharton9402c902019-12-12 09:06:14 -05007import java.math.BigInteger;
8
clementbera0bdd90f2019-07-06 11:15:23 +02009public class StrictMathBackportJava9Main {
10
11 public static void main(String[] args) {
12 testMultiplyExactLongInt();
Jake Wharton971ee702019-12-11 21:19:30 -050013 testMultiplyFull();
clementbera0bdd90f2019-07-06 11:15:23 +020014 testFloorDivLongInt();
15 testFloorModLongInt();
16 }
17
18 public static void testMultiplyExactLongInt() {
19 assertEquals(8L, StrictMath.multiplyExact(2L, 4));
20 assertEquals(Long.MAX_VALUE, StrictMath.multiplyExact(Long.MAX_VALUE, 1));
21 assertEquals(Long.MIN_VALUE, StrictMath.multiplyExact(Long.MIN_VALUE / 2L, 2));
22 try {
23 throw new AssertionError(StrictMath.multiplyExact(Long.MAX_VALUE, 2));
24 } catch (ArithmeticException expected) {
25 }
26 try {
27 throw new AssertionError(StrictMath.multiplyExact(Long.MIN_VALUE, 2));
28 } catch (ArithmeticException expected) {
29 }
30 }
31
Jake Wharton971ee702019-12-11 21:19:30 -050032 public static void testMultiplyFull() {
33 assertEquals(8L, StrictMath.multiplyFull(2, 4));
34 assertEquals(4611686014132420609L,
35 StrictMath.multiplyFull(Integer.MAX_VALUE, Integer.MAX_VALUE));
36 assertEquals(-4611686016279904256L,
37 StrictMath.multiplyFull(Integer.MAX_VALUE, Integer.MIN_VALUE));
38 assertEquals(4611686018427387904L,
39 StrictMath.multiplyFull(Integer.MIN_VALUE, Integer.MIN_VALUE));
40 }
41
Jake Wharton9402c902019-12-12 09:06:14 -050042 public static void testMultiplyHigh() {
43 long[] interestingValues = {
44 Long.MIN_VALUE, Long.MAX_VALUE,
45 Integer.MIN_VALUE, Integer.MAX_VALUE,
46 Short.MIN_VALUE, Short.MAX_VALUE,
47 Byte.MIN_VALUE, Byte.MAX_VALUE,
48 0L,
49 -1L, 1L,
50 -42L, 42L
51 };
52 for (long x : interestingValues) {
53 for (long y : interestingValues) {
54 long expected = BigInteger.valueOf(x)
55 .multiply(BigInteger.valueOf(y))
56 .shiftRight(64)
57 .longValue();
58 assertEquals(expected, StrictMath.multiplyHigh(x, y));
59 }
60 }
61 }
62
clementbera0bdd90f2019-07-06 11:15:23 +020063 public static void testFloorDivLongInt() {
64 assertEquals(1L, StrictMath.floorDiv(4L, 4));
65 assertEquals(1L, StrictMath.floorDiv(-4L, -4));
66 assertEquals(-1L, StrictMath.floorDiv(-4L, 4));
67 assertEquals(-1L, StrictMath.floorDiv(4L, -4));
68
69 assertEquals(1L, StrictMath.floorDiv(4L, 3));
70 assertEquals(1L, StrictMath.floorDiv(-4L, -3));
71 assertEquals(-2L, StrictMath.floorDiv(-4L, 3));
72 assertEquals(-2L, StrictMath.floorDiv(4L, -3));
73
74 // Spec edge case: result is actually MAX_VALUE+1 which becomes MIN_VALUE.
75 assertEquals(Long.MIN_VALUE, StrictMath.floorDiv(Long.MIN_VALUE, -1));
76 }
77
78 public static void testFloorModLongInt() {
79 assertEquals(0, StrictMath.floorMod(4L, 4));
80 assertEquals(0, StrictMath.floorMod(-4L, -4));
81 assertEquals(0, StrictMath.floorMod(-4L, 4));
82 assertEquals(0, StrictMath.floorMod(4L, -4));
83
84 assertEquals(1, StrictMath.floorMod(4L, 3));
85 assertEquals(-1, StrictMath.floorMod(-4L, -3));
86 assertEquals(2, StrictMath.floorMod(-4L, 3));
87 assertEquals(-2, StrictMath.floorMod(4L, -3));
88 }
89
90 private static void assertEquals(int expected, int actual) {
91 if (expected != actual) {
92 throw new AssertionError("Expected <" + expected + "> but was <" + actual + '>');
93 }
94 }
95
96 private static void assertEquals(long expected, long actual) {
97 if (expected != actual) {
98 throw new AssertionError("Expected <" + expected + "> but was <" + actual + '>');
99 }
100 }
101}