blob: 45be9e6fe177b7654a4adbe827260fcbdbc3c754 [file] [log] [blame] [view]
;; Machine description for RISC-V 'V' Extension for GNU compiler.
;; Copyright (C) 2022-2026 Free Software Foundation, Inc.
;; Contributed by Juzhe Zhong (juzhe.zhong@rivai.ai), RiVAI Technologies Ltd.
;; This file is part of GCC.
;; GCC is free software; you can redistribute it and/or modify
;; it under the terms of the GNU General Public License as published by
;; the Free Software Foundation; either version 3, or (at your option)
;; any later version.
;; GCC is distributed in the hope that it will be useful,
;; but WITHOUT ANY WARRANTY; without even the implied warranty of
;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
;; GNU General Public License for more details.
;; You should have received a copy of the GNU General Public License
;; along with GCC; see the file COPYING3. If not see
;; <http://www.gnu.org/licenses/>.
;; This file describes the RISC-V 'V' Extension, Version 1.0.
;;
;; This file include :
;;
;; - Intrinsics (https://github.com/riscv/rvv-intrinsic-doc)
;; - Auto-vectorization (autovec.md)
;; - Optimization (autovec-opt.md)
(include "vector-iterators.md")
(define_constants [
(INVALID_ATTRIBUTE 255)
(X0_REGNUM 0)
])
;; True if the type is RVV instructions that include VTYPE
;; global status register in the use op list.
;; We known VTYPE has 4 fields: SEW, LMUL, TA, MA.
;; The instruction need any of VTYPE field is set as true
;; in this attribute.
(define_attr "has_vtype_op" "false,true"
(cond [(eq_attr "type" "vlde,vste,vldm,vstm,vlds,vsts,\
vldux,vldox,vstux,vstox,vldff,\
vialu,viwalu,vext,vicalu,vshift,vnshift,vicmp,viminmax,\
vimul,vidiv,viwmul,vimuladd,viwmuladd,vimerge,
vmov,vimov,\
vsalu,vaalu,vsmul,vsshift,vnclip,\
vfalu,vfwalu,vfmul,vfdiv,vfwmul,vfmuladd,vfwmuladd,vfsqrt,vfrecp,\
vfcmp,vfminmax,vfsgnj,vfclass,vfmerge,vfmov,\
vfcvtitof,vfcvtftoi,vfwcvtitof,vfwcvtftoi,\
vfwcvtftof,vfncvtitof,vfncvtftoi,vfncvtftof,\
vired,viwred,vfredu,vfredo,vfwredu,vfwredo,\
vmalu,vmpop,vmffs,vmsfs,vmiota,vmidx,vimovvx,vimovxv,vfmovvf,vfmovfv,\
vslideup,vslidedown,vislide1up,vislide1down,vfslide1up,vfslide1down,\
vgather,vcompress,vlsegde,vssegte,vlsegds,vssegts,vlsegdux,vlsegdox,\
vssegtux,vssegtox,vlsegdff,vandn,vbrev,vbrev8,vrev8,vcpop,vclz,vctz,vrol,\
vror,vwsll,vclmul,vclmulh,vghsh,vgmul,vaesef,vaesem,vaesdf,vaesdm,\
vaeskf1,vaeskf2,vaesz,vsha2ms,vsha2ch,vsha2cl,vsm4k,vsm4r,vsm3me,vsm3c,\
vfncvtbf16,vfwcvtbf16,vfwmaccbf16,sf_vqmacc,sf_vfnrclip,sf_vc,sf_vc_se")
(const_string "true")]
(const_string "false")))
;; True if the type is RVV instructions that include VL
;; global status register in the use op list.
;; The instruction need vector length to be specified is set
;; in this attribute.
(define_attr "has_vl_op" "false,true"
(cond [(eq_attr "type" "vlde,vste,vldm,vstm,vlds,vsts,\
vldux,vldox,vstux,vstox,vldff,\
vialu,viwalu,vext,vicalu,vshift,vnshift,vicmp,viminmax,\
vimul,vidiv,viwmul,vimuladd,viwmuladd,vimerge,vimov,\
vsalu,vaalu,vsmul,vsshift,vnclip,\
vfalu,vfwalu,vfmul,vfdiv,vfwmul,vfmuladd,vfwmuladd,vfsqrt,vfrecp,\
vfcmp,vfminmax,vfsgnj,vfclass,vfmerge,vfmov,\
vfcvtitof,vfcvtftoi,vfwcvtitof,vfwcvtftoi,\
vfwcvtftof,vfncvtitof,vfncvtftoi,vfncvtftof,\
vired,viwred,vfredu,vfredo,vfwredu,vfwredo,\
vmalu,vmpop,vmffs,vmsfs,vmiota,vmidx,vimovxv,vfmovfv,\
vslideup,vslidedown,vislide1up,vislide1down,vfslide1up,vfslide1down,\
vgather,vcompress,vlsegde,vssegte,vlsegds,vssegts,vlsegdux,vlsegdox,\
vssegtux,vssegtox,vlsegdff,vandn,vbrev,vbrev8,vrev8,vcpop,vclz,vctz,vrol,\
vror,vwsll,vclmul,vclmulh,vghsh,vgmul,vaesef,vaesem,vaesdf,vaesdm,\
vaeskf1,vaeskf2,vaesz,vsha2ms,vsha2ch,vsha2cl,vsm4k,vsm4r,vsm3me,vsm3c,\
vfncvtbf16,vfwcvtbf16,vfwmaccbf16")
(const_string "true")]
(const_string "false")))
;; The default SEW of RVV instruction. This attribute doesn't mean the instruction
;; is necessary to require SEW check for example vlm.v which require ratio to
;; check. However, we need default value of SEW for vsetvl instruction since there
;; is no field for ratio in the vsetvl instruction encoding.
(define_attr "sew" ""
(cond [(eq_attr "mode" "RVVMF8BI,RVVMF4BI,RVVMF2BI,RVVM1BI,\
RVVM8QI,RVVM4QI,RVVM2QI,RVVM1QI,RVVMF2QI,RVVMF4QI,RVVMF8QI,\
RVVM1x8QI,RVVMF2x8QI,RVVMF4x8QI,RVVMF8x8QI,\
RVVM1x7QI,RVVMF2x7QI,RVVMF4x7QI,RVVMF8x7QI,\
RVVM1x6QI,RVVMF2x6QI,RVVMF4x6QI,RVVMF8x6QI,\
RVVM1x5QI,RVVMF2x5QI,RVVMF4x5QI,RVVMF8x5QI,\
RVVM2x4QI,RVVM1x4QI,RVVMF2x4QI,RVVMF4x4QI,RVVMF8x4QI,\
RVVM2x3QI,RVVM1x3QI,RVVMF2x3QI,RVVMF4x3QI,RVVMF8x3QI,\
RVVM4x2QI,RVVM2x2QI,RVVM1x2QI,RVVMF2x2QI,RVVMF4x2QI,RVVMF8x2QI,\
V1QI,V2QI,V4QI,V8QI,V16QI,V32QI,V64QI,V128QI,V256QI,V512QI,V1024QI,V2048QI,V4096QI,\
V1BI,V2BI,V4BI,V8BI,V16BI,V32BI,V64BI,V128BI,V256BI,V512BI,V1024BI,V2048BI,V4096BI")
(const_int 8)
(eq_attr "mode" "RVVMF16BI")
(if_then_else (match_test "TARGET_XTHEADVECTOR")
(const_int 16)
(const_int 8))
(eq_attr "mode" "RVVMF32BI")
(if_then_else (match_test "TARGET_XTHEADVECTOR")
(const_int 32)
(const_int 8))
(eq_attr "mode" "RVVMF64BI")
(if_then_else (match_test "TARGET_XTHEADVECTOR")
(const_int 64)
(const_int 8))
(eq_attr "mode" "RVVM8HI,RVVM4HI,RVVM2HI,RVVM1HI,RVVMF2HI,RVVMF4HI,\
RVVM1x8HI,RVVMF2x8HI,RVVMF4x8HI,\
RVVM1x7HI,RVVMF2x7HI,RVVMF4x7HI,\
RVVM1x6HI,RVVMF2x6HI,RVVMF4x6HI,\
RVVM1x5HI,RVVMF2x5HI,RVVMF4x5HI,\
RVVM2x4HI,RVVM1x4HI,RVVMF2x4HI,RVVMF4x4HI,\
RVVM2x3HI,RVVM1x3HI,RVVMF2x3HI,RVVMF4x3HI,\
RVVM4x2HI,RVVM2x2HI,RVVM1x2HI,RVVMF2x2HI,RVVMF4x2HI,\
RVVM8BF,RVVM4BF,RVVM2BF,RVVM1BF,RVVMF2BF,RVVMF4BF,\
RVVM1x8BF,RVVMF2x8BF,RVVMF4x8BF,\
RVVM1x7BF,RVVMF2x7BF,RVVMF4x7BF,\
RVVM1x6BF,RVVMF2x6BF,RVVMF4x6BF,\
RVVM1x5BF,RVVMF2x5BF,RVVMF4x5BF,\
RVVM2x4BF,RVVM1x4BF,RVVMF2x4BF,RVVMF4x4BF,\
RVVM2x3BF,RVVM1x3BF,RVVMF2x3BF,RVVMF4x3BF,\
RVVM4x2BF,RVVM2x2BF,RVVM1x2BF,RVVMF2x2BF,RVVMF4x2BF,\
RVVM8HF,RVVM4HF,RVVM2HF,RVVM1HF,RVVMF2HF,RVVMF4HF,\
RVVM1x8HF,RVVMF2x8HF,RVVMF4x8HF,\
RVVM1x7HF,RVVMF2x7HF,RVVMF4x7HF,\
RVVM1x6HF,RVVMF2x6HF,RVVMF4x6HF,\
RVVM1x5HF,RVVMF2x5HF,RVVMF4x5HF,\
RVVM2x4HF,RVVM1x4HF,RVVMF2x4HF,RVVMF4x4HF,\
RVVM2x3HF,RVVM1x3HF,RVVMF2x3HF,RVVMF4x3HF,\
RVVM4x2HF,RVVM2x2HF,RVVM1x2HF,RVVMF2x2HF,RVVMF4x2HF,\
V1HI,V2HI,V4HI,V8HI,V16HI,V32HI,V64HI,V128HI,V256HI,V512HI,V1024HI,V2048HI,\
V1HF,V2HF,V4HF,V8HF,V16HF,V32HF,V64HF,V128HF,V256HF,V512HF,V1024HF,V2048HF,\
V1BF,V2BF,V4BF,V8BF,V16BF,V32BF,V64BF,V128BF,V256BF,V512BF,V1024BF,V2048BF")
(const_int 16)
(eq_attr "mode" "RVVM8SI,RVVM4SI,RVVM2SI,RVVM1SI,RVVMF2SI,\
RVVM8SF,RVVM4SF,RVVM2SF,RVVM1SF,RVVMF2SF,\
RVVM1x8SI,RVVMF2x8SI,\
RVVM1x7SI,RVVMF2x7SI,\
RVVM1x6SI,RVVMF2x6SI,\
RVVM1x5SI,RVVMF2x5SI,\
RVVMF2x4SI,RVVMF2x3SI,\
RVVM2x4SI,RVVM1x4SI,\
RVVM2x3SI,RVVM1x3SI,\
RVVM4x2SI,RVVM2x2SI,RVVM1x2SI,RVVMF2x2SI,\
RVVM1x8SF,RVVMF2x8SF,\
RVVM1x7SF,RVVMF2x7SF,\
RVVM1x6SF,RVVMF2x6SF,\
RVVM1x5SF,RVVMF2x5SF,\
RVVM2x4SF,RVVM1x4SF,RVVMF2x4SF,\
RVVM2x3SF,RVVM1x3SF,RVVMF2x3SF,\
RVVM4x2SF,RVVM2x2SF,RVVM1x2SF,RVVMF2x2SF,\
V1SI,V2SI,V4SI,V8SI,V16SI,V32SI,V64SI,V128SI,V256SI,V512SI,V1024SI,\
V1SF,V2SF,V4SF,V8SF,V16SF,V32SF,V64SF,V128SF,V256SF,V512SF,V1024SF")
(const_int 32)
(eq_attr "mode" "RVVM8DI,RVVM4DI,RVVM2DI,RVVM1DI,\
RVVM8DF,RVVM4DF,RVVM2DF,RVVM1DF,\
RVVM1x8DI,RVVM1x7DI,RVVM1x6DI,RVVM1x5DI,\
RVVM2x4DI,RVVM1x4DI,\
RVVM2x3DI,RVVM1x3DI,\
RVVM4x2DI,RVVM2x2DI,RVVM1x2DI,\
RVVM1x8DF,RVVM1x7DF,RVVM1x6DF,RVVM1x5DF,\
RVVM2x4DF,RVVM1x4DF,\
RVVM2x3DF,RVVM1x3DF,\
RVVM4x2DF,RVVM2x2DF,RVVM1x2DF,\
V1DI,V2DI,V4DI,V8DI,V16DI,V32DI,V64DI,V128DI,V256DI,V512DI,\
V1DF,V2DF,V4DF,V8DF,V16DF,V32DF,V64DF,V128DF,V256DF,V512DF")
(const_int 64)]
(const_int INVALID_ATTRIBUTE)))
;; Ditto to LMUL.
(define_attr "vlmul" ""
(cond [(eq_attr "mode" "RVVM8QI,RVVM1BI") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4QI,RVVMF2BI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2QI,RVVMF4BI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1QI,RVVMF8BI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2QI,RVVMF16BI") (symbol_ref "TARGET_XTHEADVECTOR ? riscv_vector::LMUL_1 : riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4QI,RVVMF32BI") (symbol_ref "TARGET_XTHEADVECTOR ? riscv_vector::LMUL_1 : riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8QI,RVVMF64BI") (symbol_ref "TARGET_XTHEADVECTOR ? riscv_vector::LMUL_1 : riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM8HI") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4HI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2HI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM8BF") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4BF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2BF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM8HF") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4HF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2HF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM8SI") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4SI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2SI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM8SF") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4SF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2SF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM8DI") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4DI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2DI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM8DF") (symbol_ref "riscv_vector::LMUL_8")
(eq_attr "mode" "RVVM4DF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2DF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x8QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x8QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x8QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x8QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM1x7QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x7QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x7QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x7QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM1x6QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x6QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x6QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x6QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM1x5QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x5QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x5QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x5QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM2x4QI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x4QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x4QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x4QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM2x3QI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x3QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x3QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x3QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM4x2QI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2QI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2QI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x2QI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x2QI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVMF8x2QI") (symbol_ref "riscv_vector::LMUL_F8")
(eq_attr "mode" "RVVM1x8HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x8HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x8HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x7HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x7HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x7HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x6HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x6HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x6HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x5HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x5HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x5HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM2x4HI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x4HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x4HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM2x3HI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x3HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x3HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM4x2HI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2HI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2HI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x2HI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x2HI") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x8BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x8BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x8BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x7BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x7BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x7BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x6BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x6BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x6BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x5BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x5BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x5BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM2x4BF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x4BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x4BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM2x3BF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x3BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x3BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM4x2BF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2BF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2BF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x2BF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x2BF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x8HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x8HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x8HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x7HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x7HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x7HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x6HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x6HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x6HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x5HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x5HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x5HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM2x4HF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x4HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x4HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM2x3HF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x3HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x3HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM4x2HF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2HF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2HF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x2HF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVMF4x2HF") (symbol_ref "riscv_vector::LMUL_F4")
(eq_attr "mode" "RVVM1x8SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x8SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x7SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x7SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x6SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x6SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x5SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x5SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM2x4SI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x4SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM2x3SI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x3SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM4x2SI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2SI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2SI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x2SI") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x8SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x8SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x7SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x7SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x6SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x6SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x5SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x5SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM2x4SF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x4SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM2x3SF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x3SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM4x2SF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2SF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2SF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVMF2x2SF") (symbol_ref "riscv_vector::LMUL_F2")
(eq_attr "mode" "RVVM1x8DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x7DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x6DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x5DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM2x4DI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM2x3DI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM4x2DI") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2DI") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2DI") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x8DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x7DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x6DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM1x5DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM2x4DF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x4DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM2x3DF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x3DF") (symbol_ref "riscv_vector::LMUL_1")
(eq_attr "mode" "RVVM4x2DF") (symbol_ref "riscv_vector::LMUL_4")
(eq_attr "mode" "RVVM2x2DF") (symbol_ref "riscv_vector::LMUL_2")
(eq_attr "mode" "RVVM1x2DF") (symbol_ref "riscv_vector::LMUL_1")
;; VLS modes.
(eq_attr "mode" "V1QI,V1BI") (symbol_ref "riscv_vector::get_vlmul(E_V1QImode)")
(eq_attr "mode" "V2QI,V2BI") (symbol_ref "riscv_vector::get_vlmul(E_V2QImode)")
(eq_attr "mode" "V4QI,V4BI") (symbol_ref "riscv_vector::get_vlmul(E_V4QImode)")
(eq_attr "mode" "V8QI,V8BI") (symbol_ref "riscv_vector::get_vlmul(E_V8QImode)")
(eq_attr "mode" "V16QI,V16BI") (symbol_ref "riscv_vector::get_vlmul(E_V16QImode)")
(eq_attr "mode" "V32QI,V32BI") (symbol_ref "riscv_vector::get_vlmul(E_V32QImode)")
(eq_attr "mode" "V64QI,V64BI") (symbol_ref "riscv_vector::get_vlmul(E_V64QImode)")
(eq_attr "mode" "V128QI,V128BI") (symbol_ref "riscv_vector::get_vlmul(E_V128QImode)")
(eq_attr "mode" "V256QI,V256BI") (symbol_ref "riscv_vector::get_vlmul(E_V256QImode)")
(eq_attr "mode" "V512QI,V512BI") (symbol_ref "riscv_vector::get_vlmul(E_V512QImode)")
(eq_attr "mode" "V1024QI,V1024BI") (symbol_ref "riscv_vector::get_vlmul(E_V1024QImode)")
(eq_attr "mode" "V2048QI,V2048BI") (symbol_ref "riscv_vector::get_vlmul(E_V2048QImode)")
(eq_attr "mode" "V4096QI,V4096BI") (symbol_ref "riscv_vector::get_vlmul(E_V4096QImode)")
(eq_attr "mode" "V1HI") (symbol_ref "riscv_vector::get_vlmul(E_V1HImode)")
(eq_attr "mode" "V2HI") (symbol_ref "riscv_vector::get_vlmul(E_V2HImode)")
(eq_attr "mode" "V4HI") (symbol_ref "riscv_vector::get_vlmul(E_V4HImode)")
(eq_attr "mode" "V8HI") (symbol_ref "riscv_vector::get_vlmul(E_V8HImode)")
(eq_attr "mode" "V16HI") (symbol_ref "riscv_vector::get_vlmul(E_V16HImode)")
(eq_attr "mode" "V32HI") (symbol_ref "riscv_vector::get_vlmul(E_V32HImode)")
(eq_attr "mode" "V64HI") (symbol_ref "riscv_vector::get_vlmul(E_V64HImode)")
(eq_attr "mode" "V128HI") (symbol_ref "riscv_vector::get_vlmul(E_V128HImode)")
(eq_attr "mode" "V256HI") (symbol_ref "riscv_vector::get_vlmul(E_V256HImode)")
(eq_attr "mode" "V512HI") (symbol_ref "riscv_vector::get_vlmul(E_V512HImode)")
(eq_attr "mode" "V1024HI") (symbol_ref "riscv_vector::get_vlmul(E_V1024HImode)")
(eq_attr "mode" "V2048HI") (symbol_ref "riscv_vector::get_vlmul(E_V2048HImode)")
(eq_attr "mode" "V1SI") (symbol_ref "riscv_vector::get_vlmul(E_V1SImode)")
(eq_attr "mode" "V2SI") (symbol_ref "riscv_vector::get_vlmul(E_V2SImode)")
(eq_attr "mode" "V4SI") (symbol_ref "riscv_vector::get_vlmul(E_V4SImode)")
(eq_attr "mode" "V8SI") (symbol_ref "riscv_vector::get_vlmul(E_V8SImode)")
(eq_attr "mode" "V16SI") (symbol_ref "riscv_vector::get_vlmul(E_V16SImode)")
(eq_attr "mode" "V32SI") (symbol_ref "riscv_vector::get_vlmul(E_V32SImode)")
(eq_attr "mode" "V64SI") (symbol_ref "riscv_vector::get_vlmul(E_V64SImode)")
(eq_attr "mode" "V128SI") (symbol_ref "riscv_vector::get_vlmul(E_V128SImode)")
(eq_attr "mode" "V256SI") (symbol_ref "riscv_vector::get_vlmul(E_V256SImode)")
(eq_attr "mode" "V512SI") (symbol_ref "riscv_vector::get_vlmul(E_V512SImode)")
(eq_attr "mode" "V1024SI") (symbol_ref "riscv_vector::get_vlmul(E_V1024SImode)")
(eq_attr "mode" "V1DI") (symbol_ref "riscv_vector::get_vlmul(E_V1DImode)")
(eq_attr "mode" "V2DI") (symbol_ref "riscv_vector::get_vlmul(E_V2DImode)")
(eq_attr "mode" "V4DI") (symbol_ref "riscv_vector::get_vlmul(E_V4DImode)")
(eq_attr "mode" "V8DI") (symbol_ref "riscv_vector::get_vlmul(E_V8DImode)")
(eq_attr "mode" "V16DI") (symbol_ref "riscv_vector::get_vlmul(E_V16DImode)")
(eq_attr "mode" "V32DI") (symbol_ref "riscv_vector::get_vlmul(E_V32DImode)")
(eq_attr "mode" "V64DI") (symbol_ref "riscv_vector::get_vlmul(E_V64DImode)")
(eq_attr "mode" "V128DI") (symbol_ref "riscv_vector::get_vlmul(E_V128DImode)")
(eq_attr "mode" "V256DI") (symbol_ref "riscv_vector::get_vlmul(E_V256DImode)")
(eq_attr "mode" "V512DI") (symbol_ref "riscv_vector::get_vlmul(E_V512DImode)")
(eq_attr "mode" "V1HF") (symbol_ref "riscv_vector::get_vlmul(E_V1HFmode)")
(eq_attr "mode" "V2HF") (symbol_ref "riscv_vector::get_vlmul(E_V2HFmode)")
(eq_attr "mode" "V4HF") (symbol_ref "riscv_vector::get_vlmul(E_V4HFmode)")
(eq_attr "mode" "V8HF") (symbol_ref "riscv_vector::get_vlmul(E_V8HFmode)")
(eq_attr "mode" "V16HF") (symbol_ref "riscv_vector::get_vlmul(E_V16HFmode)")
(eq_attr "mode" "V32HF") (symbol_ref "riscv_vector::get_vlmul(E_V32HFmode)")
(eq_attr "mode" "V64HF") (symbol_ref "riscv_vector::get_vlmul(E_V64HFmode)")
(eq_attr "mode" "V128HF") (symbol_ref "riscv_vector::get_vlmul(E_V128HFmode)")
(eq_attr "mode" "V256HF") (symbol_ref "riscv_vector::get_vlmul(E_V256HFmode)")
(eq_attr "mode" "V512HF") (symbol_ref "riscv_vector::get_vlmul(E_V512HFmode)")
(eq_attr "mode" "V1024HF") (symbol_ref "riscv_vector::get_vlmul(E_V1024HFmode)")
(eq_attr "mode" "V2048HF") (symbol_ref "riscv_vector::get_vlmul(E_V2048HFmode)")
(eq_attr "mode" "V1BF") (symbol_ref "riscv_vector::get_vlmul(E_V1BFmode)")
(eq_attr "mode" "V2BF") (symbol_ref "riscv_vector::get_vlmul(E_V2BFmode)")
(eq_attr "mode" "V4BF") (symbol_ref "riscv_vector::get_vlmul(E_V4BFmode)")
(eq_attr "mode" "V8BF") (symbol_ref "riscv_vector::get_vlmul(E_V8BFmode)")
(eq_attr "mode" "V16BF") (symbol_ref "riscv_vector::get_vlmul(E_V16BFmode)")
(eq_attr "mode" "V32BF") (symbol_ref "riscv_vector::get_vlmul(E_V32BFmode)")
(eq_attr "mode" "V64BF") (symbol_ref "riscv_vector::get_vlmul(E_V64BFmode)")
(eq_attr "mode" "V128BF") (symbol_ref "riscv_vector::get_vlmul(E_V128BFmode)")
(eq_attr "mode" "V256BF") (symbol_ref "riscv_vector::get_vlmul(E_V256BFmode)")
(eq_attr "mode" "V512BF") (symbol_ref "riscv_vector::get_vlmul(E_V512BFmode)")
(eq_attr "mode" "V1024BF") (symbol_ref "riscv_vector::get_vlmul(E_V1024BFmode)")
(eq_attr "mode" "V2048BF") (symbol_ref "riscv_vector::get_vlmul(E_V2048BFmode)")
(eq_attr "mode" "V1SF") (symbol_ref "riscv_vector::get_vlmul(E_V1SFmode)")
(eq_attr "mode" "V2SF") (symbol_ref "riscv_vector::get_vlmul(E_V2SFmode)")
(eq_attr "mode" "V4SF") (symbol_ref "riscv_vector::get_vlmul(E_V4SFmode)")
(eq_attr "mode" "V8SF") (symbol_ref "riscv_vector::get_vlmul(E_V8SFmode)")
(eq_attr "mode" "V16SF") (symbol_ref "riscv_vector::get_vlmul(E_V16SFmode)")
(eq_attr "mode" "V32SF") (symbol_ref "riscv_vector::get_vlmul(E_V32SFmode)")
(eq_attr "mode" "V64SF") (symbol_ref "riscv_vector::get_vlmul(E_V64SFmode)")
(eq_attr "mode" "V128SF") (symbol_ref "riscv_vector::get_vlmul(E_V128SFmode)")
(eq_attr "mode" "V256SF") (symbol_ref "riscv_vector::get_vlmul(E_V256SFmode)")
(eq_attr "mode" "V512SF") (symbol_ref "riscv_vector::get_vlmul(E_V512SFmode)")
(eq_attr "mode" "V1024SF") (symbol_ref "riscv_vector::get_vlmul(E_V1024SFmode)")
(eq_attr "mode" "V1DF") (symbol_ref "riscv_vector::get_vlmul(E_V1DFmode)")
(eq_attr "mode" "V2DF") (symbol_ref "riscv_vector::get_vlmul(E_V2DFmode)")
(eq_attr "mode" "V4DF") (symbol_ref "riscv_vector::get_vlmul(E_V4DFmode)")
(eq_attr "mode" "V8DF") (symbol_ref "riscv_vector::get_vlmul(E_V8DFmode)")
(eq_attr "mode" "V16DF") (symbol_ref "riscv_vector::get_vlmul(E_V16DFmode)")
(eq_attr "mode" "V32DF") (symbol_ref "riscv_vector::get_vlmul(E_V32DFmode)")
(eq_attr "mode" "V64DF") (symbol_ref "riscv_vector::get_vlmul(E_V64DFmode)")
(eq_attr "mode" "V128DF") (symbol_ref "riscv_vector::get_vlmul(E_V128DFmode)")
(eq_attr "mode" "V256DF") (symbol_ref "riscv_vector::get_vlmul(E_V256DFmode)")
(eq_attr "mode" "V512DF") (symbol_ref "riscv_vector::get_vlmul(E_V512DFmode)")]
(const_int INVALID_ATTRIBUTE)))
;; It is valid for instruction that require sew/lmul ratio.
(define_attr "ratio" ""
(cond [(eq_attr "type" "vimov,vfmov,vldux,vldox,vstux,vstox,\
vialu,vshift,vicmp,vimul,vidiv,vsalu,\
vext,viwalu,viwmul,vicalu,vnshift,\
vimuladd,vimerge,vaalu,vsmul,vsshift,\
vnclip,viminmax,viwmuladd,\
vmiota,vmidx,vfalu,vfmul,vfminmax,vfdiv,\
vfwalu,vfwmul,vfsqrt,vfrecp,vfsgnj,vfcmp,\
vfmerge,vfcvtitof,vfcvtftoi,vfwcvtitof,\
vfwcvtftoi,vfwcvtftof,vfncvtitof,vfncvtftoi,\
vfncvtftof,vfmuladd,vfwmuladd,vfclass,vired,\
viwred,vfredu,vfredo,vfwredu,vfwredo,vimovvx,\
vimovxv,vfmovvf,vfmovfv,vslideup,vslidedown,\
vislide1up,vislide1down,vfslide1up,vfslide1down,\
vgather,vcompress,vlsegdux,vlsegdox,vssegtux,vssegtox,\
vandn,vbrev,vbrev8,vrev8,vcpop,vclz,vctz,vrol,vror,vwsll,\
vclmul,vclmulh,vghsh,vgmul,vaesef,vaesem,vaesdf,vaesdm,\
vaeskf1,vaeskf2,vaesz,vsha2ms,vsha2ch,vsha2cl,vsm4k,vsm4r,\
vsm3me,vsm3c,vfncvtbf16,vfwcvtbf16,vfwmaccbf16")
(const_int INVALID_ATTRIBUTE)
(and (eq_attr "type" "vlde,vste,vlds,vsts,vlsegde,vssegte,vlsegds,\
vssegts,vlsegdff,vssegtux,vlsegdox,vlsegdux")
(match_test "TARGET_XTHEADVECTOR"))
(const_int INVALID_ATTRIBUTE)
(eq_attr "mode" "RVVM8QI,RVVM1BI") (const_int 1)
(eq_attr "mode" "RVVM4QI,RVVMF2BI") (const_int 2)
(eq_attr "mode" "RVVM2QI,RVVMF4BI") (const_int 4)
(eq_attr "mode" "RVVM1QI,RVVMF8BI") (const_int 8)
(eq_attr "mode" "RVVMF2QI,RVVMF16BI") (const_int 16)
(eq_attr "mode" "RVVMF4QI,RVVMF32BI") (const_int 32)
(eq_attr "mode" "RVVMF8QI,RVVMF64BI") (const_int 64)
(eq_attr "mode" "RVVM8HI") (const_int 2)
(eq_attr "mode" "RVVM4HI") (const_int 4)
(eq_attr "mode" "RVVM2HI") (const_int 8)
(eq_attr "mode" "RVVM1HI") (const_int 16)
(eq_attr "mode" "RVVMF2HI") (const_int 32)
(eq_attr "mode" "RVVMF4HI") (const_int 64)
(eq_attr "mode" "RVVM8BF") (const_int 2)
(eq_attr "mode" "RVVM4BF") (const_int 4)
(eq_attr "mode" "RVVM2BF") (const_int 8)
(eq_attr "mode" "RVVM1BF") (const_int 16)
(eq_attr "mode" "RVVMF2BF") (const_int 32)
(eq_attr "mode" "RVVMF4BF") (const_int 64)
(eq_attr "mode" "RVVM8HF") (const_int 2)
(eq_attr "mode" "RVVM4HF") (const_int 4)
(eq_attr "mode" "RVVM2HF") (const_int 8)
(eq_attr "mode" "RVVM1HF") (const_int 16)
(eq_attr "mode" "RVVMF2HF") (const_int 32)
(eq_attr "mode" "RVVMF4HF") (const_int 64)
(eq_attr "mode" "RVVM8SI") (const_int 4)
(eq_attr "mode" "RVVM4SI") (const_int 8)
(eq_attr "mode" "RVVM2SI") (const_int 16)
(eq_attr "mode" "RVVM1SI") (const_int 32)
(eq_attr "mode" "RVVMF2SI") (const_int 64)
(eq_attr "mode" "RVVM8SF") (const_int 4)
(eq_attr "mode" "RVVM4SF") (const_int 8)
(eq_attr "mode" "RVVM2SF") (const_int 16)
(eq_attr "mode" "RVVM1SF") (const_int 32)
(eq_attr "mode" "RVVMF2SF") (const_int 64)
(eq_attr "mode" "RVVM8DI") (const_int 8)
(eq_attr "mode" "RVVM4DI") (const_int 16)
(eq_attr "mode" "RVVM2DI") (const_int 32)
(eq_attr "mode" "RVVM1DI") (const_int 64)
(eq_attr "mode" "RVVM8DF") (const_int 8)
(eq_attr "mode" "RVVM4DF") (const_int 16)
(eq_attr "mode" "RVVM2DF") (const_int 32)
(eq_attr "mode" "RVVM1DF") (const_int 64)
(eq_attr "mode" "RVVM1x8QI") (const_int 8)
(eq_attr "mode" "RVVMF2x8QI") (const_int 16)
(eq_attr "mode" "RVVMF4x8QI") (const_int 32)
(eq_attr "mode" "RVVMF8x8QI") (const_int 64)
(eq_attr "mode" "RVVM1x7QI") (const_int 8)
(eq_attr "mode" "RVVMF2x7QI") (const_int 16)
(eq_attr "mode" "RVVMF4x7QI") (const_int 32)
(eq_attr "mode" "RVVMF8x7QI") (const_int 64)
(eq_attr "mode" "RVVM1x6QI") (const_int 8)
(eq_attr "mode" "RVVMF2x6QI") (const_int 16)
(eq_attr "mode" "RVVMF4x6QI") (const_int 32)
(eq_attr "mode" "RVVMF8x6QI") (const_int 64)
(eq_attr "mode" "RVVM1x5QI") (const_int 8)
(eq_attr "mode" "RVVMF2x5QI") (const_int 16)
(eq_attr "mode" "RVVMF4x5QI") (const_int 32)
(eq_attr "mode" "RVVMF8x5QI") (const_int 64)
(eq_attr "mode" "RVVM2x4QI") (const_int 4)
(eq_attr "mode" "RVVM1x4QI") (const_int 8)
(eq_attr "mode" "RVVMF2x4QI") (const_int 16)
(eq_attr "mode" "RVVMF4x4QI") (const_int 32)
(eq_attr "mode" "RVVMF8x4QI") (const_int 64)
(eq_attr "mode" "RVVM2x3QI") (const_int 4)
(eq_attr "mode" "RVVM1x3QI") (const_int 8)
(eq_attr "mode" "RVVMF2x3QI") (const_int 16)
(eq_attr "mode" "RVVMF4x3QI") (const_int 32)
(eq_attr "mode" "RVVMF8x3QI") (const_int 64)
(eq_attr "mode" "RVVM4x2QI") (const_int 2)
(eq_attr "mode" "RVVM2x2QI") (const_int 4)
(eq_attr "mode" "RVVM1x2QI") (const_int 8)
(eq_attr "mode" "RVVMF2x2QI") (const_int 16)
(eq_attr "mode" "RVVMF4x2QI") (const_int 32)
(eq_attr "mode" "RVVMF8x2QI") (const_int 64)
(eq_attr "mode" "RVVM1x8HI") (const_int 16)
(eq_attr "mode" "RVVMF2x8HI") (const_int 32)
(eq_attr "mode" "RVVMF4x8HI") (const_int 64)
(eq_attr "mode" "RVVM1x7HI") (const_int 16)
(eq_attr "mode" "RVVMF2x7HI") (const_int 32)
(eq_attr "mode" "RVVMF4x7HI") (const_int 64)
(eq_attr "mode" "RVVM1x6HI") (const_int 16)
(eq_attr "mode" "RVVMF2x6HI") (const_int 32)
(eq_attr "mode" "RVVMF4x6HI") (const_int 64)
(eq_attr "mode" "RVVM1x5HI") (const_int 16)
(eq_attr "mode" "RVVMF2x5HI") (const_int 32)
(eq_attr "mode" "RVVMF4x5HI") (const_int 64)
(eq_attr "mode" "RVVM2x4HI") (const_int 8)
(eq_attr "mode" "RVVM1x4HI") (const_int 16)
(eq_attr "mode" "RVVMF2x4HI") (const_int 32)
(eq_attr "mode" "RVVMF4x4HI") (const_int 64)
(eq_attr "mode" "RVVM2x3HI") (const_int 8)
(eq_attr "mode" "RVVM1x3HI") (const_int 16)
(eq_attr "mode" "RVVMF2x3HI") (const_int 32)
(eq_attr "mode" "RVVMF4x3HI") (const_int 64)
(eq_attr "mode" "RVVM4x2HI") (const_int 4)
(eq_attr "mode" "RVVM2x2HI") (const_int 8)
(eq_attr "mode" "RVVM1x2HI") (const_int 16)
(eq_attr "mode" "RVVMF2x2HI") (const_int 32)
(eq_attr "mode" "RVVMF4x2HI") (const_int 64)
(eq_attr "mode" "RVVM1x8BF") (const_int 16)
(eq_attr "mode" "RVVMF2x8BF") (const_int 32)
(eq_attr "mode" "RVVMF4x8BF") (const_int 64)
(eq_attr "mode" "RVVM1x7BF") (const_int 16)
(eq_attr "mode" "RVVMF2x7BF") (const_int 32)
(eq_attr "mode" "RVVMF4x7BF") (const_int 64)
(eq_attr "mode" "RVVM1x6BF") (const_int 16)
(eq_attr "mode" "RVVMF2x6BF") (const_int 32)
(eq_attr "mode" "RVVMF4x6BF") (const_int 64)
(eq_attr "mode" "RVVM1x5BF") (const_int 16)
(eq_attr "mode" "RVVMF2x5BF") (const_int 32)
(eq_attr "mode" "RVVMF4x5BF") (const_int 64)
(eq_attr "mode" "RVVM2x4BF") (const_int 8)
(eq_attr "mode" "RVVM1x4BF") (const_int 16)
(eq_attr "mode" "RVVMF2x4BF") (const_int 32)
(eq_attr "mode" "RVVMF4x4BF") (const_int 64)
(eq_attr "mode" "RVVM2x3BF") (const_int 8)
(eq_attr "mode" "RVVM1x3BF") (const_int 16)
(eq_attr "mode" "RVVMF2x3BF") (const_int 32)
(eq_attr "mode" "RVVMF4x3BF") (const_int 64)
(eq_attr "mode" "RVVM4x2BF") (const_int 4)
(eq_attr "mode" "RVVM2x2BF") (const_int 8)
(eq_attr "mode" "RVVM1x2BF") (const_int 16)
(eq_attr "mode" "RVVMF2x2BF") (const_int 32)
(eq_attr "mode" "RVVMF4x2BF") (const_int 64)
(eq_attr "mode" "RVVM1x8HF") (const_int 16)
(eq_attr "mode" "RVVMF2x8HF") (const_int 32)
(eq_attr "mode" "RVVMF4x8HF") (const_int 64)
(eq_attr "mode" "RVVM1x7HF") (const_int 16)
(eq_attr "mode" "RVVMF2x7HF") (const_int 32)
(eq_attr "mode" "RVVMF4x7HF") (const_int 64)
(eq_attr "mode" "RVVM1x6HF") (const_int 16)
(eq_attr "mode" "RVVMF2x6HF") (const_int 32)
(eq_attr "mode" "RVVMF4x6HF") (const_int 64)
(eq_attr "mode" "RVVM1x5HF") (const_int 16)
(eq_attr "mode" "RVVMF2x5HF") (const_int 32)
(eq_attr "mode" "RVVMF4x5HF") (const_int 64)
(eq_attr "mode" "RVVM2x4HF") (const_int 8)
(eq_attr "mode" "RVVM1x4HF") (const_int 16)
(eq_attr "mode" "RVVMF2x4HF") (const_int 32)
(eq_attr "mode" "RVVMF4x4HF") (const_int 64)
(eq_attr "mode" "RVVM2x3HF") (const_int 8)
(eq_attr "mode" "RVVM1x3HF") (const_int 16)
(eq_attr "mode" "RVVMF2x3HF") (const_int 32)
(eq_attr "mode" "RVVMF4x3HF") (const_int 64)
(eq_attr "mode" "RVVM4x2HF") (const_int 4)
(eq_attr "mode" "RVVM2x2HF") (const_int 8)
(eq_attr "mode" "RVVM1x2HF") (const_int 16)
(eq_attr "mode" "RVVMF2x2HF") (const_int 32)
(eq_attr "mode" "RVVMF4x2HF") (const_int 64)
(eq_attr "mode" "RVVM1x8SI") (const_int 32)
(eq_attr "mode" "RVVMF2x8SI") (const_int 64)
(eq_attr "mode" "RVVM1x7SI") (const_int 32)
(eq_attr "mode" "RVVMF2x7SI") (const_int 64)
(eq_attr "mode" "RVVM1x6SI") (const_int 32)
(eq_attr "mode" "RVVMF2x6SI") (const_int 64)
(eq_attr "mode" "RVVM1x5SI") (const_int 32)
(eq_attr "mode" "RVVMF2x5SI") (const_int 64)
(eq_attr "mode" "RVVM2x4SI") (const_int 16)
(eq_attr "mode" "RVVM1x4SI") (const_int 32)
(eq_attr "mode" "RVVMF2x4SI") (const_int 64)
(eq_attr "mode" "RVVM2x3SI") (const_int 16)
(eq_attr "mode" "RVVM1x3SI") (const_int 32)
(eq_attr "mode" "RVVMF2x3SI") (const_int 64)
(eq_attr "mode" "RVVM4x2SI") (const_int 8)
(eq_attr "mode" "RVVM2x2SI") (const_int 16)
(eq_attr "mode" "RVVM1x2SI") (const_int 32)
(eq_attr "mode" "RVVMF2x2SI") (const_int 64)
(eq_attr "mode" "RVVM1x8SF") (const_int 32)
(eq_attr "mode" "RVVMF2x8SF") (const_int 64)
(eq_attr "mode" "RVVM1x7SF") (const_int 32)
(eq_attr "mode" "RVVMF2x7SF") (const_int 64)
(eq_attr "mode" "RVVM1x6SF") (const_int 32)
(eq_attr "mode" "RVVMF2x6SF") (const_int 64)
(eq_attr "mode" "RVVM1x5SF") (const_int 32)
(eq_attr "mode" "RVVMF2x5SF") (const_int 64)
(eq_attr "mode" "RVVM2x4SF") (const_int 16)
(eq_attr "mode" "RVVM1x4SF") (const_int 32)
(eq_attr "mode" "RVVMF2x4SF") (const_int 64)
(eq_attr "mode" "RVVM2x3SF") (const_int 16)
(eq_attr "mode" "RVVM1x3SF") (const_int 32)
(eq_attr "mode" "RVVMF2x3SF") (const_int 64)
(eq_attr "mode" "RVVM4x2SF") (const_int 8)
(eq_attr "mode" "RVVM2x2SF") (const_int 16)
(eq_attr "mode" "RVVM1x2SF") (const_int 32)
(eq_attr "mode" "RVVMF2x2SF") (const_int 64)
(eq_attr "mode" "RVVM1x8DI") (const_int 64)
(eq_attr "mode" "RVVM1x7DI") (const_int 64)
(eq_attr "mode" "RVVM1x6DI") (const_int 64)
(eq_attr "mode" "RVVM1x5DI") (const_int 64)
(eq_attr "mode" "RVVM2x4DI") (const_int 32)
(eq_attr "mode" "RVVM1x4DI") (const_int 64)
(eq_attr "mode" "RVVM2x3DI") (const_int 32)
(eq_attr "mode" "RVVM1x3DI") (const_int 64)
(eq_attr "mode" "RVVM4x2DI") (const_int 16)
(eq_attr "mode" "RVVM2x2DI") (const_int 32)
(eq_attr "mode" "RVVM1x2DI") (const_int 64)
(eq_attr "mode" "RVVM1x8DF") (const_int 64)
(eq_attr "mode" "RVVM1x7DF") (const_int 64)
(eq_attr "mode" "RVVM1x6DF") (const_int 64)
(eq_attr "mode" "RVVM1x5DF") (const_int 64)
(eq_attr "mode" "RVVM2x4DF") (const_int 32)
(eq_attr "mode" "RVVM1x4DF") (const_int 64)
(eq_attr "mode" "RVVM2x3DF") (const_int 32)
(eq_attr "mode" "RVVM1x3DF") (const_int 64)
(eq_attr "mode" "RVVM4x2DF") (const_int 16)
(eq_attr "mode" "RVVM2x2DF") (const_int 32)
(eq_attr "mode" "RVVM1x2DF") (const_int 64)
;; VLS modes.
(eq_attr "mode" "V1QI,V1BI") (symbol_ref "riscv_vector::get_ratio(E_V1QImode)")
(eq_attr "mode" "V2QI,V2BI") (symbol_ref "riscv_vector::get_ratio(E_V2QImode)")
(eq_attr "mode" "V4QI,V4BI") (symbol_ref "riscv_vector::get_ratio(E_V4QImode)")
(eq_attr "mode" "V8QI,V8BI") (symbol_ref "riscv_vector::get_ratio(E_V8QImode)")
(eq_attr "mode" "V16QI,V16BI") (symbol_ref "riscv_vector::get_ratio(E_V16QImode)")
(eq_attr "mode" "V32QI,V32BI") (symbol_ref "riscv_vector::get_ratio(E_V32QImode)")
(eq_attr "mode" "V64QI,V64BI") (symbol_ref "riscv_vector::get_ratio(E_V64QImode)")
(eq_attr "mode" "V128QI,V128BI") (symbol_ref "riscv_vector::get_ratio(E_V128QImode)")
(eq_attr "mode" "V256QI,V256BI") (symbol_ref "riscv_vector::get_ratio(E_V256QImode)")
(eq_attr "mode" "V512QI,V512BI") (symbol_ref "riscv_vector::get_ratio(E_V512QImode)")
(eq_attr "mode" "V1024QI,V1024BI") (symbol_ref "riscv_vector::get_ratio(E_V1024QImode)")
(eq_attr "mode" "V2048QI,V2048BI") (symbol_ref "riscv_vector::get_ratio(E_V2048QImode)")
(eq_attr "mode" "V4096QI,V4096BI") (symbol_ref "riscv_vector::get_ratio(E_V4096QImode)")
(eq_attr "mode" "V1HI") (symbol_ref "riscv_vector::get_ratio(E_V1HImode)")
(eq_attr "mode" "V2HI") (symbol_ref "riscv_vector::get_ratio(E_V2HImode)")
(eq_attr "mode" "V4HI") (symbol_ref "riscv_vector::get_ratio(E_V4HImode)")
(eq_attr "mode" "V8HI") (symbol_ref "riscv_vector::get_ratio(E_V8HImode)")
(eq_attr "mode" "V16HI") (symbol_ref "riscv_vector::get_ratio(E_V16HImode)")
(eq_attr "mode" "V32HI") (symbol_ref "riscv_vector::get_ratio(E_V32HImode)")
(eq_attr "mode" "V64HI") (symbol_ref "riscv_vector::get_ratio(E_V64HImode)")
(eq_attr "mode" "V128HI") (symbol_ref "riscv_vector::get_ratio(E_V128HImode)")
(eq_attr "mode" "V256HI") (symbol_ref "riscv_vector::get_ratio(E_V256HImode)")
(eq_attr "mode" "V512HI") (symbol_ref "riscv_vector::get_ratio(E_V512HImode)")
(eq_attr "mode" "V1024HI") (symbol_ref "riscv_vector::get_ratio(E_V1024HImode)")
(eq_attr "mode" "V2048HI") (symbol_ref "riscv_vector::get_ratio(E_V2048HImode)")
(eq_attr "mode" "V1SI") (symbol_ref "riscv_vector::get_ratio(E_V1SImode)")
(eq_attr "mode" "V2SI") (symbol_ref "riscv_vector::get_ratio(E_V2SImode)")
(eq_attr "mode" "V4SI") (symbol_ref "riscv_vector::get_ratio(E_V4SImode)")
(eq_attr "mode" "V8SI") (symbol_ref "riscv_vector::get_ratio(E_V8SImode)")
(eq_attr "mode" "V16SI") (symbol_ref "riscv_vector::get_ratio(E_V16SImode)")
(eq_attr "mode" "V32SI") (symbol_ref "riscv_vector::get_ratio(E_V32SImode)")
(eq_attr "mode" "V64SI") (symbol_ref "riscv_vector::get_ratio(E_V64SImode)")
(eq_attr "mode" "V128SI") (symbol_ref "riscv_vector::get_ratio(E_V128SImode)")
(eq_attr "mode" "V256SI") (symbol_ref "riscv_vector::get_ratio(E_V256SImode)")
(eq_attr "mode" "V512SI") (symbol_ref "riscv_vector::get_ratio(E_V512SImode)")
(eq_attr "mode" "V1024SI") (symbol_ref "riscv_vector::get_ratio(E_V1024SImode)")
(eq_attr "mode" "V1DI") (symbol_ref "riscv_vector::get_ratio(E_V1DImode)")
(eq_attr "mode" "V2DI") (symbol_ref "riscv_vector::get_ratio(E_V2DImode)")
(eq_attr "mode" "V4DI") (symbol_ref "riscv_vector::get_ratio(E_V4DImode)")
(eq_attr "mode" "V8DI") (symbol_ref "riscv_vector::get_ratio(E_V8DImode)")
(eq_attr "mode" "V16DI") (symbol_ref "riscv_vector::get_ratio(E_V16DImode)")
(eq_attr "mode" "V32DI") (symbol_ref "riscv_vector::get_ratio(E_V32DImode)")
(eq_attr "mode" "V64DI") (symbol_ref "riscv_vector::get_ratio(E_V64DImode)")
(eq_attr "mode" "V128DI") (symbol_ref "riscv_vector::get_ratio(E_V128DImode)")
(eq_attr "mode" "V256DI") (symbol_ref "riscv_vector::get_ratio(E_V256DImode)")
(eq_attr "mode" "V512DI") (symbol_ref "riscv_vector::get_ratio(E_V512DImode)")
(eq_attr "mode" "V1HF") (symbol_ref "riscv_vector::get_ratio(E_V1HFmode)")
(eq_attr "mode" "V2HF") (symbol_ref "riscv_vector::get_ratio(E_V2HFmode)")
(eq_attr "mode" "V4HF") (symbol_ref "riscv_vector::get_ratio(E_V4HFmode)")
(eq_attr "mode" "V8HF") (symbol_ref "riscv_vector::get_ratio(E_V8HFmode)")
(eq_attr "mode" "V16HF") (symbol_ref "riscv_vector::get_ratio(E_V16HFmode)")
(eq_attr "mode" "V32HF") (symbol_ref "riscv_vector::get_ratio(E_V32HFmode)")
(eq_attr "mode" "V64HF") (symbol_ref "riscv_vector::get_ratio(E_V64HFmode)")
(eq_attr "mode" "V128HF") (symbol_ref "riscv_vector::get_ratio(E_V128HFmode)")
(eq_attr "mode" "V256HF") (symbol_ref "riscv_vector::get_ratio(E_V256HFmode)")
(eq_attr "mode" "V512HF") (symbol_ref "riscv_vector::get_ratio(E_V512HFmode)")
(eq_attr "mode" "V1024HF") (symbol_ref "riscv_vector::get_ratio(E_V1024HFmode)")
(eq_attr "mode" "V2048HF") (symbol_ref "riscv_vector::get_ratio(E_V2048HFmode)")
(eq_attr "mode" "V1BF") (symbol_ref "riscv_vector::get_ratio(E_V1BFmode)")
(eq_attr "mode" "V2BF") (symbol_ref "riscv_vector::get_ratio(E_V2BFmode)")
(eq_attr "mode" "V4BF") (symbol_ref "riscv_vector::get_ratio(E_V4BFmode)")
(eq_attr "mode" "V8BF") (symbol_ref "riscv_vector::get_ratio(E_V8BFmode)")
(eq_attr "mode" "V16BF") (symbol_ref "riscv_vector::get_ratio(E_V16BFmode)")
(eq_attr "mode" "V32BF") (symbol_ref "riscv_vector::get_ratio(E_V32BFmode)")
(eq_attr "mode" "V64BF") (symbol_ref "riscv_vector::get_ratio(E_V64BFmode)")
(eq_attr "mode" "V128BF") (symbol_ref "riscv_vector::get_ratio(E_V128BFmode)")
(eq_attr "mode" "V256BF") (symbol_ref "riscv_vector::get_ratio(E_V256BFmode)")
(eq_attr "mode" "V512BF") (symbol_ref "riscv_vector::get_ratio(E_V512BFmode)")
(eq_attr "mode" "V1024BF") (symbol_ref "riscv_vector::get_ratio(E_V1024BFmode)")
(eq_attr "mode" "V2048BF") (symbol_ref "riscv_vector::get_ratio(E_V2048BFmode)")
(eq_attr "mode" "V1SF") (symbol_ref "riscv_vector::get_ratio(E_V1SFmode)")
(eq_attr "mode" "V2SF") (symbol_ref "riscv_vector::get_ratio(E_V2SFmode)")
(eq_attr "mode" "V4SF") (symbol_ref "riscv_vector::get_ratio(E_V4SFmode)")
(eq_attr "mode" "V8SF") (symbol_ref "riscv_vector::get_ratio(E_V8SFmode)")
(eq_attr "mode" "V16SF") (symbol_ref "riscv_vector::get_ratio(E_V16SFmode)")
(eq_attr "mode" "V32SF") (symbol_ref "riscv_vector::get_ratio(E_V32SFmode)")
(eq_attr "mode" "V64SF") (symbol_ref "riscv_vector::get_ratio(E_V64SFmode)")
(eq_attr "mode" "V128SF") (symbol_ref "riscv_vector::get_ratio(E_V128SFmode)")
(eq_attr "mode" "V256SF") (symbol_ref "riscv_vector::get_ratio(E_V256SFmode)")
(eq_attr "mode" "V512SF") (symbol_ref "riscv_vector::get_ratio(E_V512SFmode)")
(eq_attr "mode" "V1024SF") (symbol_ref "riscv_vector::get_ratio(E_V1024SFmode)")
(eq_attr "mode" "V1DF") (symbol_ref "riscv_vector::get_ratio(E_V1DFmode)")
(eq_attr "mode" "V2DF") (symbol_ref "riscv_vector::get_ratio(E_V2DFmode)")
(eq_attr "mode" "V4DF") (symbol_ref "riscv_vector::get_ratio(E_V4DFmode)")
(eq_attr "mode" "V8DF") (symbol_ref "riscv_vector::get_ratio(E_V8DFmode)")
(eq_attr "mode" "V16DF") (symbol_ref "riscv_vector::get_ratio(E_V16DFmode)")
(eq_attr "mode" "V32DF") (symbol_ref "riscv_vector::get_ratio(E_V32DFmode)")
(eq_attr "mode" "V64DF") (symbol_ref "riscv_vector::get_ratio(E_V64DFmode)")
(eq_attr "mode" "V128DF") (symbol_ref "riscv_vector::get_ratio(E_V128DFmode)")
(eq_attr "mode" "V256DF") (symbol_ref "riscv_vector::get_ratio(E_V256DFmode)")
(eq_attr "mode" "V512DF") (symbol_ref "riscv_vector::get_ratio(E_V512DFmode)")]
(const_int INVALID_ATTRIBUTE)))
;; The index of operand[] to get the merge op.
(define_attr "merge_op_idx" ""
(cond [(eq_attr "type" "vlde,vimov,vfmov,vldm,vlds,vmalu,vldux,vldox,vicmp,\
vialu,vshift,viminmax,vimul,vidiv,vsalu,vext,viwalu,\
viwmul,vnshift,vaalu,vsmul,vsshift,vnclip,vmsfs,\
vmiota,vmidx,vfalu,vfmul,vfminmax,vfdiv,vfwalu,vfwmul,\
vfsqrt,vfrecp,vfsgnj,vfcmp,vfcvtitof,vfcvtftoi,vfwcvtitof,\
vfwcvtftoi,vfwcvtftof,vfncvtitof,vfncvtftoi,vfncvtftof,vfclass,\
vired,viwred,vfredu,vfredo,vfwredu,vfwredo,vimovxv,vfmovfv,\
vslideup,vslidedown,vislide1up,vislide1down,vfslide1up,vfslide1down,\
vgather,vldff,viwmuladd,vfwmuladd,vlsegde,vlsegds,vlsegdux,vlsegdox,vlsegdff,\
vandn,vbrev,vbrev8,vrev8,vrol,vror,vwsll,vclmul,vclmulh,\
vfncvtbf16,vfwcvtbf16,vfwmaccbf16")
(const_int 2)
(eq_attr "type" "vimerge,vfmerge,vcompress,vghsh,vgmul,vaesef,vaesem,vaesdf,vaesdm,\
vaeskf1,vaeskf2,vaesz,vsha2ms,vsha2ch,vsha2cl,vsm4k,vsm4r,vsm3me,vsm3c")
(const_int 1)
(eq_attr "type" "vimuladd,vfmuladd")
(const_int 2)]
(const_int INVALID_ATTRIBUTE)))
;; The index of operand[] represents the machine mode of the instruction.
(define_attr "mode_idx" ""
(cond [(eq_attr "type" "vlde,vste,vldm,vstm,vlds,vsts,vldux,vldox,vldff,vldr,vstr,\
vlsegde,vlsegds,vlsegdux,vlsegdox,vlsegdff,vialu,vext,vicalu,\
vshift,vicmp,viminmax,vimul,vidiv,vimuladd,vimerge,vimov,\
vsalu,vaalu,vsmul,vsshift,vfalu,vfmul,vfdiv,vfmuladd,vfsqrt,vfrecp,\
vfcmp,vfminmax,vfsgnj,vfclass,vfmerge,vfmov,\
vfcvtitof,vfncvtitof,vfncvtftoi,vfncvtftof,vmalu,vmiota,vmidx,\
vimovxv,vfmovfv,vslideup,vslidedown,vislide1up,vislide1down,vfslide1up,vfslide1down,\
vgather,vcompress,vmov,vnclip,vnshift,vandn,vcpop,vclz,vctz,vrol,vror")
(const_int 0)
(eq_attr "type" "vimovvx,vfmovvf")
(const_int 1)
(eq_attr "type" "vssegte,vmpop,vmffs")
(const_int 2)
(eq_attr "type" "vstux,vstox,vssegts,vssegtux,vssegtox,vfcvtftoi,vfwcvtitof,vfwcvtftoi,
vfwcvtftof,vmsfs,vired,viwred,vfredu,vfredo,vfwredu,vfwredo,vwsll")
(const_int 3)
(eq_attr "type" "viwalu,viwmul,viwmuladd,vfwalu,vfwmul,vfwmuladd")
(const_int 4)]
(const_int INVALID_ATTRIBUTE)))
;; The index of operand[] to get the avl op.
(define_attr "vl_op_idx" ""
(cond [(eq_attr "type" "vlde,vste,vimov,vfmov,vldm,vstm,vmalu,vsts,vstux,\
vstox,vext,vmsfs,vmiota,vfsqrt,vfrecp,vfcvtitof,vldff,\
vfcvtftoi,vfwcvtitof,vfwcvtftoi,vfwcvtftof,vfncvtitof,\
vfncvtftoi,vfncvtftof,vfclass,vimovxv,vfmovfv,vcompress,\
vlsegde,vssegts,vssegtux,vssegtox,vlsegdff,vbrev,vbrev8,vrev8,\
vghsh,vaeskf1,vaeskf2,vsha2ms,vsha2ch,vsha2cl,vsm4k,vsm3me,vsm3c,\
vfncvtbf16,vfwcvtbf16")
(const_int 4)
;; If operands[3] of "vlds" is not vector mode, it is pred_broadcast.
;; whereas it is pred_strided_load if operands[3] is vector mode.
(eq_attr "type" "vlds")
(if_then_else (match_test "VECTOR_MODE_P (GET_MODE (operands[3]))")
(const_int 5)
(const_int 4))
(eq_attr "type" "vldux,vldox,vialu,vshift,viminmax,vimul,vidiv,vsalu,\
viwalu,viwmul,vnshift,vimerge,vaalu,vsmul,\
vsshift,vnclip,vfalu,vfmul,vfminmax,vfdiv,vfwalu,vfwmul,\
vfsgnj,vfmerge,vired,viwred,vfredu,vfredo,vfwredu,vfwredo,\
vslideup,vslidedown,vislide1up,vislide1down,vfslide1up,vfslide1down,\
vgather,viwmuladd,vfwmuladd,vlsegds,vlsegdux,vlsegdox,vandn,vrol,\
vror,vwsll,vclmul,vclmulh,vfwmaccbf16")
(const_int 5)
(eq_attr "type" "vicmp,vimuladd,vfcmp,vfmuladd")
(const_int 6)
(eq_attr "type" "vmpop,vmffs,vmidx,vssegte,vcpop,vclz,vctz,vgmul,vaesef,vaesem,vaesdf,\
vaesdm,vaesz,vsm4r")
(const_int 3)]
(const_int INVALID_ATTRIBUTE)))
;; The tail policy op value.
(define_attr "ta" ""
(cond [(eq_attr "type" "vlde,vimov,vfmov,vext,vmiota,vfsqrt,vfrecp,\
vfcvtitof,vfcvtftoi,vfwcvtitof,vfwcvtftoi,vfwcvtftof,\
vfncvtitof,vfncvtftoi,vfncvtftof,vfclass,vimovxv,vfmovfv,\
vcompress,vldff,vlsegde,vlsegdff,vbrev,vbrev8,vrev8,vghsh,\
vaeskf1,vaeskf2,vsha2ms,vsha2ch,vsha2cl,vsm4k,vsm3me,vsm3c,\
vfncvtbf16,vfwcvtbf16")
(symbol_ref "riscv_vector::get_ta(operands[5])")
;; If operands[3] of "vlds" is not vector mode, it is pred_broadcast.
;; whereas it is pred_strided_load if operands[3] is vector mode.
(eq_attr "type" "vlds")
(if_then_else (match_test "VECTOR_MODE_P (GET_MODE (operands[3]))")
(symbol_ref "riscv_vector::get_ta(operands[6])")
(symbol_ref "riscv_vector::get_ta(operands[5])"))
(eq_attr "type" "vldux,vldox,vialu,vshift,viminmax,vimul,vidiv,vsalu,\
viwalu,viwmul,vnshift,vimerge,vaalu,vsmul,\
vsshift,vnclip,vfalu,vfmul,vfminmax,vfdiv,\
vfwalu,vfwmul,vfsgnj,vfmerge,vired,viwred,vfredu,\
vfredo,vfwredu,vfwredo,vslideup,vslidedown,vislide1up,\
vislide1down,vfslide1up,vfslide1down,vgather,viwmuladd,vfwmuladd,\
vlsegds,vlsegdux,vlsegdox,vandn,vrol,vror,vwsll,vclmul,vclmulh,\
vfwmaccbf16,sf_vqmacc,sf_vfnrclip")
(symbol_ref "riscv_vector::get_ta(operands[6])")
(eq_attr "type" "vimuladd,vfmuladd")
(symbol_ref "riscv_vector::get_ta(operands[7])")
(eq_attr "type" "vmidx,vgmul,vaesef,vaesem,vaesdf,vaesdm,vaesz,vsm4r")
(symbol_ref "riscv_vector::get_ta(operands[4])")]
(const_int INVALID_ATTRIBUTE)))
;; The mask policy op value.
(define_attr "ma" ""
(cond [(eq_attr "type" "vlde,vext,vmiota,vfsqrt,vfrecp,vfcvtitof,vfcvtftoi,\
vfwcvtitof,vfwcvtftoi,vfwcvtftof,vfncvtitof,vfncvtftoi,\
vfncvtftof,vfclass,vldff,vlsegde,vlsegdff,vbrev,vbrev8,vrev8,\
vfncvtbf16,vfwcvtbf16")
(symbol_ref "riscv_vector::get_ma(operands[6])")
;; If operands[3] of "vlds" is not vector mode, it is pred_broadcast.
;; whereas it is pred_strided_load if operands[3] is vector mode.
(eq_attr "type" "vlds")
(if_then_else (match_test "VECTOR_MODE_P (GET_MODE (operands[3]))")
(symbol_ref "riscv_vector::get_ma(operands[7])")
(symbol_ref "riscv_vector::get_ma(operands[6])"))
(eq_attr "type" "vldux,vldox,vialu,vshift,viminmax,vimul,vidiv,vsalu,\
viwalu,viwmul,vnshift,vaalu,vsmul,vsshift,\
vnclip,vicmp,vfalu,vfmul,vfminmax,vfdiv,\
vfwalu,vfwmul,vfsgnj,vfcmp,vslideup,vslidedown,\
vislide1up,vislide1down,vfslide1up,vfslide1down,vgather,\
viwmuladd,vfwmuladd,vlsegds,vlsegdux,vlsegdox,vandn,vrol,\
vror,vwsll,vclmul,vclmulh,vfwmaccbf16,sf_vqmacc,sf_vfnrclip")
(symbol_ref "riscv_vector::get_ma(operands[7])")
(eq_attr "type" "vimuladd,vfmuladd")
(symbol_ref "riscv_vector::get_ma(operands[8])")
(eq_attr "type" "vmsfs,vmidx")
(symbol_ref "riscv_vector::get_ma(operands[5])")]
(const_int INVALID_ATTRIBUTE)))
;; The avl type value.
(define_attr "avl_type_idx" ""
(cond [(eq_attr "type" "vlde,vldff,vste,vimov,vfmov,vext,vimerge,\
vfsqrt,vfrecp,vfmerge,vfcvtitof,vfcvtftoi,vfwcvtitof,\
vfwcvtftoi,vfwcvtftof,vfncvtitof,vfncvtftoi,vfncvtftof,\
vfclass,vired,viwred,vfredu,vfredo,vfwredu,vfwredo,\
vimovxv,vfmovfv,vlsegde,vlsegdff,vmiota,vbrev,vbrev8,vrev8,\
vfncvtbf16,vfwcvtbf16")
(const_int 7)
(eq_attr "type" "vldm,vstm,vmalu,vmalu,vgmul,vaesef,vaesem,vaesdf,vaesdm,vaesz,\
vsm4r")
(const_int 5)
;; If operands[3] of "vlds" is not vector mode, it is pred_broadcast.
;; whereas it is pred_strided_load if operands[3] is vector mode.
(eq_attr "type" "vlds")
(if_then_else (match_test "VECTOR_MODE_P (GET_MODE (operands[3]))")
(const_int 8)
(const_int 7))
(eq_attr "type" "vldux,vldox,vialu,vshift,viminmax,vimul,vidiv,vsalu,\
viwalu,viwmul,vnshift,vaalu,vsmul,vsshift,\
vnclip,vicmp,vfalu,vfmul,vfminmax,vfdiv,vfwalu,vfwmul,\
vfsgnj,vfcmp,vslideup,vslidedown,vislide1up,\
vislide1down,vfslide1up,vfslide1down,vgather,viwmuladd,vfwmuladd,\
vlsegds,vlsegdux,vlsegdox,vandn,vrol,vror,vclmul,vclmulh,vwsll,\
vfwmaccbf16")
(const_int 8)
(eq_attr "type" "vstux,vstox,vssegts,vssegtux,vssegtox")
(const_int 5)
(eq_attr "type" "vimuladd,vfmuladd")
(const_int 9)
(eq_attr "type" "vmsfs,vmidx,vcompress,vghsh,vaeskf1,vaeskf2,vsha2ms,vsha2ch,vsha2cl,\
vsm4k,vsm3me,vsm3c")
(const_int 6)
(eq_attr "type" "vmpop,vmffs,vssegte,vcpop,vclz,vctz")
(const_int 4)]
(const_int INVALID_ATTRIBUTE)))
;; Defines rounding mode of an fixed-point operation.
(define_attr "vxrm_mode" "rnu,rne,rdn,rod,clobber,none"
(cond [(eq_attr "type" "vaalu,vsmul,vsshift,vnclip")
(cond
[(match_test "INTVAL (operands[9]) == riscv_vector::VXRM_RNU")
(const_string "rnu")
(match_test "INTVAL (operands[9]) == riscv_vector::VXRM_RNE")
(const_string "rne")
(match_test "INTVAL (operands[9]) == riscv_vector::VXRM_RDN")
(const_string "rdn")
(match_test "INTVAL (operands[9]) == riscv_vector::VXRM_ROD")
(const_string "rod")]
(const_string "none"))
(match_test "CALL_P (insn)")
(const_string "clobber")]
(const_string "none")))
;; Defines rounding mode of an floating-point operation.
(define_attr "frm_mode" ""
(cond [(eq_attr "type" "vfalu,vfwalu,vfmul,vfdiv,vfwmul")
(symbol_ref "riscv_vector::FRM_DYN")]
(symbol_ref "riscv_vector::FRM_NONE")))
(include "thead-vector.md")
;; -----------------------------------------------------------------
;; ---- Miscellaneous Operations
;; -----------------------------------------------------------------
(define_insn "@vundefined<mode>"
[(set (match_operand:V_VLS 0 "register_operand" "=vr")
(unspec:V_VLS [(reg:SI X0_REGNUM)] UNSPEC_VUNDEF))]
"TARGET_VECTOR"
""
[(set_attr "type" "vector")])
(define_insn "@vundefined<mode>"
[(set (match_operand:VB_VLS 0 "register_operand" "=vr")
(unspec:VB_VLS [(reg:SI X0_REGNUM)] UNSPEC_VUNDEF))]
"TARGET_VECTOR"
""
[(set_attr "type" "vector")])
(define_insn "@vundefined<mode>"
[(set (match_operand:VT 0 "register_operand" "=vr")
(unspec:VT [(reg:SI X0_REGNUM)] UNSPEC_VUNDEF))]
"TARGET_VECTOR"
""
[(set_attr "type" "vector")])
(define_expand "@vreinterpret<mode>"
[(set (match_operand:V_VLS 0 "register_operand")
(match_operand 1 "vector_any_register_operand"))]
"TARGET_VECTOR"
{
emit_move_insn (operands[0], gen_lowpart (<MODE>mode, operands[1]));
DONE;
}
)
(define_expand "@vreinterpret<mode>"
[(set (match_operand:VB 0 "register_operand")
(match_operand 1 "vector_any_register_operand"))]
"TARGET_VECTOR"
{
emit_move_insn (operands[0], gen_lowpart (<MODE>mode, operands[1]));
DONE;
}
)
;; This pattern is used to hold the AVL operand for
;; RVV instructions that implicitly use VLMAX AVL.
;; RVV instruction implicitly use GPR that is ultimately
;; defined by this pattern is safe for VSETVL pass emit
;; a vsetvl instruction modify this register after RA.
;; Case 1:
;; vlmax_avl a5
;; ... (across many blocks)
;; vadd (implicit use a5) ====> emit: vsetvl a5,zero
;; Case 2:
;; vlmax_avl a5
;; ... (across many blocks)
;; mv a6,a5
;; ... (across many blocks)
;; vadd (implicit use a6) ====> emit: vsetvl a6,zero
;; Case 3:
;; vlmax_avl a5
;; ... (across many blocks)
;; store mem,a5 (spill)
;; ... (across many blocks)
;; load a7,mem (spill)
;; ... (across many blocks)
;; vadd (implicit use a7) ====> emit: vsetvl a7,zero
;; Such cases are all safe for VSETVL PASS to emit a vsetvl
;; instruction that modifies the AVL operand.
(define_insn "@vlmax_avl<mode>"
[(set (match_operand:P 0 "register_operand" "=r")
(unspec:P [(match_operand:P 1 "const_int_operand" "i")] UNSPEC_VLMAX))]
"TARGET_VECTOR"
""
[(set_attr "type" "vsetvl_pre")]
)
;; Set VXRM
(define_insn "vxrmsi"
[(set (reg:SI VXRM_REGNUM)
(match_operand:SI 0 "const_int_operand" "i"))]
"TARGET_VECTOR"
"csrwi\tvxrm,%0"
[(set_attr "type" "wrvxrm")
(set_attr "mode" "SI")])
;; Set FRM
(define_insn "fsrmsi_backup"
[(set (match_operand:SI 0 "register_operand" "=r,r")
(reg:SI FRM_REGNUM))
(set (reg:SI FRM_REGNUM)
(match_operand:SI 1 "reg_or_int_operand" "r,i"))]
"TARGET_VECTOR"
"@
fsrm\t%0,%1
fsrmi\t%0,%1"
[(set_attr "type" "wrfrm,wrfrm")
(set_attr "mode" "SI")]
)
(define_insn "fsrmsi_restore"
[(set (reg:SI FRM_REGNUM)
(match_operand:SI 0 "reg_or_int_operand" "r,i"))]
"TARGET_VECTOR"
"@
fsrm\t%0
fsrmi\t%0"
[(set_attr "type" "wrfrm,wrfrm")
(set_attr "mode" "SI")]
)
;; Read FRM
(define_insn "frrmsi"
[(set (match_operand:SI 0 "register_operand" "=r")
(reg:SI FRM_REGNUM))]
"TARGET_VECTOR"
"frrm\t%0"
[(set_attr "type" "fmove")
(set_attr "mode" "SI")]
)
;; -----------------------------------------------------------------
;; ---- Moves Operations
;; -----------------------------------------------------------------
(define_expand "mov<mode>"
[(set (match_operand:V 0 "reg_or_mem_operand")
(match_operand:V 1 "general_operand"))]
"TARGET_VECTOR"
{
/* For whole register move, we transform the pattern into the format
that excludes the clobber of scratch register.
We include clobber of a scalar scratch register which is going to be
used for emit of vsetvl instruction after reload_completed since we
need vsetvl instruction to set VL/VTYPE global status for fractional
vector load/store.
For example:
[(set (match_operand:RVVMF8QI v24)
(match_operand:RVVMF8QI (mem: a4)))
(clobber (scratch:SI a5))]
====>> vsetvl a5,zero,e8,mf8
====>> vle8.v v24,(a4)
Philosophy:
- Clobber a scalar scratch register for each mov<mode>.
- Classify the machine_mode mode = <MODE>mode into 2 class:
Whole register move and fractional register move.
- Transform and remove scratch clobber register for whole
register move so that we can avoid occupying the scalar
registers.
- We can not leave it to TARGET_SECONDARY_RELOAD since it happens
before spilling. The clobber scratch is used by spilling fractional
registers in IRA/LRA so it's too early. */
if (TARGET_XTHEADVECTOR && reg_or_mem_operand (operands[1], <MODE>mode))
{
emit_insn (gen_pred_th_whole_mov (<MODE>mode, operands[0], operands[1],
RVV_VLMAX, GEN_INT(riscv_vector::VLMAX)));
DONE;
}
if (riscv_vector::legitimize_move (operands[0], &operands[1]))
DONE;
})
;; This pattern is used for code-gen for whole register load/stores.
;; Also applicable for all register moves.
;; Fractional vector modes load/store are not allowed to match this pattern.
;; Mask modes load/store are not allowed to match this pattern.
;; We separate "*mov<mode>" into "*mov<mode>_whole" and "*mov<mode>_fract" because
;; we don't want to include fractional load/store in "*mov<mode>" which will
;; create unexpected patterns in LRA.
;; For example:
;; ira rtl:
;; (insn 20 19 9 2 (set (reg/v:RVVMF4QI 97 v1 [ v1 ])
;; (reg:RVVMF4QI 134 [ _1 ])) "rvv.c":9:22 571 {*movvnx2qi_fract}
;; (nil))
;; When the value of pseudo register 134 of the insn above is discovered already
;; spilled in the memory during LRA.
;; LRA will reload this pattern into a memory load instruction pattern.
;; Because RVVMF4QI is a fractional vector, we want LRA reload this pattern into
;; (insn 20 19 9 2 (parallel [
;; (set (reg:RVVMF4QI 98 v2 [orig:134 _1 ] [134])
;; (mem/c:RVVMF4QI (reg:SI 13 a3 [155]) [1 %sfp+[-2, -2] S[2, 2] A8]))
;; (clobber (reg:SI 14 a4 [149]))])
;; So that we could be able to emit vsetvl instruction using clobber scratch a4.
;; To let LRA generate the expected pattern, we should exclude fractional vector
;; load/store in "*mov<mode>_whole". Otherwise, it will reload this pattern into:
;; (insn 20 19 9 2 (set (reg:RVVMF4QI 98 v2 [orig:134 _1 ] [134])
;; (mem/c:RVVMF4QI (reg:SI 13 a3 [155]) [1 %sfp+[-2, -2] S[2, 2] A8])))
;; which is not the pattern we want.
;; According the facts above, we make "*mov<mode>_whole" includes load/store/move for whole
;; vector modes according to '-march' and "*mov<mode>_fract" only include fractional vector modes.
(define_insn_and_split "*mov<mode>_whole"
[(set (match_operand:V_WHOLE 0 "reg_or_mem_operand" "=vr, m,vr")
(match_operand:V_WHOLE 1 "reg_or_mem_operand" " m,vr,vr"))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"@
vl%m1re<sew>.v\t%0,%1
vs%m1r.v\t%1,%0
#"
"&& !memory_operand (operands[0], <MODE>mode)
&& !memory_operand (operands[1], <MODE>mode)"
[(parallel [(set (match_dup 0) (match_dup 1))
(use (reg:SI VTYPE_REGNUM))])]
""
[(set_attr "type" "vldr,vstr,vmov")
(set_attr "mode" "<MODE>")])
;; Full-register moves like vmv1r.v require a valid vtype.
;; The ABI does not guarantee that the vtype is valid after a function
;; call so we need to make it dependent on the vtype and have
;; the vsetvl pass insert a vsetvl if necessary.
;; To facilitate optimization we keep the reg-reg move patterns "regular"
;; until split time and only then switch to a pattern like below that
;; uses the vtype register.
;; As the use of these patterns is limited (in the general context)
;; there is no need for helper functions and we can just create the RTX
;; directly.
(define_insn "*mov<mode>_reg_whole_vtype"
[(set (match_operand:V_WHOLE 0 "reg_or_mem_operand" "=vr")
(match_operand:V_WHOLE 1 "reg_or_mem_operand" " vr"))
(use (reg:SI VTYPE_REGNUM))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"vmv%m1r.v\t%0,%1"
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_insn_and_split "*mov<mode>_fract"
[(set (match_operand:V_FRACT 0 "register_operand" "=vr")
(match_operand:V_FRACT 1 "register_operand" " vr"))]
"TARGET_VECTOR"
"#"
"&& 1"
[(parallel [(set (match_dup 0) (match_dup 1))
(use (reg:SI VTYPE_REGNUM))])]
""
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_insn "*mov<mode>_fract_vtype"
[(set (match_operand:V_FRACT 0 "register_operand" "=vr")
(match_operand:V_FRACT 1 "register_operand" " vr"))
(use (reg:SI VTYPE_REGNUM))]
"TARGET_VECTOR"
"vmv1r.v\t%0,%1"
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_expand "mov<mode>"
[(set (match_operand:VB 0 "reg_or_mem_operand")
(match_operand:VB 1 "general_operand"))]
"TARGET_VECTOR"
{
if (TARGET_XTHEADVECTOR && reg_or_mem_operand (operands[1], <MODE>mode))
{
emit_insn (gen_pred_th_whole_mov (<MODE>mode, operands[0], operands[1],
RVV_VLMAX, GEN_INT(riscv_vector::VLMAX)));
DONE;
}
if (riscv_vector::legitimize_move (operands[0], &operands[1]))
DONE;
})
(define_insn_and_split "*mov<mode>"
[(set (match_operand:VB 0 "register_operand" "=vr")
(match_operand:VB 1 "register_operand" " vr"))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"#"
"&& 1"
[(parallel [(set (match_dup 0) (match_dup 1))
(use (reg:SI VTYPE_REGNUM))])]
""
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_insn "*mov<mode>_vtype"
[(set (match_operand:VB 0 "register_operand" "=vr")
(match_operand:VB 1 "register_operand" " vr"))
(use (reg:SI VTYPE_REGNUM))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"vmv1r.v\t%0,%1"
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_expand "@mov<V_FRACT:mode><P:mode>_lra"
[(parallel
[(set (match_operand:V_FRACT 0 "reg_or_mem_operand")
(match_operand:V_FRACT 1 "reg_or_mem_operand"))
(clobber (match_scratch:P 2))])]
"TARGET_VECTOR && (lra_in_progress || reload_completed)"
{})
(define_expand "@mov<VB:mode><P:mode>_lra"
[(parallel
[(set (match_operand:VB 0 "reg_or_mem_operand")
(match_operand:VB 1 "reg_or_mem_operand"))
(clobber (match_scratch:P 2))])]
"TARGET_VECTOR && (lra_in_progress || reload_completed)"
{})
(define_insn_and_split "*mov<V_FRACT:mode><P:mode>_lra"
[(set (match_operand:V_FRACT 0 "reg_or_mem_operand" "=vr, m,vr")
(match_operand:V_FRACT 1 "reg_or_mem_operand" " m,vr,vr"))
(clobber (match_scratch:P 2 "=&r,&r,r"))]
"TARGET_VECTOR && (lra_in_progress || reload_completed)"
"#"
"&& reload_completed"
[(const_int 0)]
{
if (REG_P (operands[0]) && REG_P (operands[1]))
emit_insn (gen_rtx_SET (operands[0], operands[1]));
else
{
riscv_vector::emit_vlmax_vsetvl (<V_FRACT:MODE>mode, operands[2]);
riscv_vector::emit_vlmax_insn_lra (code_for_pred_mov (<V_FRACT:MODE>mode),
riscv_vector::UNARY_OP, operands, operands[2]);
}
DONE;
}
[(set_attr "type" "vector")]
)
(define_insn_and_split "*mov<VB:mode><P:mode>_lra"
[(set (match_operand:VB 0 "reg_or_mem_operand" "=vr, m,vr")
(match_operand:VB 1 "reg_or_mem_operand" " m,vr,vr"))
(clobber (match_scratch:P 2 "=&r,&r,r"))]
"TARGET_VECTOR && (lra_in_progress || reload_completed)"
"#"
"&& reload_completed"
[(const_int 0)]
{
if (REG_P (operands[0]) && REG_P (operands[1]))
emit_insn (gen_rtx_SET (operands[0], operands[1]));
else
{
riscv_vector::emit_vlmax_vsetvl (<VB:MODE>mode, operands[2]);
riscv_vector::emit_vlmax_insn_lra (code_for_pred_mov (<VB:MODE>mode),
riscv_vector::UNARY_MASK_OP, operands, operands[2]);
}
DONE;
}
[(set_attr "type" "vector")]
)
;; Define tuple modes data movement.
;; operands[2] is used to save the offset of each subpart.
;; operands[3] is used to calculate the address for each subpart.
;; operands[4] is VL of vsetvli instruction.
(define_expand "mov<mode>"
[(parallel [(set (match_operand:VT 0 "reg_or_mem_operand")
(match_operand:VT 1 "general_operand"))
(clobber (match_dup 2))
(clobber (match_dup 3))
(clobber (match_dup 4))])]
"TARGET_VECTOR"
{
/* Need to force register if mem <- !reg. */
if (MEM_P (operands[0]) && !REG_P (operands[1]))
operands[1] = force_reg (<MODE>mode, operands[1]);
if (GET_CODE (operands[1]) == CONST_VECTOR)
{
riscv_vector::expand_tuple_move (operands);
DONE;
}
operands[2] = gen_rtx_SCRATCH (Pmode);
operands[3] = gen_rtx_SCRATCH (Pmode);
operands[4] = gen_rtx_SCRATCH (Pmode);
})
(define_insn_and_split "*mov<VT:mode>_<P:mode>"
[(set (match_operand:VT 0 "reg_or_mem_operand" "=vr,vr, m")
(match_operand:VT 1 "reg_or_mem_operand" " vr, m,vr"))
(clobber (match_scratch:P 2 "=X,&r,&r"))
(clobber (match_scratch:P 3 "=X,&r,&r"))
(clobber (match_scratch:P 4 "=X,&r,&r"))]
"TARGET_VECTOR"
"#"
"&& reload_completed"
[(const_int 0)]
{
riscv_vector::expand_tuple_move (operands);
DONE;
}
[(set_attr "type" "vmov,vlde,vste")
(set_attr "mode" "<VT:MODE>")
(set (attr "merge_op_idx") (const_int INVALID_ATTRIBUTE))
(set (attr "avl_type_idx") (const_int INVALID_ATTRIBUTE))
(set (attr "mode_idx") (const_int INVALID_ATTRIBUTE))])
;; -----------------------------------------------------------------
;; ---- VLS Moves Operations
;; -----------------------------------------------------------------
(define_expand "mov<mode>"
[(set (match_operand:VLS_AVL_IMM 0 "reg_or_mem_operand")
(match_operand:VLS_AVL_IMM 1 "general_operand"))]
"TARGET_VECTOR"
{
if (riscv_vector::legitimize_move (operands[0], &operands[1]))
DONE;
})
(define_insn_and_split "*mov<mode>"
[(set (match_operand:VLS_AVL_IMM 0 "reg_or_mem_operand" "=vr, m, vr")
(match_operand:VLS_AVL_IMM 1 "reg_or_mem_operand" " m,vr, vr"))]
"TARGET_VECTOR
&& (register_operand (operands[0], <MODE>mode)
|| register_operand (operands[1], <MODE>mode))"
"@
#
#
vmv%m1r.v\t%0,%1"
"&& reload_completed
&& (!register_operand (operands[0], <MODE>mode)
|| !register_operand (operands[1], <MODE>mode))"
[(const_int 0)]
{
bool ok_p = riscv_vector::legitimize_move (operands[0], &operands[1]);
gcc_assert (ok_p);
DONE;
}
[(set_attr "type" "vlde,vste,vmov")
(set_attr "mode" "<MODE>")
(set (attr "merge_op_idx") (const_int INVALID_ATTRIBUTE))
(set (attr "has_vl_op") (const_string "false"))
(set (attr "has_vtype_op") (const_string "false"))
(set (attr "avl_type_idx") (const_int INVALID_ATTRIBUTE))
(set (attr "mode_idx") (const_int INVALID_ATTRIBUTE))]
)
(define_expand "mov<mode>"
[(set (match_operand:VLS_AVL_REG 0 "reg_or_mem_operand")
(match_operand:VLS_AVL_REG 1 "general_operand"))]
"TARGET_VECTOR"
{
bool ok_p = riscv_vector::legitimize_move (operands[0], &operands[1]);
gcc_assert (ok_p);
DONE;
})
(define_expand "@mov<VLS_AVL_REG:mode><P:mode>_lra"
[(parallel
[(set (match_operand:VLS_AVL_REG 0 "reg_or_mem_operand")
(match_operand:VLS_AVL_REG 1 "reg_or_mem_operand"))
(clobber (match_scratch:P 2))])]
"TARGET_VECTOR && (lra_in_progress || reload_completed)"
{})
(define_insn_and_split "*mov<VLS_AVL_REG:mode><P:mode>_lra"
[(set (match_operand:VLS_AVL_REG 0 "reg_or_mem_operand" "=vr, m,vr")
(match_operand:VLS_AVL_REG 1 "reg_or_mem_operand" " m,vr,vr"))
(clobber (match_scratch:P 2 "=&r,&r,r"))]
"TARGET_VECTOR && (lra_in_progress || reload_completed)
&& (register_operand (operands[0], <VLS_AVL_REG:MODE>mode)
|| register_operand (operands[1], <VLS_AVL_REG:MODE>mode))"
"#"
"&& reload_completed"
[(const_int 0)]
{
if (REG_P (operands[0]) && REG_P (operands[1]))
emit_insn (gen_rtx_SET (operands[0], operands[1]));
else
{
emit_move_insn (operands[2], gen_int_mode (GET_MODE_NUNITS (<VLS_AVL_REG:MODE>mode),
Pmode));
unsigned insn_flags
= GET_MODE_CLASS (<VLS_AVL_REG:MODE>mode) == MODE_VECTOR_BOOL
? riscv_vector::UNARY_MASK_OP
: riscv_vector::UNARY_OP;
riscv_vector::emit_nonvlmax_insn (code_for_pred_mov (<VLS_AVL_REG:MODE>mode),
insn_flags, operands, operands[2]);
}
DONE;
}
[(set_attr "type" "vlde,vste,vmov")
(set_attr "mode" "<VLS_AVL_REG:MODE>")
(set (attr "merge_op_idx") (const_int INVALID_ATTRIBUTE))
(set (attr "avl_type_idx") (const_int INVALID_ATTRIBUTE))
(set (attr "mode_idx") (const_int INVALID_ATTRIBUTE))]
)
(define_insn_and_split "*mov<mode>_vls"
[(set (match_operand:VLS 0 "register_operand" "=vr")
(match_operand:VLS 1 "register_operand" " vr"))]
"TARGET_VECTOR"
"#"
"&& 1"
[(parallel [(set (match_dup 0) (match_dup 1))
(use (reg:SI VTYPE_REGNUM))])]
""
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_insn "*mov<mode>_vls_vtype"
[(set (match_operand:VLS 0 "register_operand" "=vr")
(match_operand:VLS 1 "register_operand" " vr"))
(use (reg:SI VTYPE_REGNUM))]
"TARGET_VECTOR"
"vmv%m1r.v\t%0,%1"
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_insn_and_split "*mov<mode>_vls"
[(set (match_operand:VLSB 0 "register_operand" "=vr")
(match_operand:VLSB 1 "register_operand" " vr"))]
"TARGET_VECTOR"
"#"
"&& 1"
[(parallel [(set (match_dup 0) (match_dup 1))
(use (reg:SI VTYPE_REGNUM))])]
""
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
(define_insn "*mov<mode>_vls_vtype"
[(set (match_operand:VLSB 0 "register_operand" "=vr")
(match_operand:VLSB 1 "register_operand" " vr"))
(use (reg:SI VTYPE_REGNUM))]
"TARGET_VECTOR"
"vmv1r.v\t%0,%1"
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
;; According to RVV ISA:
;; If an element accessed by a vector memory instruction is not naturally aligned to the size of the element,
;; either the element is transferred successfully or an address misaligned exception is raised on that element.
(define_expand "movmisalign<mode>"
[(set (match_operand:V_VLS 0 "nonimmediate_operand")
(match_operand:V_VLS 1 "general_operand"))]
"TARGET_VECTOR && TARGET_VECTOR_MISALIGN_SUPPORTED"
{
emit_move_insn (operands[0], operands[1]);
DONE;
}
)
;; -----------------------------------------------------------------
;; ---- Duplicate Operations
;; -----------------------------------------------------------------
(define_expand "vec_duplicate<mode>"
[(set (match_operand:V_VLS 0 "register_operand")
(vec_duplicate:V_VLS
(match_operand:<VEL> 1 "any_broadcast_operand")))]
"TARGET_VECTOR"
{
/* Don't keep a DImode broadcast for RV32 in the vec_duplicate form.
Otherwise combine or late combine could end up doing
"64-bit broadcast" (!= vmv.v.x)
+ vadd.vv
= vadd.vx
which would be invalid. */
bool gt_p = maybe_gt (GET_MODE_SIZE (<VEL>mode), GET_MODE_SIZE (Pmode));
if (!FLOAT_MODE_P (<VEL>mode) && gt_p)
{
riscv_vector::emit_vlmax_insn
(code_for_pred_strided_broadcast
(<MODE>mode), riscv_vector::UNARY_OP, operands);
DONE;
}
/* Even though we can eventually broadcast any permissible
constant by moving it into a register we need to force
any non-immediate one into a register here.
If we didn't do that we couldn't fwprop/late-combine
vec_duplicate 123.45f
+ vfadd.vv
= vfadd.vf
because the constant is valid for vec_duplicate but not
for vfadd.vf. Therefore we need to do
fa0 = 123.45f
vec_duplicate fa0
+ vfadd.vv
= vfadd.vf */
if (!satisfies_constraint_P (operands[1])
&& !satisfies_constraint_J (operands[1])
&& !rtx_equal_p (operands[1], CONST0_RTX (<VEL>mode))
&& !memory_operand (operands[1], <VEL>mode))
operands[1] = force_reg (<VEL>mode, operands[1]);
/* Otherwise keep the vec_duplicate pattern until split. */
})
;; According to GCC internal:
;; This pattern only handles duplicates of non-constant inputs.
;; Constant vectors go through the movm pattern instead.
;; So "direct_broadcast_operand" can only be mem or reg, no CONSTANT.
(define_insn_and_split "*vec_duplicate<mode>"
[(set (match_operand:V_VLS 0 "register_operand")
(vec_duplicate:V_VLS
(match_operand:<VEL> 1 "any_broadcast_operand")))]
"TARGET_VECTOR && can_create_pseudo_p ()"
"#"
"&& 1"
[(const_int 0)]
{
if (riscv_vector::can_be_broadcast_p (operands[1]))
riscv_vector::emit_vlmax_insn (code_for_pred_broadcast (<MODE>mode),
riscv_vector::UNARY_OP, operands);
else
riscv_vector::emit_vlmax_insn (code_for_pred_strided_broadcast
(<MODE>mode), riscv_vector::UNARY_OP,
operands);
DONE;
}
[(set_attr "type" "vector")]
)
;; -----------------------------------------------------------------
;; ---- 6. Configuration-Setting Instructions
;; -----------------------------------------------------------------
;; Includes:
;; - 6.1 vsetvli/vsetivli/vsetvl instructions
;; -----------------------------------------------------------------
;; we don't define vsetvli as unspec_volatile which has side effects.
;; This instruction can be scheduled by the instruction scheduler.
;; This means these instructions will be deleted when
;; there is no instructions using vl or vtype in the following.
;; rd | rs1 | AVL value | Effect on vl
;; - | !x0 | x[rs1] | Normal stripmining
;; !x0 | x0 | ~0 | Set vl to VLMAX
;; operands[0]: VL.
;; operands[1]: AVL.
;; operands[2]: SEW
;; operands[3]: LMUL
;; operands[4]: Tail policy 0 or 1 (undisturbed/agnostic)
;; operands[5]: Mask policy 0 or 1 (undisturbed/agnostic)
;; We define 2 types of "vsetvl*" instruction patterns:
;; - "@vsetvl<mode>" is a parallel format which has side effects.
;; - "@vsetvl<mode>_no_side_effects" has no side effects.
;; - "@vsetvl<mode>" is used by "vsetvl" intrinsics and "insert-vsetvl" PASS.
;; - "@vsetvl<mode>_no_side_effects" is used by GCC standard patterns.
;; - "@vsetvl<mode>" includes VL/VTYPE global registers status (define set)
;; and each RVV instruction includes VL/VTYPE global registers status (use)
;; so that we can guarantee each RVV instruction can execute with correct
;; VL/VTYPE global registers status after "insert-vsetvl" PASS.
;; - "@vsetvl<mode>_no_side_effects" has no side effects and excludes VL/VTYPE
;; global registers status (define set). It's only used by GCC standard pattern
;; expansion. For example: "mov<mode>" pattern for fractional vector modes which
;; need to set VL/VTYPE. Then we could manually call this pattern to gain benefits
;; from the optimization of each GCC internal PASS.
;; 1. void foo (float *in, float *out)
;; {
;; vfloat32mf2_t v = *(vfloat32mf2_t*)in;
;; *(vfloat32mf2_t*)out = v;
;; }
;; We could eliminate the second "vsetvl" by calling "@vsetvl<mode>_no_side_effects".
;;
;; "@vsetvl<mode>": ;; "@vsetvl<mode>_no_side_effects":
;; vsetvli a4,zero,e32,mf2,ta,ma ;; vsetvli a4,zero,e32,mf2,ta,ma
;; vle32.v v24,(a0) ;; vle32.v v24,(a0)
;; vsetvli a4,zero,e32,mf2,ta,ma ;; --
;; vse32.v v24,(a1) ;; vse32.v v24,(a1)
;; ret ;; ret
;; 2. void foo (int8_t *in, int8_t *out, int M)
;; {
;; for (int i = 0; i < M; i++){
;; vint8mf2_t v = *(vint8mf2_t*)(in + i);
;; *(vint8mf2_t*)(out + i) = v;
;; }
;; }
;;
;; Hoist "vsetvl" instruction in LICM:
;; "@vsetvl<mode>": ;; "@vsetvl<mode>_no_side_effects":
;; - ;; vsetvli a4,zero,e32,mf2,ta,ma
;; LOOP: ;; LOOP:
;; vsetvli a4,zero,e32,mf2,ta,ma ;; -
;; vle32.v v24,(a0) ;; vle32.v v24,(a0)
;; vsetvli a4,zero,e32,mf2,ta,ma ;; -
;; vse32.v v24,(a1) ;; vse32.v v24,(a1)
;; However, it may produce wrong codegen if we exclude VL/VTYPE in "vsetvl<mode>".
;; 3. void foo (int8_t *in, int8_t *out, int32_t *in2, int32_t *out2, int M)
;; {
;; for (int i = 0; i < M; i++){
;; vint8mf2_t v = *(vint8mf2_t*)(in + i);
;; vint32mf2_t v2 = *(vint32mf2_t*)(in + i + i);
;; *(vint8mf2_t*)(out + i) = v;
;; *(vint32mf2_t*)(out + i + i) = v2;
;; }
;; }
;;
;; vsetvli a6,zero,e8,mf2,ta,ma
;; vsetvli a2,zero,e32,mf2,ta,ma
;; LOOP:
;; vle8.v v25,(a0)
;; vle32.v v24,(a5)
;; addi a0,a0,1
;; vse8.v v25,(a1)
;; vse32.v v24,(a3)
;;
;; Both vle8.v and vle32.v are using the wrong VL/VTYPE status.
;; We leave it to "insert-vsetvl" PASS to correct this situation.
;; The "insert-vsetvl" PASS mechanism:
;; 1. Before "insert-vsetvl" PASS, only RVV instructions are generated
;; by GCC standard pattern expansion has the corresponding "vsetvl".
;; We exploit each GCC internal optimization pass to optimize the "vsetvl".
;; 2. Correct the VL/VTYPE status for each GCC standard pattern RVV instructions.
;; Insert vsetvl for each RVV instructions that has no VL/VTYPE status if necessary.
;; For example: RVV intrinsics.
;; 3. Optimize "vsetvl" instructions.
(define_insn "@vsetvl<mode>"
[(set (match_operand:P 0 "register_operand" "=r")
(unspec:P [(match_operand:P 1 "vector_length_operand" "rvl")
(match_operand 2 "const_int_operand" "i")
(match_operand 3 "const_int_operand" "i")
(match_operand 4 "const_int_operand" "i")
(match_operand 5 "const_int_operand" "i")] UNSPEC_VSETVL))
(set (reg:SI VL_REGNUM)
(unspec:SI [(match_dup 1)
(match_dup 2)
(match_dup 3)] UNSPEC_VSETVL))
(set (reg:SI VTYPE_REGNUM)
(unspec:SI [(match_dup 2)
(match_dup 3)
(match_dup 4)
(match_dup 5)] UNSPEC_VSETVL))]
"TARGET_VECTOR"
"vset%i1vli\t%0,%1,e%2,%m3,t%p4,m%p5"
[(set_attr "type" "vsetvl")
(set_attr "mode" "<MODE>")
(set (attr "sew") (symbol_ref "INTVAL (operands[2])"))
(set (attr "vlmul") (symbol_ref "INTVAL (operands[3])"))
(set (attr "ta") (symbol_ref "INTVAL (operands[4])"))
(set (attr "ma") (symbol_ref "INTVAL (operands[5])"))])
;; vsetvl zero,zero,vtype instruction.
;; This pattern has no side effects and does not set X0 register.
(define_insn "vsetvl_vtype_change_only"
[(set (reg:SI VTYPE_REGNUM)
(unspec:SI
[(match_operand 0 "const_int_operand" "i")
(match_operand 1 "const_int_operand" "i")
(match_operand 2 "const_int_operand" "i")
(match_operand 3 "const_int_operand" "i")] UNSPEC_VSETVL))]
"TARGET_VECTOR"
"vsetvli\tzero,zero,e%0,%m1,t%p2,m%p3"
[(set_attr "type" "vsetvl")
(set_attr "mode" "SI")
(set (attr "sew") (symbol_ref "INTVAL (operands[0])"))
(set (attr "vlmul") (symbol_ref "INTVAL (operands[1])"))
(set (attr "ta") (symbol_ref "INTVAL (operands[2])"))
(set (attr "ma") (symbol_ref "INTVAL (operands[3])"))])
;; vsetvl zero,rs1,vtype instruction.
;; The reason we need this pattern since we should avoid setting X0 register
;; in vsetvl instruction pattern.
(define_insn "@vsetvl_discard_result<mode>"
[(set (reg:SI VL_REGNUM)
(unspec:SI [(match_operand:P 0 "vector_length_operand" "rvl")
(match_operand 1 "const_int_operand" "i")
(match_operand 2 "const_int_operand" "i")] UNSPEC_VSETVL))
(set (reg:SI VTYPE_REGNUM)
(unspec:SI [(match_dup 1)
(match_dup 2)
(match_operand 3 "const_int_operand" "i")
(match_operand 4 "const_int_operand" "i")] UNSPEC_VSETVL))]
"TARGET_VECTOR"
"vset%i0vli\tzero,%0,e%1,%m2,t%p3,m%p4"
[(set_attr "type" "vsetvl")
(set_attr "mode" "<MODE>")
(set (attr "sew") (symbol_ref "INTVAL (operands[1])"))
(set (attr "vlmul") (symbol_ref "INTVAL (operands[2])"))
(set (attr "ta") (symbol_ref "INTVAL (operands[3])"))
(set (attr "ma") (symbol_ref "INTVAL (operands[4])"))])
;; It's emit by vsetvl/vsetvlmax intrinsics with no side effects.
;; Since we have many optimization passes from "expand" to "reload_completed",
;; such pattern can allow us gain benefits of these optimizations.
(define_insn_and_split "@vsetvl<mode>_no_side_effects"
[(set (match_operand:P 0 "register_operand" "=r")
(unspec:P [(match_operand:P 1 "vector_length_operand" "rvl")
(match_operand 2 "const_int_operand" "i")
(match_operand 3 "const_int_operand" "i")
(match_operand 4 "const_int_operand" "i")
(match_operand 5 "const_int_operand" "i")] UNSPEC_VSETVL))]
"TARGET_VECTOR"
"#"
"&& epilogue_completed"
[(parallel
[(set (match_dup 0)
(unspec:P [(match_dup 1) (match_dup 2) (match_dup 3)
(match_dup 4) (match_dup 5)] UNSPEC_VSETVL))
(set (reg:SI VL_REGNUM)
(unspec:SI [(match_dup 1) (match_dup 2) (match_dup 3)] UNSPEC_VSETVL))
(set (reg:SI VTYPE_REGNUM)
(unspec:SI [(match_dup 2) (match_dup 3) (match_dup 4)
(match_dup 5)] UNSPEC_VSETVL))])]
""
[(set_attr "type" "vsetvl")
(set_attr "mode" "SI")])
;; This pattern use to combine below two insns and then further remove
;; unnecessary sign_extend operations:
;; (set (reg:DI 134 [ _1 ])
;; (unspec:DI [
;; (const_int 19 [0x13])
;; (const_int 8 [0x8])
;; (const_int 5 [0x5])
;; (const_int 2 [0x2]) repeated x2
;; ] UNSPEC_VSETVL))
;; (set (reg/v:DI 135 [ <retval> ])
;; (sign_extend:DI (subreg:SI (reg:DI 134 [ _1 ]) 0)))
;;
;; The reason we can remove signe_extend is because currently the vl value
;; returned by the vsetvl instruction ranges from 0 to 65536 (uint16_t), and
;; bits 17 to 63 (including 31) are always 0, so there is no change after
;; sign_extend. Note that for HI and QI modes we cannot do this.
;; Of course, if the range of instructions returned by vsetvl later expands
;; to 32bits, then this combine pattern needs to be removed. But that could be
;; a long time from now.
(define_insn_and_split "*vsetvldi_no_side_effects_si_extend"
[(set (match_operand:DI 0 "register_operand")
(sign_extend:DI
(subreg:SI
(unspec:DI [(match_operand:P 1 "vector_length_operand")
(match_operand 2 "const_int_operand")
(match_operand 3 "const_int_operand")
(match_operand 4 "const_int_operand")
(match_operand 5 "const_int_operand")] UNSPEC_VSETVL) 0)))]
"TARGET_VECTOR && TARGET_64BIT"
"#"
"&& 1"
[(set (match_dup 0)
(unspec:DI [(match_dup 1)
(match_dup 2)
(match_dup 3)
(match_dup 4)
(match_dup 5)] UNSPEC_VSETVL))]
""
[(set_attr "type" "vsetvl")
(set_attr "mode" "SI")])
;; RVV machine description matching format
;; (define_insn ""
;; [(set (match_operand:MODE 0)
;; (if_then_else:MODE
;; (unspec:<MODE:VM>
;; [(match_operand:<VM> 1 "vector_mask_operand")
;; (match_operand N + 4 "vector_length_operand")
;; (match_operand N + 5 "const_int_operand")
;; (match_operand N + 6 "const_int_operand")
;; (reg:SI VL_REGNUM)
;; (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
;; (instruction operation:MODE
;; (match_operand 3
;; (match_operand 4
;; (match_operand 5
;; ................
;; (match_operand N + 3)
;; (match_operand:MODE 2 "vector_reg_or_const0_operand")))]
;;
;; (unspec:[........] UNSPEC_VPREDICATE) is a predicate wrapper.
;; Include mask predicate && length predicate && vector policy.
;; -------------------------------------------------------------------------------
;; ---- Predicated Mov
;; -------------------------------------------------------------------------------
;; Includes:
;; - 7.4. Vector Unit-Stride Instructions
;; - 11.15 Vector Integer Merge Instructions
;; - 11.16 Vector Integer Move Instructions
;; - 13.16 Vector Floating-Point Move Instruction
;; - 15.1 Vector Mask-Register Logical Instructions
;; -------------------------------------------------------------------------------
;; vle.v/vse.v/vmv.v.v.
;; For vle.v/vmv.v.v, we may need merge and mask operand.
;; For vse.v, we don't need merge operand, so it should always match "vu".
;; constraint alternative 0 ~ 1 match vle.v.
;; constraint alternative 2 match vse.v.
;; constraint alternative 3 match vmv.v.v.
;; If operand 3 is a const_vector, then it is left to pred_broadcast patterns.
(define_expand "@pred_mov<mode>"
[(set (match_operand:V_VLS 0 "nonimmediate_operand")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 4 "vector_length_operand")
(match_operand 5 "const_int_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 3 "vector_move_operand")
(match_operand:V_VLS 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{})
;; vle.v/vse.v,vmv.v.v
(define_insn_and_split "*pred_mov<mode>"
[(set (match_operand:V_VLS 0 "nonimmediate_operand" "=vr, vr, vd, m, vr, vr")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1, Wc1, vm, vmWc1, Wc1, Wc1")
(match_operand 4 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 3 "reg_or_mem_operand" " m, m, m, vr, vr, vr")
(match_operand:V_VLS 2 "vector_merge_operand" " 0, vu, vu, vu, vu, 0")))]
"(TARGET_VECTOR
&& (register_operand (operands[0], <MODE>mode)
|| register_operand (operands[3], <MODE>mode)))"
"@
vle<sew>.v\t%0,%3%p1
vle<sew>.v\t%0,%3
vle<sew>.v\t%0,%3,%1.t
vse<sew>.v\t%3,%0%p1
vmv.v.v\t%0,%3
vmv.v.v\t%0,%3"
"&& riscv_vector::whole_reg_to_reg_move_p (operands, <MODE>mode, 7)"
[(set (match_dup 0) (match_dup 3))]
""
[(set_attr "type" "vlde,vlde,vlde,vste,vimov,vimov")
(set_attr "mode" "<MODE>")])
;; Dedicated pattern for vse.v instruction since we can't reuse pred_mov pattern to include
;; memory operand as input which will produce inferior codegen.
(define_insn "@pred_store<mode>"
[(set (match_operand:V_VLS 0 "memory_operand" "+m")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 3 "vector_length_operand" " rvl")
(match_operand 4 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 2 "register_operand" " vr")
(match_dup 0)))]
"TARGET_VECTOR"
"vse<sew>.v\t%2,%0%p1"
[(set_attr "type" "vste")
(set_attr "mode" "<MODE>")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "vl_op_idx" "3")])
;; vlm.v/vsm.v/vmclr.m/vmset.m.
;; constraint alternative 0 match vlm.v.
;; constraint alternative 1 match vsm.v.
;; constraint alternative 3 match vmclr.m.
;; constraint alternative 4 match vmset.m.
(define_insn_and_split "@pred_mov<mode>"
[(set (match_operand:VB_VLS 0 "nonimmediate_operand" "=vr, m, vr, vr, vr")
(if_then_else:VB_VLS
(unspec:VB_VLS
[(match_operand:VB_VLS 1 "vector_all_trues_mask_operand" "Wc1, Wc1, Wc1, Wc1, Wc1")
(match_operand 4 "vector_length_operand" "rvl, rvl, rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:VB_VLS 3 "vector_move_operand" " m, vr, vr, Wc0, Wc1")
(match_operand:VB_VLS 2 "vector_undef_operand" " vu, vu, vu, vu, vu")))]
"TARGET_VECTOR"
"@
vlm.v\t%0,%3
vsm.v\t%3,%0
vmmv.m\t%0,%3
vmclr.m\t%0
vmset.m\t%0"
"&& riscv_vector::whole_reg_to_reg_move_p (operands, <MODE>mode, 5)"
[(set (match_dup 0) (match_dup 3))]
""
[(set_attr "type" "vldm,vstm,vmalu,vmalu,vmalu")
(set_attr "mode" "<MODE>")])
;; Dedicated pattern for vsm.v instruction since we can't reuse pred_mov pattern to include
;; memory operand as input which will produce inferior codegen.
(define_insn "@pred_store<mode>"
[(set (match_operand:VB 0 "memory_operand" "+m")
(if_then_else:VB
(unspec:VB
[(match_operand:VB 1 "vector_all_trues_mask_operand" "Wc1")
(match_operand 3 "vector_length_operand" "rvl")
(match_operand 4 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:VB 2 "register_operand" " vr")
(match_dup 0)))]
"TARGET_VECTOR"
"vsm.v\t%2,%0"
[(set_attr "type" "vstm")
(set_attr "mode" "<MODE>")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "vl_op_idx" "3")])
(define_insn "@pred_merge<mode>"
[(set (match_operand:V_VLS 0 "register_operand" "=vd,vd,vd,vd")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_merge:V_VLS
(match_operand:V_VLS 3 "vector_arith_operand" " vr,vr,vi,vi")
(match_operand:V_VLS 2 "register_operand" " vr,vr,vr,vr")
(match_operand:<VM> 4 "register_operand" " vm,vm,vm,vm"))
(match_operand:V_VLS 1 "vector_merge_operand" " vu, 0,vu, 0")))]
"TARGET_VECTOR"
"vmerge.v%o3m\t%0,%2,%v3,%4"
[(set_attr "type" "vimerge")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_merge<mode>_scalar"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "=vd,vd")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_merge:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 3 "register_operand" " r, r"))
(match_operand:V_VLSI_QHS 2 "register_operand" " vr,vr")
(match_operand:<VM> 4 "register_operand" " vm,vm"))
(match_operand:V_VLSI_QHS 1 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vmerge.vxm\t%0,%2,%3,%4"
[(set_attr "type" "vimerge")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_merge<mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_merge:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 3 "reg_or_int_operand"))
(match_operand:V_VLSI_D 2 "register_operand")
(match_operand:<VM> 4 "register_operand"))
(match_operand:V_VLSI_D 1 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[3],
/* vl */operands[5],
<MODE>mode,
riscv_vector::simm5_p (operands[3]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_merge<mode> (operands[0], operands[1],
operands[2], broadcast_scalar, operands[4], operands[5],
operands[6], operands[7]));
},
(riscv_vector::avl_type) INTVAL (operands[7])))
DONE;
})
(define_insn "*pred_merge<mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_merge:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 3 "register_operand" " r, r"))
(match_operand:V_VLSI_D 2 "register_operand" " vr,vr")
(match_operand:<VM> 4 "register_operand" " vm,vm"))
(match_operand:V_VLSI_D 1 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vmerge.vxm\t%0,%2,%3,%4"
[(set_attr "type" "vimerge")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_merge<mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_merge:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 3 "register_operand" " r, r")))
(match_operand:V_VLSI_D 2 "register_operand" " vr,vr")
(match_operand:<VM> 4 "register_operand" " vm,vm"))
(match_operand:V_VLSI_D 1 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"vmerge.vxm\t%0,%2,%3,%4"
[(set_attr "type" "vimerge")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated Broadcast
;; -------------------------------------------------------------------------------
;; Includes:
;; - 7.5. Vector Strided Instructions (zero stride)
;; - 11.16 Vector Integer Move Instructions (vmv.v.x)
;; - 13.16 Vector Floating-Point Move Instruction (vfmv.v.f)
;; - 16.1 Integer Scalar Move Instructions (vmv.s.x)
;; - 16.2 Floating-Point Scalar Move Instructions (vfmv.s.f)
;; -------------------------------------------------------------------------------
;; According to RVV ISA, vector-scalar instruction doesn't support
;; operand fetched from 2 consecutive registers, so we should use
;; vlse.v which is a memory access to broadcast a DImode scalar into a vector.
;;
;; Since the optimization flow in GCC is as follows:
;; expand --> LICM (Loop invariant) --> split.
;; To use LICM optimization, we postpone generation of vlse.v to split stage since
;; a memory access instruction can not be optimized by LICM (Loop invariant).
(define_expand "@pred_broadcast<mode>"
[(set (match_operand:V_VLS 0 "register_operand")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_broadcast_mask_operand")
(match_operand 4 "vector_length_operand")
(match_operand 5 "const_int_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
;; (vec_duplicate:V_VLS ;; wrapper activated by wrap_vec_dup below.
(match_operand:<VEL> 3 "direct_broadcast_operand") ;; )
(match_operand:V_VLS 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
bool wrap_vec_dup = true;
rtx vec_cst = NULL_RTX;
if (immediate_operand (operands[3], <VEL>mode)
&& (vec_cst = gen_const_vec_duplicate (<MODE>mode, operands[3]))
&& (/* -> pred_broadcast<mode>_zero */
(vector_least_significant_set_mask_operand (operands[1],
<VM>mode)
&& vector_const_0_operand (vec_cst, <MODE>mode))
|| (/* pred_broadcast<mode>_imm */
vector_all_trues_mask_operand (operands[1], <VM>mode)
&& vector_const_int_or_double_0_operand (vec_cst,
<MODE>mode))))
{
operands[3] = vec_cst;
wrap_vec_dup = false;
}
else if (GET_MODE_SIZE (<VEL>mode) > UNITS_PER_WORD
&& satisfies_constraint_Wb1 (operands[1])
&& (immediate_operand (operands[3], Xmode)
|| (CONST_POLY_INT_P (operands[3])
&& known_ge (rtx_to_poly_int64 (operands[3]), 0U)
&& known_le (rtx_to_poly_int64 (operands[3]),
GET_MODE_SIZE (<MODE>mode)))))
{
rtx tmp = gen_reg_rtx (Pmode);
poly_int64 value = rtx_to_poly_int64 (operands[3]);
emit_move_insn (tmp, gen_int_mode (value, Xmode));
operands[3] = gen_rtx_SIGN_EXTEND (<VEL>mode, tmp);
}
/* For a vmv.v.x never load (const_int 0) or valid immediate operands
into a register, because we can use vmv.v.i. */
else if (satisfies_constraint_Wc1 (operands[1])
&& (satisfies_constraint_P (operands[3])
|| operands[3] == CONST0_RTX (<VEL>mode)))
;
/* For vmv.s.x we have vmv.s.x v1, zero. */
else if (satisfies_constraint_Wb1 (operands[1])
&& operands[3] == CONST0_RTX (<VEL>mode))
;
else
operands[3] = force_reg (<VEL>mode, operands[3]);
if (wrap_vec_dup)
operands[3] = gen_rtx_VEC_DUPLICATE (<MODE>mode, operands[3]);
})
(define_insn_and_rewrite "*pred_broadcast<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vr, vr, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_broadcast_mask_operand" "Wc1,Wc1,Wb1,Wb1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_duplicate:V_VLSI
(match_operand:<VEL> 3 "direct_broadcast_operand" " rP, rP, rJ, rJ"))
(match_operand:V_VLSI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"@
vmv.v.%o3\t%0,%3
vmv.v.%o3\t%0,%3
vmv.s.x\t%0,%z3
vmv.s.x\t%0,%z3"
"&& (operands[1] == CONSTM1_RTX (<VM>mode)
&& operands[4] == CONST1_RTX (Pmode)
&& (register_operand (operands[3], <VEL>mode)
|| satisfies_constraint_J (operands[3])))"
{
/* A broadcast of a single element is just a vmv.s.x. */
operands[1] = riscv_vector::gen_scalar_move_mask (<VM>mode);
}
[(set_attr "type" "vimov,vimov,vimovxv,vimovxv")
(set_attr "mode" "<MODE>")])
(define_insn_and_rewrite "pred_broadcast<mode>_zvfh"
[(set (match_operand:V_VLSF 0 "register_operand" "=vr, vr, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_broadcast_mask_operand" "Wc1,Wc1,Wb1,Wb1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_duplicate:V_VLSF
(match_operand:<VEL> 3 "direct_broadcast_operand" " f, f, f, f"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"@
vfmv.v.f\t%0,%3
vfmv.v.f\t%0,%3
vfmv.s.f\t%0,%3
vfmv.s.f\t%0,%3"
"&& (operands[1] == CONSTM1_RTX (<VM>mode)
&& operands[4] == CONST1_RTX (Pmode)
&& (register_operand (operands[3], <VEL>mode)
|| satisfies_constraint_J (operands[3])))"
{
/* A broadcast of a single element is just a vfmv.s.f. */
operands[1] = riscv_vector::gen_scalar_move_mask (<VM>mode);
}
[(set_attr "type" "vfmov,vfmov,vfmovfv,vfmovfv")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_broadcast<mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vr, vr, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_broadcast_mask_operand" "Wc1,Wc1,Wb1,Wb1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 3 "register_operand" " r, r, r, r")))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"@
vmv.v.x\t%0,%3
vmv.v.x\t%0,%3
vmv.s.x\t%0,%3
vmv.s.x\t%0,%3"
[(set_attr "type" "vimov,vimov,vimovxv,vimovxv")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_broadcast<mode>_zero"
[(set (match_operand:V_VLS 0 "register_operand" "=vr, vr")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_least_significant_set_mask_operand" "Wb1, Wb1")
(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 3 "vector_const_0_operand" "Wc0, Wc0")
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vmv.s.x\t%0,zero"
[(set_attr "type" "vimovxv,vimovxv")
(set_attr "mode" "<MODE>")])
;; Because (vec_duplicate imm) will be converted to (const_vector imm),
;; This pattern is used to handle this case.
(define_insn "*pred_broadcast<mode>_imm"
[(set (match_operand:V_VLS 0 "register_operand" "=vr, vr")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_all_trues_mask_operand" " Wc1, Wc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 3 "vector_const_int_or_double_0_operand" "viWc0, viWc0")
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vmv.v.i\t%0,%v3"
[(set_attr "type" "vimov,vimov")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_strided_broadcast<mode>"
[(set (match_operand:V_VLS 0 "register_operand")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "strided_broadcast_mask_operand")
(match_operand 4 "vector_length_operand")
(match_operand 5 "const_int_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_duplicate:V_VLS
(match_operand:<VEL> 3 "strided_broadcast_operand"))
(match_operand:V_VLS 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (satisfies_constraint_Wb1 (operands[1]))
{
/* If we're asked to set a single element (like vmv.s.x but we
need to go via memory here) and the tail policy is agnostic
we can overwrite all elements.
Thus, set the mask to broadcast. */
operands[1] = CONSTM1_RTX (<VM>mode);
if (!satisfies_constraint_vu (operands[2])
&& GET_MODE_SIZE (<VEL>mode) > UNITS_PER_WORD)
{
/* Case 2: vmv.s.x (TU, x == memory) ==>
vl = 0 or 1; + vlse.v (TU) in RV32 system */
/* In this case we must not overwrite the residual elements,
so set the vector length to 0/1. */
operands[4] = riscv_vector::gen_avl_for_scalar_move (operands[4]);
}
}
})
(define_insn_and_split "*pred_strided_broadcast<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "strided_broadcast_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_duplicate:V_VLSI
(match_operand:<VEL> 3 "strided_broadcast_operand" " A, A, A, A"))
(match_operand:V_VLSI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"@
vlse<sew>.v\t%0,%3,zero,%1.t
vlse<sew>.v\t%0,%3,zero,%1.t
vlse<sew>.v\t%0,%3,zero
vlse<sew>.v\t%0,%3,zero"
"&& !strided_load_broadcast_p () && can_create_pseudo_p ()"
[(const_int 0)]
{
rtx tmp = gen_reg_rtx (V1DImode);
emit_move_insn (tmp, gen_lowpart (V1DImode, operands[3]));
tmp = lowpart_subreg (<MODE>mode, tmp, V1DImode);
emit_insn
(gen_pred_gather<mode>_scalar
(operands[0], operands[1], operands[2], tmp, CONST0_RTX (Pmode),
operands[4], operands[5], operands[6], operands[7]));
DONE;
}
[(set_attr "type" "vlds,vlds,vlds,vlds")
(set_attr "mode" "<MODE>")])
(define_insn_and_split "*pred_strided_broadcast<mode>_zvfhmin"
[(set (match_operand:V_VLSF_FALLBACK 0 "register_operand" "=vr, vr, vr, vr")
(if_then_else:V_VLSF_FALLBACK
(unspec:<VM>
[(match_operand:<VM> 1 "strided_broadcast_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 4 "vector_length_operand" "rvl, rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_duplicate:V_VLSF_FALLBACK
(match_operand:<VEL> 3 "strided_broadcast_operand" " A, A, A, A"))
(match_operand:V_VLSF_FALLBACK 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"@
vlse<sew>.v\t%0,%3,zero,%1.t
vlse<sew>.v\t%0,%3,zero,%1.t
vlse<sew>.v\t%0,%3,zero
vlse<sew>.v\t%0,%3,zero"
"&& !strided_load_broadcast_p ()
&& (<VEL>mode == HFmode
|| <VEL>mode == BFmode)
&& can_create_pseudo_p ()"
[(const_int 0)]
{
poly_uint64 nunits = GET_MODE_NUNITS (<MODE>mode);
machine_mode vmodehi
= riscv_vector::get_vector_mode (HImode, nunits).require ();
rtx ops[] = {gen_lowpart (vmodehi, operands[0]),
gen_lowpart (HImode, operands[3])};
riscv_vector::emit_avltype_insn (code_for_pred_broadcast (vmodehi),
riscv_vector::UNARY_OP, ops,
(riscv_vector::avl_type) INTVAL (operands[7]),
operands[4]);
DONE;
}
[(set_attr "type" "vlds,vlds,vlds,vlds")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated Strided loads/stores
;; -------------------------------------------------------------------------------
;; Includes:
;; - 7.5. Vector Strided Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_strided_load<mode>"
[(set (match_operand:V_VLS 0 "register_operand" "=vr, vr, vd, vr, vr, vd")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1, Wc1, vm, vmWc1, Wc1, vm")
(match_operand 5 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS
[(match_operand:V_VLS 3 "memory_operand" " m, m, m, m, m, m")
(mem:BLK (scratch))
(match_operand 4 "<V_VLS:stride_predicate>" "<V_VLS:stride_load_constraint>")] UNSPEC_STRIDED)
(match_operand:V_VLS 2 "vector_merge_operand" " 0, vu, vu, 0, vu, vu")))]
"TARGET_VECTOR"
"@
vlse<sew>.v\t%0,%3,%z4%p1
vlse<sew>.v\t%0,%3,%z4
vlse<sew>.v\t%0,%3,%z4,%1.t
vle<sew>.v\t%0,%3%p1
vle<sew>.v\t%0,%3
vle<sew>.v\t%0,%3,%1.t"
[(set_attr "type" "vlds")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_strided_store<mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(match_operand:V_VLS 0 "memory_operand" " +m, m")
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1, vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 2 "<V_VLS:stride_predicate>" "<V_VLS:stride_store_constraint>")
(match_operand:V_VLS 3 "register_operand" " vr, vr")] UNSPEC_STRIDED))]
"TARGET_VECTOR"
"@
vsse<sew>.v\t%3,%0,%z2%p1
vse<sew>.v\t%3,%0%p1"
[(set_attr "type" "vsts")
(set_attr "mode" "<MODE>")
(set (attr "avl_type_idx") (const_int 5))])
;; -------------------------------------------------------------------------------
;; ---- Predicated indexed loads/stores
;; -------------------------------------------------------------------------------
;; Includes:
;; - 7.6. Vector Indexed Instructions
;; -------------------------------------------------------------------------------
;; DEST eew is same as SOURCE eew, DEST register can overlap SOURCE.
(define_insn "@pred_indexed_<order>load<mode>_same_eew"
[(set (match_operand:VINDEXED 0 "register_operand" "=vd, vr,vd, vr")
(if_then_else:VINDEXED
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1,vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VINDEXED
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ,rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX> 4 "register_operand" " vr, vr,vr, vr")] ORDER)
(match_operand:VINDEXED 2 "vector_merge_operand" " vu, vu, 0, 0")))]
"TARGET_VECTOR"
"vl<order>xei<sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
;; DEST eew is greater than SOURCE eew.
(define_insn "@pred_indexed_<order>load<mode>_x2_greater_eew"
[(set (match_operand:VEEWEXT2 0 "register_operand" "=&vr, &vr")
(if_then_else:VEEWEXT2
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEEWEXT2
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX_DOUBLE_TRUNC> 4 "register_operand" " vr, vr")] ORDER)
(match_operand:VEEWEXT2 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xei<double_trunc_sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>load<mode>_x4_greater_eew"
[(set (match_operand:VEEWEXT4 0 "register_operand" "=&vr, &vr")
(if_then_else:VEEWEXT4
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEEWEXT4
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX_QUAD_TRUNC> 4 "register_operand" " vr, vr")] ORDER)
(match_operand:VEEWEXT4 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xei<quad_trunc_sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>load<mode>_x8_greater_eew"
[(set (match_operand:VEEWEXT8 0 "register_operand" "=&vr, &vr")
(if_then_else:VEEWEXT8
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEEWEXT8
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX_OCT_TRUNC> 4 "register_operand" " vr, vr")] ORDER)
(match_operand:VEEWEXT8 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xei<oct_trunc_sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
;; DEST eew is smaller than SOURCE eew.
(define_insn "@pred_indexed_<order>load<mode>_x2_smaller_eew"
[(set (match_operand:VEEWTRUNC2 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:VEEWTRUNC2
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEEWTRUNC2
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ, rJ, rJ, rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX_DOUBLE_EXT> 4 "register_operand" " 0, 0, 0, 0, vr, vr")] ORDER)
(match_operand:VEEWTRUNC2 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vl<order>xei<double_ext_sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>load<mode>_x4_smaller_eew"
[(set (match_operand:VEEWTRUNC4 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:VEEWTRUNC4
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEEWTRUNC4
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ, rJ, rJ, rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX_QUAD_EXT> 4 "register_operand" " 0, 0, 0, 0, vr, vr")] ORDER)
(match_operand:VEEWTRUNC4 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vl<order>xei<quad_ext_sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>load<mode>_x8_smaller_eew"
[(set (match_operand:VEEWTRUNC8 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:VEEWTRUNC8
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEEWTRUNC8
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ, rJ, rJ, rJ, rJ")
(mem:BLK (scratch))
(match_operand:<VINDEX_OCT_EXT> 4 "register_operand" " 0, 0, 0, 0, vr, vr")] ORDER)
(match_operand:VEEWTRUNC8 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vl<order>xei<oct_ext_sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vld<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_same_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX> 2 "register_operand" " vr")
(match_operand:VINDEXED 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_x2_greater_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX_DOUBLE_TRUNC> 2 "register_operand" " vr")
(match_operand:VEEWEXT2 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<double_trunc_sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_x4_greater_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX_QUAD_TRUNC> 2 "register_operand" " vr")
(match_operand:VEEWEXT4 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<quad_trunc_sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_x8_greater_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX_OCT_TRUNC> 2 "register_operand" " vr")
(match_operand:VEEWEXT8 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<oct_trunc_sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_x2_smaller_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX_DOUBLE_EXT> 2 "register_operand" " vr")
(match_operand:VEEWTRUNC2 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<double_ext_sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_x4_smaller_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX_QUAD_EXT> 2 "register_operand" " vr")
(match_operand:VEEWTRUNC4 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<quad_ext_sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_indexed_<order>store<mode>_x8_smaller_eew"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:<VINDEX_OCT_EXT> 2 "register_operand" " vr")
(match_operand:VEEWTRUNC8 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xei<oct_ext_sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vst<order>x")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated integer binary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 11.1 Vector Single-Width Integer Add and Subtract
;; - 11.4 Vector Integer Add-with-Carry/Subtract-with-Borrow Instructions
;; - 11.5 Vector Bitwise Logical Instructions
;; - 11.6 Vector Single-Width Bit Shift Instructions
;; - 11.9 Vector Integer Min/Max Instructions
;; - 11.10 Vector Single-Width Integer Multiply Instructions
;; - 11.11 Vector Integer Divide Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr, vd, vd, vr, vr, vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1, Wc1, vm, vm,Wc1,Wc1, vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl, rvl,rvl,rvl,rvl,rvl,rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_int_binop:V_VLSI
(match_operand:V_VLSI 3 "<binop_rhs1_predicate>" "<binop_rhs1_constraint>")
(match_operand:V_VLSI 4 "<binop_rhs2_predicate>" "<binop_rhs2_constraint>"))
(match_operand:V_VLSI 2 "vector_merge_operand" "vu,0,vu,0,vu,0,vu,0,vu,0,vu,0")))]
"TARGET_VECTOR"
"@
v<insn>.vv\t%0,%3,%4%p1
v<insn>.vv\t%0,%3,%4%p1
v<insn>.vv\t%0,%3,%4%p1
v<insn>.vv\t%0,%3,%4%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_reverse_vi_variant_insn>\t%0,<binop_reverse_vi_variant_op>%p1
v<binop_reverse_vi_variant_insn>\t%0,<binop_reverse_vi_variant_op>%p1
v<binop_reverse_vi_variant_insn>\t%0,<binop_reverse_vi_variant_op>%p1
v<binop_reverse_vi_variant_insn>\t%0,<binop_reverse_vi_variant_op>%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
;; vx instructions patterns.
;; Note: Unlike vv patterns, we should split them since they are variant.
;; For vsll.vx/vsra.vx/vsrl.vx the scalar mode should be Pmode whereas the
;; scalar mode is inner mode of the RVV mode for other vx patterns.
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd,vd, vr, vr,vd,vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1,vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl,rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_shift:V_VLSI
(match_operand:V_VLSI 3 "register_operand" "vr,vr, vr, vr,vr,vr, vr, vr")
(match_operand 4 "pmode_reg_or_uimm5_operand" " r, r, r, r, K, K, K, K"))
(match_operand:V_VLSI 2 "vector_merge_operand" "vu, 0, vu, 0,vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.v%o4\t%0,%3,%4%p1"
[(set_attr "type" "vshift")
(set_attr "mode" "<MODE>")])
;; Handle GET_MODE_INNER (mode) = QImode, HImode, SImode.
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_commutative_binop:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))
(match_operand:V_VLSI_QHS 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI_QHS 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_non_commutative_binop:V_VLSI_QHS
(match_operand:V_VLSI_QHS 3 "register_operand" "vr,vr, vr, vr")
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ")))
(match_operand:V_VLSI_QHS 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_sub<mode>_reverse_scalar"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))
(match_operand:V_VLSI_QHS 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI_QHS 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vrsub.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vialu")
(set_attr "mode" "<MODE>")])
;; Handle GET_MODE_INNER (mode) = DImode. We need to split them since
;; we need to deal with SEW = 64 in RV32 system.
(define_expand "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_commutative_binop:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "reg_or_int_operand"))
(match_operand:V_VLSI_D 3 "register_operand"))
(match_operand:V_VLSI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
riscv_vector::has_vi_variant_p (<CODE>, operands[4]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_<optab><mode> (operands[0], operands[1],
operands[2], operands[3], broadcast_scalar, operands[5],
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_commutative_binop:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))
(match_operand:V_VLSI_D 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_<optab><mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_commutative_binop:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ")))
(match_operand:V_VLSI_D 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_non_commutative_binop:V_VLSI_D
(match_operand:V_VLSI_D 3 "register_operand")
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "reg_or_int_operand")))
(match_operand:V_VLSI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
riscv_vector::has_vi_variant_p (<CODE>, operands[4]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_<optab><mode> (operands[0], operands[1],
operands[2], operands[3], broadcast_scalar, operands[5],
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_non_commutative_binop:V_VLSI_D
(match_operand:V_VLSI_D 3 "register_operand" "vr,vr, vr, vr")
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ")))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_<optab><mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_non_commutative_binop:V_VLSI_D
(match_operand:V_VLSI_D 3 "register_operand" "vr,vr, vr, vr")
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_sub<mode>_reverse_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "reg_or_int_operand"))
(match_operand:V_VLSI_D 3 "register_operand"))
(match_operand:V_VLSI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
riscv_vector::neg_simm5_p (operands[4]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_sub<mode> (operands[0], operands[1],
operands[2], broadcast_scalar, operands[3], operands[5],
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_sub<mode>_reverse_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))
(match_operand:V_VLSI_D 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vrsub.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vialu")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_sub<mode>_extended_reverse_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ")))
(match_operand:V_VLSI_D 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"vrsub.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vialu")
(set_attr "mode" "<MODE>")])
;; Multiply High instructions.
(define_insn "@pred_mulh<v_su><mode>"
[(set (match_operand:VFULLI 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VFULLI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VFULLI
[(match_operand:VFULLI 3 "register_operand" "vr,vr, vr, vr")
(match_operand:VFULLI 4 "register_operand" "vr,vr, vr, vr")] VMULH)
(match_operand:VFULLI 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vmulh<v_su>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vimul")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_mulh<v_su><mode>_scalar"
[(set (match_operand:VI_QHS 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_QHS
[(vec_duplicate:VI_QHS
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))
(match_operand:VI_QHS 3 "register_operand" "vr,vr, vr, vr")] VMULH)
(match_operand:VI_QHS 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vmulh<v_su>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vimul")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_mulh<v_su><mode>_scalar"
[(set (match_operand:VFULLI_D 0 "register_operand")
(if_then_else:VFULLI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VFULLI_D
[(vec_duplicate:VFULLI_D
(match_operand:<VEL> 4 "reg_or_int_operand"))
(match_operand:VFULLI_D 3 "register_operand")] VMULH)
(match_operand:VFULLI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_mulh<v_su><mode> (operands[0], operands[1],
operands[2], operands[3], broadcast_scalar, operands[5],
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_mulh<v_su><mode>_scalar"
[(set (match_operand:VFULLI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VFULLI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VFULLI_D
[(vec_duplicate:VFULLI_D
(match_operand:<VEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ"))
(match_operand:VFULLI_D 3 "register_operand" "vr,vr, vr, vr")] VMULH)
(match_operand:VFULLI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vmulh<v_su>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vimul")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_mulh<v_su><mode>_extended_scalar"
[(set (match_operand:VFULLI_D 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VFULLI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VFULLI_D
[(vec_duplicate:VFULLI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" "rJ,rJ, rJ, rJ")))
(match_operand:VFULLI_D 3 "register_operand" "vr,vr, vr, vr")] VMULH)
(match_operand:VFULLI_D 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"vmulh<v_su>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vimul")
(set_attr "mode" "<MODE>")])
;; Vector Integer Add-with-Carry / Subtract-with-Borrow Instructions
(define_insn "@pred_adc<mode>"
[(set (match_operand:VI 0 "register_operand" "=vd,vd,vd,vd")
(if_then_else:VI
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI
[(plus:VI
(match_operand:VI 2 "register_operand" "vr,vr,vr,vr")
(match_operand:VI 3 "vector_arith_operand" "vr,vr,vi,vi"))
(match_operand:<VM> 4 "register_operand" "vm,vm,vm,vm")] UNSPEC_VADC)
(match_operand:VI 1 "vector_merge_operand" "vu, 0,vu, 0")))]
"TARGET_VECTOR"
"vadc.v%o3m\t%0,%2,%v3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "@pred_sbc<mode>"
[(set (match_operand:VI 0 "register_operand" "=vd,vd")
(if_then_else:VI
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI
[(minus:VI
(match_operand:VI 2 "register_operand" "vr,vr")
(match_operand:VI 3 "register_operand" "vr,vr"))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VSBC)
(match_operand:VI 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR"
"vsbc.vvm\t%0,%2,%3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "@pred_adc<mode>_scalar"
[(set (match_operand:VI_QHS 0 "register_operand" "=vd,vd")
(if_then_else:VI_QHS
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_QHS
[(plus:VI_QHS
(vec_duplicate:VI_QHS
(match_operand:<VEL> 3 "register_operand" " r, r"))
(match_operand:VI_QHS 2 "register_operand" "vr,vr"))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VADC)
(match_operand:VI_QHS 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR"
"vadc.vxm\t%0,%2,%3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "@pred_sbc<mode>_scalar"
[(set (match_operand:VI_QHS 0 "register_operand" "=vd,vd")
(if_then_else:VI_QHS
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_QHS
[(minus:VI_QHS
(match_operand:VI_QHS 2 "register_operand" "vr,vr")
(vec_duplicate:VI_QHS
(match_operand:<VEL> 3 "reg_or_0_operand" "rJ,rJ")))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VSBC)
(match_operand:VI_QHS 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR"
"vsbc.vxm\t%0,%2,%z3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_expand "@pred_adc<mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_D
[(plus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 3 "reg_or_int_operand"))
(match_operand:VI_D 2 "register_operand"))
(match_operand:<VM> 4 "register_operand")] UNSPEC_VADC)
(match_operand:VI_D 1 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[3],
/* vl */operands[5],
<MODE>mode,
riscv_vector::simm5_p (operands[3]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_adc<mode> (operands[0], operands[1],
operands[2], broadcast_scalar, operands[4], operands[5],
operands[6], operands[7]));
},
(riscv_vector::avl_type) INTVAL (operands[7])))
DONE;
})
(define_insn "*pred_adc<mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd,vd")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_D
[(plus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 3 "reg_or_0_operand" "rJ,rJ"))
(match_operand:VI_D 2 "register_operand" "vr,vr"))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VADC)
(match_operand:VI_D 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR"
"vadc.vxm\t%0,%2,%z3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "*pred_adc<mode>_extended_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd,vd")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_D
[(plus:VI_D
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 3 "reg_or_0_operand" "rJ,rJ")))
(match_operand:VI_D 2 "register_operand" "vr,vr"))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VADC)
(match_operand:VI_D 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"vadc.vxm\t%0,%2,%z3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_expand "@pred_sbc<mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_D
[(minus:VI_D
(match_operand:VI_D 2 "register_operand")
(vec_duplicate:VI_D
(match_operand:<VEL> 3 "reg_or_int_operand")))
(match_operand:<VM> 4 "register_operand")] UNSPEC_VSBC)
(match_operand:VI_D 1 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[3],
/* vl */operands[5],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_sbc<mode> (operands[0], operands[1],
operands[2], broadcast_scalar, operands[4], operands[5],
operands[6], operands[7]));
},
(riscv_vector::avl_type) INTVAL (operands[7])))
DONE;
})
(define_insn "*pred_sbc<mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd,vd")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_D
[(minus:VI_D
(match_operand:VI_D 2 "register_operand" "vr,vr")
(vec_duplicate:VI_D
(match_operand:<VEL> 3 "reg_or_0_operand" "rJ,rJ")))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VSBC)
(match_operand:VI_D 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR"
"vsbc.vxm\t%0,%2,%z3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "*pred_sbc<mode>_extended_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd,vd")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_D
[(minus:VI_D
(match_operand:VI_D 2 "register_operand" "vr,vr")
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 3 "reg_or_0_operand" "rJ,rJ"))))
(match_operand:<VM> 4 "register_operand" "vm,vm")] UNSPEC_VSBC)
(match_operand:VI_D 1 "vector_merge_operand" "vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"vsbc.vxm\t%0,%2,%z3,%4"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "@pred_madc<mode>"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr, &vr")
(unspec:<VM>
[(plus:VI
(match_operand:VI 1 "register_operand" " %0, vr, vr")
(match_operand:VI 2 "vector_arith_operand" "vrvi, vr, vi"))
(match_operand:<VM> 3 "register_operand" " vm, vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" " rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMADC))]
"TARGET_VECTOR"
"vmadc.v%o2m\t%0,%1,%v2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none,none")])
(define_insn "@pred_msbc<mode>"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr")
(unspec:<VM>
[(minus:VI
(match_operand:VI 1 "register_operand" " 0, vr, vr")
(match_operand:VI 2 "register_operand" " vr, 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl,rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMSBC))]
"TARGET_VECTOR"
"vmsbc.vvm\t%0,%1,%2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,thv,none")])
(define_insn "@pred_madc<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(plus:VI_QHS
(vec_duplicate:VI_QHS
(match_operand:<VEL> 2 "register_operand" " r, r"))
(match_operand:VI_QHS 1 "register_operand" " 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMADC))]
"TARGET_VECTOR"
"vmadc.vxm\t%0,%1,%2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none")])
(define_insn "@pred_msbc<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(minus:VI_QHS
(vec_duplicate:VI_QHS
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_QHS 1 "register_operand" " 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMSBC))]
"TARGET_VECTOR"
"vmsbc.vxm\t%0,%1,%z2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none")])
(define_expand "@pred_madc<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(unspec:<VM>
[(plus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_int_operand"))
(match_operand:VI_D 1 "register_operand"))
(match_operand:<VM> 3 "register_operand")
(unspec:<VM>
[(match_operand 4 "vector_length_operand")
(match_operand 5 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMADC))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[2],
/* vl */operands[4],
<MODE>mode,
riscv_vector::simm5_p (operands[2]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_madc<mode> (operands[0], operands[1],
broadcast_scalar, operands[3], operands[4], operands[5]));
},
(riscv_vector::avl_type) INTVAL (operands[5])))
DONE;
})
(define_insn "*pred_madc<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(plus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMADC))]
"TARGET_VECTOR"
"vmadc.vxm\t%0,%1,%z2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none")])
(define_insn "*pred_madc<mode>_extended_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(plus:VI_D
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMADC))]
"TARGET_VECTOR && !TARGET_64BIT"
"vmadc.vxm\t%0,%1,%z2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none")])
(define_expand "@pred_msbc<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(unspec:<VM>
[(minus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_int_operand"))
(match_operand:VI_D 1 "register_operand"))
(match_operand:<VM> 3 "register_operand")
(unspec:<VM>
[(match_operand 4 "vector_length_operand")
(match_operand 5 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMSBC))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[2],
/* vl */operands[4],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_msbc<mode> (operands[0], operands[1],
broadcast_scalar, operands[3], operands[4], operands[5]));
},
(riscv_vector::avl_type) INTVAL (operands[5])))
DONE;
})
(define_insn "*pred_msbc<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(minus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMSBC))]
"TARGET_VECTOR"
"vmsbc.vxm\t%0,%1,%z2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none")])
(define_insn "*pred_msbc<mode>_extended_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(minus:VI_D
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(match_operand:<VM> 3 "register_operand" " vm, vm")
(unspec:<VM>
[(match_operand 4 "vector_length_operand" "rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_VMSBC))]
"TARGET_VECTOR && !TARGET_64BIT"
"vmsbc.vxm\t%0,%1,%z2,%3"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))
(set_attr "spec_restriction" "thv,none")])
(define_insn "@pred_madc<mode>_overflow"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr, &vr")
(unspec:<VM>
[(plus:VI
(match_operand:VI 1 "register_operand" " %0, vr, vr")
(match_operand:VI 2 "vector_arith_operand" "vrvi, vr, vi"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" " rvl, rvl, rvl")
(match_operand 4 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
"vmadc.v%o2\t%0,%1,%v2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none,none")])
(define_insn "@pred_msbc<mode>_overflow"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr, &vr")
(unspec:<VM>
[(minus:VI
(match_operand:VI 1 "register_operand" " 0, vr, vr, vr")
(match_operand:VI 2 "register_operand" " vr, 0, vr, vi"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 4 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
"vmsbc.vv\t%0,%1,%2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,thv,none,none")])
(define_insn "@pred_madc<mode>_overflow_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(plus:VI_QHS
(vec_duplicate:VI_QHS
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_QHS 1 "register_operand" " 0, vr"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" "rvl, rvl")
(match_operand 4 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
"vmadc.vx\t%0,%1,%z2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none")])
(define_insn "@pred_msbc<mode>_overflow_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(minus:VI_QHS
(vec_duplicate:VI_QHS
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_QHS 1 "register_operand" " 0, vr"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" "rvl, rvl")
(match_operand 4 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
"vmsbc.vx\t%0,%1,%z2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none")])
(define_expand "@pred_madc<mode>_overflow_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(unspec:<VM>
[(plus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_int_operand"))
(match_operand:VI_D 1 "register_operand"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand")
(match_operand 4 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[2],
/* vl */operands[3],
<MODE>mode,
riscv_vector::simm5_p (operands[2]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_madc<mode>_overflow (operands[0], operands[1],
broadcast_scalar, operands[3], operands[4]));
},
(riscv_vector::avl_type) INTVAL (operands[4])))
DONE;
})
(define_insn "*pred_madc<mode>_overflow_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(plus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" "rvl, rvl")
(match_operand 4 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
"vmadc.vx\t%0,%1,%z2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none")])
(define_insn "*pred_madc<mode>_overflow_extended_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(plus:VI_D
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" "rvl, rvl")
(match_operand 4 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR && !TARGET_64BIT"
"vmadc.vx\t%0,%1,%z2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none")])
(define_expand "@pred_msbc<mode>_overflow_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(unspec:<VM>
[(minus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_int_operand"))
(match_operand:VI_D 1 "register_operand"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand")
(match_operand 4 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[2],
/* vl */operands[3],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_msbc<mode>_overflow (operands[0], operands[1],
broadcast_scalar, operands[3], operands[4]));
},
(riscv_vector::avl_type) INTVAL (operands[4])))
DONE;
})
(define_insn "*pred_msbc<mode>_overflow_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(minus:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" "rvl, rvl")
(match_operand 4 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR"
"vmsbc.vx\t%0,%1,%z2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none")])
(define_insn "*pred_msbc<mode>_overflow_extended_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, &vr")
(unspec:<VM>
[(minus:VI_D
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:VI_D 1 "register_operand" " 0, vr"))
(unspec:<VM>
[(match_operand 3 "vector_length_operand" "rvl, rvl")
(match_operand 4 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)] UNSPEC_OVERFLOW))]
"TARGET_VECTOR && !TARGET_64BIT"
"vmsbc.vx\t%0,%1,%z2"
[(set_attr "type" "vicalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "3")
(set (attr "avl_type_idx") (const_int 4))
(set_attr "spec_restriction" "thv,none")])
;; -------------------------------------------------------------------------------
;; ---- Predicated integer unary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - vneg.v/vnot.v
;; -------------------------------------------------------------------------------
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_int_unop:V_VLSI
(match_operand:V_VLSI 3 "register_operand" "vr,vr, vr, vr"))
(match_operand:V_VLSI 2 "vector_merge_operand" "vu, 0, vu, 0")))]
"TARGET_VECTOR"
{
/* vneg.v = vrsub vd,vs,x0 = vrsub vd,vs,0. */
return (<CODE> == NEG) ? "vrsub.vi\t%0,%3,0%p1" : "v<insn>.v\t%0,%3%p1";
}
[(set_attr "type" "vialu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[5])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; -------------------------------------------------------------------------------
;; ---- Predicated integer widening binary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 11.2 Vector Widening Integer Add/Subtract
;; - 11.3 Vector Integer Extension
;; - 11.12 Vector Widening Integer Multiply Instructions
;; -------------------------------------------------------------------------------
;; Vector Double-Widening Sign-extend and Zero-extend.
(define_insn "@pred_<optab><mode>_vf2"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"v<sz>ext.vf2\t%0,%3%p1"
[(set_attr "type" "vext")
(set_attr "mode" "<MODE>")])
;; Vector Quad-Widening Sign-extend and Zero-extend.
(define_insn "@pred_<optab><mode>_vf4"
[(set (match_operand:VQEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VQEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_extend:VQEXTI
(match_operand:<V_QUAD_TRUNC> 3 "register_operand" " vr, vr"))
(match_operand:VQEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"v<sz>ext.vf4\t%0,%3%p1"
[(set_attr "type" "vext")
(set_attr "mode" "<MODE>")])
;; Vector Oct-Widening Sign-extend and Zero-extend.
(define_insn "@pred_<optab><mode>_vf8"
[(set (match_operand:VOEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VOEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_extend:VOEXTI
(match_operand:<V_OCT_TRUNC> 3 "register_operand" " vr, vr"))
(match_operand:VOEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR && !TARGET_XTHEADVECTOR"
"v<sz>ext.vf8\t%0,%3%p1"
[(set_attr "type" "vext")
(set_attr "mode" "<MODE>")])
;; Vector Widening Add/Subtract/Multiply.
(define_insn "@pred_dual_widen_<any_widen_binop:optab><any_extend:su><mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_widen_binop:VWEXTI
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr")))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vw<any_widen_binop:insn><any_extend:u>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vi<widen_binop_insn_type>")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_dual_widen_<any_widen_binop:optab><any_extend:su><mode>_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_widen_binop:VWEXTI
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(any_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ, rJ"))))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vw<any_widen_binop:insn><any_extend:u>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vi<widen_binop_insn_type>")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_single_widen_sub<any_extend:su><mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:VWEXTI
(match_operand:VWEXTI 3 "register_operand" " vr, vr")
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr")))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vwsub<any_extend:u>.wv\t%0,%3,%4%p1"
[(set_attr "type" "viwalu")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_single_widen_add<any_extend:su><mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr"))
(match_operand:VWEXTI 3 "register_operand" " vr, vr"))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vwadd<any_extend:u>.wv\t%0,%3,%4%p1"
[(set_attr "type" "viwalu")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_single_widen_<plus_minus:optab><any_extend:su><mode>_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:VWEXTI
(match_operand:VWEXTI 3 "register_operand" " vr,vr, vr, vr")
(any_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ,rJ, rJ, rJ"))))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vw<plus_minus:insn><any_extend:u>.wx\t%0,%3,%z4%p1"
[(set_attr "type" "vi<widen_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_single_widen_add<any_extend:su><mode>_extended_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(vec_duplicate:VWEXTI
(any_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ,rJ, rJ, rJ")))
(match_operand:VWEXTI 3 "register_operand" " vr,vr, vr, vr"))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vwadd<any_extend:u>.wx\t%0,%3,%z4%p1"
[(set_attr "type" "viwalu")
(set_attr "mode_idx" "3")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_single_widen_sub<any_extend:su><mode>_extended_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:VWEXTI
(match_operand:VWEXTI 3 "register_operand" " vr,vr, vr, vr")
(vec_duplicate:VWEXTI
(any_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ,rJ, rJ, rJ"))))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vwsub<any_extend:u>.wx\t%0,%3,%z4%p1"
[(set_attr "type" "viwalu")
(set_attr "mode_idx" "3")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_widen_mulsu<mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(mult:VWEXTI
(sign_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(zero_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr")))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vwmulsu.vv\t%0,%3,%4%p1"
[(set_attr "type" "viwmul")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_widen_mulsu<mode>_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(mult:VWEXTI
(sign_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(zero_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ, rJ"))))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vwmulsu.vx\t%0,%3,%z4%p1"
[(set_attr "type" "viwmul")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
;; vwcvt<u>.x.x.v
(define_insn "@pred_<optab><mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr,&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(vec_duplicate:VWEXTI
(reg:<VEL> X0_REGNUM)))
(match_operand:VWEXTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vwcvt<u>.x.x.v\t%0,%3%p1"
[(set_attr "type" "viwalu")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set_attr "vl_op_idx" "4")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[5])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; -------------------------------------------------------------------------------
;; ---- Predicated integer Narrowing operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 11.7 Vector Narrowing Integer Right Shift Instructions
;; -------------------------------------------------------------------------------
;; The destination EEW is smaller than the source EEW and the overlap is in the
;; lowest-numbered part of the source register group
;; e.g, when LMUL = 1, vnsrl.wi v0,v0,3 is legal but a destination of v1 is not.
(define_insn "@pred_narrow_<optab><mode>"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd,vd, vr, vr,vd, vr, &vr, &vr, vd, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1,vm,Wc1,vmWc1,vmWc1, vm,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl,rvl,rvl, rvl, rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(truncate:<V_DOUBLE_TRUNC>
(any_shiftrt:VWEXTI
(match_operand:VWEXTI 3 "register_operand" " vr,vr, vr, vr, 0, 0, vr, vr, 0, 0, vr, vr")
(match_operand:<V_DOUBLE_TRUNC> 4 "vector_shift_operand" " 0, 0, 0, 0,vr, vr, vr, vr, vk, vk, vk, vk")))
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " 0,vu, 0, vu,vu, vu, vu, 0, vu, vu, vu, 0")))]
"TARGET_VECTOR"
"vn<insn>.w%o4\t%0,%3,%v4%p1"
[(set_attr "type" "vnshift")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set_attr "spec_restriction" "none,none,thv,thv,none,thv,none,none,none,thv,none,none")])
(define_insn "@pred_narrow_<optab><mode>_scalar"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(truncate:<V_DOUBLE_TRUNC>
(any_shiftrt:VWEXTI
(match_operand:VWEXTI 3 "register_operand" " 0, 0, 0, 0, vr, vr")
(match_operand 4 "pmode_reg_or_uimm5_operand" " rK, rK, rK, rK, rK, rK")))
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
{
/* vnsrl vd,vs,x0 = vnsrl vd,vs,0. */
if (REG_P (operands[4]) && REGNO (operands[4]) == 0)
return "vn<insn>.wi\t%0,%3,0%p1";
return "vn<insn>.w%o4\t%0,%3,%4%p1";
}
[(set_attr "type" "vnshift")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set_attr "spec_restriction" "none,none,thv,thv,none,none")])
;; vncvt.x.x.w
(define_insn "@pred_trunc<mode>"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(truncate:<V_DOUBLE_TRUNC>
(match_operand:VWEXTI 3 "register_operand" " 0, 0, 0, 0, vr, vr"))
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
;; vncvt.x.x.w = vnsrl vd,vs,x0 = vnsrl vd,vs,0
"vnsrl.wi\t%0,%3,0%p1";
[(set_attr "type" "vnshift")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set_attr "vl_op_idx" "4")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[5])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))
(set_attr "spec_restriction" "none,none,thv,thv,none,none")])
;; -------------------------------------------------------------------------------
;; ---- Predicated fixed-point operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 12.1 Vector Single-Width Saturating Add and Subtract
;; - 12.2 Vector Single-Width Averaging Add and Subtract
;; - 12.3 Vector Single-Width Fractional Multiply with Rounding and Saturation
;; - 12.4 Vector Single-Width Scaling Shift Instructions
;; - 12.5 Vector Narrowing Fixed-Point Clip Instructions
;; -------------------------------------------------------------------------------
;; Saturating Add and Subtract
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr, vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1, vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl,rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_sat_int_binop:V_VLSI
(match_operand:V_VLSI 3 "<binop_rhs1_predicate>" " vr, vr, vr, vr, vr, vr, vr, vr")
(match_operand:V_VLSI 4 "<binop_rhs2_predicate>" "<binop_rhs2_constraint>"))
(match_operand:V_VLSI 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"@
v<insn>.vv\t%0,%3,%4%p1
v<insn>.vv\t%0,%3,%4%p1
v<insn>.vv\t%0,%3,%4%p1
v<insn>.vv\t%0,%3,%4%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1
v<binop_vi_variant_insn>\t%0,<binop_vi_variant_op>%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
;; Handle GET_MODE_INNER (mode) = QImode, HImode, SImode.
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:VI_QHS 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_plus_binop:VI_QHS
(vec_duplicate:VI_QHS
(match_operand:<VEL> 4 "register_operand" " r, r, r, r"))
(match_operand:VI_QHS 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:VI_QHS 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:VI_QHS 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_minus_binop:VI_QHS
(match_operand:VI_QHS 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:VI_QHS
(match_operand:<VEL> 4 "register_operand" " r, r, r, r")))
(match_operand:VI_QHS 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_<optab><mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_plus_binop:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 4 "reg_or_int_operand"))
(match_operand:VI_D 3 "register_operand"))
(match_operand:VI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
riscv_vector::has_vi_variant_p (<CODE>, operands[4]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_<optab><mode> (operands[0], operands[1],
operands[2], operands[3], broadcast_scalar, operands[5],
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_<optab><mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_plus_binop:VI_D
(vec_duplicate:VI_D
(match_operand:<VEL> 4 "register_operand" " r, r, r, r"))
(match_operand:VI_D 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:VI_D 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_<optab><mode>_extended_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_plus_binop:VI_D
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "register_operand" " r, r, r, r")))
(match_operand:VI_D 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:VI_D 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"v<insn>.vx\t%0,%3,%4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_<optab><mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_minus_binop:VI_D
(match_operand:VI_D 3 "register_operand")
(vec_duplicate:VI_D
(match_operand:<VEL> 4 "reg_or_int_operand")))
(match_operand:VI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
riscv_vector::has_vi_variant_p (<CODE>, operands[4]),
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_<optab><mode> (operands[0], operands[1],
operands[2], operands[3], broadcast_scalar, operands[5],
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_<optab><mode>_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_minus_binop:VI_D
(match_operand:VI_D 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:VI_D
(match_operand:<VEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ")))
(match_operand:VI_D 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_<optab><mode>_extended_scalar"
[(set (match_operand:VI_D 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(sat_int_minus_binop:VI_D
(match_operand:VI_D 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:VI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))))
(match_operand:VI_D 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"v<insn>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<sat_op><mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSI
[(match_operand:V_VLSI 3 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSI 4 "register_operand" " vr, vr, vr, vr")] VSAT_OP)
(match_operand:V_VLSI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<sat_op>.vv\t%0,%3,%4%p1"
[(set_attr "type" "<sat_insn_type>")
(set_attr "mode" "<MODE>")])
;; Handle GET_MODE_INNER (mode) = QImode, HImode, SImode.
(define_insn "@pred_<sat_op><mode>_scalar"
[(set (match_operand:VI_QHS 0 "register_operand" "=vd, vr, vd, vr")
(if_then_else:VI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI_QHS
[(match_operand:VI_QHS 3 "register_operand" " vr, vr, vr, vr")
(match_operand:<VEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ")] VSAT_ARITH_OP)
(match_operand:VI_QHS 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<sat_op>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<sat_insn_type>")
(set_attr "mode_idx" "3")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<sat_op><mode>_scalar"
[(set (match_operand:VI 0 "register_operand" "=vd, vr, vd, vr")
(if_then_else:VI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VI
[(match_operand:VI 3 "register_operand" " vr, vr, vr, vr")
(match_operand 4 "pmode_reg_or_uimm5_operand" " rK, rK, rK, rK")] VSAT_SHIFT_OP)
(match_operand:VI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<sat_op>.v%o4\t%0,%3,%4%p1"
[(set_attr "type" "<sat_insn_type>")
(set_attr "mode" "<MODE>")])
;; Handle GET_MODE_INNER (mode) = DImode. We need to split them since
;; we need to deal with SEW = 64 in RV32 system.
(define_expand "@pred_<sat_op><mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "vector_length_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSI_D
[(match_operand:V_VLSI_D 3 "register_operand")
(match_operand:<VEL> 4 "reg_or_int_operand")] VSAT_ARITH_OP)
(match_operand:V_VLSI_D 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[4],
/* vl */operands[5],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_<sat_op><mode> (operands[0], operands[1],
operands[2], operands[3], broadcast_scalar, operands[5],
operands[6], operands[7], operands[8], operands[9]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_<sat_op><mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vr, vd, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSI_D
[(match_operand:V_VLSI_D 3 "register_operand" " vr, vr, vr, vr")
(match_operand:<VEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ")] VSAT_ARITH_OP)
(match_operand:V_VLSI_D 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<sat_op>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<sat_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_<sat_op><mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vr, vd, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSI_D
[(match_operand:V_VLSI_D 3 "register_operand" " vr, vr, vr, vr")
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))] VSAT_ARITH_OP)
(match_operand:V_VLSI_D 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && !TARGET_64BIT"
"v<sat_op>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "<sat_insn_type>")
(set_attr "mode" "<MODE>")])
;; CLIP
(define_insn "@pred_narrow_clip<v_su><mode>"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd,vd, vr, vr,vd, vr, &vr, &vr, vd, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1,vm,Wc1,vmWc1,vmWc1, vm,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl,rvl,rvl, rvl, rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i, i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_DOUBLE_TRUNC>
[(match_operand:VWEXTI 3 "register_operand" " vr,vr, vr, vr, 0, 0, vr, vr, 0, 0, vr, vr")
(match_operand:<V_DOUBLE_TRUNC> 4 "vector_shift_operand" " 0, 0, 0, 0,vr, vr, vr, vr, vk, vk, vk, vk")] VNCLIP)
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " 0,vu, 0, vu,vu, vu, vu, 0, vu, vu, vu, 0")))]
"TARGET_VECTOR"
"vnclip<v_su>.w%o4\t%0,%3,%v4%p1"
[(set_attr "type" "vnclip")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set_attr "spec_restriction" "thv,thv,thv,thv,thv,thv,none,none,thv,thv,none,none")])
(define_insn "@pred_narrow_clip<v_su><mode>_scalar"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI VXRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_DOUBLE_TRUNC>
[(match_operand:VWEXTI 3 "register_operand" " 0, 0, 0, 0, vr, vr")
(match_operand 4 "pmode_reg_or_uimm5_operand" " rK, rK, rK, rK, rK, rK")] VNCLIP)
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vnclip<v_su>.w%o4\t%0,%3,%4%p1"
[(set_attr "type" "vnclip")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set_attr "spec_restriction" "thv,thv,thv,thv,none,none")])
;; -------------------------------------------------------------------------------
;; ---- Predicated integer comparison operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 11.8 Vector Integer Comparison Instructions
;; -------------------------------------------------------------------------------
(define_expand "@pred_cmp<mode>"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ltge_operator"
[(match_operand:V_VLSI 4 "register_operand")
(match_operand:V_VLSI 5 "vector_arith_operand")])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{})
(define_insn "*pred_cmp<mode>_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "comparison_except_ltge_operator"
[(match_operand:V_VLSI 3 "register_operand" " vr")
(match_operand:V_VLSI 4 "vector_arith_operand" "vrvi")])
(match_dup 1)))]
"TARGET_VECTOR"
"vms%B2.v%o4\t%0,%3,%v4,v0.t"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_cmp<mode>"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, vr, vr, &vr, &vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ltge_operator"
[(match_operand:V_VLSI 4 "register_operand" " vr, vr, vr, vr, vr, vr, vr, vr")
(match_operand:V_VLSI 5 "vector_arith_operand" " vr, vr, vi, vi, vr, vr, vi, vi")])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode)"
"vms%B3.v%o5\t%0,%4,%v5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,thv,thv,rvv,rvv,rvv,rvv")])
;; We use early-clobber for source LMUL > dest LMUL.
(define_insn "*pred_cmp<mode>_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, vr, vr, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ltge_operator"
[(match_operand:V_VLSI 4 "register_operand" " vr, 0, vr, 0, 0, vr, 0, vr, vr")
(match_operand:V_VLSI 5 "vector_arith_operand" " vrvi, vrvi, 0, 0, vrvi, 0, 0, vrvi, vrvi")])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, vu, vu, 0, 0, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode)"
"vms%B3.v%o5\t%0,%4,%v5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,thv,thv,thv,thv,none,none")])
(define_expand "@pred_ltge<mode>"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "ltge_operator"
[(match_operand:V_VLSI 4 "register_operand")
(match_operand:V_VLSI 5 "vector_neg_arith_operand")])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{})
(define_insn "*pred_ltge<mode>_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "ltge_operator"
[(match_operand:V_VLSI 3 "register_operand" " vr")
(match_operand:V_VLSI 4 "vector_neg_arith_operand" "vrvj")])
(match_dup 1)))]
"TARGET_VECTOR"
"vms%B2.v%o4\t%0,%3,%v4,v0.t"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_ltge<mode>"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, vr, vr, &vr, &vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "ltge_operator"
[(match_operand:V_VLSI 4 "register_operand" " vr, vr, vr, vr, vr, vr, vr, vr")
(match_operand:V_VLSI 5 "vector_neg_arith_operand" " vr, vr, vj, vj, vr, vr, vj, vj")])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode)"
"vms%B3.v%o5\t%0,%4,%v5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,thv,thv,rvv,rvv,rvv,rvv")])
;; We use early-clobber for source LMUL > dest LMUL.
(define_insn "*pred_ltge<mode>_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, vr, vr, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "ltge_operator"
[(match_operand:V_VLSI 4 "register_operand" " vr, 0, vr, 0, 0, vr, 0, vr, vr")
(match_operand:V_VLSI 5 "vector_neg_arith_operand" " vrvj, vrvj, 0, 0, vrvj, 0, 0, vrvj, vrvj")])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, vu, vu, 0, 0, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode)"
"vms%B3.v%o5\t%0,%4,%v5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,thv,thv,thv,thv,none,none")])
(define_expand "@pred_cmp<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_QHS 4 "register_operand")
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 5 "register_operand"))])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{})
(define_insn "*pred_cmp<mode>_scalar_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "comparison_except_ge_operator"
[(match_operand:V_VLSI_QHS 3 "register_operand" " vr")
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 4 "register_operand" " r"))])
(match_dup 1)))]
"TARGET_VECTOR"
"vms%B2.vx\t%0,%3,%4,v0.t"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_cmp<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_QHS 4 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 5 "register_operand" " r, r, r, r"))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode)"
"vms%B3.vx\t%0,%4,%5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,rvv,rvv")])
;; We use early-clobber for source LMUL > dest LMUL.
(define_insn "*pred_cmp<mode>_scalar_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_QHS 4 "register_operand" " vr, 0, 0, vr, vr")
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 5 "register_operand" " r, r, r, r, r"))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode)"
"vms%B3.vx\t%0,%4,%5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,none,none")])
;; Handle GET_MODE_INNER (mode) = DImode. We need to split them since
;; we need to deal with SEW = 64 in RV32 system.
(define_expand "@pred_cmp<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 4 "register_operand")
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 5 "reg_or_int_operand"))])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
enum rtx_code code = GET_CODE (operands[3]);
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[5],
/* vl */operands[6],
<MODE>mode,
riscv_vector::has_vi_variant_p (code, operands[5]),
code == LT || code == LTU ?
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_ltge<mode> (operands[0], operands[1],
operands[2], operands[3], operands[4], broadcast_scalar,
operands[6], operands[7], operands[8]));
}
:
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_cmp<mode> (operands[0], operands[1],
operands[2], operands[3], operands[4], broadcast_scalar,
operands[6], operands[7], operands[8]));
},
(riscv_vector::avl_type) INTVAL (operands[8])))
DONE;
})
(define_insn "*pred_cmp<mode>_scalar_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 3 "register_operand" " vr")
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 4 "register_operand" " r"))])
(match_dup 1)))]
"TARGET_VECTOR"
"vms%B2.vx\t%0,%3,%4,v0.t"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_cmp<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 4 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 5 "register_operand" " r, r, r, r"))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode)"
"vms%B3.vx\t%0,%4,%5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,rvv,rvv")])
;; We use early-clobber for source LMUL > dest LMUL.
(define_insn "*pred_cmp<mode>_scalar_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 4 "register_operand" " vr, 0, 0, vr, vr")
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 5 "register_operand" " r, r, r, r, r"))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode)"
"vms%B3.vx\t%0,%4,%5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,none,none")])
(define_insn "*pred_cmp<mode>_extended_scalar_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 3 "register_operand" " vr")
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "register_operand" " r")))])
(match_dup 1)))]
"TARGET_VECTOR && !TARGET_64BIT"
"vms%B2.vx\t%0,%3,%4,v0.t"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_cmp<mode>_extended_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 4 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 5 "register_operand" " r, r, r, r")))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode) && !TARGET_64BIT"
"vms%B3.vx\t%0,%4,%5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,rvv,rvv")])
(define_insn "*pred_cmp<mode>_extended_scalar_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "comparison_except_ge_operator"
[(match_operand:V_VLSI_D 4 "register_operand" " vr, 0, 0, vr, vr")
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 5 "register_operand" " r, r, r, r, r")))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode) && !TARGET_64BIT"
"vms%B3.vx\t%0,%4,%5%p1"
[(set_attr "type" "vicmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,none,none")])
;; GE, vmsge.vx/vmsgeu.vx
;;
;; unmasked va >= x
;; - pseudoinstruction: vmsge{u}.vx vd, va, x
;; - expansion: vmslt{u}.vx vd, va, x; vmnand.mm vd, vd, vd
;;
;; masked va >= x, vd != v0
;; - pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t
;; - expansion: vmslt{u}.vx vd, va, x, v0.t; vmxor.mm vd, vd, v0
;;
;; masked va >= x, vd == v0
;; - pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t, vt
;; - expansion: vmslt{u}.vx vt, va, x; vmandn.mm vd, vd, vt
(define_expand "@pred_ge<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "ge_operator"
[(match_operand:V_VLSI 4 "register_operand")
(vec_duplicate:V_VLSI
(match_operand:<VEL> 5 "reg_or_int_operand"))])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{
enum rtx_code code = GET_CODE (operands[3]);
rtx undef = RVV_VUNDEF (<VM>mode);
rtx tmp = gen_reg_rtx (<VM>mode);
if (code == GEU && rtx_equal_p (operands[5], const0_rtx))
{
/* If vmsgeu with 0 immediate, expand it to vmset. */
if (satisfies_constraint_Wc1 (operands[1]))
emit_insn (
gen_pred_mov (<VM>mode, operands[0], CONSTM1_RTX (<VM>mode), undef,
CONSTM1_RTX (<VM>mode), operands[6], operands[8]));
else
{
/* If vmsgeu_mask with 0 immediate, expand it to vmor mask, maskedoff.
*/
if (rtx_equal_p (operands[1], operands[2]))
emit_move_insn (operands[0], operands[1]);
else if (register_operand (operands[2], <VM>mode))
emit_insn (gen_pred (IOR, <VM>mode, operands[0],
CONSTM1_RTX (<VM>mode), undef, operands[1],
operands[2], operands[6], operands[8]));
else
emit_insn (gen_pred (IOR, <VM>mode, operands[0],
CONSTM1_RTX (<VM>mode), undef, operands[1],
operands[1], operands[6], operands[8]));
}
}
else if (riscv_vector::neg_simm5_p (operands[5]))
emit_insn (
gen_pred_ltge<mode> (operands[0], operands[1], operands[2], operands[3],
operands[4],
gen_const_vec_duplicate (<MODE>mode, operands[5]),
operands[6], operands[7], operands[8]));
else
{
if (code == GE)
operands[3] = gen_rtx_fmt_ee (LT, <VM>mode, XEXP (operands[3], 0),
XEXP (operands[3], 1));
else
operands[3] = gen_rtx_fmt_ee (LTU, <VM>mode, XEXP (operands[3], 0),
XEXP (operands[3], 1));
if (GET_MODE_BITSIZE (<VEL>mode) <= GET_MODE_BITSIZE (Pmode))
operands[5] = force_reg (<VEL>mode, operands[5]);
if (satisfies_constraint_Wc1 (operands[1]))
{
/* unmasked va >= x
- pseudoinstruction: vmsge{u}.vx vd, va, x
- expansion: vmslt{u}.vx vd, va, x; vmnand.mm vd, vd, vd. */
emit_insn (
gen_pred_cmp<mode>_scalar (tmp, operands[1], operands[2],
operands[3], operands[4], operands[5],
operands[6], operands[7], operands[8]));
emit_insn (gen_pred_nand<vm> (operands[0], CONSTM1_RTX (<VM>mode),
undef, tmp, tmp, operands[6], operands[8]));
}
else
{
if (rtx_equal_p (operands[1], operands[2]))
{
/* masked va >= x, vd == v0
- pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t, vt
- expansion: vmslt{u}.vx vt, va, x; vmandn.mm vd, vd, vt. */
emit_insn (gen_pred_cmp<mode>_scalar (
tmp, CONSTM1_RTX (<VM>mode), undef, operands[3], operands[4],
operands[5], operands[6], operands[7], operands[8]));
emit_insn (
gen_pred_andnot<vm> (operands[0], CONSTM1_RTX (<VM>mode), undef,
operands[1], tmp, operands[6], operands[8]));
}
else
{
/* masked va >= x, vd != v0
- pseudoinstruction: vmsge{u}.vx vd, va, x, v0.t
- expansion: vmslt{u}.vx vd, va, x, v0.t; vmxor.mm vd, vd, v0.
*/
emit_insn (gen_pred_cmp<mode>_scalar (
tmp, operands[1], operands[2], operands[3], operands[4],
operands[5], operands[6], operands[7], operands[8]));
emit_insn (gen_pred (XOR, <VM>mode, operands[0],
CONSTM1_RTX (<VM>mode), undef, tmp,
operands[1], operands[6], operands[8]));
}
}
}
DONE;
})
;; -------------------------------------------------------------------------------
;; ---- Predicated integer ternary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 11.13 Vector Single-Width Integer Multiply-Add Instructions
;; -------------------------------------------------------------------------------
(define_expand "@pred_mul_plus<mode>"
[(set (match_operand:V_VLSI 0 "register_operand")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI
(mult:V_VLSI
(match_operand:V_VLSI 2 "register_operand")
(match_operand:V_VLSI 3 "register_operand"))
(match_operand:V_VLSI 4 "register_operand"))
(match_operand:V_VLSI 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_mul_plus<mode>_undef"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1,Wc1")
(match_operand 6 "vector_length_operand" "rvl,rvl, rvl,rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI
(mult:V_VLSI
(match_operand:V_VLSI 3 "register_operand" " 0, vr, 0, vr")
(match_operand:V_VLSI 4 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSI 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSI 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vmadd.vv\t%0,%4,%5%p1
vmacc.vv\t%0,%3,%4%p1
vmadd.vv\t%0,%4,%5%p1
vmacc.vv\t%0,%3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_madd<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI
(mult:V_VLSI
(match_operand:V_VLSI 2 "register_operand" " 0, 0")
(match_operand:V_VLSI 3 "register_operand" " vr, vr"))
(match_operand:V_VLSI 4 "register_operand" " vr, vr"))
(match_dup 2)))]
"TARGET_VECTOR"
"@
vmadd.vv\t%0,%3,%4%p1
vmadd.vv\t%0,%3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "2")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_insn "*pred_macc<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI
(mult:V_VLSI
(match_operand:V_VLSI 2 "register_operand" " vr, vr")
(match_operand:V_VLSI 3 "register_operand" " vr, vr"))
(match_operand:V_VLSI 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR"
"vmacc.vv\t%0,%2,%3%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_expand "@pred_mul_plus<mode>_scalar"
[(set (match_operand:V_VLSI_QHS 0 "register_operand")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_QHS
(mult:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 2 "register_operand"))
(match_operand:V_VLSI_QHS 3 "register_operand"))
(match_operand:V_VLSI_QHS 4 "register_operand"))
(match_operand:V_VLSI_QHS 5 "register_operand")))]
"TARGET_VECTOR"
{})
(define_expand "@pred_mul_minus_vx_<mode>"
[(set (match_operand:V_VLSI_QHS 0 "register_operand")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_QHS
(match_operand:V_VLSI_QHS 4 "register_operand")
(mult:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 2 "register_operand"))
(match_operand:V_VLSI_QHS 3 "register_operand")))
(match_operand:V_VLSI_QHS 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_expand "@pred_mul_minus_vx_<mode>"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(match_operand:V_VLSI_D 4 "register_operand")
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 2 "register_operand"))
(match_operand:V_VLSI_D 3 "register_operand")))
(match_operand:V_VLSI_D 5 "vector_merge_operand")))]
"TARGET_VECTOR && TARGET_64BIT"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_madd<mode>_scalar"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI
(mult:V_VLSI
(vec_duplicate:V_VLSI
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:V_VLSI 3 "register_operand" " 0, 0"))
(match_operand:V_VLSI 4 "register_operand" " vr, vr"))
(match_dup 3)))]
"TARGET_VECTOR"
"@
vmadd.vx\t%0,%z2,%4%p1
vmadd.vx\t%0,%z2,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "3")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_insn "*pred_macc<mode>_scalar"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI
(mult:V_VLSI
(vec_duplicate:V_VLSI
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:V_VLSI 3 "register_operand" " vr, vr"))
(match_operand:V_VLSI 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vmacc.vx\t%0,%z2,%3%p1
vmacc.vx\t%0,%z2,%3%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_expand "@pred_mul_plus<mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_D
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 2 "reg_or_int_operand"))
(match_operand:V_VLSI_D 3 "register_operand"))
(match_operand:V_VLSI_D 4 "register_operand"))
(match_operand:V_VLSI_D 5 "register_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[2],
/* vl */operands[6],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_mul_plus<mode> (operands[0], operands[1],
broadcast_scalar, operands[3], operands[4], operands[5],
operands[6], operands[7], operands[8], operands[9]));
},
(riscv_vector::avl_type) INTVAL (operands[9])))
DONE;
})
(define_insn "*pred_madd<mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_D
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:V_VLSI_D 3 "register_operand" " 0, 0"))
(match_operand:V_VLSI_D 4 "register_operand" " vr, vr"))
(match_dup 3)))]
"TARGET_VECTOR && !TARGET_64BIT"
"@
vmadd.vx\t%0,%z2,%4%p1
vmadd.vx\t%0,%z2,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "3")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_insn "*pred_macc<mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_D
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:V_VLSI_D 3 "register_operand" " vr, vr"))
(match_operand:V_VLSI_D 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR && !TARGET_64BIT"
"@
vmacc.vx\t%0,%z2,%3%p1
vmacc.vx\t%0,%z2,%3%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_expand "@pred_minus_mul<mode>"
[(set (match_operand:V_VLSI 0 "register_operand")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI
(match_operand:V_VLSI 4 "register_operand")
(mult:V_VLSI
(match_operand:V_VLSI 2 "register_operand")
(match_operand:V_VLSI 3 "register_operand")))
(match_operand:V_VLSI 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_minus_mul<mode>_undef"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 6 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI
(match_operand:V_VLSI 5 "register_operand" " vr, 0, vr, 0")
(mult:V_VLSI
(match_operand:V_VLSI 3 "register_operand" " 0, vr, 0, vr")
(match_operand:V_VLSI 4 "register_operand" " vr, vr, vr, vr")))
(match_operand:V_VLSI 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vnmsub.vv\t%0,%4,%5%p1
vnmsac.vv\t%0,%3,%4%p1
vnmsub.vv\t%0,%4,%5%p1
vnmsac.vv\t%0,%3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_nmsub<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI
(match_operand:V_VLSI 4 "register_operand" " vr, vr")
(mult:V_VLSI
(match_operand:V_VLSI 2 "register_operand" " 0, 0")
(match_operand:V_VLSI 3 "register_operand" " vr, vr")))
(match_dup 2)))]
"TARGET_VECTOR"
"@
vnmsub.vv\t%0,%3,%4%p1
vnmsub.vv\t%0,%3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "2")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_insn "*pred_nmsac<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI
(match_operand:V_VLSI 4 "register_operand" " 0, 0")
(mult:V_VLSI
(match_operand:V_VLSI 2 "register_operand" " vr, vr")
(match_operand:V_VLSI 3 "register_operand" " vr, vr")))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vnmsac.vv\t%0,%2,%3%p1
vnmsac.vv\t%0,%2,%3%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_expand "@pred_minus_mul<mode>_scalar"
[(set (match_operand:V_VLSI_QHS 0 "register_operand")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_QHS
(match_operand:V_VLSI_QHS 4 "register_operand")
(mult:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 2 "register_operand"))
(match_operand:V_VLSI_QHS 3 "register_operand")))
(match_operand:V_VLSI_QHS 5 "register_operand")))]
"TARGET_VECTOR"
{})
(define_insn "*pred_nmsub<mode>_scalar"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI
(match_operand:V_VLSI 4 "register_operand" " vr, vr")
(mult:V_VLSI
(vec_duplicate:V_VLSI
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:V_VLSI 3 "register_operand" " 0, 0")))
(match_dup 3)))]
"TARGET_VECTOR"
"@
vnmsub.vx\t%0,%z2,%4%p1
vnmsub.vx\t%0,%z2,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "3")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_insn "*pred_nmsac<mode>_scalar"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI
(match_operand:V_VLSI 4 "register_operand" " 0, 0")
(mult:V_VLSI
(vec_duplicate:V_VLSI
(match_operand:<VEL> 2 "reg_or_0_operand" " rJ, rJ"))
(match_operand:V_VLSI 3 "register_operand" " vr, vr")))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vnmsac.vx\t%0,%z2,%3%p1
vnmsac.vx\t%0,%z2,%3%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_expand "@pred_minus_mul<mode>_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(match_operand:V_VLSI_D 4 "register_operand")
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 2 "reg_or_int_operand"))
(match_operand:V_VLSI_D 3 "register_operand")))
(match_operand:V_VLSI_D 5 "register_operand")))]
"TARGET_VECTOR"
{
if (riscv_vector::sew64_scalar_helper (
operands,
/* scalar op */&operands[2],
/* vl */operands[6],
<MODE>mode,
false,
[] (rtx *operands, rtx broadcast_scalar) {
emit_insn (gen_pred_minus_mul<mode> (operands[0], operands[1],
broadcast_scalar, operands[3], operands[4], operands[5],
operands[6], operands[7], operands[8], operands[9]));
},
(riscv_vector::avl_type) INTVAL (operands[9])))
DONE;
})
(define_insn "*pred_nmsub<mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(match_operand:V_VLSI_D 4 "register_operand" " vr, vr")
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:V_VLSI_D 3 "register_operand" " 0, 0")))
(match_dup 3)))]
"TARGET_VECTOR && !TARGET_64BIT"
"@
vnmsub.vx\t%0,%z2,%4%p1
vnmsub.vx\t%0,%z2,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "3")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
(define_insn "*pred_nmsac<mode>_extended_scalar"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(match_operand:V_VLSI_D 4 "register_operand" " 0, 0")
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(sign_extend:<VEL>
(match_operand:<VSUBEL> 2 "reg_or_0_operand" " rJ, rJ")))
(match_operand:V_VLSI_D 3 "register_operand" " vr, vr")))
(match_dup 4)))]
"TARGET_VECTOR && !TARGET_64BIT"
"@
vnmsac.vx\t%0,%z2,%3%p1
vnmsac.vx\t%0,%z2,%3%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))])
;; -------------------------------------------------------------------------------
;; ---- Predicated widen integer ternary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 11.14 Vector Widening Integer Multiply-Add Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_widen_mul_plus<su><mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr"))
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTI 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vwmacc<u>.vv\t%0,%3,%4%p1"
[(set_attr "type" "viwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_widen_mul_plus<su><mode>_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(any_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 3 "register_operand" " r")))
(any_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTI 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vwmacc<u>.vx\t%0,%3,%4%p1"
[(set_attr "type" "viwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_widen_mul_plussu<mode>"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(sign_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr"))
(zero_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTI 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vwmaccsu.vv\t%0,%3,%4%p1"
[(set_attr "type" "viwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_widen_mul_plussu<mode>_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(sign_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 3 "register_operand" " r")))
(zero_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTI 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vwmaccsu.vx\t%0,%3,%4%p1"
[(set_attr "type" "viwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
(define_insn "@pred_widen_mul_plusus<mode>_scalar"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(zero_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 3 "register_operand" " r")))
(sign_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTI 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vwmaccus.vx\t%0,%3,%4%p1"
[(set_attr "type" "viwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated BOOL mask operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 15.1 Vector Mask-Register Logical Instructions
;; - 15.2 Vector count population in mask vcpop.m
;; - 15.3 vfirst find-first-set mask bit
;; - 15.4 vmsbf.m set-before-first mask bit
;; - 15.5 vmsif.m set-including-first mask bit
;; - 15.6 vmsof.m set-only-first mask bit
;; - 15.8 Vector Iota Instruction
;; - 15.9 Vector Element Index Instruction
;; -------------------------------------------------------------------------------
;; We keep this pattern same as pred_mov so that we can gain more optimizations.
;; For example, if we have vmxor.mm v1,v1,v1. It will be optimized as vmclr.m which
;; is generated by pred_mov.
(define_insn "@pred_<optab><mode>"
[(set (match_operand:VB_VLS 0 "register_operand" "=vr")
(if_then_else:VB_VLS
(unspec:VB_VLS
[(match_operand:VB_VLS 1 "vector_all_trues_mask_operand" "Wc1")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_bitwise:VB_VLS
(match_operand:VB_VLS 3 "register_operand" " vr")
(match_operand:VB_VLS 4 "register_operand" " vr"))
(match_operand:VB_VLS 2 "vector_undef_operand" " vu")))]
"TARGET_VECTOR"
"vm<insn>.mm\t%0,%3,%4"
[(set_attr "type" "vmalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "5")
(set (attr "avl_type_idx") (const_int 6))])
(define_insn "@pred_n<optab><mode>"
[(set (match_operand:VB_VLS 0 "register_operand" "=vr")
(if_then_else:VB_VLS
(unspec:VB_VLS
[(match_operand:VB_VLS 1 "vector_all_trues_mask_operand" "Wc1")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(not:VB_VLS
(any_bitwise:VB_VLS
(match_operand:VB_VLS 3 "register_operand" " vr")
(match_operand:VB_VLS 4 "register_operand" " vr")))
(match_operand:VB_VLS 2 "vector_undef_operand" " vu")))]
"TARGET_VECTOR"
"vm<ninsn>.mm\t%0,%3,%4"
[(set_attr "type" "vmalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "5")
(set (attr "avl_type_idx") (const_int 6))])
(define_insn "@pred_<optab>not<mode>"
[(set (match_operand:VB_VLS 0 "register_operand" "=vr")
(if_then_else:VB_VLS
(unspec:VB_VLS
[(match_operand:VB_VLS 1 "vector_all_trues_mask_operand" "Wc1")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(and_ior:VB_VLS
(match_operand:VB_VLS 3 "register_operand" " vr")
(not:VB_VLS
(match_operand:VB_VLS 4 "register_operand" " vr")))
(match_operand:VB_VLS 2 "vector_undef_operand" " vu")))]
"TARGET_VECTOR"
"vm<insn>n.mm\t%0,%3,%4"
[(set_attr "type" "vmalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "5")
(set (attr "avl_type_idx") (const_int 6))])
(define_insn "@pred_not<mode>"
[(set (match_operand:VB_VLS 0 "register_operand" "=vr")
(if_then_else:VB_VLS
(unspec:VB_VLS
[(match_operand:VB_VLS 1 "vector_all_trues_mask_operand" "Wc1")
(match_operand 4 "vector_length_operand" "rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(not:VB_VLS
(match_operand:VB_VLS 3 "register_operand" " vr"))
(match_operand:VB_VLS 2 "vector_undef_operand" " vu")))]
"TARGET_VECTOR"
"vmnot.m\t%0,%3"
[(set_attr "type" "vmalu")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "avl_type_idx") (const_int 5))])
(define_insn "@pred_popcount<VB_VLS:mode><P:mode>"
[(set (match_operand:P 0 "register_operand" "=r")
(popcount:P
(unspec:VB_VLS
[(and:VB_VLS
(match_operand:VB_VLS 1 "vector_mask_operand" "vmWc1")
(match_operand:VB_VLS 2 "register_operand" " vr"))
(match_operand 3 "vector_length_operand" " rvl")
(match_operand 4 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)))]
"TARGET_VECTOR"
"vcpop.m\t%0,%2%p1"
[(set_attr "type" "vmpop")
(set_attr "mode" "<VB_VLS:MODE>")])
(define_insn "@pred_ffs<VB_VLS:mode><P:mode>"
[(set (match_operand:P 0 "register_operand" "=r")
(plus:P
(ffs:P
(unspec:VB_VLS
[(and:VB_VLS
(match_operand:VB_VLS 1 "vector_mask_operand" "vmWc1")
(match_operand:VB_VLS 2 "register_operand" " vr"))
(match_operand 3 "vector_length_operand" " rvl")
(match_operand 4 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE))
(const_int -1)))]
"TARGET_VECTOR"
"vfirst.m\t%0,%2%p1"
[(set_attr "type" "vmffs")
(set_attr "mode" "<VB_VLS:MODE>")])
(define_insn "@pred_<misc_op><mode>"
[(set (match_operand:VB_VLS 0 "register_operand" "=&vr, &vr")
(if_then_else:VB_VLS
(unspec:VB_VLS
[(match_operand:VB_VLS 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VB_VLS
[(match_operand:VB_VLS 3 "register_operand" " vr, vr")] VMISC)
(match_operand:VB_VLS 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vm<misc_op>.m\t%0,%3%p1"
[(set_attr "type" "vmsfs")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_iota<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=&vr, &vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSI
[(match_operand:<VM> 3 "register_operand" " vr, vr")] UNSPEC_VIOTA)
(match_operand:V_VLSI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"viota.m\t%0,%3%p1"
[(set_attr "type" "vmiota")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_series<mode>"
[(set (match_operand:V_VLSI 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 3 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 4 "const_int_operand" " i, i, i, i")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_series:V_VLSI (const_int 0) (const_int 1))
(match_operand:V_VLSI 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vid.v\t%0%p1"
[(set_attr "type" "vmidx")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point binary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.2 Vector Single-Width Floating-Point Add/Subtract Instructions
;; - 13.4 Vector Single-Width Floating-Point Multiply/Divide Instructions
;; - 13.11 Vector Floating-Point MIN/MAX Instructions
;; - 13.12 Vector Floating-Point Sign-Injection Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(any_float_binop:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.vv\t%0,%3,%4%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_float_binop_nofrm:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.vv\t%0,%3,%4%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<ieee_fmaxmin_op><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr")]
UNSPEC_VFMAXMIN)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<ieee_fmaxmin_op>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfminmax")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(commutative_float_binop:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f"))
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.vf\t%0,%3,%4%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(commutative_float_binop_nofrm:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f"))
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.vf\t%0,%3,%4%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<ieee_fmaxmin_op><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f"))]
UNSPEC_VFMAXMIN)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"v<ieee_fmaxmin_op>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfminmax")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<optab><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(non_commutative_float_binop:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f")))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.vf\t%0,%3,%4%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_<optab><mode>_reverse_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(non_commutative_float_binop:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f"))
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfr<insn>.vf\t%0,%3,%4%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_<copysign><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr")] VCOPYSIGNS)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfsgnj<nx>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfsgnj")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_ncopysign<mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(neg:V_VLSF
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr")] UNSPEC_VCOPYSIGN))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfsgnjn.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfsgnj")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<copysign><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f"))] VCOPYSIGNS)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfsgnj<nx>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfsgnj")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_ncopysign<mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(neg:V_VLSF
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f, f, f, f"))] UNSPEC_VCOPYSIGN))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfsgnjn.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfsgnj")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point ternary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.6 Vector Single-Width Floating-Point Fused Multiply-Add Instructions
;; -------------------------------------------------------------------------------
(define_expand "@pred_mul_<optab><mode>"
[(set (match_operand:V_VLSF 0 "register_operand")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(match_operand 10 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 2 "register_operand")
(match_operand:V_VLSF 3 "register_operand"))
(match_operand:V_VLSF 4 "register_operand"))
(match_operand:V_VLSF 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_mul_<optab><mode>_undef"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1")
(match_operand 6 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(match_operand 10 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " 0,vr, 0, vr")
(match_operand:V_VLSF 4 "register_operand" " vr,vr, vr, vr"))
(match_operand:V_VLSF 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSF 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vf<madd_msub>.vv\t%0,%4,%5%p1
vf<macc_msac>.vv\t%0,%3,%4%p1
vf<madd_msub>.vv\t%0,%4,%5%p1
vf<macc_msac>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[10])"))])
(define_insn "*pred_<madd_msub><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 2 "register_operand" " 0, 0")
(match_operand:V_VLSF 3 "register_operand" " vr, vr"))
(match_operand:V_VLSF 4 "register_operand" " vr, vr"))
(match_dup 2)))]
"TARGET_VECTOR"
"@
vf<madd_msub>.vv\t%0,%3,%4%p1
vf<madd_msub>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "2")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "*pred_<macc_msac><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 2 "register_operand" " vr, vr")
(match_operand:V_VLSF 3 "register_operand" " vr, vr"))
(match_operand:V_VLSF 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vf<macc_msac>.vv\t%0,%2,%3%p1
vf<macc_msac>.vv\t%0,%2,%3%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_expand "@pred_mul_<optab><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(match_operand 10 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 2 "register_operand"))
(match_operand:V_VLSF 3 "register_operand"))
(match_operand:V_VLSF 4 "register_operand"))
(match_operand:V_VLSF 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_mul_<optab><mode>_scalar_undef"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 6 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(match_operand 10 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 3 "register_operand" " f, f, f, f"))
(match_operand:V_VLSF 4 "register_operand" " 0, vr, 0, vr"))
(match_operand:V_VLSF 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSF 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vf<madd_msub>.vf\t%0,%3,%5%p1
vf<macc_msac>.vf\t%0,%3,%4%p1
vf<madd_msub>.vf\t%0,%3,%5%p1
vf<macc_msac>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[10])"))])
(define_insn "*pred_<madd_msub><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 2 "register_operand" " f, f"))
(match_operand:V_VLSF 3 "register_operand" " 0, 0"))
(match_operand:V_VLSF 4 "register_operand" " vr, vr"))
(match_dup 3)))]
"TARGET_VECTOR"
"@
vf<madd_msub>.vf\t%0,%2,%4%p1
vf<madd_msub>.vf\t%0,%2,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "3")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "*pred_<macc_msac><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 2 "register_operand" " f, f"))
(match_operand:V_VLSF 3 "register_operand" "vr, vr"))
(match_operand:V_VLSF 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vf<macc_msac>.vf\t%0,%2,%3%p1
vf<macc_msac>.vf\t%0,%2,%3%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_expand "@pred_mul_neg_<optab><mode>"
[(set (match_operand:V_VLSF 0 "register_operand")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(match_operand 10 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 2 "register_operand")
(match_operand:V_VLSF 3 "register_operand")))
(match_operand:V_VLSF 4 "register_operand"))
(match_operand:V_VLSF 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_mul_neg_<optab><mode>_undef"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd,vd,vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,vm,Wc1,Wc1")
(match_operand 6 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(match_operand 10 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " 0,vr, 0, vr")
(match_operand:V_VLSF 4 "register_operand" " vr,vr, vr, vr")))
(match_operand:V_VLSF 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSF 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vf<nmsub_nmadd>.vv\t%0,%4,%5%p1
vf<nmsac_nmacc>.vv\t%0,%3,%4%p1
vf<nmsub_nmadd>.vv\t%0,%4,%5%p1
vf<nmsac_nmacc>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[10])"))])
(define_insn "*pred_<nmsub_nmadd><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 2 "register_operand" " 0, 0")
(match_operand:V_VLSF 3 "register_operand" " vr, vr")))
(match_operand:V_VLSF 4 "register_operand" " vr, vr"))
(match_dup 2)))]
"TARGET_VECTOR"
"@
vf<nmsub_nmadd>.vv\t%0,%3,%4%p1
vf<nmsub_nmadd>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "2")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "*pred_<nmsac_nmacc><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(match_operand:V_VLSF 2 "register_operand" " vr, vr")
(match_operand:V_VLSF 3 "register_operand" " vr, vr")))
(match_operand:V_VLSF 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vf<nmsac_nmacc>.vv\t%0,%2,%3%p1
vf<nmsac_nmacc>.vv\t%0,%2,%3%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_expand "@pred_mul_neg_<optab><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(match_operand 10 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 2 "register_operand"))
(match_operand:V_VLSF 3 "register_operand")))
(match_operand:V_VLSF 4 "register_operand"))
(match_operand:V_VLSF 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_mul_neg_<optab><mode>_scalar_undef"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd,vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 6 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(match_operand 10 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 3 "register_operand" " f, f, f, f"))
(match_operand:V_VLSF 4 "register_operand" " 0, vr, 0, vr")))
(match_operand:V_VLSF 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSF 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vf<nmsub_nmadd>.vf\t%0,%3,%5%p1
vf<nmsac_nmacc>.vf\t%0,%3,%4%p1
vf<nmsub_nmadd>.vf\t%0,%3,%5%p1
vf<nmsac_nmacc>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[10])"))])
(define_insn "*pred_<nmsub_nmadd><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 2 "register_operand" " f, f"))
(match_operand:V_VLSF 3 "register_operand" " 0, 0")))
(match_operand:V_VLSF 4 "register_operand" " vr, vr"))
(match_dup 3)))]
"TARGET_VECTOR"
"@
vf<nmsub_nmadd>.vf\t%0,%2,%4%p1
vf<nmsub_nmadd>.vf\t%0,%2,%4%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "3")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "*pred_<nmsac_nmacc><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:V_VLSF
(neg:V_VLSF
(mult:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 2 "register_operand" " f, f"))
(match_operand:V_VLSF 3 "register_operand" " vr, vr")))
(match_operand:V_VLSF 4 "register_operand" " 0, 0"))
(match_dup 4)))]
"TARGET_VECTOR"
"@
vf<nmsac_nmacc>.vf\t%0,%2,%3%p1
vf<nmsac_nmacc>.vf\t%0,%2,%3%p1"
[(set_attr "type" "vfmuladd")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "4")
(set_attr "vl_op_idx" "5")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[6])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[7])"))
(set (attr "avl_type_idx") (const_int 8))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point unary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.8 Vector Floating-Point Square-Root Instruction
;; - 13.9 Vector Floating-Point Reciprocal Square-Root Estimate Instruction
;; - 13.10 Vector Floating-Point Reciprocal Estimate Instruction
;; - 13.12 Vector Floating-Point Sign-Injection Instructions (vfneg.v/vfabs.v)
;; - 13.14 Vector Floating-Point Classify Instruction
;; -------------------------------------------------------------------------------
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(any_float_unop:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.v\t%0,%3%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[5])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
(define_insn "@pred_<optab><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_float_unop_nofrm:V_VLSF
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<insn>.v\t%0,%3%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")
(set_attr "vl_op_idx" "4")
(set (attr "ta") (symbol_ref "riscv_vector::get_ta(operands[5])"))
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
(define_insn "@pred_<misc_op><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")] VFMISC)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<misc_op>.v\t%0,%3%p1"
[(set_attr "type" "<float_insn_type>")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<misc_frm_op><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLSF
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")] VFMISC_FRM)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vf<misc_frm_op>.v\t%0,%3%p1"
[(set_attr "type" "<float_frm_insn_type>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
(define_insn "@pred_class<mode>"
[(set (match_operand:<VCONVERT> 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:<VCONVERT>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<VCONVERT>
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")] UNSPEC_VFCLASS)
(match_operand:<VCONVERT> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfclass.v\t%0,%3%p1"
[(set_attr "type" "vfclass")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point widen binary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.3 Vector Widening Floating-Point Add/Subtract Instructions
;; - 13.5 Vector Widening Floating-Point Multiply
;; -------------------------------------------------------------------------------
;; Vector Widening Add/Subtract/Multiply.
(define_insn "@pred_dual_widen_<optab><mode>"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr, &vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(any_widen_binop:VWEXTF
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr")))
(match_operand:VWEXTF 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfw<insn>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vf<widen_binop_insn_type>")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_dual_widen_<optab><mode>_scalar"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr, &vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(any_widen_binop:VWEXTF
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(vec_duplicate:VWEXTF
(float_extend:<VEL>
(match_operand:<VSUBEL> 4 "register_operand" " f, f"))))
(match_operand:VWEXTF 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfw<insn>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vf<widen_binop_insn_type>")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_single_widen_add<mode>"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr, &vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTF
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr"))
(match_operand:VWEXTF 3 "register_operand" " vr, vr"))
(match_operand:VWEXTF 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfwadd.wv\t%0,%3,%4%p1"
[(set_attr "type" "vfwalu")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_single_widen_sub<mode>"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr, &vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(match_operand 9 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(minus:VWEXTF
(match_operand:VWEXTF 3 "register_operand" " vr, vr")
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr, vr")))
(match_operand:VWEXTF 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfwsub.wv\t%0,%3,%4%p1"
[(set_attr "type" "vfwalu")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_single_widen_<plus_minus:optab><mode>_scalar"
[(set (match_operand:VWEXTF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:VWEXTF
(vec_duplicate:VWEXTF
(float_extend:<VEL>
(match_operand:<VSUBEL> 4 "register_operand" " f, f, f, f")))
(match_operand:VWEXTF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:VWEXTF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfw<insn>.wf\t%0,%3,%4%p1"
[(set_attr "type" "vf<widen_binop_insn_type>")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
;; -------------------------------------------------------------------------------
;; ---- Predicated widen floating-point ternary operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.7 Vector Widening Floating-Point Fused Multiply-Add Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_widen_mul_<optab><mode>"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(match_operand 9 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:VWEXTF
(mult:VWEXTF
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr"))
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTF 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vfw<macc_msac>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_widen_mul_<optab><mode>_scalar"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(match_operand 9 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:VWEXTF
(mult:VWEXTF
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr"))
(vec_duplicate:VWEXTF
(float_extend:<VEL>
(match_operand:<VSUBEL> 3 "register_operand" " f"))))
(match_operand:VWEXTF 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vfw<macc_msac>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_widen_mul_neg_<optab><mode>"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(match_operand 9 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:VWEXTF
(neg:VWEXTF
(mult:VWEXTF
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr"))
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr"))))
(match_operand:VWEXTF 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vfw<nmsac_nmacc>.vv\t%0,%3,%4%p1"
[(set_attr "type" "vfwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
(define_insn "@pred_widen_mul_neg_<optab><mode>_scalar"
[(set (match_operand:VWEXTF 0 "register_operand" "=&vr")
(if_then_else:VWEXTF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(match_operand 9 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(plus_minus:VWEXTF
(neg:VWEXTF
(mult:VWEXTF
(float_extend:VWEXTF
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 3 "register_operand" " f")))
(float_extend:VWEXTF
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr"))))
(match_operand:VWEXTF 2 "register_operand" " 0"))
(match_dup 2)))]
"TARGET_VECTOR"
"vfw<nmsac_nmacc>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfwmuladd")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point comparison operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.13 Vector Floating-Point Compare Instructions
;; -------------------------------------------------------------------------------
(define_expand "@pred_cmp<mode>"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "signed_order_operator"
[(match_operand:V_VLSF 4 "register_operand")
(match_operand:V_VLSF 5 "register_operand")])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{})
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_cmp<mode>"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "signed_order_operator"
[(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr")
(match_operand:V_VLSF 5 "register_operand" " vr, vr, vr, vr")])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode)"
"vmf%B3.vv\t%0,%4,%5%p1"
[(set_attr "type" "vfcmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,rvv,rvv")])
(define_insn "*pred_cmp<mode>_narrow_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "signed_order_operator"
[(match_operand:V_VLSF 3 "register_operand" " vr")
(match_operand:V_VLSF 4 "register_operand" " vr")])
(match_dup 1)))]
"TARGET_VECTOR"
"vmf%B2.vv\t%0,%3,%4,v0.t"
[(set_attr "type" "vfcmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We use early-clobber for source LMUL > dest LMUL.
(define_insn "*pred_cmp<mode>_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, vr, vr, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "signed_order_operator"
[(match_operand:V_VLSF 4 "register_operand" " vr, 0, vr, 0, 0, vr, 0, vr, vr")
(match_operand:V_VLSF 5 "register_operand" " vr, vr, 0, 0, vr, 0, 0, vr, vr")])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, vu, vu, 0, 0, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode)"
"vmf%B3.vv\t%0,%4,%5%p1"
[(set_attr "type" "vfcmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,thv,thv,thv,thv,none,none")])
(define_expand "@pred_cmp<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "signed_order_operator"
[(match_operand:V_VLSF 4 "register_operand")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 5 "register_operand"))])
(match_operand:<VM> 2 "vector_merge_operand")))]
"TARGET_VECTOR"
{})
(define_insn "*pred_cmp<mode>_scalar_merge_tie_mask"
[(set (match_operand:<VM> 0 "register_operand" "=vm")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "register_operand" " 0")
(match_operand 5 "vector_length_operand" "rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 2 "signed_order_operator"
[(match_operand:V_VLSF 3 "register_operand" " vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 4 "register_operand" " f"))])
(match_dup 1)))]
"TARGET_VECTOR"
"vmf%B2.vf\t%0,%3,%4,v0.t"
[(set_attr "type" "vfcmp")
(set_attr "mode" "<MODE>")
(set_attr "merge_op_idx" "1")
(set_attr "vl_op_idx" "5")
(set (attr "ma") (symbol_ref "riscv_vector::get_ma(operands[6])"))
(set (attr "avl_type_idx") (const_int 7))])
;; We don't use early-clobber for LMUL <= 1 to get better codegen.
(define_insn "*pred_cmp<mode>_scalar"
[(set (match_operand:<VM> 0 "register_operand" "=vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "signed_order_operator"
[(match_operand:V_VLSF 4 "register_operand" " vr, vr, vr, vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 5 "register_operand" " f, f, f, f"))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_le_one (<MODE>mode)"
"vmf%B3.vf\t%0,%4,%5%p1"
[(set_attr "type" "vfcmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "thv,thv,rvv,rvv")])
;; We use early-clobber for source LMUL > dest LMUL.
(define_insn "*pred_cmp<mode>_scalar_narrow"
[(set (match_operand:<VM> 0 "register_operand" "=vm, vr, vr, &vr, &vr")
(if_then_else:<VM>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " 0,vmWc1,vmWc1,vmWc1,vmWc1")
(match_operand 6 "vector_length_operand" " rvl, rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operator:<VM> 3 "signed_order_operator"
[(match_operand:V_VLSF 4 "register_operand" " vr, 0, 0, vr, vr")
(vec_duplicate:V_VLSF
(match_operand:<VEL> 5 "register_operand" " f, f, f, f, f"))])
(match_operand:<VM> 2 "vector_merge_operand" " vu, vu, 0, vu, 0")))]
"TARGET_VECTOR && riscv_vector::cmp_lmul_gt_one (<MODE>mode)"
"vmf%B3.vf\t%0,%4,%5%p1"
[(set_attr "type" "vfcmp")
(set_attr "mode" "<MODE>")
(set_attr "spec_restriction" "none,thv,thv,none,none")])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point merge
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.15 Vector Floating-Point Merge Instruction
;; -------------------------------------------------------------------------------
(define_insn "@pred_merge<mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd,vd")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand 5 "vector_length_operand" "rvl,rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(vec_merge:V_VLSF
(vec_duplicate:V_VLSF
(match_operand:<VEL> 3 "register_operand" " f, f"))
(match_operand:V_VLSF 2 "register_operand" " vr,vr")
(match_operand:<VM> 4 "register_operand" " vm,vm"))
(match_operand:V_VLSF 1 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfmerge.vfm\t%0,%2,%3,%4"
[(set_attr "type" "vfmerge")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point conversions
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.17 Single-Width Floating-Point/Integer Type-Convert Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_fcvt_x<v_su>_f<mode>"
[(set (match_operand:<VCONVERT> 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:<VCONVERT>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<VCONVERT>
[(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")] VFCVTS)
(match_operand:<VCONVERT> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfcvt.x<v_su>.f.v\t%0,%3%p1"
[(set_attr "type" "vfcvtftoi")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
(define_insn "@pred_<fix_cvt><mode>"
[(set (match_operand:<VCONVERT> 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:<VCONVERT>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_fix:<VCONVERT>
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:<VCONVERT> 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfcvt.rtz.x<u>.f.v\t%0,%3%p1"
[(set_attr "type" "vfcvtftoi")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_<float_cvt><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(any_float:V_VLSF
(match_operand:<VCONVERT> 3 "register_operand" " vr, vr, vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfcvt.f.x<u>.v\t%0,%3%p1"
[(set_attr "type" "vfcvtitof")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point widen conversions
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.18 Widening Floating-Point/Integer Type-Convert Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_widen_fcvt_x<v_su>_f<mode>"
[(set (match_operand:VWCONVERTI 0 "register_operand" "=&vr, &vr")
(if_then_else:VWCONVERTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VWCONVERTI
[(match_operand:<VNCONVERT> 3 "register_operand" " vr, vr")] VFCVTS)
(match_operand:VWCONVERTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfwcvt.x<v_su>.f.v\t%0,%3%p1"
[(set_attr "type" "vfwcvtftoi")
(set_attr "mode" "<VNCONVERT>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
(define_insn "@pred_widen_<fix_cvt><mode>"
[(set (match_operand:VWCONVERTI 0 "register_operand" "=&vr, &vr")
(if_then_else:VWCONVERTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_fix:VWCONVERTI
(match_operand:<VNCONVERT> 3 "register_operand" " vr, vr"))
(match_operand:VWCONVERTI 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfwcvt.rtz.x<u>.f.v\t%0,%3%p1"
[(set_attr "type" "vfwcvtftoi")
(set_attr "mode" "<VNCONVERT>")])
(define_insn "@pred_widen_<float_cvt><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "=&vr, &vr")
(if_then_else:V_VLSF
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_float:V_VLSF
(match_operand:<VNCONVERT> 3 "register_operand" " vr, vr"))
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfwcvt.f.x<u>.v\t%0,%3%p1"
[(set_attr "type" "vfwcvtitof")
(set_attr "mode" "<VNCONVERT>")])
(define_insn "@pred_extend<mode>"
[(set (match_operand:VWEXTF_ZVFHMIN 0 "register_operand" "=&vr, &vr")
(if_then_else:VWEXTF_ZVFHMIN
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(float_extend:VWEXTF_ZVFHMIN
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" " vr, vr"))
(match_operand:VWEXTF_ZVFHMIN 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vfwcvt.f.f.v\t%0,%3%p1"
[(set_attr "type" "vfwcvtftof")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated floating-point narrow conversions
;; -------------------------------------------------------------------------------
;; Includes:
;; - 13.19 Narrowing Floating-Point/Integer Type-Convert Instructions
;; -------------------------------------------------------------------------------
(define_insn "@pred_narrow_fcvt_x<v_su>_f<mode>"
[(set (match_operand:<VNCONVERT> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<VNCONVERT>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<VNCONVERT>
[(match_operand:V_VLSF 3 "register_operand" " 0, 0, 0, 0, vr, vr")] VFCVTS)
(match_operand:<VNCONVERT> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfncvt.x<v_su>.f.w\t%0,%3%p1"
[(set_attr "type" "vfncvtftoi")
(set_attr "mode" "<VNCONVERT>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))
(set_attr "spec_restriction" "none,none,thv,thv,none,none")])
(define_insn "@pred_narrow_<fix_cvt><mode>"
[(set (match_operand:<VNCONVERT> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<VNCONVERT>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(any_fix:<VNCONVERT>
(match_operand:V_VLSF 3 "register_operand" " 0, 0, 0, 0, vr, vr"))
(match_operand:<VNCONVERT> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfncvt.rtz.x<u>.f.w\t%0,%3%p1"
[(set_attr "type" "vfncvtftoi")
(set_attr "mode" "<VNCONVERT>")])
(define_insn "@pred_narrow_<float_cvt><mode>"
[(set (match_operand:<VNCONVERT> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<VNCONVERT>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(any_float:<VNCONVERT>
(match_operand:VWCONVERTI 3 "register_operand" " 0, 0, 0, 0, vr, vr"))
(match_operand:<VNCONVERT> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfncvt.f.x<u>.w\t%0,%3%p1"
[(set_attr "type" "vfncvtitof")
(set_attr "mode" "<VNCONVERT>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))
(set_attr "spec_restriction" "none,none,thv,thv,none,none")])
(define_insn "@pred_trunc<mode>"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(float_truncate:<V_DOUBLE_TRUNC>
(match_operand:VWEXTF_ZVFHMIN 3 "register_operand" " 0, 0, 0, 0, vr, vr"))
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfncvt.f.f.w\t%0,%3%p1"
[(set_attr "type" "vfncvtftof")
(set_attr "mode" "<V_DOUBLE_TRUNC>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))
(set_attr "spec_restriction" "none,none,thv,thv,none,none")])
(define_insn "@pred_rod_trunc<mode>"
[(set (match_operand:<V_DOUBLE_TRUNC> 0 "register_operand" "=vd, vd, vr, vr, &vr, &vr")
(if_then_else:<V_DOUBLE_TRUNC>
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1,vmWc1,vmWc1")
(match_operand 4 "vector_length_operand" "rvl,rvl,rvl,rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_DOUBLE_TRUNC>
[(float_truncate:<V_DOUBLE_TRUNC>
(match_operand:VWEXTF_ZVFHMIN 3 "register_operand" " 0, 0, 0, 0, vr, vr"))] UNSPEC_ROD)
(match_operand:<V_DOUBLE_TRUNC> 2 "vector_merge_operand" " vu, 0, vu, 0, vu, 0")))]
"TARGET_VECTOR"
"vfncvt.rod.f.f.w\t%0,%3%p1"
[(set_attr "type" "vfncvtftof")
(set_attr "mode" "<V_DOUBLE_TRUNC>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated reduction operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 14.1 Vector Single-Width Integer Reduction Instructions
;; - 14.2 Vector Widening Integer Reduction Instructions
;; - 14.3 Vector Single-Width Floating-Point Reduction Instructions
;; - 14.4 Vector Widening Floating-Point Reduction Instructions
;; -------------------------------------------------------------------------------
;;
;; NOTE for VL0 safe variantreduction:
;; The VL0 safe variantis used by the auto vectorizer to generate vectorized code
;; only, because the auto vectorizer expect reduction should propgat the start
;; value to dest even VL=0, the only way is force vd=vs1 by constraint.
;; Integer Reduction (vred(sum|maxu|max|minu|min|and|or|xor).vs)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_LMUL1> 0 "register_operand" "=vr, vr")
(unspec:<V_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_LMUL1> [
(match_operand:V_VLSI 3 "register_operand" " vr, vr")
(match_operand:<V_LMUL1> 4 "register_operand" " vr, vr")
] ANY_REDUC)
(match_operand:<V_LMUL1> 2 "vector_merge_operand" " vu, 0")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"v<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vired")
(set_attr "mode" "<MODE>")])
;; Integer Reduction (vred(sum|maxu|max|minu|min|and|or|xor).vs)
;; but for auto vectorizer (see "NOTE for VL0 safe variantreduction" for detail)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_LMUL1> 0 "register_operand" "=vr")
(unspec:<V_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_LMUL1> [
(match_operand:V_VLSI 3 "register_operand" " vr")
(match_operand:<V_LMUL1> 4 "register_operand" " 0")
] ANY_REDUC_VL0_SAFE)
(match_operand:<V_LMUL1> 2 "vector_merge_operand" " vu")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"v<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vired")
(set_attr "mode" "<MODE>")])
;; Integer Widen Reduction Sum (vwredsum[u].vs)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_EXT_LMUL1> 0 "register_operand" "=vr, vr")
(unspec:<V_EXT_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_EXT_LMUL1> [
(match_operand:VI_QHS 3 "register_operand" " vr, vr")
(match_operand:<V_EXT_LMUL1> 4 "register_operand" " vr, vr")
] ANY_WREDUC)
(match_operand:<V_EXT_LMUL1> 2 "vector_merge_operand" " vu, 0")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"v<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "viwred")
(set_attr "mode" "<MODE>")])
;; Integer Widen Reduction Sum (vwredsum[u].vs)
;; but for auto vectorizer (see "NOTE for VL0 safe variantreduction" for detail)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_EXT_LMUL1> 0 "register_operand" "=vr")
(unspec:<V_EXT_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_EXT_LMUL1> [
(match_operand:VI_QHS 3 "register_operand" " vr")
(match_operand:<V_EXT_LMUL1> 4 "register_operand" " 0")
] ANY_WREDUC_VL0_SAFE)
(match_operand:<V_EXT_LMUL1> 2 "vector_merge_operand" " vu")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"v<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "viwred")
(set_attr "mode" "<MODE>")])
;; Float Reduction (vfred(max|min).vs)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_LMUL1> 0 "register_operand" "=vr, vr")
(unspec:<V_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_LMUL1> [
(match_operand:V_VLSF 3 "register_operand" " vr, vr")
(match_operand:<V_LMUL1> 4 "register_operand" " vr, vr")
] ANY_FREDUC)
(match_operand:<V_LMUL1> 2 "vector_merge_operand" " vu, 0")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"vf<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vfredu")
(set_attr "mode" "<MODE>")])
;; Float Reduction (vfred(max|min).vs)
;; but for auto vectorizer (see "NOTE for VL0 safe variantreduction" for detail)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_LMUL1> 0 "register_operand" "=vr")
(unspec:<V_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_LMUL1> [
(match_operand:V_VLSF 3 "register_operand" " vr")
(match_operand:<V_LMUL1> 4 "register_operand" " 0")
] ANY_FREDUC_VL0_SAFE)
(match_operand:<V_LMUL1> 2 "vector_merge_operand" " vu")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"vf<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vfredu")
(set_attr "mode" "<MODE>")])
;; Float Reduction Sum (vfred[ou]sum.vs)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_LMUL1> 0 "register_operand" "=vr,vr")
(unspec:<V_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_LMUL1> [
(match_operand:V_VLSF 3 "register_operand" " vr, vr")
(match_operand:<V_LMUL1> 4 "register_operand" " vr, vr")
] ANY_FREDUC_SUM)
(match_operand:<V_LMUL1> 2 "vector_merge_operand" " vu, 0")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"vf<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vfred<order>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
;; Float Reduction Sum (vfred[ou]sum.vs)
;; but for auto vectorizer (see "NOTE for VL0 safe variantreduction" for detail)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_LMUL1> 0 "register_operand" "=vr")
(unspec:<V_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_LMUL1> [
(match_operand:V_VLSF 3 "register_operand" " vr")
(match_operand:<V_LMUL1> 4 "register_operand" " 0")
] ANY_FREDUC_SUM_VL0_SAFE)
(match_operand:<V_LMUL1> 2 "vector_merge_operand" " vu")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"vf<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vfred<order>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
;; Float Widen Reduction Sum (vfwred[ou]sum.vs)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_EXT_LMUL1> 0 "register_operand" "=vr, vr")
(unspec:<V_EXT_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_EXT_LMUL1> [
(match_operand:VF_HS 3 "register_operand" " vr, vr")
(match_operand:<V_EXT_LMUL1> 4 "register_operand" " vr, vr")
] ANY_FWREDUC_SUM)
(match_operand:<V_EXT_LMUL1> 2 "vector_merge_operand" " vu, 0")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"vf<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vfwred<order>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
;; Float Widen Reduction Sum (vfwred[ou]sum.vs)
;; but for auto vectorizer (see "NOTE for VL0 safe variantreduction" for detail)
(define_insn "@pred_<reduc_op_pat_name><mode>"
[(set (match_operand:<V_EXT_LMUL1> 0 "register_operand" "=vr")
(unspec:<V_EXT_LMUL1>
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 5 "vector_length_operand" " rvl")
(match_operand 6 "const_int_operand" " i")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)
(reg:SI FRM_REGNUM)] UNSPEC_VPREDICATE)
(unspec:<V_EXT_LMUL1> [
(match_operand:VF_HS 3 "register_operand" " vr")
(match_operand:<V_EXT_LMUL1> 4 "register_operand" " 0")
] ANY_FWREDUC_SUM_VL0_SAFE)
(match_operand:<V_EXT_LMUL1> 2 "vector_merge_operand" " vu")] UNSPEC_REDUC))]
"TARGET_VECTOR"
"vf<reduc_op>.vs\t%0,%3,%4%p1"
[(set_attr "type" "vfwred<order>")
(set_attr "mode" "<MODE>")
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[8])"))])
;; -------------------------------------------------------------------------------
;; ---- Predicated permutation operations
;; -------------------------------------------------------------------------------
;; Includes:
;; - 16.1 Integer Scalar Move Instructions
;; - 16.2 Floating-Point Scalar Move Instructions
;; - 16.3 Vector Slide Instructions
;; - 16.4 Vector Register Gather Instructions
;; - 16.5 Vector Compress Instruction
;; -------------------------------------------------------------------------------
(define_expand "@pred_extract_first<mode>"
[(set (match_operand:<VEL> 0 "register_operand")
(unspec:<VEL>
[(vec_select:<VEL>
(match_operand:V_VLSI 1 "reg_or_mem_operand")
(parallel [(const_int 0)]))
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE))]
"TARGET_VECTOR"
{
if (MEM_P (operands[1]))
{
/* Combine vle.v + vmv.x.s ==> lw. */
emit_move_insn (operands[0], gen_rtx_MEM (<VEL>mode, XEXP (operands[1], 0)));
DONE;
}
})
(define_insn_and_split "*pred_extract_first<mode>"
[(set (match_operand:<VEL> 0 "register_operand" "=r")
(unspec:<VEL>
[(vec_select:<VEL>
(match_operand:V_VLSI 1 "register_operand" "vr")
(parallel [(const_int 0)]))
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE))]
"TARGET_VECTOR"
"vmv.x.s\t%0,%1"
"known_gt (GET_MODE_BITSIZE (<VEL>mode), GET_MODE_BITSIZE (Pmode))"
[(const_int 0)]
{
/* In rv32 system, we can't use vmv.x.s directly.
Instead, we should generate this following code sequence:
vsrl.vx v16,v8,a0
vmv.x.s a1,v16
vmv.x.s a0,v8 */
rtx nbits = force_reg (Pmode, gen_int_mode (GET_MODE_BITSIZE (Pmode), Pmode));
rtx high_bits = gen_reg_rtx (<MODE>mode);
emit_insn (gen_pred_scalar (LSHIFTRT, <MODE>mode, high_bits, CONSTM1_RTX (<VM>mode),
RVV_VUNDEF (<MODE>mode), operands[1], nbits, /* vl */ const1_rtx,
gen_int_mode (riscv_vector::TAIL_ANY, Pmode),
gen_int_mode (riscv_vector::MASK_ANY, Pmode),
gen_int_mode (riscv_vector::NONVLMAX, Pmode)));
emit_insn (gen_pred_extract_first_trunc (<MODE>mode,
gen_highpart (SImode, operands[0]), high_bits));
emit_insn (gen_pred_extract_first_trunc (<MODE>mode,
gen_lowpart (SImode, operands[0]), operands[1]));
DONE;
}
[(set_attr "type" "vimovvx")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_extract_first_trunc<mode>"
[(set (match_operand:SI 0 "register_operand" "=r")
(truncate:SI
(unspec:<VEL>
[(vec_select:<VEL>
(match_operand:V_VLSI_D 1 "register_operand" "vr")
(parallel [(const_int 0)]))
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)))]
"TARGET_VECTOR"
"vmv.x.s\t%0,%1"
[(set_attr "type" "vimovvx")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_extract_first<mode>"
[(set (match_operand:<VEL> 0 "register_operand")
(unspec:<VEL>
[(vec_select:<VEL>
(match_operand:V_VLSF 1 "reg_or_mem_operand")
(parallel [(const_int 0)]))
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE))]
"TARGET_VECTOR"
{
if (MEM_P (operands[1]))
{
/* Combine vle.v + vmv.f.s ==> flw. */
emit_move_insn (operands[0], gen_rtx_MEM (<VEL>mode, XEXP (operands[1], 0)));
DONE;
}
})
(define_insn "*pred_extract_first<mode>"
[(set (match_operand:<VEL> 0 "register_operand" "=f")
(unspec:<VEL>
[(vec_select:<VEL>
(match_operand:V_VLSF 1 "register_operand" "vr")
(parallel [(const_int 0)]))
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE))]
"TARGET_VECTOR"
"vfmv.f.s\t%0,%1"
[(set_attr "type" "vfmovvf")
(set_attr "mode" "<MODE>")])
;; vslide instructions
(define_insn "@pred_slide<ud><mode>"
[(set (match_operand:V_VLS 0 "register_operand" "<ud_constraint>")
(unspec:V_VLS
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0, vu, 0")
(match_operand:V_VLS 3 "register_operand" " vr, vr, vr, vr")
(match_operand 4 "pmode_reg_or_uimm5_operand" " rK, rK, rK, rK")] VSLIDES))]
"TARGET_VECTOR"
"vslide<ud>.v%o4\t%0,%3,%4%p1"
[(set_attr "type" "vslide<ud>")
(set_attr "mode" "<MODE>")])
;; vslide1 instructions
(define_insn "@pred_slide<ud><mode>"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "<ud_constraint>")
(unspec:V_VLSI_QHS
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLSI_QHS 2 "vector_merge_operand" " vu, 0, vu, 0")
(match_operand:V_VLSI_QHS 3 "register_operand" " vr, vr, vr, vr")
(match_operand:<VEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ")] VSLIDES1))]
"TARGET_VECTOR"
"vslide<ud>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vislide<ud>")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_slide<ud><mode>"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(unspec:V_VLSI_D
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 5 "reg_or_int_operand")
(match_operand 6 "const_int_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLSI_D 2 "vector_merge_operand")
(match_operand:V_VLSI_D 3 "register_operand")
(match_operand:<VEL> 4 "reg_or_int_operand")] VSLIDES1))]
"TARGET_VECTOR"
{
poly_uint64 nunits = GET_MODE_NUNITS (<MODE>mode) * 2;
machine_mode vsimode = riscv_vector::get_vector_mode (SImode, nunits).require ();
machine_mode vbimode = riscv_vector::get_vector_mode (BImode, nunits).require ();
if (riscv_vector::slide1_sew64_helper (<UNSPEC>, <MODE>mode,
vsimode, vbimode,
operands))
DONE;
})
(define_insn "*pred_slide<ud><mode>"
[(set (match_operand:V_VLSI_D 0 "register_operand" "<ud_constraint>")
(unspec:V_VLSI_D
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLSI_D 2 "vector_merge_operand" " vu, 0, vu, 0")
(match_operand:V_VLSI_D 3 "register_operand" " vr, vr, vr, vr")
(match_operand:<VEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ")] VSLIDES1))]
"TARGET_VECTOR"
"vslide<ud>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vislide<ud>")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_slide<ud><mode>_extended"
[(set (match_operand:V_VLSI_D 0 "register_operand" "<ud_constraint>")
(unspec:V_VLSI_D
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLSI_D 2 "vector_merge_operand" " vu, 0, vu, 0")
(match_operand:V_VLSI_D 3 "register_operand" " vr, vr, vr, vr")
(sign_extend:<VEL>
(match_operand:<VSUBEL> 4 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))] VSLIDES1))]
"TARGET_VECTOR && !TARGET_64BIT"
"vslide<ud>.vx\t%0,%3,%z4%p1"
[(set_attr "type" "vislide<ud>")
(set_attr "mode" "<MODE>")])
;; vfslide1 instructions
(define_insn "@pred_slide<ud><mode>"
[(set (match_operand:V_VLSF 0 "register_operand" "<ud_constraint>")
(unspec:V_VLSF
[(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm,Wc1,Wc1")
(match_operand 5 "vector_length_operand" "rvl,rvl,rvl,rvl")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLSF 2 "vector_merge_operand" " vu, 0, vu, 0")
(match_operand:V_VLSF 3 "register_operand" " vr, vr, vr, vr")
(match_operand:<VEL> 4 "register_operand" " f, f, f, f")] VFSLIDES1))]
"TARGET_VECTOR"
"vfslide<ud>.vf\t%0,%3,%4%p1"
[(set_attr "type" "vfslide<ud>")
(set_attr "mode" "<MODE>")])
;; vrgather
(define_insn "@pred_gather<mode>"
[(set (match_operand:V_VLS 0 "register_operand" "=&vr, &vr")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS
[(match_operand:V_VLS 3 "register_operand" " vr, vr")
(match_operand:<VINDEX> 4 "register_operand" " vr, vr")] UNSPEC_VRGATHER)
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vrgather.vv\t%0,%3,%4%p1"
[(set_attr "type" "vgather")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_gather<mode>_scalar"
[(set (match_operand:V_VLS 0 "register_operand" "=&vr, &vr")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS
[(match_operand:V_VLS 3 "register_operand" " vr, vr")
(match_operand 4 "pmode_reg_or_uimm5_operand" " rK, rK")] UNSPEC_VRGATHER)
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vrgather.v%o4\t%0,%3,%4%p1"
[(set_attr "type" "vgather")
(set_attr "mode" "<MODE>")])
;; vrgatherei16
(define_insn "@pred_gatherei16<mode>"
[(set (match_operand:VEI16 0 "register_operand" "=&vr, &vr")
(if_then_else:VEI16
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VEI16
[(match_operand:VEI16 3 "register_operand" " vr, vr")
(match_operand:<VINDEXEI16> 4 "register_operand" " vr, vr")] UNSPEC_VRGATHEREI16)
(match_operand:VEI16 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vrgatherei16.vv\t%0,%3,%4%p1"
[(set_attr "type" "vgather")
(set_attr "mode" "<MODE>")])
;; vcompress
(define_insn "@pred_compress<mode>"
[(set (match_operand:V_VLS 0 "register_operand" "=&vr, &vr")
(unspec:V_VLS
[(unspec:<VM>
[(match_operand:<VM> 3 "register_operand" " vm, vm")
(match_operand 4 "vector_length_operand" " rvl, rvl")
(match_operand 5 "const_int_operand" " i, i")
(match_operand 6 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand:V_VLS 2 "register_operand" " vr, vr")
(match_operand:V_VLS 1 "vector_merge_operand" " vu, 0")] UNSPEC_VCOMPRESS))]
"TARGET_VECTOR"
"vcompress.vm\t%0,%2,%3"
[(set_attr "type" "vcompress")
(set_attr "mode" "<MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated Fault-Only-First loads
;; -------------------------------------------------------------------------------
;; Includes:
;; - 7.7. Unit-stride Fault-Only-First Loads
;; -------------------------------------------------------------------------------
(define_insn "@read_vl<mode>"
[(set (match_operand:P 0 "register_operand" "=r")
(unspec:P [(reg:SI VL_REGNUM)] UNSPEC_READ_VL))]
"TARGET_VECTOR"
"csrr\t%0,vl"
[(set_attr "type" "rdvl")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_fault_load<mode>"
[(set (match_operand:V_VLS 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 4 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS
[(match_operand:V_VLS 3 "memory_operand" " m, m, m, m")] UNSPEC_VLEFF)
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0, vu, 0")))
(set (reg:SI VL_REGNUM)
(unspec:SI
[(if_then_else:V_VLS
(unspec:<VM>
[(match_dup 1) (match_dup 4) (match_dup 5)
(match_dup 6) (match_dup 7)
(reg:SI VL_REGNUM) (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS [(match_dup 3)] UNSPEC_VLEFF)
(match_dup 2))] UNSPEC_MODIFY_VL))]
"TARGET_VECTOR"
"vle<sew>ff.v\t%0,%3%p1"
[(set_attr "type" "vldff")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_fault_load_set_vl<V_VLS:mode><P:mode>"
[(set (match_operand:V_VLS 0 "register_operand" "= vd, vd, vr, vr")
(if_then_else:V_VLS
(unspec:<V_VLS:VM>
[(match_operand:<V_VLS:VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 4 "vector_length_operand" " rvl, rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i, i")
(match_operand 6 "const_int_operand" " i, i, i, i")
(match_operand 7 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS
[(match_operand:V_VLS 3 "memory_operand" " m, m, m, m")] UNSPEC_VLEFF)
(match_operand:V_VLS 2 "vector_merge_operand" " vu, 0, vu, 0")))
(set (reg:SI VL_REGNUM)
(unspec:SI
[(if_then_else:V_VLS
(unspec:<V_VLS:VM>
[(match_dup 1) (match_dup 4) (match_dup 5)
(match_dup 6) (match_dup 7)
(reg:SI VL_REGNUM) (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V_VLS [(match_dup 3)] UNSPEC_VLEFF)
(match_dup 2))] UNSPEC_MODIFY_VL))
(set (match_operand:P 8 "register_operand" "= r, r, r, r")
(unspec:P [(reg:SI VL_REGNUM)] UNSPEC_READ_VL))]
"TARGET_VECTOR"
"vle<sew>ff.v\t%0,%3%p1"
[(set_attr "type" "vldff")
(set_attr "mode" "<V_VLS:MODE>")])
;; -------------------------------------------------------------------------------
;; ---- Predicated Segment loads/stores
;; -------------------------------------------------------------------------------
;; Includes:
;; - 7.8.1. Vector Unit-Stride Segment Loads and Stores
;; - 7.8.2. Vector Strided Segment Loads and Stores
;; - 7.8.3. Vector Indexed Segment Loads and Stores
;; -------------------------------------------------------------------------------
(define_insn "@pred_unit_strided_load<mode>"
[(set (match_operand:VT 0 "register_operand" "=vr, vr, vd")
(if_then_else:VT
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1, Wc1, vm")
(match_operand 4 "vector_length_operand" " rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i")
(match_operand 6 "const_int_operand" " i, i, i")
(match_operand 7 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VT
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ, rJ")
(mem:BLK (scratch))] UNSPEC_UNIT_STRIDED)
(match_operand:VT 2 "vector_merge_operand" " 0, vu, vu")))]
"TARGET_VECTOR"
"vlseg<nf>e<sew>.v\t%0,(%z3)%p1"
[(set_attr "type" "vlsegde")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_unit_strided_store<mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 3 "vector_length_operand" " rvl")
(match_operand 4 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:VT 2 "register_operand" " vr")
(mem:BLK (scratch))] UNSPEC_UNIT_STRIDED))]
"TARGET_VECTOR"
"vsseg<nf>e<sew>.v\t%2,(%z1)%p0"
[(set_attr "type" "vssegte")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_strided_load<mode>"
[(set (match_operand:VT 0 "register_operand" "=vr, vr, vd")
(if_then_else:VT
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1, Wc1, vm")
(match_operand 5 "vector_length_operand" " rvl, rvl, rvl")
(match_operand 6 "const_int_operand" " i, i, i")
(match_operand 7 "const_int_operand" " i, i, i")
(match_operand 8 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VT
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ, rJ")
(match_operand 4 "pmode_reg_or_0_operand" " rJ, rJ, rJ")
(mem:BLK (scratch))] UNSPEC_STRIDED)
(match_operand:VT 2 "vector_merge_operand" " 0, vu, vu")))]
"TARGET_VECTOR"
"vlsseg<nf>e<sew>.v\t%0,(%z3),%z4%p1"
[(set_attr "type" "vlsegds")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_strided_store<mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand 2 "pmode_reg_or_0_operand" " rJ")
(match_operand:VT 3 "register_operand" " vr")
(mem:BLK (scratch))] UNSPEC_STRIDED))]
"TARGET_VECTOR"
"vssseg<nf>e<sew>.v\t%3,(%z1),%z2%p0"
[(set_attr "type" "vssegts")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_fault_load<mode>"
[(set (match_operand:VT 0 "register_operand" "=vr, vr, vd")
(if_then_else:VT
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1, Wc1, vm")
(match_operand 4 "vector_length_operand" " rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i")
(match_operand 6 "const_int_operand" " i, i, i")
(match_operand 7 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VT
[(match_operand:VT 3 "memory_operand" " m, m, m")
(mem:BLK (scratch))] UNSPEC_VLEFF)
(match_operand:VT 2 "vector_merge_operand" " 0, vu, vu")))
(set (reg:SI VL_REGNUM)
(unspec:SI
[(if_then_else:VT
(unspec:<VM>
[(match_dup 1) (match_dup 4) (match_dup 5)
(match_dup 6) (match_dup 7)
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VT
[(match_dup 3) (mem:BLK (scratch))] UNSPEC_VLEFF)
(match_dup 2))] UNSPEC_MODIFY_VL))]
"TARGET_VECTOR"
"vlseg<nf>e<sew>ff.v\t%0,%3%p1"
[(set_attr "type" "vlsegdff")
(set_attr "mode" "<MODE>")])
(define_insn "@pred_fault_load_set_vl<VT:mode><P:mode>"
[(set (match_operand:VT 0 "register_operand" "= vr, vr, vd")
(if_then_else:VT
(unspec:<VT:VM>
[(match_operand:<VT:VM> 1 "vector_mask_operand" "vmWc1, Wc1, vm")
(match_operand 4 "vector_length_operand" " rvl, rvl, rvl")
(match_operand 5 "const_int_operand" " i, i, i")
(match_operand 6 "const_int_operand" " i, i, i")
(match_operand 7 "const_int_operand" " i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VT
[(match_operand:VT 3 "memory_operand" " m, m, m")
(mem:BLK (scratch))] UNSPEC_VLEFF)
(match_operand:VT 2 "vector_merge_operand" " 0, vu, vu")))
(set (reg:SI VL_REGNUM)
(unspec:SI
[(if_then_else:VT
(unspec:<VT:VM>
[(match_dup 1) (match_dup 4) (match_dup 5)
(match_dup 6) (match_dup 7)
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:VT
[(match_dup 3) (mem:BLK (scratch))] UNSPEC_VLEFF)
(match_dup 2))] UNSPEC_MODIFY_VL))
(set (match_operand:P 8 "register_operand" "= r, r, r")
(unspec:P [(reg:SI VL_REGNUM)] UNSPEC_READ_VL))]
"TARGET_VECTOR"
"vlseg<nf>e<sew>ff.v\t%0,%3%p1"
[(set_attr "type" "vlsegdff")
(set_attr "mode" "<VT:MODE>")])
(define_insn "@pred_indexed_<order>load<V1T:mode><RATIO64I:mode>"
[(set (match_operand:V1T 0 "register_operand" "=&vr, &vr")
(if_then_else:V1T
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V1T
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:RATIO64I 4 "register_operand" " vr, vr")] ORDER)
(match_operand:V1T 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xseg<nf>ei<RATIO64I:sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vlsegd<order>x")
(set_attr "mode" "<V1T:MODE>")])
(define_insn "@pred_indexed_<order>load<V2T:mode><RATIO32I:mode>"
[(set (match_operand:V2T 0 "register_operand" "=&vr, &vr")
(if_then_else:V2T
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V2T
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:RATIO32I 4 "register_operand" " vr, vr")] ORDER)
(match_operand:V2T 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xseg<nf>ei<RATIO32I:sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vlsegd<order>x")
(set_attr "mode" "<V2T:MODE>")])
(define_insn "@pred_indexed_<order>load<V4T:mode><RATIO16I:mode>"
[(set (match_operand:V4T 0 "register_operand" "=&vr, &vr")
(if_then_else:V4T
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V4T
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:RATIO16I 4 "register_operand" " vr, vr")] ORDER)
(match_operand:V4T 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xseg<nf>ei<RATIO16I:sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vlsegd<order>x")
(set_attr "mode" "<V4T:MODE>")])
(define_insn "@pred_indexed_<order>load<V8T:mode><RATIO8I:mode>"
[(set (match_operand:V8T 0 "register_operand" "=&vr, &vr")
(if_then_else:V8T
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V8T
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:RATIO8I 4 "register_operand" " vr, vr")] ORDER)
(match_operand:V8T 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xseg<nf>ei<RATIO8I:sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vlsegd<order>x")
(set_attr "mode" "<V8T:MODE>")])
(define_insn "@pred_indexed_<order>load<V16T:mode><RATIO4I:mode>"
[(set (match_operand:V16T 0 "register_operand" "=&vr, &vr")
(if_then_else:V16T
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V16T
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:RATIO4I 4 "register_operand" " vr, vr")] ORDER)
(match_operand:V16T 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xseg<nf>ei<RATIO4I:sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vlsegd<order>x")
(set_attr "mode" "<V16T:MODE>")])
(define_insn "@pred_indexed_<order>load<V32T:mode><RATIO2I:mode>"
[(set (match_operand:V32T 0 "register_operand" "=&vr, &vr")
(if_then_else:V32T
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
(match_operand 5 "vector_length_operand" " rvl, rvl")
(match_operand 6 "const_int_operand" " i, i")
(match_operand 7 "const_int_operand" " i, i")
(match_operand 8 "const_int_operand" " i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(unspec:V32T
[(match_operand 3 "pmode_reg_or_0_operand" " rJ, rJ")
(mem:BLK (scratch))
(match_operand:RATIO2I 4 "register_operand" " vr, vr")] ORDER)
(match_operand:V32T 2 "vector_merge_operand" " vu, 0")))]
"TARGET_VECTOR"
"vl<order>xseg<nf>ei<RATIO2I:sew>.v\t%0,(%z3),%4%p1"
[(set_attr "type" "vlsegd<order>x")
(set_attr "mode" "<V32T:MODE>")])
(define_insn "@pred_indexed_<order>store<V1T:mode><RATIO64I:mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:RATIO64I 2 "register_operand" " vr")
(match_operand:V1T 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xseg<nf>ei<RATIO64I:sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vssegt<order>x")
(set_attr "mode" "<V1T:MODE>")])
(define_insn "@pred_indexed_<order>store<V2T:mode><RATIO32I:mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:RATIO32I 2 "register_operand" " vr")
(match_operand:V2T 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xseg<nf>ei<RATIO32I:sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vssegt<order>x")
(set_attr "mode" "<V2T:MODE>")])
(define_insn "@pred_indexed_<order>store<V4T:mode><RATIO16I:mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:RATIO16I 2 "register_operand" " vr")
(match_operand:V4T 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xseg<nf>ei<RATIO16I:sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vssegt<order>x")
(set_attr "mode" "<V4T:MODE>")])
(define_insn "@pred_indexed_<order>store<V8T:mode><RATIO8I:mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:RATIO8I 2 "register_operand" " vr")
(match_operand:V8T 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xseg<nf>ei<RATIO8I:sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vssegt<order>x")
(set_attr "mode" "<V8T:MODE>")])
(define_insn "@pred_indexed_<order>store<V16T:mode><RATIO4I:mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:RATIO4I 2 "register_operand" " vr")
(match_operand:V16T 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xseg<nf>ei<RATIO4I:sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vssegt<order>x")
(set_attr "mode" "<V16T:MODE>")])
(define_insn "@pred_indexed_<order>store<V32T:mode><RATIO2I:mode>"
[(set (mem:BLK (scratch))
(unspec:BLK
[(unspec:<VM>
[(match_operand:<VM> 0 "vector_mask_operand" "vmWc1")
(match_operand 4 "vector_length_operand" " rvl")
(match_operand 5 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(match_operand 1 "pmode_reg_or_0_operand" " rJ")
(match_operand:RATIO2I 2 "register_operand" " vr")
(match_operand:V32T 3 "register_operand" " vr")] ORDER))]
"TARGET_VECTOR"
"vs<order>xseg<nf>ei<RATIO2I:sew>.v\t%3,(%z1),%2%p0"
[(set_attr "type" "vssegt<order>x")
(set_attr "mode" "<V32T:MODE>")])
(define_insn "*pred_mul_minus_vx<mode>_undef"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 6 "vector_length_operand" "rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_QHS
(match_operand:V_VLSI_QHS 5 "register_operand" " vr, 0, vr, 0")
(mult:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 3 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))
(match_operand:V_VLSI_QHS 4 "register_operand" " 0, vr, 0, vr")))
(match_operand:V_VLSI_QHS 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vnmsub.vx\t%0,%z3,%5%p1
vnmsac.vx\t%0,%z3,%4%p1
vnmsub.vx\t%0,%z3,%5%p1
vnmsac.vx\t%0,%z3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_mul_minus_vx<mode>_undef"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 6 "vector_length_operand" "rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(minus:V_VLSI_D
(match_operand:V_VLSI_D 5 "register_operand" " vr, 0, vr, 0")
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 3 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))
(match_operand:V_VLSI_D 4 "register_operand" " 0, vr, 0, vr")))
(match_operand:V_VLSI_D 2 "vector_undef_operand")))]
"TARGET_VECTOR && TARGET_64BIT"
"@
vnmsub.vx\t%0,%z3,%5%p1
vnmsac.vx\t%0,%z3,%4%p1
vnmsub.vx\t%0,%z3,%5%p1
vnmsac.vx\t%0,%z3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_mul_plus_vx<mode>_undef"
[(set (match_operand:V_VLSI_QHS 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 6 "vector_length_operand" "rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_QHS
(mult:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 3 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))
(match_operand:V_VLSI_QHS 4 "register_operand" " 0, vr, 0, vr"))
(match_operand:V_VLSI_QHS 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSI_QHS 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"@
vmadd.vx\t%0,%z3,%5%p1
vmacc.vx\t%0,%z3,%4%p1
vmadd.vx\t%0,%z3,%5%p1
vmacc.vx\t%0,%z3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_insn "*pred_mul_plus_vx<mode>_undef"
[(set (match_operand:V_VLSI_D 0 "register_operand" "=vd, vd, vr, vr")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
(match_operand 6 "vector_length_operand" "rvl, rvl, rvl, rvl")
(match_operand 7 "const_int_operand" " i, i, i, i")
(match_operand 8 "const_int_operand" " i, i, i, i")
(match_operand 9 "const_int_operand" " i, i, i, i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_D
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 3 "reg_or_0_operand" " rJ, rJ, rJ, rJ"))
(match_operand:V_VLSI_D 4 "register_operand" " 0, vr, 0, vr"))
(match_operand:V_VLSI_D 5 "register_operand" " vr, 0, vr, 0"))
(match_operand:V_VLSI_D 2 "vector_undef_operand")))]
"TARGET_VECTOR && TARGET_64BIT"
"@
vmadd.vx\t%0,%z3,%5%p1
vmacc.vx\t%0,%z3,%4%p1
vmadd.vx\t%0,%z3,%5%p1
vmacc.vx\t%0,%z3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_mul_plus_vx<mode>"
[(set (match_operand:V_VLSI_QHS 0 "register_operand")
(if_then_else:V_VLSI_QHS
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_QHS
(mult:V_VLSI_QHS
(vec_duplicate:V_VLSI_QHS
(match_operand:<VEL> 2 "reg_or_0_operand"))
(match_operand:V_VLSI_QHS 3 "register_operand"))
(match_operand:V_VLSI_QHS 4 "register_operand"))
(match_operand:V_VLSI_QHS 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_expand "@pred_mul_plus_vx<mode>"
[(set (match_operand:V_VLSI_D 0 "register_operand")
(if_then_else:V_VLSI_D
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:V_VLSI_D
(mult:V_VLSI_D
(vec_duplicate:V_VLSI_D
(match_operand:<VEL> 2 "reg_or_0_operand"))
(match_operand:V_VLSI_D 3 "register_operand"))
(match_operand:V_VLSI_D 4 "register_operand"))
(match_operand:V_VLSI_D 5 "vector_merge_operand")))]
"TARGET_VECTOR && TARGET_64BIT"
{
riscv_vector::prepare_ternary_operands (operands);
})
(define_insn "*pred_widen_mul_plus_u_vx<mode>_undef"
[(set (match_operand:VWEXTI 0 "register_operand" "=&vr")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand" "vmWc1")
(match_operand 6 "vector_length_operand" " rvl")
(match_operand 7 "const_int_operand" " i")
(match_operand 8 "const_int_operand" " i")
(match_operand 9 "const_int_operand" " i")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(zero_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 3 "register_operand" " rJ")))
(zero_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" " vr")))
(match_operand:VWEXTI 5 "register_operand" " 0"))
(match_operand:VWEXTI 2 "vector_undef_operand")))]
"TARGET_VECTOR"
"vwmaccu.vx\t%0,%z3,%4%p1"
[(set_attr "type" "vimuladd")
(set_attr "mode" "<MODE>")])
(define_expand "@pred_widen_mul_plus_u_vx<mode>"
[(set (match_operand:VWEXTI 0 "register_operand")
(if_then_else:VWEXTI
(unspec:<VM>
[(match_operand:<VM> 1 "vector_mask_operand")
(match_operand 6 "vector_length_operand")
(match_operand 7 "const_int_operand")
(match_operand 8 "const_int_operand")
(match_operand 9 "const_int_operand")
(reg:SI VL_REGNUM)
(reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
(plus:VWEXTI
(mult:VWEXTI
(zero_extend:VWEXTI
(vec_duplicate:<V_DOUBLE_TRUNC>
(match_operand:<VSUBEL> 2 "register_operand")))
(zero_extend:VWEXTI
(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand")))
(match_operand:VWEXTI 4 "register_operand"))
(match_operand:VWEXTI 5 "vector_merge_operand")))]
"TARGET_VECTOR"
{
riscv_vector::prepare_ternary_operands (operands);
})
(include "autovec.md")
(include "autovec-opt.md")
(include "sifive-vector.md")
(include "andes-vector.md")