https://gcc.gnu.org/bugzilla/show_bug.cgi?id=118832
--- Comment #3 from Robin Dapp <rdapp at gcc dot gnu.org> ---
The mechanism that introduces those unsplit instructions always seems to be via
reload. At some point we see a REG_EQUAL note with a const_vector. As we,
generally, can rematerialize constants we try to do that. And I don't think we
can ever prevent moving constants to a register.
Those VLA const_vectors aren't easily synthesized, though, and almost always
require a few instructions.
So just making everything unsplittable from LRA on is not going to help us
directly, it would just break in a different way.
Therefore I'm afraid we just need to make sure we don't use or rely on unsplit
instructions in the const-move expander.
For the case here the following helps:
diff --git a/gcc/config/riscv/riscv-v.cc b/gcc/config/riscv/riscv-v.cc
index 9847439ca77..a7559d11e19 100644
--- a/gcc/config/riscv/riscv-v.cc
+++ b/gcc/config/riscv/riscv-v.cc
@@ -1265,7 +1265,16 @@ expand_const_vector (rtx target, rtx src)
element. Use element width = 64 and broadcast a vector with
all element equal to 0x0706050403020100. */
rtx ele = builder.get_merged_repeating_sequence ();
- rtx dup = expand_vector_broadcast (builder.new_mode (), ele);
+ rtx dup;
+ if (lra_in_progress)
+ {
+ dup = gen_reg_rtx (builder.new_mode ());
+ rtx ops[] = {dup, ele};
+ emit_vlmax_insn (code_for_pred_broadcast
+ (builder.new_mode ()), UNARY_OP, ops);
+ }
+ else
+ dup = expand_vector_broadcast (builder.new_mode (), ele);
emit_move_insn (result, gen_lowpart (mode, dup));
}
else
But we'd need to audit the other cases still.