https://gcc.gnu.org/g:8d577a01cdbe02a23724b710b579b7811c983c33
commit r15-6873-g8d577a01cdbe02a23724b710b579b7811c983c33 Author: Jin Ma <ji...@linux.alibaba.com> Date: Mon Jan 13 11:15:55 2025 -0700 RISC-V: Fix the result error caused by not updating ratio when using "use_max_sew" to merge vsetvl When the vsetvl instructions of the two RVV instructions are merged using "use_max_sew", it is possible to update the sew of prev if prev.sew < next.sew, but keep the original ratio, which is obviously wrong. when the subsequent instructions are equal to the wrong ratio, it is possible to generate the wrong "vsetvli zero,zero" instruction, which will lead to unknown avl. gcc/ChangeLog: * config/riscv/riscv-vsetvl.cc (demand_system::use_max_sew): Also set the ratio for PREV. gcc/testsuite/ChangeLog: * gcc.target/riscv/rvv/base/bug-10.c: New test. Diff: --- gcc/config/riscv/riscv-vsetvl.cc | 1 + gcc/testsuite/gcc.target/riscv/rvv/base/bug-10.c | 14 ++++++++++++++ 2 files changed, 15 insertions(+) diff --git a/gcc/config/riscv/riscv-vsetvl.cc b/gcc/config/riscv/riscv-vsetvl.cc index 851e52a20ba6..e9de21787dda 100644 --- a/gcc/config/riscv/riscv-vsetvl.cc +++ b/gcc/config/riscv/riscv-vsetvl.cc @@ -1722,6 +1722,7 @@ private: { int max_sew = MAX (prev.get_sew (), next.get_sew ()); prev.set_sew (max_sew); + prev.set_ratio (calculate_ratio (prev.get_sew (), prev.get_vlmul ())); use_min_of_max_sew (prev, next); } inline void use_next_sew_lmul (vsetvl_info &prev, const vsetvl_info &next) diff --git a/gcc/testsuite/gcc.target/riscv/rvv/base/bug-10.c b/gcc/testsuite/gcc.target/riscv/rvv/base/bug-10.c new file mode 100644 index 000000000000..af3a8610d63f --- /dev/null +++ b/gcc/testsuite/gcc.target/riscv/rvv/base/bug-10.c @@ -0,0 +1,14 @@ +/* { dg-do compile { target { rv64 } } } */ +/* { dg-options " -march=rv64gcv_zvfh -mabi=lp64d -O2 --param=vsetvl-strategy=optim -fno-schedule-insns -fno-schedule-insns2 -fno-schedule-fusion " } */ + +#include <riscv_vector.h> + +void +foo (uint8_t *ptr, vfloat16m4_t *v1, vuint32m8_t *v2, vuint8m2_t *v3, size_t vl) +{ + *v1 = __riscv_vfmv_s_f_f16m4 (1, vl); + *v2 = __riscv_vmv_s_x_u32m8 (2963090659u, vl); + *v3 = __riscv_vsll_vx_u8m2 (__riscv_vid_v_u8m2 (vl), 2, vl); +} + +/* { dg-final { scan-assembler-not {vsetvli.*zero,zero} } }*/