On 5/18/23 20:14, Andrew Pinski via Gcc-patches wrote:
While working something else, I noticed we could improve
the following function code generation:
```
unsigned f(unsigned t)
{
if (t & ~(1<<30)) __builtin_unreachable();
return t != 0;
}
```
Right know we just emit a comparison against 0 instead
of just a shift right by 30.
There is code in do_store_flag which already optimizes
`(t & 1<<30) != 0` to `(t >> 30) & 1`. This patch
extends it to handle the case where we know t has a
nonzero of just one bit set.
OK? Bootstrapped and tested on x86_64-linux-gnu with no regressions.
gcc/ChangeLog:
* expr.cc (do_store_flag): Extend the one bit checking case
to handle the case where we don't have an and but rather still
one bit is known to be non-zero.
So as we touched on in IRC, the concern is targets where the cost of the
shift depends on the number of bits shifted. Can we look at costing
here to determine the initial RTL generation approach?
Another approach that would work for some targets is a single bit
extract. In theory we should be discovering the extract idiom from the
shift+and form, but I'm always concerned that it's going to be missed
for one or more oddball reasons.
jeff