Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

UInt64 to Double conversions are incorrect #43895

Closed
tannergooding opened this issue Oct 27, 2020 · 11 comments · Fixed by #102179
Closed

UInt64 to Double conversions are incorrect #43895

tannergooding opened this issue Oct 27, 2020 · 11 comments · Fixed by #102179
Assignees
Labels
area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI Priority:1 Work that is critical for the release, but we could probably ship without
Milestone

Comments

@tannergooding
Copy link
Member

tannergooding commented Oct 27, 2020

Conversions from UInt64 to Double for values greater than long.MaxValue are currently incorrect. The same issue may exist for UInt32 to Double for values greater than int.MaxValue but I have not confirmed.

The simple repro case is detailed here: dotnet/csharplang#4074

using System;
namespace App
{
    internal static class Program
    {
        internal static void Main()
        {
            /// Displays 'True'.
           Console.WriteLine(10648738977740919977d != 10648738977740919977);
        }
    }
}

You can see approximately what the runtime generates by looking at: https://sharplab.io/#v2:EYLgxg9gTgpgtADwGwBYA0AXEBDAzgWzQBMQBqAHwAEAmARgFgAoSgZgAIa2BhNgbybaCO7IhACuwADYw2AWQAUYyRAB2AczYIAlHwFD9lAOyaA3HsEBfJhaA===

public double M(ulong x) {
    return x;
}

Which results in:

    L0000: vzeroupper
    L0003: vxorps xmm0, xmm0, xmm0
    L0007: vcvtsi2sd xmm0, xmm0, rdx
    L000c: test rdx, rdx
    L000f: jge short L0019
    L0011: vaddsd xmm0, xmm0, [C.M(UInt64)]
    L0019: ret

The constant used by L0011 appears to be 1.8446744073709552E+19 (0x43f0000000000000)

category:correctness
theme:optimization
skill-level:beginner
cost:small
impact:small

@Dotnet-GitSync-Bot Dotnet-GitSync-Bot added area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI untriaged New issue has not been triaged by the area owner labels Oct 27, 2020
@tannergooding
Copy link
Member Author

This looks to be a "known" issue and was done for "back compat": https://github.com/dotnet/runtime/blob/master/src/coreclr/src/jit/codegenxarch.cpp#L6435-L6468

Clang vs MSVC generate different code with the MSVC variant being similar to our own, but which produces a correct result: https://godbolt.org/z/P7j6n8

@tannergooding
Copy link
Member Author

Given this is .NET Core and given this is a correctness issue; I would say we take the breaking change and ensure we generate the correct IEEE compliant conversion.

@JulieLeeMSFT JulieLeeMSFT added this to the 6.0.0 milestone Nov 12, 2020
@JulieLeeMSFT JulieLeeMSFT removed the untriaged New issue has not been triaged by the area owner label Nov 13, 2020
@briansull briansull self-assigned this Feb 8, 2021
@briansull
Copy link
Contributor

I will investigate

@briansull
Copy link
Contributor

This is the backwartds compat comment in the JIT source code:

        // The instruction sequence below is less accurate than what clang
        // and gcc generate. However, we keep the current sequence for backward compatibility.
        // If we change the instructions below, FloatingPointUtils::convertUInt64ToDobule
        // should be also updated for consistent conversion result.

@JulieLeeMSFT
Copy link
Member

@briansull to discuss with @davidwrighton

@JulieLeeMSFT
Copy link
Member

CC @dotnet/jit-contrib

@JulieLeeMSFT
Copy link
Member

@davidwrighton recommends to fix this issue.
#47478 issues on Double to Int conversion will be handled separately.

@JulieLeeMSFT JulieLeeMSFT assigned sandreenko and unassigned briansull Mar 29, 2021
@briansull briansull self-assigned this Jul 26, 2021
@JulieLeeMSFT JulieLeeMSFT added the Priority:1 Work that is critical for the release, but we could probably ship without label Jul 28, 2021
@JulieLeeMSFT JulieLeeMSFT modified the milestones: 6.0.0, 7.0.0 Jul 28, 2021
@JulieLeeMSFT
Copy link
Member

Moved to .NET 7 as priority 1. For Vectors handling, consider a way to make it work without control flow.

CC @dotnet/jit-contrib

@JulieLeeMSFT JulieLeeMSFT modified the milestones: 7.0.0, 8.0.0 Jun 3, 2022
@JulieLeeMSFT
Copy link
Member

Moving to .NET 8.

@JulieLeeMSFT
Copy link
Member

@tannergooding, assigning this to you for now. Please feel free to move out to Future.

@tannergooding tannergooding modified the milestones: 8.0.0, 9.0.0 Jul 28, 2023
@tannergooding
Copy link
Member Author

This got moved to early .NET 9 so we can handle all the "breaking changes" at once and early in the release

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI Priority:1 Work that is critical for the release, but we could probably ship without
Projects
Status: Done
6 participants