Issue 115719
Summary [LIBC]: Implementation of `stdc_first_trailing_one` seems wrong
Labels libc
Assignees
Reporter strncmp
    While studying the code of LLVM libc I spotted this [function](https://github.com/llvm/llvm-project/blob/bc368e4b578730bf0b10acd5412e476ccf7a5807/libc/src/__support/math_extras.h#L149) which is the backend implementation of the `stdc_first_trailing_one` family. The edge case testing seems wrong, since the max value (a value filled with ones) would yield zero, meaning that no bits set to the value one were found. That's wrong according the the standard. This function returns zero, only when it cannot find the first trailing bit set to one. The only value with this property is zero, but the function tests for the max value instead. Here is the wording from [N3220](https://www.open-std.org/JTC1/SC22/WG14/www/docs/n3220.pdf):
![εικόνα](https://github.com/user-attachments/assets/4995916e-4e51-4176-b799-4908ec9b4a30)
The implementation should be something like the following:
```Cpp
template <typename T>
[[nodiscard]] LIBC_INLINE constexpr cpp::enable_if_t<cpp::is_unsigned_v<T>, int>
first_trailing_one(T value) {
  return value == T(0) ? 0 : cpp::countr_zero(value) + 1;
}
```
I also tested the [gcc intrinsics](https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html#index-_005f_005fbuiltin_005fstdc_005ffirst_005ftrailing_005fone) where the results seem to follow the wording of the standard.
_______________________________________________
llvm-bugs mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-bugs

Reply via email to