AVR: Tweak 16-bit addition with const that didn't get a LD_REGS register.

The 16-bit additions like addhi3 have two forms: One with a scratch:QI
and one without, where the latter is required because reload cannot
deal with a scratch when spill code pops a 16-bit addition.

Passes like combine and fwprop1 may come up with the non-scratch version,
which is sub-optimal in the case when the addition is performed in a
NO_LD_REGS register because the operands will be spilled to LD_REGS.
Having a scratch:QI at disposal can lead to better code with less spills.

gcc/
	* config/avr/avr.md (*add<mode>3_split) [!reload_completed]:
	Add a scratch:QI to 16-bit additions with constant.
This commit is contained in:
Georg-Johann Lay 2024-08-18 18:26:16 +02:00
parent 22acd3c4d1
commit 1ed1dd521b

View File

@ -1724,12 +1724,28 @@
(match_operand:ALL2 2 "nonmemory_or_const_operand" "r,s,IJ YIJ,n Ynn")))]
""
"#"
"&& reload_completed"
"&& 1"
[(parallel [(set (match_dup 0)
(plus:ALL2 (match_dup 1)
(match_dup 2)))
(clobber (reg:CC REG_CC))])]
""
{
// Passes like combine and fwprop1 may remove the scratch from an
// addhi3 insn. Add the scratch again because having a QImode
// scratch reg available is better than spilling the operands in
// the case when we don't get a d-regs register.
if (! reload_completed
&& const_operand (operands[2], <MODE>mode)
&& ! stack_register_operand (operands[0], HImode)
&& ! stack_register_operand (operands[1], HImode))
{
emit (gen_add<mode>3_clobber (operands[0], operands[1], operands[2]));
DONE;
}
if (! reload_completed)
FAIL;
}
[(set_attr "isa" "*,*,adiw,*")])
;; "*addhi3"