From 8b93a0f3eb46cbc4ba8eece8eba58aaade4399b6 Mon Sep 17 00:00:00 2001 From: Juzhe-Zhong Date: Tue, 5 Dec 2023 11:22:50 +0800 Subject: [PATCH] RISC-V: Add blocker for gather/scatter auto-vectorization This patch fixes ICE exposed on full coverage testing: === g++: Unexpected fails for rv64gc_zve32f_zvfh_zfh lp64d medlow --param=riscv-autovec-lmul=dynamic === FAIL: g++.dg/pr106219.C -std=gnu++14 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++17 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++20 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++98 (internal compiler error: in require, at machmode.h:313) === g++: Unexpected fails for rv64gc_zve32f_zvfh_zfh lp64d medlow --param=riscv-autovec-lmul=dynamic --param=riscv-autovec-preference=fixed-vlmax === FAIL: g++.dg/pr106219.C -std=gnu++14 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++17 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++20 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++98 (internal compiler error: in require, at machmode.h:313) === g++: Unexpected fails for rv64gc_zve32f_zvfh_zfh lp64d medlow --param=riscv-autovec-lmul=m4 === FAIL: g++.dg/pr106219.C -std=gnu++14 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++17 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++20 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++98 (internal compiler error: in require, at machmode.h:313) === g++: Unexpected fails for rv64gc_zve32f_zvfh_zfh lp64d medlow --param=riscv-autovec-lmul=m4 --param=riscv-autovec-preference=fixed-vlmax === FAIL: g++.dg/pr106219.C -std=gnu++14 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++17 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++20 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++98 (internal compiler error: in require, at machmode.h:313) === g++: Unexpected fails for rv64gc_zve32f_zvfh_zfh lp64d medlow --param=riscv-autovec-lmul=m8 === FAIL: g++.dg/pr106219.C -std=gnu++14 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++17 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++20 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++98 (internal compiler error: in require, at machmode.h:313) === g++: Unexpected fails for rv64gc_zve32f_zvfh_zfh lp64d medlow --param=riscv-autovec-lmul=m8 --param=riscv-autovec-preference=fixed-vlmax === FAIL: g++.dg/pr106219.C -std=gnu++14 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++17 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++20 (internal compiler error: in require, at machmode.h:313) FAIL: g++.dg/pr106219.C -std=gnu++98 (internal compiler error: in require, at machmode.h:313) The rootcause is we can't extend RVVM4SImode into RVVM8DImode on zve32f. Add a blocker of it to disable such auto-vectorization in this situation. gcc/ChangeLog: * config/riscv/autovec.md: Add blocker. * config/riscv/riscv-protos.h (gather_scatter_valid_offset_p): New function. * config/riscv/riscv-v.cc (gather_scatter_valid_offset_p): Ditto. gcc/testsuite/ChangeLog: * g++.target/riscv/rvv/autovec/bug-2.C: New test. --- gcc/config/riscv/autovec.md | 24 ++++++++++---------- gcc/config/riscv/riscv-protos.h | 1 + gcc/config/riscv/riscv-v.cc | 18 +++++++++++++++ gcc/testsuite/g++.target/riscv/rvv/autovec/bug-2.C | 26 ++++++++++++++++++++++ 4 files changed, 57 insertions(+), 12 deletions(-) create mode 100644 gcc/testsuite/g++.target/riscv/rvv/autovec/bug-2.C diff --git a/gcc/config/riscv/autovec.md b/gcc/config/riscv/autovec.md index 2d727c2609b..b9f7aa204da 100644 --- a/gcc/config/riscv/autovec.md +++ b/gcc/config/riscv/autovec.md @@ -59,7 +59,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, true); DONE; @@ -74,7 +74,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, true); DONE; @@ -89,7 +89,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, true); DONE; @@ -104,7 +104,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, true); DONE; @@ -119,7 +119,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, true); DONE; @@ -134,7 +134,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, true); DONE; @@ -172,7 +172,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, false); DONE; @@ -187,7 +187,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, false); DONE; @@ -202,7 +202,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, false); DONE; @@ -217,7 +217,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, false); DONE; @@ -232,7 +232,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, false); DONE; @@ -247,7 +247,7 @@ (match_operand: 5 "vector_mask_operand") (match_operand 6 "autovec_length_operand") (match_operand 7 "const_0_operand")] - "TARGET_VECTOR" + "TARGET_VECTOR && riscv_vector::gather_scatter_valid_offset_p (mode)" { riscv_vector::expand_gather_scatter (operands, false); DONE; diff --git a/gcc/config/riscv/riscv-protos.h b/gcc/config/riscv/riscv-protos.h index 695ee24ad6f..bfbd2bf0d18 100644 --- a/gcc/config/riscv/riscv-protos.h +++ b/gcc/config/riscv/riscv-protos.h @@ -606,6 +606,7 @@ enum vlmul_type get_vlmul (rtx_insn *); int count_regno_occurrences (rtx_insn *, unsigned int); bool imm_avl_p (machine_mode); bool can_be_broadcasted_p (rtx); +bool gather_scatter_valid_offset_p (machine_mode); } /* We classify builtin types into two classes: diff --git a/gcc/config/riscv/riscv-v.cc b/gcc/config/riscv/riscv-v.cc index 588c127343e..dd659f99f91 100644 --- a/gcc/config/riscv/riscv-v.cc +++ b/gcc/config/riscv/riscv-v.cc @@ -4686,4 +4686,22 @@ emit_vec_extract (rtx target, rtx src, poly_int64 index) emit_move_insn (target, ops[0].value); } +/* Return true if the offset mode is valid mode that we use for gather/scatter + autovectorization. */ +bool +gather_scatter_valid_offset_p (machine_mode mode) +{ + /* If the element size of offset mode is already >= Pmode size, + we don't need any extensions. */ + if (known_ge (GET_MODE_SIZE (GET_MODE_INNER (mode)), UNITS_PER_WORD)) + return true; + + /* Since we are very likely extend the offset mode into vector Pmode, + Disable gather/scatter autovectorization if we can't extend the offset + mode into vector Pmode. */ + if (!get_vector_mode (Pmode, GET_MODE_NUNITS (mode)).exists ()) + return false; + return true; +} + } // namespace riscv_vector diff --git a/gcc/testsuite/g++.target/riscv/rvv/autovec/bug-2.C b/gcc/testsuite/g++.target/riscv/rvv/autovec/bug-2.C new file mode 100644 index 00000000000..53bc4a30072 --- /dev/null +++ b/gcc/testsuite/g++.target/riscv/rvv/autovec/bug-2.C @@ -0,0 +1,26 @@ +/* { dg-options "-march=rv64gc_zve32f -mabi=lp64d -O3 --param=riscv-autovec-lmul=m4" } */ + +int max(int __b) { + if (0 < __b) + return __b; + return 0; +} +struct Plane { + Plane(int, int); + int *Row(); +}; +float *ConvolveXSampleAndTranspose_rowp; +int ConvolveXSampleAndTranspose_res, ConvolveXSampleAndTranspose_r; +void ConvolveXSampleAndTranspose() { + Plane out(0, ConvolveXSampleAndTranspose_res); + for (int y;;) { + float sum; + for (int i = ConvolveXSampleAndTranspose_r; i; ++i) + sum += i; + for (; ConvolveXSampleAndTranspose_r; ++ConvolveXSampleAndTranspose_r) + sum += + ConvolveXSampleAndTranspose_rowp[max(ConvolveXSampleAndTranspose_r)] * + ConvolveXSampleAndTranspose_r; + out.Row()[y] = sum; + } +} -- 2.11.4.GIT