Revert "Merge java.lang.StrictMath from jdk-25+26 into the goog/main branch"
This reverts commit 74caa38f7f0a55a9a4ce2e3b103eef6774e530fe.
Reason for revert: Droidmonitor initiated the revert due to http://b/442831244. Will be verifying through ABTD before submission.
Fix: 442831244
Bug: 439527159
Change-Id: I62d0cb050f1c2cbca5007e46a268e7f2a726aa41
diff --git a/EXPECTED_UPSTREAM b/EXPECTED_UPSTREAM
index 805184e..7562c02 100644
--- a/EXPECTED_UPSTREAM
+++ b/EXPECTED_UPSTREAM
@@ -173,7 +173,7 @@
ojluni/src/main/java/java/lang/LiveStackFrameInfo.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/LiveStackFrameInfo.java
ojluni/src/main/java/java/lang/Long.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/Long.java
ojluni/src/main/java/java/lang/MatchException.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/MatchException.java
-ojluni/src/main/java/java/lang/Math.java,jdk/jdk-25+26,src/java.base/share/classes/java/lang/Math.java
+ojluni/src/main/java/java/lang/Math.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/Math.java
ojluni/src/main/java/java/lang/NegativeArraySizeException.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/NegativeArraySizeException.java
ojluni/src/main/java/java/lang/NoClassDefFoundError.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/NoClassDefFoundError.java
ojluni/src/main/java/java/lang/NoSuchFieldError.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/NoSuchFieldError.java
@@ -206,7 +206,7 @@
ojluni/src/main/java/java/lang/StackStreamFactory.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/StackStreamFactory.java
ojluni/src/main/java/java/lang/StackTraceElement.java,jdk11u/jdk-11.0.26-ga,src/java.base/share/classes/java/lang/StackTraceElement.java
ojluni/src/main/java/java/lang/StackWalker.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/StackWalker.java
-ojluni/src/main/java/java/lang/StrictMath.java,jdk/jdk-25+26,src/java.base/share/classes/java/lang/StrictMath.java
+ojluni/src/main/java/java/lang/StrictMath.java,jdk21u/jdk-21.0.6-ga,src/java.base/share/classes/java/lang/StrictMath.java
ojluni/src/main/java/java/lang/String.java,jdk17u/jdk-17.0.14-ga,src/java.base/share/classes/java/lang/String.java
ojluni/src/main/java/java/lang/StringBuffer.java,jdk11u/jdk-11.0.26-ga,src/java.base/share/classes/java/lang/StringBuffer.java
ojluni/src/main/java/java/lang/StringBuilder.java,jdk11u/jdk-11.0.26-ga,src/java.base/share/classes/java/lang/StringBuilder.java
@@ -2001,7 +2001,6 @@
ojluni/src/test/java/lang/Math/Clamp.java,jdk21u/jdk-21.0.6-ga,test/jdk/java/lang/Math/Clamp.java
ojluni/src/test/java/lang/Math/DivModTests.java,jdk21u/jdk-21.0.6-ga,test/jdk/java/lang/Math/DivModTests.java
ojluni/src/test/java/lang/Math/ExactArithTests.java,jdk21u/jdk-21.0.6-ga,test/jdk/java/lang/Math/ExactArithTests.java
-ojluni/src/test/java/lang/Math/IntegralPowTest.java,jdk/jdk-25+26,test/jdk/java/lang/Math/IntegralPowTest.java
ojluni/src/test/java/lang/Math/MultiplicationTests.java,jdk21u/jdk-21.0.6-ga,test/jdk/java/lang/Math/MultiplicationTests.java
ojluni/src/test/java/lang/StackWalker/AcrossThreads.java,jdk21u/jdk-21.0.6-ga,test/jdk/java/lang/StackWalker/AcrossThreads.java
ojluni/src/test/java/lang/StackWalker/Basic.java,jdk21u/jdk-21.0.6-ga,test/jdk/java/lang/StackWalker/Basic.java
diff --git a/api/current.txt b/api/current.txt
index 6bb9909..d8247b0 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -3774,8 +3774,6 @@
method public static double nextUp(double);
method public static float nextUp(float);
method public static double pow(double, double);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static int powExact(int, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long powExact(long, int);
method public static double random();
method public static double rint(double);
method public static int round(float);
@@ -3796,12 +3794,7 @@
method public static double toRadians(double);
method public static double ulp(double);
method public static float ulp(float);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static int unsignedMultiplyExact(int, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long unsignedMultiplyExact(long, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long unsignedMultiplyExact(long, long);
method public static long unsignedMultiplyHigh(long, long);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static int unsignedPowExact(int, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long unsignedPowExact(long, int);
field public static final double E = 2.718281828459045;
field public static final double PI = 3.141592653589793;
field public static final double TAU = 6.283185307179586;
@@ -4223,8 +4216,6 @@
method public static double nextUp(double);
method public static float nextUp(float);
method public static double pow(double, double);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static int powExact(int, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long powExact(long, int);
method public static double random();
method public static double rint(double);
method public static int round(float);
@@ -4245,12 +4236,7 @@
method public static double toRadians(double);
method public static double ulp(double);
method public static float ulp(float);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static int unsignedMultiplyExact(int, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long unsignedMultiplyExact(long, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long unsignedMultiplyExact(long, long);
method public static long unsignedMultiplyHigh(long, long);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static int unsignedPowExact(int, int);
- method @FlaggedApi("com.android.libcore.openjdk_25_v1_apis") public static long unsignedPowExact(long, int);
field public static final double E = 2.718281828459045;
field public static final double PI = 3.141592653589793;
field public static final double TAU = 6.283185307179586;
diff --git a/ojluni/annotations/flagged_api/java/lang/Math.annotated.java b/ojluni/annotations/flagged_api/java/lang/Math.annotated.java
index 941c7a8..c554610 100644
--- a/ojluni/annotations/flagged_api/java/lang/Math.annotated.java
+++ b/ojluni/annotations/flagged_api/java/lang/Math.annotated.java
@@ -1,6 +1,6 @@
/*
* Copyright (C) 2014 The Android Open Source Project
- * Copyright (c) 1994, 2025, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1994, 2023, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -32,133 +32,57 @@
Math() { throw new RuntimeException("Stub!"); }
-public static native double IEEEremainder(double f1, double f2);
-
-public static double abs(double a) { throw new RuntimeException("Stub!"); }
-
-public static float abs(float a) { throw new RuntimeException("Stub!"); }
-
-public static int abs(int a) { throw new RuntimeException("Stub!"); }
-
-public static long abs(long a) { throw new RuntimeException("Stub!"); }
-
-public static int absExact(int a) { throw new RuntimeException("Stub!"); }
-
-public static long absExact(long a) { throw new RuntimeException("Stub!"); }
-
-public static native double acos(double a);
-
-public static int addExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long addExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static native double asin(double a);
-
-public static native double atan(double a);
-
-public static native double atan2(double y, double x);
-
-public static native double cbrt(double a);
-
-public static native double ceil(double a);
-
-public static int ceilDiv(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilDiv(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilDiv(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int ceilDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int ceilMod(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static int ceilMod(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilMod(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static double clamp(double value, double min, double max) { throw new RuntimeException("Stub!"); }
-
-public static float clamp(float value, float min, float max) { throw new RuntimeException("Stub!"); }
-
-public static int clamp(long value, int min, int max) { throw new RuntimeException("Stub!"); }
-
-public static long clamp(long value, long min, long max) { throw new RuntimeException("Stub!"); }
-
-public static double copySign(double magnitude, double sign) { throw new RuntimeException("Stub!"); }
-
-public static float copySign(float magnitude, float sign) { throw new RuntimeException("Stub!"); }
+public static native double sin(double a);
public static native double cos(double a);
-public static native double cosh(double x);
+public static native double tan(double a);
-public static int decrementExact(int a) { throw new RuntimeException("Stub!"); }
+public static native double asin(double a);
-public static long decrementExact(long a) { throw new RuntimeException("Stub!"); }
+public static native double acos(double a);
-public static int divideExact(int x, int y) { throw new RuntimeException("Stub!"); }
+public static native double atan(double a);
-public static long divideExact(long x, long y) { throw new RuntimeException("Stub!"); }
+public static double toRadians(double angdeg) { throw new RuntimeException("Stub!"); }
+
+public static double toDegrees(double angrad) { throw new RuntimeException("Stub!"); }
public static native double exp(double a);
-public static native double expm1(double x);
-
-public static native double floor(double a);
-
-public static int floorDiv(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorDiv(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorDiv(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int floorDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int floorMod(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static int floorMod(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorMod(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static double fma(double a, double b, double c) { throw new RuntimeException("Stub!"); }
-
-public static float fma(float a, float b, float c) { throw new RuntimeException("Stub!"); }
-
-public static int getExponent(double d) { throw new RuntimeException("Stub!"); }
-
-public static int getExponent(float f) { throw new RuntimeException("Stub!"); }
-
-public static native double hypot(double x, double y);
-
-public static int incrementExact(int a) { throw new RuntimeException("Stub!"); }
-
-public static long incrementExact(long a) { throw new RuntimeException("Stub!"); }
-
public static native double log(double a);
public static native double log10(double a);
-public static native double log1p(double x);
+public static native double sqrt(double a);
-public static double max(double a, double b) { throw new RuntimeException("Stub!"); }
+public static native double cbrt(double a);
-public static float max(float a, float b) { throw new RuntimeException("Stub!"); }
+public static native double IEEEremainder(double f1, double f2);
-public static int max(int a, int b) { throw new RuntimeException("Stub!"); }
+public static native double ceil(double a);
-public static long max(long a, long b) { throw new RuntimeException("Stub!"); }
+public static native double floor(double a);
-public static double min(double a, double b) { throw new RuntimeException("Stub!"); }
+public static native double rint(double a);
-public static float min(float a, float b) { throw new RuntimeException("Stub!"); }
+public static native double atan2(double y, double x);
-public static int min(int a, int b) { throw new RuntimeException("Stub!"); }
+public static native double pow(double a, double b);
-public static long min(long a, long b) { throw new RuntimeException("Stub!"); }
+public static int round(float a) { throw new RuntimeException("Stub!"); }
+
+public static long round(double a) { throw new RuntimeException("Stub!"); }
+
+public static double random() { throw new RuntimeException("Stub!"); }
+
+public static int addExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long addExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int subtractExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long subtractExact(long x, long y) { throw new RuntimeException("Stub!"); }
public static int multiplyExact(int x, int y) { throw new RuntimeException("Stub!"); }
@@ -166,95 +90,168 @@
public static long multiplyExact(long x, long y) { throw new RuntimeException("Stub!"); }
-public static long multiplyFull(int x, int y) { throw new RuntimeException("Stub!"); }
-public static long multiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+public static int divideExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long divideExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int floorDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long floorDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int incrementExact(int a) { throw new RuntimeException("Stub!"); }
+
+public static long incrementExact(long a) { throw new RuntimeException("Stub!"); }
+
+public static int decrementExact(int a) { throw new RuntimeException("Stub!"); }
+
+public static long decrementExact(long a) { throw new RuntimeException("Stub!"); }
public static int negateExact(int a) { throw new RuntimeException("Stub!"); }
public static long negateExact(long a) { throw new RuntimeException("Stub!"); }
-public static double nextAfter(double start, double direction) { throw new RuntimeException("Stub!"); }
-
-public static float nextAfter(float start, double direction) { throw new RuntimeException("Stub!"); }
-
-public static double nextDown(double d) { throw new RuntimeException("Stub!"); }
-
-public static float nextDown(float f) { throw new RuntimeException("Stub!"); }
-
-public static double nextUp(double d) { throw new RuntimeException("Stub!"); }
-
-public static float nextUp(float f) { throw new RuntimeException("Stub!"); }
-
-public static native double pow(double a, double b);
-
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static int powExact(int x, int n) { throw new RuntimeException("Stub!"); }
-
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long powExact(long x, int n) { throw new RuntimeException("Stub!"); }
-
-public static double random() { throw new RuntimeException("Stub!"); }
-
-public static native double rint(double a);
-
-public static long round(double a) { throw new RuntimeException("Stub!"); }
-
-public static int round(float a) { throw new RuntimeException("Stub!"); }
-
-public static double scalb(double d, int scaleFactor) { throw new RuntimeException("Stub!"); }
-
-public static float scalb(float f, int scaleFactor) { throw new RuntimeException("Stub!"); }
-
-public static double signum(double d) { throw new RuntimeException("Stub!"); }
-
-public static float signum(float f) { throw new RuntimeException("Stub!"); }
-
-public static native double sin(double a);
-
-public static native double sinh(double x);
-
-public static native double sqrt(double a);
-
-public static int subtractExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long subtractExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static native double tan(double a);
-
-public static native double tanh(double x);
-
-public static double toDegrees(double angrad) { throw new RuntimeException("Stub!"); }
-
public static int toIntExact(long value) { throw new RuntimeException("Stub!"); }
-public static double toRadians(double angdeg) { throw new RuntimeException("Stub!"); }
+public static long multiplyFull(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long multiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static long unsignedMultiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int floorDiv(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long floorDiv(long x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long floorDiv(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int floorMod(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static int floorMod(long x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long floorMod(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilDiv(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilDiv(long x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilDiv(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilMod(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilMod(long x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilMod(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int abs(int a) { throw new RuntimeException("Stub!"); }
+
+public static int absExact(int a) { throw new RuntimeException("Stub!"); }
+
+public static long abs(long a) { throw new RuntimeException("Stub!"); }
+
+public static long absExact(long a) { throw new RuntimeException("Stub!"); }
+
+public static float abs(float a) { throw new RuntimeException("Stub!"); }
+
+public static double abs(double a) { throw new RuntimeException("Stub!"); }
+
+public static int max(int a, int b) { throw new RuntimeException("Stub!"); }
+
+public static long max(long a, long b) { throw new RuntimeException("Stub!"); }
+
+public static float max(float a, float b) { throw new RuntimeException("Stub!"); }
+
+public static double max(double a, double b) { throw new RuntimeException("Stub!"); }
+
+public static int min(int a, int b) { throw new RuntimeException("Stub!"); }
+
+public static long min(long a, long b) { throw new RuntimeException("Stub!"); }
+
+public static float min(float a, float b) { throw new RuntimeException("Stub!"); }
+
+public static double min(double a, double b) { throw new RuntimeException("Stub!"); }
+
+
+public static int clamp(long value, int min, int max) { throw new RuntimeException("Stub!"); }
+
+
+public static long clamp(long value, long min, long max) { throw new RuntimeException("Stub!"); }
+
+
+public static double clamp(double value, double min, double max) { throw new RuntimeException("Stub!"); }
+
+
+public static float clamp(float value, float min, float max) { throw new RuntimeException("Stub!"); }
+
+public static double fma(double a, double b, double c) { throw new RuntimeException("Stub!"); }
+
+public static float fma(float a, float b, float c) { throw new RuntimeException("Stub!"); }
public static double ulp(double d) { throw new RuntimeException("Stub!"); }
public static float ulp(float f) { throw new RuntimeException("Stub!"); }
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static int unsignedMultiplyExact(int x, int y) { throw new RuntimeException("Stub!"); }
+public static double signum(double d) { throw new RuntimeException("Stub!"); }
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long unsignedMultiplyExact(long x, int y) { throw new RuntimeException("Stub!"); }
+public static float signum(float f) { throw new RuntimeException("Stub!"); }
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long unsignedMultiplyExact(long x, long y) { throw new RuntimeException("Stub!"); }
+public static native double sinh(double x);
-public static long unsignedMultiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+public static native double cosh(double x);
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static int unsignedPowExact(int x, int n) { throw new RuntimeException("Stub!"); }
+public static native double tanh(double x);
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long unsignedPowExact(long x, int n) { throw new RuntimeException("Stub!"); }
+public static native double hypot(double x, double y);
+
+public static native double expm1(double x);
+
+public static native double log1p(double x);
+
+public static double copySign(double magnitude, double sign) { throw new RuntimeException("Stub!"); }
+
+public static float copySign(float magnitude, float sign) { throw new RuntimeException("Stub!"); }
+
+public static int getExponent(float f) { throw new RuntimeException("Stub!"); }
+
+public static int getExponent(double d) { throw new RuntimeException("Stub!"); }
+
+public static double nextAfter(double start, double direction) { throw new RuntimeException("Stub!"); }
+
+public static float nextAfter(float start, double direction) { throw new RuntimeException("Stub!"); }
+
+public static double nextUp(double d) { throw new RuntimeException("Stub!"); }
+
+public static float nextUp(float f) { throw new RuntimeException("Stub!"); }
+
+public static double nextDown(double d) { throw new RuntimeException("Stub!"); }
+
+public static float nextDown(float f) { throw new RuntimeException("Stub!"); }
+
+public static double scalb(double d, int scaleFactor) { throw new RuntimeException("Stub!"); }
+
+public static float scalb(float f, int scaleFactor) { throw new RuntimeException("Stub!"); }
public static final double E = 2.718281828459045;
public static final double PI = 3.141592653589793;
+
public static final double TAU = 6.283185307179586;
}
diff --git a/ojluni/annotations/flagged_api/java/lang/StrictMath.annotated.java b/ojluni/annotations/flagged_api/java/lang/StrictMath.annotated.java
index 777f1cf..1eace71 100644
--- a/ojluni/annotations/flagged_api/java/lang/StrictMath.annotated.java
+++ b/ojluni/annotations/flagged_api/java/lang/StrictMath.annotated.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1999, 2025, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 2023, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -31,133 +31,57 @@
StrictMath() { throw new RuntimeException("Stub!"); }
-public static native double IEEEremainder(double f1, double f2);
-
-public static double abs(double a) { throw new RuntimeException("Stub!"); }
-
-public static float abs(float a) { throw new RuntimeException("Stub!"); }
-
-public static int abs(int a) { throw new RuntimeException("Stub!"); }
-
-public static long abs(long a) { throw new RuntimeException("Stub!"); }
-
-public static int absExact(int a) { throw new RuntimeException("Stub!"); }
-
-public static long absExact(long a) { throw new RuntimeException("Stub!"); }
-
-public static native double acos(double a);
-
-public static int addExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long addExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static native double asin(double a);
-
-public static native double atan(double a);
-
-public static native double atan2(double y, double x);
-
-public static native double cbrt(double a);
-
-public static double ceil(double a) { throw new RuntimeException("Stub!"); }
-
-public static int ceilDiv(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilDiv(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilDiv(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int ceilDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int ceilMod(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static int ceilMod(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long ceilMod(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static double clamp(double value, double min, double max) { throw new RuntimeException("Stub!"); }
-
-public static float clamp(float value, float min, float max) { throw new RuntimeException("Stub!"); }
-
-public static int clamp(long value, int min, int max) { throw new RuntimeException("Stub!"); }
-
-public static long clamp(long value, long min, long max) { throw new RuntimeException("Stub!"); }
-
-public static double copySign(double magnitude, double sign) { throw new RuntimeException("Stub!"); }
-
-public static float copySign(float magnitude, float sign) { throw new RuntimeException("Stub!"); }
+public static native double sin(double a);
public static native double cos(double a);
-public static native double cosh(double x);
+public static native double tan(double a);
-public static int decrementExact(int a) { throw new RuntimeException("Stub!"); }
+public static native double asin(double a);
-public static long decrementExact(long a) { throw new RuntimeException("Stub!"); }
+public static native double acos(double a);
-public static int divideExact(int x, int y) { throw new RuntimeException("Stub!"); }
+public static native double atan(double a);
-public static long divideExact(long x, long y) { throw new RuntimeException("Stub!"); }
+public static double toRadians(double angdeg) { throw new RuntimeException("Stub!"); }
+
+public static double toDegrees(double angrad) { throw new RuntimeException("Stub!"); }
public static native double exp(double a);
-public static native double expm1(double x);
-
-public static double floor(double a) { throw new RuntimeException("Stub!"); }
-
-public static int floorDiv(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorDiv(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorDiv(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int floorDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static int floorMod(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static int floorMod(long x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long floorMod(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static double fma(double a, double b, double c) { throw new RuntimeException("Stub!"); }
-
-public static float fma(float a, float b, float c) { throw new RuntimeException("Stub!"); }
-
-public static int getExponent(double d) { throw new RuntimeException("Stub!"); }
-
-public static int getExponent(float f) { throw new RuntimeException("Stub!"); }
-
-public static native double hypot(double x, double y);
-
-public static int incrementExact(int a) { throw new RuntimeException("Stub!"); }
-
-public static long incrementExact(long a) { throw new RuntimeException("Stub!"); }
-
public static native double log(double a);
public static native double log10(double a);
-public static native double log1p(double x);
+public static native double sqrt(double a);
-public static double max(double a, double b) { throw new RuntimeException("Stub!"); }
+public static native double cbrt(double a);
-public static float max(float a, float b) { throw new RuntimeException("Stub!"); }
+public static native double IEEEremainder(double f1, double f2);
-public static int max(int a, int b) { throw new RuntimeException("Stub!"); }
+public static double ceil(double a) { throw new RuntimeException("Stub!"); }
-public static long max(long a, long b) { throw new RuntimeException("Stub!"); }
+public static double floor(double a) { throw new RuntimeException("Stub!"); }
-public static double min(double a, double b) { throw new RuntimeException("Stub!"); }
+public static double rint(double a) { throw new RuntimeException("Stub!"); }
-public static float min(float a, float b) { throw new RuntimeException("Stub!"); }
+public static native double atan2(double y, double x);
-public static int min(int a, int b) { throw new RuntimeException("Stub!"); }
+public static native double pow(double a, double b);
-public static long min(long a, long b) { throw new RuntimeException("Stub!"); }
+public static int round(float a) { throw new RuntimeException("Stub!"); }
+
+public static long round(double a) { throw new RuntimeException("Stub!"); }
+
+public static double random() { throw new RuntimeException("Stub!"); }
+
+public static int addExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long addExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int subtractExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long subtractExact(long x, long y) { throw new RuntimeException("Stub!"); }
public static int multiplyExact(int x, int y) { throw new RuntimeException("Stub!"); }
@@ -165,95 +89,168 @@
public static long multiplyExact(long x, long y) { throw new RuntimeException("Stub!"); }
-public static long multiplyFull(int x, int y) { throw new RuntimeException("Stub!"); }
-public static long multiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+public static int divideExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long divideExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int floorDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long floorDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilDivExact(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilDivExact(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int incrementExact(int a) { throw new RuntimeException("Stub!"); }
+
+public static long incrementExact(long a) { throw new RuntimeException("Stub!"); }
+
+public static int decrementExact(int a) { throw new RuntimeException("Stub!"); }
+
+public static long decrementExact(long a) { throw new RuntimeException("Stub!"); }
public static int negateExact(int a) { throw new RuntimeException("Stub!"); }
public static long negateExact(long a) { throw new RuntimeException("Stub!"); }
-public static double nextAfter(double start, double direction) { throw new RuntimeException("Stub!"); }
-
-public static float nextAfter(float start, double direction) { throw new RuntimeException("Stub!"); }
-
-public static double nextDown(double d) { throw new RuntimeException("Stub!"); }
-
-public static float nextDown(float f) { throw new RuntimeException("Stub!"); }
-
-public static double nextUp(double d) { throw new RuntimeException("Stub!"); }
-
-public static float nextUp(float f) { throw new RuntimeException("Stub!"); }
-
-public static native double pow(double a, double b);
-
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static int powExact(int x, int n) { throw new RuntimeException("Stub!"); }
-
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long powExact(long x, int n) { throw new RuntimeException("Stub!"); }
-
-public static double random() { throw new RuntimeException("Stub!"); }
-
-public static double rint(double a) { throw new RuntimeException("Stub!"); }
-
-public static long round(double a) { throw new RuntimeException("Stub!"); }
-
-public static int round(float a) { throw new RuntimeException("Stub!"); }
-
-public static double scalb(double d, int scaleFactor) { throw new RuntimeException("Stub!"); }
-
-public static float scalb(float f, int scaleFactor) { throw new RuntimeException("Stub!"); }
-
-public static double signum(double d) { throw new RuntimeException("Stub!"); }
-
-public static float signum(float f) { throw new RuntimeException("Stub!"); }
-
-public static native double sin(double a);
-
-public static native double sinh(double x);
-
-public static native double sqrt(double a);
-
-public static int subtractExact(int x, int y) { throw new RuntimeException("Stub!"); }
-
-public static long subtractExact(long x, long y) { throw new RuntimeException("Stub!"); }
-
-public static native double tan(double a);
-
-public static native double tanh(double x);
-
-public static double toDegrees(double angrad) { throw new RuntimeException("Stub!"); }
-
public static int toIntExact(long value) { throw new RuntimeException("Stub!"); }
-public static double toRadians(double angdeg) { throw new RuntimeException("Stub!"); }
+public static long multiplyFull(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long multiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static long unsignedMultiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int floorDiv(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long floorDiv(long x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long floorDiv(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int floorMod(int x, int y) { throw new RuntimeException("Stub!"); }
+
+public static int floorMod(long x, int y) { throw new RuntimeException("Stub!"); }
+
+public static long floorMod(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilDiv(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilDiv(long x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilDiv(long x, long y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilMod(int x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static int ceilMod(long x, int y) { throw new RuntimeException("Stub!"); }
+
+
+public static long ceilMod(long x, long y) { throw new RuntimeException("Stub!"); }
+
+public static int abs(int a) { throw new RuntimeException("Stub!"); }
+
+public static int absExact(int a) { throw new RuntimeException("Stub!"); }
+
+public static long abs(long a) { throw new RuntimeException("Stub!"); }
+
+public static long absExact(long a) { throw new RuntimeException("Stub!"); }
+
+public static float abs(float a) { throw new RuntimeException("Stub!"); }
+
+public static double abs(double a) { throw new RuntimeException("Stub!"); }
+
+public static int max(int a, int b) { throw new RuntimeException("Stub!"); }
+
+public static long max(long a, long b) { throw new RuntimeException("Stub!"); }
+
+public static float max(float a, float b) { throw new RuntimeException("Stub!"); }
+
+public static double max(double a, double b) { throw new RuntimeException("Stub!"); }
+
+public static int min(int a, int b) { throw new RuntimeException("Stub!"); }
+
+public static long min(long a, long b) { throw new RuntimeException("Stub!"); }
+
+public static float min(float a, float b) { throw new RuntimeException("Stub!"); }
+
+public static double min(double a, double b) { throw new RuntimeException("Stub!"); }
+
+
+public static int clamp(long value, int min, int max) { throw new RuntimeException("Stub!"); }
+
+
+public static long clamp(long value, long min, long max) { throw new RuntimeException("Stub!"); }
+
+
+public static double clamp(double value, double min, double max) { throw new RuntimeException("Stub!"); }
+
+
+public static float clamp(float value, float min, float max) { throw new RuntimeException("Stub!"); }
+
+public static double fma(double a, double b, double c) { throw new RuntimeException("Stub!"); }
+
+public static float fma(float a, float b, float c) { throw new RuntimeException("Stub!"); }
public static double ulp(double d) { throw new RuntimeException("Stub!"); }
public static float ulp(float f) { throw new RuntimeException("Stub!"); }
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static int unsignedMultiplyExact(int x, int y) { throw new RuntimeException("Stub!"); }
+public static double signum(double d) { throw new RuntimeException("Stub!"); }
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long unsignedMultiplyExact(long x, int y) { throw new RuntimeException("Stub!"); }
+public static float signum(float f) { throw new RuntimeException("Stub!"); }
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long unsignedMultiplyExact(long x, long y) { throw new RuntimeException("Stub!"); }
+public static native double sinh(double x);
-public static long unsignedMultiplyHigh(long x, long y) { throw new RuntimeException("Stub!"); }
+public static native double cosh(double x);
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static int unsignedPowExact(int x, int n) { throw new RuntimeException("Stub!"); }
+public static native double tanh(double x);
-@android.annotation.FlaggedApi(com.android.libcore.Flags.FLAG_OPENJDK_25_V1_APIS)
-public static long unsignedPowExact(long x, int n) { throw new RuntimeException("Stub!"); }
+public static native double hypot(double x, double y);
+
+public static native double expm1(double x);
+
+public static native double log1p(double x);
+
+public static double copySign(double magnitude, double sign) { throw new RuntimeException("Stub!"); }
+
+public static float copySign(float magnitude, float sign) { throw new RuntimeException("Stub!"); }
+
+public static int getExponent(float f) { throw new RuntimeException("Stub!"); }
+
+public static int getExponent(double d) { throw new RuntimeException("Stub!"); }
+
+public static double nextAfter(double start, double direction) { throw new RuntimeException("Stub!"); }
+
+public static float nextAfter(float start, double direction) { throw new RuntimeException("Stub!"); }
+
+public static double nextUp(double d) { throw new RuntimeException("Stub!"); }
+
+public static float nextUp(float f) { throw new RuntimeException("Stub!"); }
+
+public static double nextDown(double d) { throw new RuntimeException("Stub!"); }
+
+public static float nextDown(float f) { throw new RuntimeException("Stub!"); }
+
+public static double scalb(double d, int scaleFactor) { throw new RuntimeException("Stub!"); }
+
+public static float scalb(float f, int scaleFactor) { throw new RuntimeException("Stub!"); }
public static final double E = 2.718281828459045;
public static final double PI = 3.141592653589793;
+
public static final double TAU = 6.283185307179586;
}
diff --git a/ojluni/src/main/java/java/lang/Math.java b/ojluni/src/main/java/java/lang/Math.java
index fc5beb8..30ba9fb 100644
--- a/ojluni/src/main/java/java/lang/Math.java
+++ b/ojluni/src/main/java/java/lang/Math.java
@@ -1,6 +1,6 @@
/*
* Copyright (C) 2014 The Android Open Source Project
- * Copyright (c) 1994, 2025, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1994, 2023, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -39,8 +39,6 @@
// OS's libm functions. libm has well-defined behavior for special cases. Where known these are
// marked with the tag above and the documentation has been modified as needed.
// Android-changed: Fixed method links in the last paragraph.
-import static java.lang.Double.*;
-
/**
* The class {@code Math} contains methods for performing basic
* numeric operations such as the elementary exponential, logarithm,
@@ -65,46 +63,44 @@
* <p>The quality of implementation specifications concern two
* properties, accuracy of the returned result and monotonicity of the
* method. Accuracy of the floating-point {@code Math} methods is
- * measured in terms of <dfn>{@index ulp}s</dfn>, {@index "units in
- * the last place"}. For a given floating-point format, an
- * {@linkplain #ulp(double) ulp} of a specific real number value is
- * the distance between the two floating-point values bracketing that
- * numerical value. When discussing the accuracy of a method as a
- * whole rather than at a specific argument, the number of ulps cited
- * is for the worst-case error at any argument. If a method always
- * has an error less than 0.5 ulps, the method always returns the
- * floating-point number nearest the exact result; such a method is
- * <dfn>correctly rounded</dfn>. A {@index "correctly rounded"}
- * method is generally the best a floating-point approximation can be;
- * however, it is impractical for many floating-point methods to be
- * correctly rounded. Instead, for the {@code Math} class, a larger
- * error bound of 1 or 2 ulps is allowed for certain methods.
- * Informally, with a 1 ulp error bound, when the exact result is a
- * representable number, the exact result should be returned as the
- * computed result; otherwise, either of the two floating-point values
- * which bracket the exact result may be returned. For exact results
- * large in magnitude, one of the endpoints of the bracket may be
- * infinite. Besides accuracy at individual arguments, maintaining
- * proper relations between the method at different arguments is also
- * important. Therefore, most methods with more than 0.5 ulp errors
- * are required to be <dfn>{@index "semi-monotonic"}</dfn>: whenever
- * the mathematical function is non-decreasing, so is the
- * floating-point approximation, likewise, whenever the mathematical
- * function is non-increasing, so is the floating-point approximation.
- * Not all approximations that have 1 ulp accuracy will automatically
- * meet the monotonicity requirements.
+ * measured in terms of <i>ulps</i>, units in the last place. For a
+ * given floating-point format, an {@linkplain #ulp(double) ulp} of a
+ * specific real number value is the distance between the two
+ * floating-point values bracketing that numerical value. When
+ * discussing the accuracy of a method as a whole rather than at a
+ * specific argument, the number of ulps cited is for the worst-case
+ * error at any argument. If a method always has an error less than
+ * 0.5 ulps, the method always returns the floating-point number
+ * nearest the exact result; such a method is <i>correctly
+ * rounded</i>. A correctly rounded method is generally the best a
+ * floating-point approximation can be; however, it is impractical for
+ * many floating-point methods to be correctly rounded. Instead, for
+ * the {@code Math} class, a larger error bound of 1 or 2 ulps is
+ * allowed for certain methods. Informally, with a 1 ulp error bound,
+ * when the exact result is a representable number, the exact result
+ * should be returned as the computed result; otherwise, either of the
+ * two floating-point values which bracket the exact result may be
+ * returned. For exact results large in magnitude, one of the
+ * endpoints of the bracket may be infinite. Besides accuracy at
+ * individual arguments, maintaining proper relations between the
+ * method at different arguments is also important. Therefore, most
+ * methods with more than 0.5 ulp errors are required to be
+ * <i>semi-monotonic</i>: whenever the mathematical function is
+ * non-decreasing, so is the floating-point approximation, likewise,
+ * whenever the mathematical function is non-increasing, so is the
+ * floating-point approximation. Not all approximations that have 1
+ * ulp accuracy will automatically meet the monotonicity requirements.
*
* <p>
* The platform uses signed two's complement integer arithmetic with
- * {@code int} and {@code long} primitive types. The developer should
- * choose the primitive type to ensure that arithmetic operations
- * consistently produce correct results, which in some cases means the
- * operations will not overflow the range of values of the
- * computation. The best practice is to choose the primitive type and
- * algorithm to avoid overflow. In cases where the size is {@code int}
- * or {@code long} and overflow errors need to be detected, the
- * methods whose names end with {@code Exact} throw an {@code
- * ArithmeticException} when the results overflow.
+ * int and long primitive types. The developer should choose
+ * the primitive type to ensure that arithmetic operations consistently
+ * produce correct results, which in some cases means the operations
+ * will not overflow the range of values of the computation.
+ * The best practice is to choose the primitive type and algorithm to avoid
+ * overflow. In cases where the size is {@code int} or {@code long} and
+ * overflow errors need to be detected, the methods whose names end with
+ * {@code Exact} throw an {@code ArithmeticException} when the results overflow.
*
* <h2><a id=Ieee754RecommendedOps>IEEE 754 Recommended
* Operations</a></h2>
@@ -128,9 +124,10 @@
* implementation condition than required for most of the methods in
* question that are also included in this class.
*
- * @spec https://standards.ieee.org/ieee/754/6210/
- * IEEE Standard for Floating-Point Arithmetic
+ * @see <a href="https://standards.ieee.org/ieee/754/6210/">
+ * <cite>IEEE Standard for Floating-Point Arithmetic</cite></a>
*
+ * @author Joseph D. Darcy
* @since 1.0
*/
@@ -237,7 +234,7 @@
* <li>If the argument is zero, then the result is a zero with the
* same sign as the argument.</ul>
*
- * <p>The computed result must be within 1.25 ulps of the exact result.
+ * <p>The computed result must be within 1 ulp of the exact result.
* Results must be semi-monotonic.
*
* @param a an angle, in radians.
@@ -256,7 +253,7 @@
/**
* Returns the arc sine of a value; the returned angle is in the
- * range −<i>pi</i>/2 through <i>pi</i>/2. Special cases:
+ * range -<i>pi</i>/2 through <i>pi</i>/2. Special cases:
* <ul><li>If the argument is NaN or its absolute value is greater
* than 1, then the result is NaN.
* <li>If the argument is zero, then the result is a zero with the
@@ -304,7 +301,7 @@
/**
* Returns the arc tangent of a value; the returned angle is in the
- * range −<i>pi</i>/2 through <i>pi</i>/2. Special cases:
+ * range -<i>pi</i>/2 through <i>pi</i>/2. Special cases:
* <ul><li>If the argument is NaN, then the result is NaN.
* <li>If the argument is zero, then the result is a zero with the
* same sign as the argument.
@@ -518,7 +515,6 @@
*/
// BEGIN Android-changed: Reimplement in native
/*
- @IntrinsicCandidate
public static double cbrt(double a) {
return StrictMath.cbrt(a);
}
@@ -657,7 +653,7 @@
* coordinates ({@code x}, {@code y}) to polar
* coordinates (r, <i>theta</i>).
* This method computes the phase <i>theta</i> by computing an arc tangent
- * of {@code y/x} in the range of −<i>pi</i> to <i>pi</i>. Special
+ * of {@code y/x} in the range of -<i>pi</i> to <i>pi</i>. Special
* cases:
* <ul><li>If either argument is NaN, then the result is NaN.
* <li>If the first argument is positive zero and the second argument
@@ -2181,7 +2177,6 @@
* @param b another argument.
* @return the larger of {@code a} and {@code b}.
*/
- @IntrinsicCandidate
public static long max(long a, long b) {
return (a >= b) ? a : b;
}
@@ -2277,7 +2272,6 @@
* @param b another argument.
* @return the smaller of {@code a} and {@code b}.
*/
- @IntrinsicCandidate
public static long min(long a, long b) {
return (a <= b) ? a : b;
}
@@ -2815,7 +2809,7 @@
/**
* Returns the hyperbolic sine of a {@code double} value.
* The hyperbolic sine of <i>x</i> is defined to be
- * (<i>e<sup>x</sup> − e<sup>−x</sup></i>)/2
+ * (<i>e<sup>x</sup> - e<sup>-x</sup></i>)/2
* where <i>e</i> is {@linkplain Math#E Euler's number}.
*
* <p>Special cases:
@@ -2850,7 +2844,7 @@
/**
* Returns the hyperbolic cosine of a {@code double} value.
* The hyperbolic cosine of <i>x</i> is defined to be
- * (<i>e<sup>x</sup> + e<sup>−x</sup></i>)/2
+ * (<i>e<sup>x</sup> + e<sup>-x</sup></i>)/2
* where <i>e</i> is {@linkplain Math#E Euler's number}.
*
* <p>Special cases:
@@ -2884,7 +2878,7 @@
/**
* Returns the hyperbolic tangent of a {@code double} value.
* The hyperbolic tangent of <i>x</i> is defined to be
- * (<i>e<sup>x</sup> − e<sup>−x</sup></i>)/(<i>e<sup>x</sup> + e<sup>−x</sup></i>),
+ * (<i>e<sup>x</sup> - e<sup>-x</sup></i>)/(<i>e<sup>x</sup> + e<sup>-x</sup></i>),
* in other words, {@linkplain Math#sinh
* sinh(<i>x</i>)}/{@linkplain Math#cosh cosh(<i>x</i>)}. Note
* that the absolute value of the exact tanh is always less than
@@ -2919,11 +2913,11 @@
*/
// BEGIN Android-changed: Reimplement in native
/*
- @IntrinsicCandidate
public static double tanh(double x) {
return StrictMath.tanh(x);
}
*/
+ // END Android-changed: Reimplement in native
@CriticalNative
public static native double tanh(double x);
@@ -2943,7 +2937,7 @@
* <li> If both arguments are zero, the result is positive zero.
* </ul>
*
- * <p>The computed result must be within 1.5 ulps of the exact
+ * <p>The computed result must be within 1 ulp of the exact
* result. If one parameter is held constant, the results must be
* semi-monotonic in the other parameter.
*
@@ -2964,7 +2958,7 @@
public static native double hypot(double x, double y);
/**
- * Returns <i>e</i><sup>x</sup> −1. Note that for values of
+ * Returns <i>e</i><sup>x</sup> -1. Note that for values of
* <i>x</i> near 0, the exact sum of
* {@code expm1(x)} + 1 is much closer to the true
* result of <i>e</i><sup>x</sup> than {@code exp(x)}.
@@ -2993,7 +2987,7 @@
* returned.
*
* @param x the exponent to raise <i>e</i> to in the computation of
- * <i>e</i><sup>{@code x}</sup> −1.
+ * <i>e</i><sup>{@code x}</sup> -1.
* @return the value <i>e</i><sup>{@code x}</sup> - 1.
* @since 1.5
*/
@@ -3489,9 +3483,6 @@
}
}
- private static final double F_UP = 0x1p1023; // normal, exact, 2^DoubleConsts.EXP_BIAS
- private static final double F_DOWN = 0x1p-1023; // subnormal, exact, 2^-DoubleConsts.EXP_BIAS
-
/**
* Returns {@code d} × 2<sup>{@code scaleFactor}</sup>
* rounded as if performed by a single correctly rounded
@@ -3523,25 +3514,60 @@
* @since 1.6
*/
public static double scalb(double d, int scaleFactor) {
- if (scaleFactor > -DoubleConsts.EXP_BIAS) {
- if (scaleFactor <= DoubleConsts.EXP_BIAS) {
- return d * primPowerOfTwoD(scaleFactor);
- }
- if (scaleFactor <= 2 * DoubleConsts.EXP_BIAS) {
- return d * primPowerOfTwoD(scaleFactor - DoubleConsts.EXP_BIAS) * F_UP;
- }
- if (scaleFactor < 2 * DoubleConsts.EXP_BIAS + PRECISION - 1) {
- return d * primPowerOfTwoD(scaleFactor - 2 * DoubleConsts.EXP_BIAS) * F_UP * F_UP;
- }
- return d * F_UP * F_UP * F_UP;
+ /*
+ * When scaling up, it does not matter what order the
+ * multiply-store operations are done; the result will be
+ * finite or overflow regardless of the operation ordering.
+ * However, to get the correct result when scaling down, a
+ * particular ordering must be used.
+ *
+ * When scaling down, the multiply-store operations are
+ * sequenced so that it is not possible for two consecutive
+ * multiply-stores to return subnormal results. If one
+ * multiply-store result is subnormal, the next multiply will
+ * round it away to zero. This is done by first multiplying
+ * by 2 ^ (scaleFactor % n) and then multiplying several
+ * times by 2^n as needed where n is the exponent of number
+ * that is a convenient power of two. In this way, at most one
+ * real rounding error occurs.
+ */
+
+ // magnitude of a power of two so large that scaling a finite
+ // nonzero value by it would be guaranteed to over or
+ // underflow; due to rounding, scaling down takes an
+ // additional power of two which is reflected here
+ final int MAX_SCALE = Double.MAX_EXPONENT + -Double.MIN_EXPONENT +
+ DoubleConsts.SIGNIFICAND_WIDTH + 1;
+ int exp_adjust = 0;
+ int scale_increment = 0;
+ double exp_delta = Double.NaN;
+
+ // Make sure scaling factor is in a reasonable range
+
+ if(scaleFactor < 0) {
+ scaleFactor = Math.max(scaleFactor, -MAX_SCALE);
+ scale_increment = -512;
+ exp_delta = twoToTheDoubleScaleDown;
}
- if (scaleFactor > -2 * DoubleConsts.EXP_BIAS) {
- return d * primPowerOfTwoD(scaleFactor + DoubleConsts.EXP_BIAS) * F_DOWN;
+ else {
+ scaleFactor = Math.min(scaleFactor, MAX_SCALE);
+ scale_increment = 512;
+ exp_delta = twoToTheDoubleScaleUp;
}
- if (scaleFactor > -2 * DoubleConsts.EXP_BIAS - PRECISION) {
- return d * primPowerOfTwoD(scaleFactor + 2 * DoubleConsts.EXP_BIAS) * F_DOWN * F_DOWN;
+
+ // Calculate (scaleFactor % +/-512), 512 = 2^9, using
+ // technique from "Hacker's Delight" section 10-2.
+ int t = (scaleFactor >> 9-1) >>> 32 - 9;
+ exp_adjust = ((scaleFactor + t) & (512 -1)) - t;
+
+ d *= powerOfTwoD(exp_adjust);
+ scaleFactor -= exp_adjust;
+
+ while(scaleFactor != 0) {
+ d *= exp_delta;
+ scaleFactor -= scale_increment;
}
- return d * MIN_VALUE * MIN_VALUE;
+ return d;
}
/**
@@ -3595,20 +3621,18 @@
return (float)((double)f*powerOfTwoD(scaleFactor));
}
+ // Constants used in scalb
+ static double twoToTheDoubleScaleUp = powerOfTwoD(512);
+ static double twoToTheDoubleScaleDown = powerOfTwoD(-512);
+
/**
* Returns a floating-point power of two in the normal range.
*/
static double powerOfTwoD(int n) {
assert(n >= Double.MIN_EXPONENT && n <= Double.MAX_EXPONENT);
- return primPowerOfTwoD(n);
- }
-
- /**
- * Returns a floating-point power of two in the normal range.
- * No checks are performed on the argument.
- */
- private static double primPowerOfTwoD(int n) {
- return longBitsToDouble((long) (n + DoubleConsts.EXP_BIAS) << PRECISION - 1);
+ return Double.longBitsToDouble((((long)n + (long)DoubleConsts.EXP_BIAS) <<
+ (DoubleConsts.SIGNIFICAND_WIDTH-1))
+ & DoubleConsts.EXP_BIT_MASK);
}
/**
@@ -3620,229 +3644,4 @@
(FloatConsts.SIGNIFICAND_WIDTH-1))
& FloatConsts.EXP_BIT_MASK);
}
-
- /**
- * Returns the product of the unsigned arguments,
- * throwing an exception if the result overflows an unsigned {@code int}.
- *
- * @param x the first unsigned value
- * @param y the second unsigned value
- * @return the result
- * @throws ArithmeticException if the result overflows an unsigned int
- * @since 25
- */
- public static int unsignedMultiplyExact(int x, int y) {
- long r = (x & 0xFFFF_FFFFL) * (y & 0xFFFF_FFFFL);
- if (r >>> 32 != 0) {
- throw new ArithmeticException("unsigned integer overflow");
- }
- return (int)r;
- }
-
- /**
- * Returns the product of the unsigned arguments,
- * throwing an exception if the result overflows an unsigned {@code long}.
- *
- * @param x the first unsigned value
- * @param y the second unsigned value
- * @return the result
- * @throws ArithmeticException if the result overflows an unsigned long
- * @since 25
- */
- public static long unsignedMultiplyExact(long x, int y) {
- return unsignedMultiplyExact(x, y & 0xFFFF_FFFFL);
- }
-
- /**
- * Returns the product of the unsigned arguments,
- * throwing an exception if the result overflows an unsigned {@code long}.
- *
- * @param x the first unsigned value
- * @param y the second unsigned value
- * @return the result
- * @throws ArithmeticException if the result overflows an unsigned long
- * @since 25
- */
- public static long unsignedMultiplyExact(long x, long y) {
- long l = x * y;
- long h = unsignedMultiplyHigh(x, y);
- if (h == 0) {
- return l;
- }
- throw new ArithmeticException("unsigned long overflow");
- }
-
- /**
- * Returns {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows an {@code int}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows an int.
- * @since 25
- */
- public static int powExact(int x, int n) {
- /* See the comment in unsignedPowExact(long,int) for the details. */
- if (n < 0) {
- throw new ArithmeticException("negative exponent");
- }
- if (n == 0) {
- return 1;
- }
- if (x == 0 || x == 1) {
- return x;
- }
- if (x == -1) {
- return (n & 0b1) == 0 ? 1 : -1;
- }
-
- int p = 1;
- while (n > 1) {
- if ((n & 0b1) != 0) {
- p *= x;
- }
- x = multiplyExact(x, x);
- n >>>= 1;
- }
- return multiplyExact(p, x);
- }
-
- /**
- * Returns unsigned {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows an unsigned {@code int}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the unsigned base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows an unsigned int.
- * @since 25
- */
- public static int unsignedPowExact(int x, int n) {
- /* See the comment in unsignedPowExact(long,int) for the details. */
- if (n < 0) {
- throw new ArithmeticException("negative exponent");
- }
- if (n == 0) {
- return 1;
- }
- if (x == 0 || x == 1) {
- return x;
- }
-
- int p = 1;
- while (n > 1) {
- if ((n & 0b1) != 0) {
- p *= x;
- }
- x = unsignedMultiplyExact(x, x);
- n >>>= 1;
- }
- return unsignedMultiplyExact(p, x);
- }
-
- /**
- * Returns {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows a {@code long}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows a long.
- * @since 25
- */
- public static long powExact(long x, int n) {
- /* See the comment in unsignedPowExact(long,int) for the details. */
- if (n < 0) {
- throw new ArithmeticException("negative exponent");
- }
- if (n == 0) {
- return 1;
- }
- if (x == 0 || x == 1) {
- return x;
- }
- if (x == -1) {
- return (n & 0b1) != 0 ? -1 : 1;
- }
-
- long p = 1;
- while (n > 1) {
- if ((n & 0b1) != 0) {
- p *= x;
- }
- x = multiplyExact(x, x);
- n >>>= 1;
- }
- return multiplyExact(p, x);
- }
-
- /**
- * Returns unsigned {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows an unsigned {@code long}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the unsigned base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows an unsigned long.
- * @since 25
- */
- public static long unsignedPowExact(long x, int n) {
- if (n < 0) {
- throw new ArithmeticException("negative exponent");
- }
- if (n == 0) {
- return 1;
- }
- /*
- * To keep the code as simple as possible, there are intentionally
- * no fast paths, except for |x| <= 1.
- * The reason is that the number of loop iterations below can be kept
- * very small when |x| > 1, but not necessarily when |x| <= 1.
- */
- if (x == 0 || x == 1) {
- return x;
- }
-
- /*
- * Let x0 and n0 > 0 be the entry values of x and n, resp.
- * The useful loop invariants are:
- * p * x^n = x0^n0
- * |p| < |x|
- *
- * Since |x0| >= 2 here, and since |x0|^(2^6) >= 2^Long.SIZE, the squaring
- * of x in the loop overflows at latest during the 6th iteration,
- * so by then the method throws.
- * Thus, the loop executes at most 5 successful iterations, and fails
- * not later than at the 6th.
- *
- * But n is right-shifted at each iteration.
- * If the method returns, there are thus floor(log2(n0)) iterations.
- */
- long p = 1;
- while (n > 1) {
- if ((n & 0b1) != 0) {
- /*
- * The invariant |p| < |x| holds, so we have |p*x| < |x*x|.
- * That is, if p*x overflows, so does x*x below, which is
- * always executed.
- * In other words, a plain * can be used here, since we are
- * piggybacking on the squaring of x to throw.
- */
- p *= x;
- }
- x = unsignedMultiplyExact(x, x);
- n >>>= 1;
- }
- return unsignedMultiplyExact(p, x);
- }
-
}
diff --git a/ojluni/src/main/java/java/lang/StrictMath.java b/ojluni/src/main/java/java/lang/StrictMath.java
index 9dc4600..431bc07 100644
--- a/ojluni/src/main/java/java/lang/StrictMath.java
+++ b/ojluni/src/main/java/java/lang/StrictMath.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 1999, 2025, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1999, 2023, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -100,8 +100,8 @@
* href="Math.html#Ieee754RecommendedOps">relate to the IEEE 754
* recommended operations</a>.
*
- * @spec https://standards.ieee.org/ieee/754/6210/
- * IEEE Standard for Floating-Point Arithmetic
+ * @see <a href="https://standards.ieee.org/ieee/754/6210/">
+ * <cite>IEEE Standard for Floating-Point Arithmetic</cite></a>
*
* @author Joseph D. Darcy
* @since 1.3
@@ -205,7 +205,7 @@
/**
* Returns the arc sine of a value; the returned angle is in the
- * range −<i>pi</i>/2 through <i>pi</i>/2. Special cases:
+ * range -<i>pi</i>/2 through <i>pi</i>/2. Special cases:
* <ul><li>If the argument is NaN or its absolute value is greater
* than 1, then the result is NaN.
* <li>If the argument is zero, then the result is a zero with the
@@ -241,7 +241,7 @@
/**
* Returns the arc tangent of a value; the returned angle is in the
- * range −<i>pi</i>/2 through <i>pi</i>/2. Special cases:
+ * range -<i>pi</i>/2 through <i>pi</i>/2. Special cases:
* <ul><li>If the argument is NaN, then the result is NaN.
* <li>If the argument is zero, then the result is a zero with the
* same sign as the argument.
@@ -585,7 +585,7 @@
* coordinates ({@code x}, {@code y}) to polar
* coordinates (r, <i>theta</i>).
* This method computes the phase <i>theta</i> by computing an arc tangent
- * of {@code y/x} in the range of −<i>pi</i> to <i>pi</i>. Special
+ * of {@code y/x} in the range of -<i>pi</i> to <i>pi</i>. Special
* cases:
* <ul><li>If either argument is NaN, then the result is NaN.
* <li>If the first argument is positive zero and the second argument
@@ -2163,7 +2163,7 @@
/**
* Returns the hyperbolic sine of a {@code double} value.
* The hyperbolic sine of <i>x</i> is defined to be
- * (<i>e<sup>x</sup> − e<sup>−x</sup></i>)/2
+ * (<i>e<sup>x</sup> - e<sup>-x</sup></i>)/2
* where <i>e</i> is {@linkplain Math#E Euler's number}.
*
* <p>Special cases:
@@ -2193,7 +2193,7 @@
/**
* Returns the hyperbolic cosine of a {@code double} value.
* The hyperbolic cosine of <i>x</i> is defined to be
- * (<i>e<sup>x</sup> + e<sup>−x</sup></i>)/2
+ * (<i>e<sup>x</sup> + e<sup>-x</sup></i>)/2
* where <i>e</i> is {@linkplain Math#E Euler's number}.
*
* <p>Special cases:
@@ -2222,7 +2222,7 @@
/**
* Returns the hyperbolic tangent of a {@code double} value.
* The hyperbolic tangent of <i>x</i> is defined to be
- * (<i>e<sup>x</sup> − e<sup>−x</sup></i>)/(<i>e<sup>x</sup> + e<sup>−x</sup></i>),
+ * (<i>e<sup>x</sup> - e<sup>-x</sup></i>)/(<i>e<sup>x</sup> + e<sup>-x</sup></i>),
* in other words, {@linkplain Math#sinh
* sinh(<i>x</i>)}/{@linkplain Math#cosh cosh(<i>x</i>)}. Note
* that the absolute value of the exact tanh is always less than
@@ -2288,7 +2288,7 @@
public static native double hypot(double x, double y);
/**
- * Returns <i>e</i><sup>x</sup> −1. Note that for values of
+ * Returns <i>e</i><sup>x</sup> -1. Note that for values of
* <i>x</i> near 0, the exact sum of
* {@code expm1(x)} + 1 is much closer to the true
* result of <i>e</i><sup>x</sup> than {@code exp(x)}.
@@ -2309,7 +2309,7 @@
* </ul>
*
* @param x the exponent to raise <i>e</i> to in the computation of
- * <i>e</i><sup>{@code x}</sup> −1.
+ * <i>e</i><sup>{@code x}</sup> -1.
* @return the value <i>e</i><sup>{@code x}</sup> - 1.
* @since 1.5
*/
@@ -2685,111 +2685,4 @@
public static float scalb(float f, int scaleFactor) {
return Math.scalb(f, scaleFactor);
}
-
- /**
- * Returns the product of the unsigned arguments,
- * throwing an exception if the result overflows an unsigned {@code int}.
- *
- * @param x the first unsigned value
- * @param y the second unsigned value
- * @return the result
- * @throws ArithmeticException if the result overflows an unsigned int
- * @since 25
- */
- public static int unsignedMultiplyExact(int x, int y) {
- return Math.unsignedMultiplyExact(x, y);
- }
-
- /**
- * Returns the product of the unsigned arguments,
- * throwing an exception if the result overflows an unsigned {@code long}.
- *
- * @param x the first unsigned value
- * @param y the second unsigned value
- * @return the result
- * @throws ArithmeticException if the result overflows an unsigned long
- * @since 25
- */
- public static long unsignedMultiplyExact(long x, int y) {
- return Math.unsignedMultiplyExact(x, y);
- }
-
- /**
- * Returns the product of the unsigned arguments,
- * throwing an exception if the result overflows an unsigned {@code long}.
- *
- * @param x the first unsigned value
- * @param y the second unsigned value
- * @return the result
- * @throws ArithmeticException if the result overflows an unsigned long
- * @since 25
- */
- public static long unsignedMultiplyExact(long x, long y) {
- return Math.unsignedMultiplyExact(x, y);
- }
-
- /**
- * Returns {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows an {@code int}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows an int.
- * @since 25
- */
- public static int powExact(int x, int n) {
- return Math.powExact(x, n);
- }
-
- /**
- * Returns unsigned {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows an unsigned {@code int}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the unsigned base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows an unsigned int.
- * @since 25
- */
- public static int unsignedPowExact(int x, int n) {
- return Math.unsignedPowExact(x, n);
- }
-
- /**
- * Returns {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows a {@code long}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows a long.
- * @since 25
- */
- public static long powExact(long x, int n) {
- return Math.powExact(x, n);
- }
-
- /**
- * Returns unsigned {@code x} raised to the power of {@code n},
- * throwing an exception if the result overflows an unsigned {@code long}.
- * When {@code n} is 0, the returned value is 1.
- *
- * @param x the unsigned base.
- * @param n the exponent.
- * @return {@code x} raised to the power of {@code n}.
- * @throws ArithmeticException when {@code n} is negative,
- * or when the result overflows an unsigned long.
- * @since 25
- */
- public static long unsignedPowExact(long x, int n) {
- return Math.unsignedPowExact(x, n);
- }
-
}
diff --git a/ojluni/src/test/java/lang/Math/IntegralPowTest.java b/ojluni/src/test/java/lang/Math/IntegralPowTest.java
deleted file mode 100644
index 8a033d1..0000000
--- a/ojluni/src/test/java/lang/Math/IntegralPowTest.java
+++ /dev/null
@@ -1,394 +0,0 @@
-/*
- * Copyright (c) 2025, Oracle and/or its affiliates. All rights reserved.
- * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
- *
- * This code is free software; you can redistribute it and/or modify it
- * under the terms of the GNU General Public License version 2 only, as
- * published by the Free Software Foundation.
- *
- * This code is distributed in the hope that it will be useful, but WITHOUT
- * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
- * version 2 for more details (a copy is included in the LICENSE file that
- * accompanied this code).
- *
- * You should have received a copy of the GNU General Public License version
- * 2 along with this work; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
- *
- * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
- * or visit www.oracle.com if you need additional information or have any
- * questions.
- */
-
-/*
- * @test
- * @bug 8355992
- * @summary Tests for StrictMath.*PowExact and .*unsignedMultiplyExact
- * @run junit IntegralPowTest
- */
-
-package test.java.lang.Math;
-
-import java.math.BigInteger;
-
-import static java.lang.StrictMath.*;
-import static java.math.BigInteger.ONE;
-import static org.testng.Assert.assertEquals;
-import static org.testng.Assert.assertThrows;
-import org.testng.annotations.Test;
-
-@SuppressWarnings("BadShiftAmount")
-public class IntegralPowTest {
-
- private static final long MASK_32 = (1L << Integer.SIZE) - 1; // 2^32 - 1
- private static final BigInteger MASK_64 = ONE.shiftLeft(Long.SIZE).subtract(ONE); // 2^64 - 1
- private static final double INT_F = Integer.SIZE * Math.log(2);
- private static final double LONG_F = Long.SIZE * Math.log(2);
- private static final int INT_XMAX = 0x1_0000;
- private static final int LONG_XMAX = 0x10_0000;
-
- private static BigInteger unsignedBigInteger(int x) {
- return BigInteger.valueOf(x & MASK_32);
- }
-
- private static BigInteger unsignedBigInteger(long x) {
- return BigInteger.valueOf(x).and(MASK_64);
- }
-
- private static int slowPowExact(int x, int n) {
- BigInteger pow = BigInteger.valueOf(x).pow(n);
- return pow.intValueExact();
- }
-
- private static int slowUnsignedPowExact(int x, int n) {
- BigInteger pow = unsignedBigInteger(x).pow(n);
- if (pow.bitLength() > Integer.SIZE) {
- throw new ArithmeticException();
- }
- return pow.intValue();
- }
-
- private static long slowPowExact(long x, int n) {
- BigInteger pow = BigInteger.valueOf(x).pow(n);
- return pow.longValueExact();
- }
-
- private static long slowUnsignedPowExact(long x, int n) {
- BigInteger pow = unsignedBigInteger(x).pow(n);
- if (pow.bitLength() > Long.SIZE) {
- throw new ArithmeticException();
- }
- return pow.longValue();
- }
-
- @Test
- public void testIntUnsignedMultiplyExact() {
- assertEquals(0, unsignedMultiplyExact(0, 0));
- assertEquals(0, unsignedMultiplyExact(1, 0));
- assertEquals(0, unsignedMultiplyExact(-1, 0));
- assertEquals(1, unsignedMultiplyExact(1, 1));
- assertEquals(-1, unsignedMultiplyExact(1, -1));
- assertEquals(1 << 31, unsignedMultiplyExact(1 << 15, 1 << 16));
- assertEquals(1 << 31, unsignedMultiplyExact(1 << 10, 1 << 21));
- /* 2^32 - 1 = (2^16 + 1) (2^16 - 1) */
- assertEquals(-1, unsignedMultiplyExact((1 << 16) + 1, (1 << 16) - 1));
-
- assertThrows(ArithmeticException.class, () -> unsignedMultiplyExact(-1, -1));
- }
-
- @Test
- public void testLongIntUnsignedMultiplyExact() {
- assertEquals(0L, unsignedMultiplyExact(0L, 0));
- assertEquals(0L, unsignedMultiplyExact(1L, 0));
- assertEquals(0L, unsignedMultiplyExact(-1L, 0));
- assertEquals(1L, unsignedMultiplyExact(1L, 1));
- assertEquals(-3 & MASK_32, unsignedMultiplyExact(1L, -3));
- assertEquals(1L << 50, unsignedMultiplyExact(1L << 25, 1 << 25));
- /* 2^64 - 1 = (2^32 + 1) (2^32 - 1) */
- assertEquals(-1L, unsignedMultiplyExact((1L << 32) + 1, -1));
-
- assertThrows(ArithmeticException.class, () -> unsignedMultiplyExact(-1L, -1));
- }
-
- @Test
- public void testLongUnsignedMultiplyExact() {
- assertEquals(0L, unsignedMultiplyExact(0L, 0L));
- assertEquals(0L, unsignedMultiplyExact(1L, 0L));
- assertEquals(0L, unsignedMultiplyExact(-1L, 0L));
- assertEquals(1L, unsignedMultiplyExact(1L, 1L));
- assertEquals(-1L, unsignedMultiplyExact(1L, -1L));
- assertEquals(1L << 63, unsignedMultiplyExact(1L << 31, 1L << 32));
- assertEquals(1L << 63, unsignedMultiplyExact(1L << 25, 1L << 38));
- /* 2^64 - 1 = (2^32 + 1) (2^32 - 1) */
- assertEquals(-1L, unsignedMultiplyExact((1L << 32) + 1, (1L << 32) - 1));
-
- assertThrows(ArithmeticException.class, () -> unsignedMultiplyExact(-1L, -1L));
- }
-
- @Test
- public void testIntPowExact() {
- assertEquals(1, powExact(0, 0));
- assertEquals(0, powExact(0, 1_000_000));
- assertEquals(1, powExact(1, 0));
- assertEquals(1, powExact(1, 1_000_000));
- assertEquals(1, powExact(-1, 0));
- assertEquals(1, powExact(-1, 1_000_000));
- assertEquals(-1, powExact(-1, 1_000_001));
-
- assertEquals(1 << -2, powExact(2, Integer.SIZE - 2));
- assertEquals(-1 << -1, powExact(-2, Integer.SIZE - 1));
- assertEquals(1_000_000_000, powExact(10, 9));
- assertEquals(-1_000_000_000, powExact(-10, 9));
-
- assertThrows(ArithmeticException.class, () -> powExact(0, -1_000_000));
- assertThrows(ArithmeticException.class, () -> powExact(1, -1_000_000));
- assertThrows(ArithmeticException.class, () -> powExact(2, Integer.SIZE - 1));
- assertThrows(ArithmeticException.class, () -> powExact(10, 10));
- assertThrows(ArithmeticException.class, () -> powExact(-10, 10));
- }
-
- @Test
- public void testUnsignedIntPowExact() {
- assertEquals(1, unsignedPowExact(0, 0));
- assertEquals(0, unsignedPowExact(0, 1_000_000));
- assertEquals(1, unsignedPowExact(1, 0));
- assertEquals(1, unsignedPowExact(1, 1_000_000));
- assertEquals(1, unsignedPowExact(-1, 0));
- assertEquals(-1, unsignedPowExact(-1, 1));
-
- assertEquals(1 << -1, unsignedPowExact(2, Integer.SIZE - 1));
- assertEquals(1_000_000_000, unsignedPowExact(10, 9));
-
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(0, -1_000_000));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(1, -1_000_000));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(-1, 2));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(2, Integer.SIZE));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(10, 10));
- }
-
- @Test
- public void testLongPowExact() {
- assertEquals(1L, powExact(0L, 0));
- assertEquals(0L, powExact(0L, 1_000_000));
- assertEquals(1L, powExact(1L, 0));
- assertEquals(1L, powExact(1L, 1_000_000));
- assertEquals(1L, powExact(-1L, 0));
- assertEquals(1L, powExact(-1L, 1_000_000));
- assertEquals(-1L, powExact(-1L, 1_000_001));
-
- assertEquals(1L << -2, powExact(2L, Long.SIZE - 2));
- assertEquals(-1L << -1, powExact(-2L, Long.SIZE - 1));
- assertEquals(1_000_000_000_000_000_000L, powExact(10L, 18));
- assertEquals(-100_000_000_000_000_000L, powExact(-10L, 17));
- assertEquals(1_000_000_000_000_000_000L, powExact(-10L, 18));
-
- assertThrows(ArithmeticException.class, () -> powExact(0L, -1_000_000));
- assertThrows(ArithmeticException.class, () -> powExact(1L, -1_000_000));
- assertThrows(ArithmeticException.class, () -> powExact(2L, Long.SIZE - 1));
- assertThrows(ArithmeticException.class, () -> powExact(10L, 19));
- assertThrows(ArithmeticException.class, () -> powExact(-10L, 19));
- }
-
- @Test
- public void testUnsignedLongPowExact() {
- assertEquals(1L, unsignedPowExact(0L, 0));
- assertEquals(0L, unsignedPowExact(0L, 1_000_000));
- assertEquals(1L, unsignedPowExact(1L, 0));
- assertEquals(1L, unsignedPowExact(1L, 1_000_000));
- assertEquals(1L, unsignedPowExact(-1L, 0));
- assertEquals(-1L, unsignedPowExact(-1L, 1));
-
- assertEquals(1L << -1, unsignedPowExact(2L, Long.SIZE - 1));
- assertEquals(10 * 1_000_000_000_000_000_000L, unsignedPowExact(10L, 19));
-
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(0L, -1_000_000));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(1L, -1_000_000));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(-1L, 2));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(2L, Long.SIZE));
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(10L, 20));
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static int expected(int x, int n) {
- try {
- return powExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static int actual(int x, int n) {
- try {
- return slowPowExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static int expectedUnsigned(int x, int n) {
- try {
- return unsignedPowExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static int actualUnsigned(int x, int n) {
- try {
- return slowUnsignedPowExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static long expected(long x, int n) {
- try {
- return powExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static long actual(long x, int n) {
- try {
- return slowPowExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static long expectedUnsigned(long x, int n) {
- try {
- return unsignedPowExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /*
- * Assumes that x^n != 0
- * Returns x^n, or 0 on overflow
- */
- private static long actualUnsigned(long x, int n) {
- try {
- return slowUnsignedPowExact(x, n);
- } catch (ArithmeticException ignore) {
- return 0;
- }
- }
-
- /* signed int */
-
- @Test
- public void testPositiveIntPowExact() {
- for (int x = 2; x <= INT_XMAX; x += 1) {
- /* An estimate for the max n such that x^n does not overflow. */
- int nmax = (int) ceil(INT_F / log(x));
- for (int n = 0; n <= nmax; ++n) {
- assertEquals(actual(x, n), expected(x, n));
- }
- int x0 = x;
- assertThrows(ArithmeticException.class, () -> powExact(x0, nmax + 1));
- }
- }
-
- @Test
- public void testNegativeIntPowExact() {
- for (int x = 2; x <= INT_XMAX; x += 1) {
- /* An estimate for the max n such that (-x)^n does not overflow. */
- int nmax = (int) ceil(INT_F / log(x));
- for (int n = 0; n <= nmax; ++n) {
- assertEquals(actual(-x, n), expected(-x, n));
- }
- int x0 = x;
- assertThrows(ArithmeticException.class, () -> powExact(-x0, nmax + 1));
- }
- }
-
- /* unsigned int */
-
- @Test
- public void testSmallUnsignedIntPowExact() {
- for (int x = 2; x <= INT_XMAX; x += 1) {
- /* An estimate for the max n such that x^n does not overflow. */
- int nmax = (int) ceil(INT_F / log(x));
- for (int n = 0; n <= nmax; ++n) {
- assertEquals(actualUnsigned(x, n), expectedUnsigned(x, n));
- }
- int x0 = x;
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(x0, nmax + 1));
- }
- }
-
- /* signed long */
-
- @Test
- public void testPositiveLongPowExact() {
- for (long x = 2; x <= LONG_XMAX; x += 5) {
- /* An estimate for the max n such that x^n does not overflow. */
- int nmax = (int) ceil(LONG_F / log(x));
- for (int n = 0; n <= nmax; ++n) {
- assertEquals(actual(x, n), expected(x, n));
- }
- long x0 = x;
- assertThrows(ArithmeticException.class, () -> powExact(x0, nmax + 1));
- }
- }
-
- @Test
- public void testNegativeLongPowExact() {
- for (long x = 2; x <= LONG_XMAX; x += 5) {
- /* An estimate for the max n such that (-x)^n does not overflow. */
- int nmax = (int) ceil(LONG_F / log(x));
- for (int n = 0; n <= nmax; ++n) {
- assertEquals(actual(-x, n), expected(-x, n));
- }
- long x0 = x;
- assertThrows(ArithmeticException.class, () -> powExact(-x0, nmax + 1));
- }
- }
-
- /* unsigned long */
-
- @Test
- public void testSmallUnsignedLongPowExact() {
- for (long x = 2; x <= LONG_XMAX; x += 5) {
- /* An estimate for the max n such that x^n does not overflow. */
- int nmax = (int) ceil(LONG_F / log(x));
- for (int n = 0; n <= nmax; ++n) {
- assertEquals(actualUnsigned(x, n), expectedUnsigned(x, n));
- }
- long x0 = x;
- assertThrows(ArithmeticException.class, () -> unsignedPowExact(x0, nmax + 1));
- }
- }
-
-}