When generating code for a two address machine (like x86) I'm
trying to peephole sequences for commutative operations like
(destination registers on left)
1. add Rm,Rn
2. ld Rn,Rm
to
1. add Rn,Rm
I have defined this peephole2
define_peephole2
[
(parallel
[
(set (match_operand:HI 0 "register_operand" "")
(match_operator:HI 1 "commutative_operator"
[(match_dup 0)
(match_operand:HI 2
"register_operand" "")]))
(clobber (reg:CC CC_REGNUM))
]
)
(set (match_dup 2) (match_dup 0))
]
"peep2_regno_dead_p( 2, REGNO (operands[0]))"
; ""
[
(parallel
[
(set (match_dup 2)
(match_op_dup 1
[(match_dup 2)
(match_dup 0 )]))
(clobber (reg:CC CC_REGNUM))
]
)
]
)
which works perfectly when Rm is never referenced after
instruction 2 in the original sequence, however it fails if Rm is
defined in the instruction immediately after instruction 2.
e.g.
1. add r2,r0
2. ld r0,r2
3. pop r2
4. ret
where r0 is the function return value. To me it seems that r2 is
dead between instructions 2 and 3 so this should be able to be
converted to ...
1. add r0,r2
3. pop r2
4. ret
for this case the following is the output from the peephole2
pass. Note that R2 is not marked as dead in the (insn 33 24 27 2)
sequence
(insn 24 20 33 2 (parallel [
(set (reg:HIreg:2 [orig:18 D.1931 ] [18])
(plus:HI (reg:HIreg:2 [orig:18 D.1931 ] [18])
(reg:HIreg:0)))
(clobber (reg:CCreg:7))
]) tl.c:7 35 {addhi3}
(expr_list:REG_DEAD (reg:HIreg:0)
(expr_list:REG_DEAD (reg:HIreg:8)
(expr_list:REG_UNUSED (reg:CCreg:7)
(nil)))))
(insn 33 24 27 2 (set (reg/i:HIreg:0)
(reg:HIreg:2 [orig:18 D.1931 ] [18])) tl.c:7 78 {*movhihi}
(nil))
(insn 27 33 36 2 (use (reg/i:HIreg:0)) tl.c:7 -1
(nil))
(note 36 27 37 2 NOTE_INSN_EPILOGUE_BEG)
Can anybody suggest a condition I should use in the
define_peephole2 to correctly handle this circumstance ?
Thanks, Paul