Difference in behaviour in native math library
Joseph D. Darcy
joe.darcy at oracle.com
Fri Jan 13 04:03:31 UTC 2023
Hi Ludovic,
Catching up on email, your understanding of my comments is correct.
Since the relevant Java specification are agnostic towards what bits are
in a NaN's significand, I don't think the Java implementations of this
these methods should be updated to accommodate additional requirements
for NaN handling used elsewhere.
Thanks,
-Joe
On 12/8/2022 11:27 AM, Ludovic Henry wrote:
> Hi Joe,
>
> I got an answer on the glibc mailing list, and the overall answer is
> "it is the expected behavior" [1].
>
> From your answer, IIUC, you would want things to stand as-is, and it's
> the test case that should be fixed, correct?
>
> Ludovic
>
> [1]
> https://sourceware.org/pipermail/libc-alpha/2022-December/143912.html
> <https://urldefense.com/v3/__https://sourceware.org/pipermail/libc-alpha/2022-December/143912.html__;!!ACWV5N9M2RV99hQ!JvhCHTYr_G9gOYrCS4khD78epumPjjRQ14dxB5Kzp6Yukj-_sVbxkEZ4OXvevB2LYd-FtibWc9goJkkKBg$>
>
> On Thu, Dec 8, 2022 at 4:08 PM Joseph D. Darcy <joe.darcy at oracle.com>
> wrote:
>
>
> On 12/8/2022 10:01 AM, Ludovic Henry wrote:
>> Hi,
>>
>> Yes, this is very much a difference of behavior at the libm/libc
>> level. I'm trying to figure out whether that behavior difference
>> is acceptable from the libm/libc level (is it considered a bug to
>> behave differently across architectures in that case?). If that
>> behaviour is acceptable in libm/libc, then is it acceptable to
>> behave differently in Java across architectures?
>>
>> From your answer Palmer, the difference _might_ not be acceptable
>> in the glibc test suite (I haven't check why the tests are
>> failing). I'm still trying to figure that one out.
>>
>> From your answer Joe, the difference _is_ acceptable from the
>> documentation. IMO the question becomes whether it's a case of
>> the implementation details bleeding into the API and whether we
>> want to be 100% compatible to avoid further issues. The fix for
>> that could be a simple `RISCV_ONLY(if (isnan(v)) return v);` or
>> equivalent in src/java.base/share/native/libjava/StrictMath.c to
>> match the behavior without any extra cost for other platforms.
>
>
> I would not support changing the library native sources (or Java
> sources) in this way to accommodate NaN handling.
>
> -Joe
>
>>
>> Thanks,
>> Ludovic
>>
>> On Thu, Dec 8, 2022 at 2:50 PM Palmer Dabbelt
>> <palmer at dabbelt.com> wrote:
>>
>> On Thu, 08 Dec 2022 08:26:30 PST (-0800),
>> ludovic at rivosinc.com wrote:
>> > Adding the right address for core-libs-dev.
>> >
>> > On Thu, Dec 8, 2022 at 12:19 PM Ludovic Henry
>> <ludovic at rivosinc.com> wrote:
>> >
>> >> Hello,
>> >>
>> >> I've noticed that some Math trigonometry tests are failing
>> in the GNU
>> >> Mauve test suite. From digging into it, it's related to
>> NaN values being
>> >> passed to java.lang.Math trigonometry functions, and how
>> these values are
>> >> handled in the native libm library.
>> >>
>> >> Given the following C test case compiled and run with `gcc
>> acos.c -lm &&
>> >> ./a.out`
>> >>
>> >> ```
>> >> #include <stdint.h>
>> >> #include <math.h>
>> >> #include <stdlib.h>
>> >> #include <stdio.h>
>> >>
>> >> void main(int argc, char* argv[]) {
>> >> int64_t bitsNaN = 0x7fff800000000000L;
>> >> double valNaN = *((double*)&bitsNaN);
>> >>
>> >> double resD = acos(valNaN);
>> >> int64_t res = *((int64_t*)&resD);
>> >> if (!(res == bitsNaN)) {
>> >> printf("expected 0x%lx but got 0x%lx\n", bitsNaN,
>> res);
>> >> exit(1);
>> >> }
>> >> }
>> >> ```
>> >>
>> >> On a Linux-x64, the test succeeds, but on Linux-RISC-V,
>> the test fails.
>> >>
>> >> You've the same test failure in the equivalent Java code:
>> >>
>> >> ```
>> >> public class acos {
>> >> public static void main (String[] args) {
>> >> long bitsNaN = 0x7fff800000000000L;
>> >> double valNaN = Double.longBitsToDouble(bitsNaN);
>> >>
>> >> long res =
>> Double.doubleToRawLongBits(Math.acos(valNaN));
>> >> if (!(res == bitsNaN)) {
>> >> throw new
>> RuntimeException(String.format("expected 0x%x but
>> >> got 0x%x", bitsNaN, res));
>> >> }
>> >> }
>> >> }
>> >> ```
>> >>
>> >> What approach should we take in these cases? Is it that
>> the test case is
>> >> wrong, and should assume that given a NaN, any value of
>> NaN returned is
>> >> valid? Or should we make sure that the behavior is the
>> same across
>> >> platforms and that we "fix" any difference in behavior of
>> the native
>> >> library?
>>
>> It might just be a glibc bug, we're failing the acos() tests:
>> https://sourceware.org/glibc/wiki/Release/2.35#RISC-V_.28rv64imafdc.2Flp64d.29
>> <https://urldefense.com/v3/__https://sourceware.org/glibc/wiki/Release/2.35*RISC-V_.28rv64imafdc.2Flp64d.29__;Iw!!ACWV5N9M2RV99hQ!JvhCHTYr_G9gOYrCS4khD78epumPjjRQ14dxB5Kzp6Yukj-_sVbxkEZ4OXvevB2LYd-FtibWc9jKIBqBRw$>
>>
>> . I haven't looked at why, but they do have some nan-related
>> bits in
>> there.
>>
>> >>
>> >> Cheers,
>> >> Ludovic
>> >>
>>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://mail.openjdk.org/pipermail/hotspot-dev/attachments/20230112/f36b365c/attachment.htm>
More information about the hotspot-dev
mailing list