http://gcc.gnu.org/bugzilla/show_bug.cgi?id=59747
--- Comment #6 from Jakub Jelinek <jakub at gcc dot gnu.org> --- The actual REGNO != REGNO transformation is correct, the problem is that the second extension is to a wider mode and while handling that we change the destination mode on the def_insn to an even wider mode. The code just assumes that the def insn sets the right REGNO rather than some other. So, I think it shouldn't be hard to detect that case. Then we either need to ensure the corresponding copy insn from the first extension will be adjusted to the wider mode, or for this case swap back the registers (revert to the original REGNO for the def insn and put the swap insn the other way around), or do it the other way around always (then no special casing would be needed; Jeff, what was the reason why you haven't handled (set (reg1) (expression)) (set (reg2) (any_extend (reg1)) as (set (reg1) (any_extend (expression))) (set (reg2) (reg1)) but instead (set (reg2) (any_extend (expression))) (set (reg1) (reg2)) ?).