aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLehua Ding <lehua.ding@rivai.ai>2023-09-22 09:43:10 +0800
committerLehua Ding <lehua.ding@rivai.ai>2023-09-22 11:01:11 +0800
commite99cdab81bd3df7979d9b6917c06c80d73dff1e0 (patch)
tree41a222e1a50b7db7a56e0606fdf6eac43e853950
parentdba79ce1681828d05f6ed73ad56d8c3f3d53411a (diff)
downloadgcc-e99cdab81bd3df7979d9b6917c06c80d73dff1e0.zip
gcc-e99cdab81bd3df7979d9b6917c06c80d73dff1e0.tar.gz
gcc-e99cdab81bd3df7979d9b6917c06c80d73dff1e0.tar.bz2
RISC-V: Split VLS avl_type from NONVLMAX avl_type
This patch split a VLS avl_type from the NONVLMAX avl_type, denoting those RVV insn with length set to the number of units of VLS modes. gcc/ChangeLog: * config/riscv/riscv-protos.h (enum avl_type): New VLS avl_type. * config/riscv/riscv-v.cc (autovec_use_vlmax_p): Move comments.
-rw-r--r--gcc/config/riscv/riscv-protos.h21
-rw-r--r--gcc/config/riscv/riscv-v.cc25
2 files changed, 25 insertions, 21 deletions
diff --git a/gcc/config/riscv/riscv-protos.h b/gcc/config/riscv/riscv-protos.h
index 07b4ffe..d8372a7 100644
--- a/gcc/config/riscv/riscv-protos.h
+++ b/gcc/config/riscv/riscv-protos.h
@@ -368,10 +368,27 @@ enum vlmul_type
NUM_LMUL = 8
};
+/* The RISC-V vsetvli pass uses "known vlmax" operations for optimization.
+ Whether or not an instruction actually is a vlmax operation is not
+ recognizable from the length operand alone but the avl_type operand
+ is used instead. In general, there are two cases:
+
+ - Emit a vlmax operation by calling emit_vlmax_insn[_lra]. Here we emit
+ a vsetvli with vlmax configuration and set the avl_type to VLMAX for
+ VLA modes or VLS for VLS modes.
+ - Emit an operation that uses the existing (last-set) length and
+ set the avl_type to NONVLMAX.
+
+ Sometimes we also need to set the VLMAX or VLS avl_type to an operation that
+ already uses a given length register. This can happen during or after
+ register allocation when we are not allowed to create a new register.
+ For that case we also allow to set the avl_type to VLMAX or VLS.
+*/
enum avl_type
{
- NONVLMAX,
- VLMAX,
+ NONVLMAX = 0,
+ VLMAX = 1,
+ VLS = 2,
};
/* Routines implemented in riscv-vector-builtins.cc. */
void init_builtins (void);
diff --git a/gcc/config/riscv/riscv-v.cc b/gcc/config/riscv/riscv-v.cc
index f63dec5..e826621 100644
--- a/gcc/config/riscv/riscv-v.cc
+++ b/gcc/config/riscv/riscv-v.cc
@@ -284,6 +284,7 @@ public:
/* Add vl operand. */
rtx len = m_vl_op;
+ bool vls_p = false;
if (m_vlmax_p)
{
if (riscv_v_ext_vls_mode_p (vtype_mode))
@@ -294,7 +295,7 @@ public:
len = gen_int_mode (nunits, Pmode);
if (!satisfies_constraint_K (len))
len = force_reg (Pmode, len);
- m_vlmax_p = false;
+ vls_p = true;
}
else if (const_vlmax_p (vtype_mode))
{
@@ -302,7 +303,7 @@ public:
the vsetvli to obtain the value of vlmax. */
poly_uint64 nunits = GET_MODE_NUNITS (vtype_mode);
len = gen_int_mode (nunits, Pmode);
- m_vlmax_p = false;
+ vls_p = true;
}
else if (can_create_pseudo_p ())
{
@@ -318,7 +319,9 @@ public:
add_policy_operand ();
/* Add avl_type operand. */
- add_avl_type_operand (m_vlmax_p ? avl_type::VLMAX : avl_type::NONVLMAX);
+ add_avl_type_operand (
+ vls_p ? avl_type::VLS
+ : (m_vlmax_p ? avl_type::VLMAX : avl_type::NONVLMAX));
/* Add rounding mode operand. */
if (m_insn_flags & FRM_DYN_P)
@@ -769,22 +772,6 @@ autovec_use_vlmax_p (void)
|| riscv_autovec_preference == RVV_FIXED_VLMAX);
}
-/* The RISC-V vsetvli pass uses "known vlmax" operations for optimization.
- Whether or not an instruction actually is a vlmax operation is not
- recognizable from the length operand alone but the avl_type operand
- is used instead. In general, there are two cases:
-
- - Emit a vlmax operation by passing a NULL length. Here we emit
- a vsetvli with vlmax configuration and set the avl_type to VLMAX.
- - Emit an operation that uses the existing (last-set) length and
- set the avl_type to NONVLMAX.
-
- Sometimes we also need to set the VLMAX avl_type to an operation that
- already uses a given length register. This can happen during or after
- register allocation when we are not allowed to create a new register.
- For that case we also allow to set the avl_type to VLMAX.
-*/
-
/* This function emits VLMAX vrgather instruction. Emit vrgather.vx/vi when sel
is a const duplicate vector. Otherwise, emit vrgather.vv. */
static void