https://gcc.gnu.org/bugzilla/show_bug.cgi?id=113474

--- Comment #1 from Robin Dapp <rdapp at gcc dot gnu.org> ---
Good catch.  Looks like the ifn expander always forces into a register.  That's
probably necessary on all targets except riscv.

diff --git a/gcc/internal-fn.cc b/gcc/internal-fn.cc
index a07f25f3aee..e923051d540 100644
--- a/gcc/internal-fn.cc
+++ b/gcc/internal-fn.cc
@@ -3118,7 +3118,8 @@ expand_vec_cond_mask_optab_fn (internal_fn, gcall *stmt,
convert_optab optab)
   rtx_op2 = expand_normal (op2);

   mask = force_reg (mask_mode, mask);
-  rtx_op1 = force_reg (mode, rtx_op1);
+  if (!insn_operand_matches (icode, 1, rtx_op1))
+    rtx_op1 = force_reg (mode, rtx_op1);

   rtx target = expand_expr (lhs, NULL_RTX, VOIDmode, EXPAND_WRITE);
   create_output_operand (&ops[0], target, mode);

gives me:

foo:
.LFB0:
        .cfi_startproc
        ble     a0,zero,.L5
        slli    a3,a0,3
        add     a3,a1,a3
        vsetivli        zero,4,e32,m1,ta,ma
        vmv.v.i v3,15
        vmv.v.i v2,0
.L3:
        ld      a5,0(a1)
        addi    a4,a5,4
        addi    a5,a5,20
        vle32.v v1,0(a5)
        vle32.v v0,0(a4)
        vmseq.vv        v0,v0,v3
        vmerge.vim      v4,v2,1,v0
        vse32.v v4,0(a4)
        vmseq.vv        v0,v1,v3
        addi    a1,a1,8
        vmerge.vim      v1,v2,1,v0
        vse32.v v1,0(a5)
        bne     a1,a3,.L3
.L5:
        ret

Reply via email to