https://gcc.gnu.org/bugzilla/show_bug.cgi?id=71343
Richard Biener <rguenth at gcc dot gnu.org> changed: What |Removed |Added ---------------------------------------------------------------------------- Status|UNCONFIRMED |NEW Last reconfirmed| |2016-05-30 Component|rtl-optimization |tree-optimization Ever confirmed|0 |1 --- Comment #1 from Richard Biener <rguenth at gcc dot gnu.org> --- Confirmed and eventually not helped by factoring *4 early: return (a << 2) + (b << 2) == (a + b) * 4; adjusted testcase for that: unsigned int test12(unsigned int a , unsigned int b) { unsigned int tem1 = a * 4; unsigned int tem2 = b * 4; return ((a << 2) + (b << 2)) == tem1 + tem2; } also fails to optimize. In the end this is a missed canonicalization though semantically shifts are not always equal to multiplication (they are for unsigned arithmetic). CSE could also handle this (it also "fails" to handle x + x as x * 2, but we canonicalize that now). I'd say the multiplication is canonical here. We do optimize unsigned int test12(unsigned int a , unsigned int b) { unsigned int tem1 = a / 4; unsigned int tem2 = b / 4; return ((a >> 2) + (b >> 2)) == tem1 + tem2; } but pretty late in DOM2. VRP1 is replacing the division by a shift.