@@ -11157,6 +11157,78 @@ riscv_macro_fusion_pair_p (rtx_insn *prev, rtx_insn *curr)
1115711157 return false ;
1115811158}
1115911159
11160+ /* If INSN is a load or store of address in the form of [base+offset],
11161+ extract the two parts and set to BASE and OFFSET. IS_LOAD is set
11162+ to TRUE if it's a load. Return TRUE if INSN is such an instruction,
11163+ otherwise return FALSE. */
11164+
11165+ static bool
11166+ fusion_load_store (rtx_insn *insn, rtx *base, rtx *offset, bool *is_load)
11167+ {
11168+ rtx x, dest, src;
11169+
11170+ gcc_assert (INSN_P (insn));
11171+ x = PATTERN (insn);
11172+ if (GET_CODE (x) != SET)
11173+ return false ;
11174+
11175+ src = SET_SRC (x);
11176+ dest = SET_DEST (x);
11177+ if (REG_P (src) && MEM_P (dest))
11178+ {
11179+ *is_load = false ;
11180+ extract_base_offset_in_addr (dest, base, offset);
11181+ }
11182+ else if (MEM_P (src) && REG_P (dest))
11183+ {
11184+ *is_load = true ;
11185+ extract_base_offset_in_addr (src, base, offset);
11186+ }
11187+ else
11188+ return false ;
11189+
11190+ return (*base != NULL_RTX && *offset != NULL_RTX);
11191+ }
11192+
11193+ static void
11194+ riscv_sched_fusion_priority (rtx_insn *insn, int max_pri, int *fusion_pri,
11195+ int *pri)
11196+ {
11197+ int tmp, off_val;
11198+ bool is_load;
11199+ rtx base, offset;
11200+
11201+ gcc_assert (INSN_P (insn));
11202+
11203+ tmp = max_pri - 1 ;
11204+ if (!fusion_load_store (insn, &base, &offset, &is_load))
11205+ {
11206+ *pri = tmp;
11207+ *fusion_pri = tmp;
11208+ return ;
11209+ }
11210+
11211+ tmp /= 2 ;
11212+
11213+ /* INSN with smaller base register goes first. */
11214+ tmp -= ((REGNO (base) & 0xff ) << 20 );
11215+
11216+ /* INSN with smaller offset goes first. */
11217+ off_val = (int )(INTVAL (offset));
11218+
11219+ /* Put loads/stores operating on adjacent words into the same
11220+ * scheduling group. */
11221+ *fusion_pri = tmp - ((off_val / (UNITS_PER_WORD * 2 )) << 1 ) + is_load;
11222+
11223+ if (off_val >= 0 )
11224+ tmp -= (off_val & 0xfffff );
11225+ else
11226+ tmp += ((- off_val) & 0xfffff );
11227+
11228+ *pri = tmp;
11229+ return ;
11230+ }
11231+
1116011232/* Adjust the cost/latency of instructions for scheduling.
1116111233 For now this is just used to change the latency of vector instructions
1116211234 according to their LMUL. We assume that an insn with LMUL == 8 requires
@@ -15823,6 +15895,9 @@ riscv_prefetch_offset_address_p (rtx x, machine_mode mode)
1582315895#undef TARGET_SCHED_MACRO_FUSION_PAIR_P
1582415896#define TARGET_SCHED_MACRO_FUSION_PAIR_P riscv_macro_fusion_pair_p
1582515897
15898+ #undef TARGET_SCHED_FUSION_PRIORITY
15899+ #define TARGET_SCHED_FUSION_PRIORITY riscv_sched_fusion_priority
15900+
1582615901#undef TARGET_SCHED_VARIABLE_ISSUE
1582715902#define TARGET_SCHED_VARIABLE_ISSUE riscv_sched_variable_issue
1582815903
0 commit comments