Re: [PATCH][v2] match.pd: drop an operand discarded by a shift
Jeffrey Law <[email protected]>
| Newsgroups | gmane.comp.gcc.patches |
|---|---|
| Message-ID | <[email protected]> |
On 8/5/2026 5:40 AM, [email protected] wrote: > From: Kyrylo Tkachov <[email protected]> > > Neither an inclusive nor an exclusive or can carry, so an operand whose set > bits all lie below the shift count contributes nothing to the result: > > int f (int a, int b) { return (a ^ (b & 1)) >> 1; } > > aarch64 -O2 before: > > and w1, w1, 1 > eor w0, w1, w0 > asr w0, w0, 1 > > after: > > asr w0, w0, 1 > > The set bits are read from tree_nonzero_bits, so the rule also fires when > the operand is a boolean, a narrow value or anything else whose range the > middle end already knows. Found by mining the optimized dumps of real code, > where the shape comes from flag bits packed into the low bits of a word. > > Bootstrapped and tested on aarch64-none-linux-gnu. > Ok for trunk? > Thanks, > Kyrill > > gcc/ChangeLog: > > * match.pd ((X | Y) >> C, (X ^ Y) >> C): New simplification. > > gcc/testsuite/ChangeLog: > > * gcc.dg/tree-ssa/shift-drops-bitop-1.c: New test. GIven this can fire for !GIMPLE and we totally drop the Y term, don't we need to either verify Y has no side effects or guard the transformation on GIMPLE? Jeff