https://gcc.gnu.org/bugzilla/show_bug.cgi?id=126245
Bug ID: 126245
Summary: [17 Regression] Improve conditional negate sequence
for RISC-V (and others?)
Product: gcc
Version: 17.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: target
Assignee: unassigned at gcc dot gnu.org
Reporter: law at gcc dot gnu.org
Target Milestone: ---
With Odysseas's patch on the trunk we probably need to improve recognition and
optimization of conditional negation in RTL.
Essentially with Odysseas patch we get a conditional move form at expand time
resulting in:
(insn 7 6 8 (set (reg:DI 141 [ _6 ])
(neg:DI (reg/v:DI 137 [ x ]))) "j.c":8:21 -1
(nil))
(insn 8 7 9 (set (reg:DI 142)
(lt:DI (reg/v:DI 137 [ x ])
(reg/v:DI 138 [ y ]))) "j.c":8:21 -1
(nil))
(insn 9 8 10 (set (reg:DI 144)
(if_then_else:DI (eq:DI (reg:DI 142)
(const_int 0 [0]))
(const_int 0 [0])
(reg:DI 141 [ _6 ]))) "j.c":8:21 -1
(nil))
(insn 10 9 11 (set (reg:DI 143)
(if_then_else:DI (ne:DI (reg:DI 142)
(const_int 0 [0]))
(const_int 0 [0])
(reg/v:DI 137 [ x ]))) "j.c":8:21 -1
(nil))
(insn 11 10 12 (set (reg:DI 140 [ _4 ])
(plus:DI (reg:DI 143)
(reg:DI 144))) "j.c":8:21 -1
(nil))
Which results in:
slt a1,a0,a1 # 8 [c=4 l=4] slt_didi3
neg a5,a0 # 7 [c=4 l=4] negdi2
czero.eqz t0,a5,a1 # 9 [c=4 l=4] *czero.eqz.didi
czero.nez a0,a0,a1 # 10 [c=4 l=4] *czero.nez.didi
add a0,a0,t0 # 16 [c=4 l=4] *adddi3/0
But this would be better. It's likely not inherently faster on a 2+ wide core,
but it's going to encode better and doesn't rely on zicond:
slt a1,a0,a1
neg a5,a1
xor a0,a5,a0
add a0,a0,a1
Given we're expanding into a conditional move style sequence, I don't see this
as being an ifcvt problem. It seems we've got a couple choices. First to try
and generate the better sequence in the conditional move expander. Second via
combiner patterns. The first seems like generally the better choice, but
that's without doing any prototyping.