https://gcc.gnu.org/bugzilla/show_bug.cgi?id=87746
--- Comment #4 from Richard Biener <rguenth at gcc dot gnu.org> --- Ick. if-conversion leaves us with quite a mess: <bb 3> [local count: 955630224]: # i_20 = PHI <i_17(10), 0(21)> _1 = replacements[i_20].subreg_loc; _2 = (long int) y_13(D); _3 = (struct rtx_def * *) _2; _ifc__42 = replacements[i_20].subreg_loc; _ifc__43 = _3; _ifc__44 = _1 == x_12(D) ? _ifc__43 : _ifc__42; replacements[i_20].subreg_loc = _ifc__44; _4 = replacements[i_20].where; _22 = _1 == x_12(D); _9 = ~_22; _18 = _4 == x_12(D); _19 = _9 & _18; _5 = (long int) y_13(D); _6 = (struct rtx_def * *) _5; _ifc__45 = replacements[i_20].where; _ifc__46 = _6; _ifc__47 = _19 ? _ifc__46 : _ifc__45; replacements[i_20].where = _ifc__47; _ifc__48 = replacements[i_20].subreg_loc; _ifc__49 = 0B; _ifc__50 = _19 ? _ifc__49 : _ifc__48; replacements[i_20].subreg_loc = _ifc__50; i_17 = i_20 + 1; if (n_replacements_11(D) > i_17) goto <bb 10>; [89.00%] else goto <bb 8>; [11.00%] throwing VN on if-converted loops improves this to the following also avoiding the ICE: <bb 3> [local count: 955630224]: # i_20 = PHI <i_17(10), 0(21)> _1 = replacements[i_20].subreg_loc; _2 = (long int) y_13(D); _3 = (struct rtx_def * *) _2; _ifc__44 = _1 != x_12(D) ? _1 : _3; replacements[i_20].subreg_loc = _ifc__44; _4 = replacements[i_20].where; _22 = _1 == x_12(D); _9 = ~_22; _18 = _4 == x_12(D); _19 = _9 & _18; _ifc__47 = _19 ? _3 : _4; replacements[i_20].where = _ifc__47; _ifc__50 = _19 ? 0B : _ifc__44; replacements[i_20].subreg_loc = _ifc__50; i_17 = i_20 + 1; if (n_replacements_11(D) > i_17) goto <bb 10>; [89.00%] else goto <bb 8>; [11.00%] The dead store is of course still confusing us. My old store-commoning patch would maybe help here. Or a region-based DSE. Or somehow integrating basic DSE with VN. Anyhow the ICE is still odd.