Issue |
138650
|
Summary |
[InstCombine] Missing algebraic fold for handwritten bitwise AND
|
Labels |
llvm:instcombine,
llvm:transforms
|
Assignees |
|
Reporter |
antoniofrighetto
|
There are a few missing folds opportunities when attempting to simplify a manual bitwise AND, as Clang emits suboptimal codegen for the following snippet:
```c
uint64_t and(uint64_t a, uint64_t b) {
uint64_t c = 0;
for (int i = 0; i < 64; i++) {
if (((a >> i) & 1) && ((b >> i) & 1)) {
c |= (uint64_t)1 << i;
}
}
return c;
}
```
We might start from folding: `(((1 << %mask) & %a) == 0) | ((1 << %mask) & %b) == 0)) ? 0 : (1 << %mask)` into `(1 << %mask) & %a & %b`. Same may be done for `(2 << %mask)`. With these folds in place, Reassociate + GVN should be able to unleash the and between `a` and `b`.
Alive2: https://alive2.llvm.org/ce/z/ehkjGQ.
Godbolt: https://godbolt.org/z/h3TMdcxG3.
Found by @purplesyringa.
_______________________________________________
llvm-bugs mailing list
llvm-bugs@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-bugs