https://gcc.gnu.org/bugzilla/show_bug.cgi?id=59874
--- Comment #13 from Uroš Bizjak <ubizjak at gmail dot com> --- (In reply to Allan Jensen from comment #8) > Thanks that looks good. I will test it when I have a chance. I am changing > the Qt sources to not assume the presence of __builtin_clzs when __BMI__ is > defined. It can use __builtin_clz() and __builtin_ctz()-16U instead, but for > general compatibility it is nice that GCC also keeps it around. There are now several possibilities: a) Use apparently de-facto standard __builtin_clzs and __builtin_ctzs. b) (gcc-7+) You can use documented __builtin_clz/__builtin_ctz builtins with operand casted to (unsigned short). When instruction is available, the compiler synthesizes 16bit insn variant from 32bit insn and zero-extension, as evident from gcc.target/i386/pr59874-?.c test cases. This is the most portable solution. c) (gcc-6.3+) Figure out how to use __lzcnt16/__tzcnt_u16, as suggested in Comment #3. This is the optimal solution, as checks for zero operand are not needed. > Note, it would be even better though if GCC could support the short forms as > generic builtins. That changes the semantics slightly, but they are named so > similarly to the clz, clzl and clzll it would be easy to assume they also > are generics, with similar semantics, and can work across all targets. > > Btw. I assume __builtin_clzs being a target specific builtin, that GCC never > had the capability of resolving it at compile-time? If that is the case, it > might actually be a bug that GCC allowed it at all in a constexpr function. Hm, I'm not versed in c++, but the provided headers that define various intrinsics are used in various c++ projects. In gcc-6.3+, the compiler folds these two builtins with constant operand at compile time, so please retry your tests with a newer compiler version.