[libc-commits] [libc] [libc][math] Implement atan2f correctly rounded to all rounding modes. (PR #86716)
via libc-commits
libc-commits at lists.llvm.org
Fri Mar 29 08:35:14 PDT 2024
lntue wrote:
> about split_d, I wonder why you use C=0x1p33+1, which makes hi fit into 53-33=20 bits, thus hi * s * k fits into 20+24+4=48 bits. You could make hi fit into 5 more bits with C=0x1p28+1. Also note that Veltkamp's algorithm also works for directed roundings, see https://inria.hal.science/hal-04480440
Hi Paul, sorry the comment was not entirely correct and need to be updated. The correct requirement for splitting is that the following needs to be exact:
```
hi * den_r = hi * (k_d * num_d + den_d)
```
where
```
num_d, den_d are single precision
1/16 <= k_d <= 1
```
So the correct precision of `den_r` is:
```
prec(den_r) = (1 + log2(msb(den_d)) - log2(lsb(k_d * num_d))) + 1 (the last +1 is for overflow from addition)
= (1 + log2(msb(num_d)) + 4 - log2(lsb(k_d)) - log2(lsb(num_d))) + 1 (num_d / den_d >= 1/16)
= (1 + 23 + log2(lsb(num_d)) + 4 - (-4) - log2(lsb(num_d))) + 1
= 33
```
The following example will demonstrate that 33 is sharp:
For `atan2f( 0x1.781fcp+28f, 0x1.dcb3cap+23f )`, if we use `C = 0x1.0p32 + 1.0` in the Veltkamp's algorithm
```
num_d = 0x1.dcb3cap+23
den_d = 0x1.781fcp+28
num_r = -0x1.138bb6p+23
den_r = 0x1.790e19e5p+28
q = -0x1.76294b4d835fap-6
hi = -0x1.76295p-6
hi * den_r = -0x1.138bb9758de248p23
round(hi * den_r, D, RN) = -0x1.138bb9758de24p23
```
https://github.com/llvm/llvm-project/pull/86716
More information about the libc-commits
mailing list