https://gcc.gnu.org/bugzilla/show_bug.cgi?id=91882
--- Comment #3 from Andrew Pinski <pinskia at gcc dot gnu.org> --- This is a job for reassociation pass really. coming into that pass we have: _1 = a_3(D) | b_4(D); if (_1 != 0) goto <bb 3>; [50.00%] else goto <bb 4>; [50.00%] <bb 3> [local count: 536870913]: _5 = a_3(D) & b_4(D); if (_5 != 0) goto <bb 4>; [50.00%] else goto <bb 5>; [50.00%] <bb 4> [local count: 805306369]: <bb 5> [local count: 1073741824]: # iftmp.0_2 = PHI <1(3), 0(4)> We should be able to transform this into: _6 = a_3(D) ^ b_4(D); if (_6 != 0) goto <bb 3>; [50.00%] else goto <bb 4>; [50.00%] <bb 3> [local count: 536870913]: if (0 != 0) goto <bb 4>; [50.00%] else goto <bb 5>; [50.00%] <bb 4> [local count: 805306369]: <bb 5> [local count: 1073741824]: # iftmp.0_2 = PHI <1(3), 0(4)> then cfg cleanup should do: _6 = a_3(D) ^ b_4(D); if (_6 != 0) goto <bb 5>; [50.00%] else goto <bb 4>; [50.00%] <bb 4> [local count: 805306369]: <bb 5> [local count: 1073741824]: # iftmp.0_2 = PHI <1(1), 0(4)> And then PHI-OPT should transform it into: _6 = a_3(D) ^ b_4(D); iftmp.0_2 = _6;