[Bug] Inconsistent rounding results in __double2int_rn (and related intrinsics) between runtime variables and compile-time constants

During testing, I found that when using __double2int_rn (as well as __double2uint_rn, __double2ull_rn, and __double2ll_rn), the rounding result when passing a runtime variable is inconsistent with the result when passing a compile-time constant directly.

This appears to be caused by a precision issue in the compiler’s constant folding behavior.

Problem Description: The input double-precision floating-point value I tested is 5.00000000000000111e-01, which is strictly greater than 0.5 (essentially 0.5 + epsilon). According to the Round-to-Nearest-Even (RNE) rounding mode, this value should be rounded to 1.

  • When passing this value via a runtime argument (loaded from memory via a pointer), the underlying GPU executes the correct hardware instruction (e.g., cvt.rni.s32.f64) and correctly evaluates the result to 1.

  • When passing this value directly as a compile-time constant (literal), the nvcc compiler folds it to 0 at compile time. It is highly likely that it loses the extremely small trailing precision when parsing the literal, treating it exactly as an absolute 0.5 (and thus rounding it to 0 according to the round-to-even rule).

Compiler Explorer Example: Compiler Explorer

Question: Could the official team confirm if this is a known bug in nvcc regarding precision loss during host-side constant folding when handling the _rn rounding family of intrinsics?

It is bug, thanks for reporting it. It does not reproduce with -Xptxas -O0or -G, so you can use this workaround in the meanwhile.

It will be fixed in an upcoming release.