https://gcc.gnu.org/g:172785c36dae189fdae68900cb455fad9d9659f2
commit r17-758-g172785c36dae189fdae68900cb455fad9d9659f2 Author: Georg-Johann Lay <[email protected]> Date: Sun May 24 22:12:31 2026 +0200 AVR: ad target/121343 - Let __load_<size> insns use hard-reg constraints. Insns that generate transparent __load_<size> calls can be simplified using hard-reg constraints instead of explicit hard registers. This handles __flash loads of 3-byte and 4-byte integral, floating point and fixed-point values on devices without LPMx instruction. PR target/121343 gcc/ * config/avr/avr.md (load_<mode>_libgcc): Rewrite to use a hard-reg constraint for operand 0. (gen_load<mode>_libgcc): Remove expander. (mov<mode>): No more special handling needed for sources that satisfy avr_load_libgcc_p. Diff: --- gcc/config/avr/avr.md | 39 ++++++++++----------------------------- 1 file changed, 10 insertions(+), 29 deletions(-) diff --git a/gcc/config/avr/avr.md b/gcc/config/avr/avr.md index 71a97a1c4a70..2110f36febf5 100644 --- a/gcc/config/avr/avr.md +++ b/gcc/config/avr/avr.md @@ -546,33 +546,18 @@ ;;======================================================================== ;; Move stuff around -;; Expand helper for mov<mode>. -(define_expand "gen_load<mode>_libgcc" - [(set (match_dup 3) - (match_dup 2)) - (set (reg:MOVMODE 22) - (match_operand:MOVMODE 1 "memory_operand")) - (set (match_operand:MOVMODE 0 "register_operand") - (reg:MOVMODE 22))] - "avr_load_libgcc_p (operands[1])" - { - operands[3] = gen_rtx_REG (HImode, REG_Z); - operands[2] = force_operand (XEXP (operands[1], 0), NULL_RTX); - operands[1] = replace_equiv_address (operands[1], operands[3]); - set_mem_addr_space (operands[1], ADDR_SPACE_FLASH); - }) - -;; "load_qi_libgcc" -;; "load_hi_libgcc" +;; On devices without LPMx, __flash values > 2 bytes +;; are loaded with libgcc's __load_<size>. +;; Must be prior to the mov<mode> insns. +;; "load_qi_libgcc" (unused) +;; "load_hi_libgcc" (unused) ;; "load_psi_libgcc" ;; "load_si_libgcc" ;; "load_sf_libgcc" (define_insn_and_split "load_<mode>_libgcc" - [(set (reg:MOVMODE 22) - (match_operand:MOVMODE 0 "memory_operand" "m"))] - "avr_load_libgcc_p (operands[0]) - && REG_P (XEXP (operands[0], 0)) - && REG_Z == REGNO (XEXP (operands[0], 0))" + [(set (match_operand:MOVMODE 0 "register_operand" "={r22}") + (match_operand:MOVMODE 1 "memory_operand" "m"))] + "avr_load_libgcc_p (operands[1])" "#" "&& reload_completed" [(scratch)] @@ -823,12 +808,8 @@ DONE; } - if (avr_load_libgcc_p (src)) - { - // For the small devices, do loads per libgcc call. - emit_insn (gen_gen_load<mode>_libgcc (dest, src)); - DONE; - } + // The avr_load_libgcc_p (src) insns are handled above by + // "load_<mode>_libgcc". They look like ordinary move insns. }) ;;========================================================================
