RFR: 8346914: UB issue in scalbnA

Axel Boldt-Christmas aboldtch at openjdk.org
Mon Jun 9 13:22:52 UTC 2025


On Thu, 5 Jun 2025 14:34:38 GMT, Johan Sjölen <jsjolen at openjdk.org> wrote:

>> I think that is equivalent, but I did not want to disrupt the general control flow of the algorithm so that it still closely resembles the original fdlibm code.
>> 
>> I also initially misread your suggestion and now I am wondering if I can actually simplify it to a simple two line change:
>> 
>> unsigned u_k = k + n; // avoid UB signed integer overflow
>> k = (int) u_k;  // safely assign to k
>> 
>> does that bypass any UB?
>
> @dholmes-ora , if `k = (int) u_k;` does not say to the compiler that it can assume that `0 <= u_k < 2**31 - 1`, then this seems like a good changeset. Frankly, I would not trust myself in this matter, I find this very finicky.

Initially I thought it would be nice if we could have expressed this as simply `k = wrapping_add(k, n);`. But it would require implementing such a method correctly, which seems non-trivial. (Some compilers have intrinsics for this I think).

Might it is the case that casting the number here is also UB (if the unsigned number is to large). What we really need is a bit_cast (and use 2s complement, which I think is only guaranteed in C++20, but I think we already make assumptions about this, or we could use int32_t which at least should be 2s complement, not 100%).

But then again looking at this code we also read from none active members of a union, which I think is a compiler language extension. (Only valid in C). 

If we keep the structure as it is, I would find the code more readable if it was `u_k <= (unsigned)std::numeric_limits<int>::max()`

-------------

PR Review Comment: https://git.openjdk.org/jdk/pull/25656#discussion_r2135710875


More information about the hotspot-dev mailing list