On 03/21/2016 06:31 AM, Dominik Vogt wrote: > Why does it drop the "parallel" and "clobber" in the combination; > is there a way to force combine to keep that? > > Trying 6 -> 7: > Failed to match this instruction: > (set (reg:DI 65) > (and:DI (subreg:DI (mem:SI (reg:DI 2 %r2 [ a ]) [1 *a_2(D)+0 S4 A32]) 0) > (const_int 4294901775 [0xffff000f]))) > > (Because all "and" instructions on s390 clobber the CC, this > pattern does not match anything without the clobber.)
The main body of combine doesn't keep them, but when it comes to recognize the new instruction, there's a path through recog that knows how to add them back. See the call to (the generated) add_clobbers function. The real failure is hidden within general_operand: the (subreg:DI (mem:SI ...)) you have there doesn't match. #ifdef INSN_SCHEDULING /* On machines that have insn scheduling, we want all memory reference to be explicit, so outlaw paradoxical SUBREGs. However, we must allow them after reload so that they can get cleaned up by cleanup_subreg_operands. */ if (!reload_completed && MEM_P (sub) && GET_MODE_SIZE (mode) > GET_MODE_SIZE (GET_MODE (sub))) return 0; #endif Probably what we need is some path through combine that recognizes that bits have already been masked so that we leave the zero-extend alone in places that it makes sense. r~