[clang] [llvm] [RISCV] Add Zvzip intrinsics (PR #186342)
Luke Lau via llvm-commits
llvm-commits at lists.llvm.org
Mon Mar 30 05:16:52 PDT 2026
================
@@ -29,3 +29,112 @@ let Predicates = [HasStdExtZvzip], Constraints = "@earlyclobber $vd" in {
def VPAIRO_VV : VALUVV<0b001111, OPMVV, "vpairo.vv">;
}
} // Predicates = [HasStdExtZvzip]
+
+defset list<VTypeInfoToWide> AllZvzipVectors = {
+ def : VTypeInfoToWide<VI8MF8, VI8MF4>;
+ def : VTypeInfoToWide<VI8MF4, VI8MF2>;
+ def : VTypeInfoToWide<VI8MF2, VI8M1>;
+ def : VTypeInfoToWide<VI8M1, VI8M2>;
+ def : VTypeInfoToWide<VI8M2, VI8M4>;
+ def : VTypeInfoToWide<VI8M4, VI8M8>;
+
+ def : VTypeInfoToWide<VI16MF4, VI16MF2>;
+ def : VTypeInfoToWide<VI16MF2, VI16M1>;
+ def : VTypeInfoToWide<VI16M1, VI16M2>;
+ def : VTypeInfoToWide<VI16M2, VI16M4>;
+ def : VTypeInfoToWide<VI16M4, VI16M8>;
+
+ def : VTypeInfoToWide<VI32MF2, VI32M1>;
+ def : VTypeInfoToWide<VI32M1, VI32M2>;
+ def : VTypeInfoToWide<VI32M2, VI32M4>;
+ def : VTypeInfoToWide<VI32M4, VI32M8>;
+
+ def : VTypeInfoToWide<VI64M1, VI64M2>;
+ def : VTypeInfoToWide<VI64M2, VI64M4>;
+ def : VTypeInfoToWide<VI64M4, VI64M8>;
+
+ // Floating-point 16-bit
+ def : VTypeInfoToWide<VF16MF4, VF16MF2>;
+ def : VTypeInfoToWide<VF16MF2, VF16M1>;
+ def : VTypeInfoToWide<VF16M1, VF16M2>;
+ def : VTypeInfoToWide<VF16M2, VF16M4>;
+ def : VTypeInfoToWide<VF16M4, VF16M8>;
+
+ // Floating-point 32-bit
+ def : VTypeInfoToWide<VF32MF2, VF32M1>;
+ def : VTypeInfoToWide<VF32M1, VF32M2>;
+ def : VTypeInfoToWide<VF32M2, VF32M4>;
+ def : VTypeInfoToWide<VF32M4, VF32M8>;
+
+ // Floating-point 64-bit
+ def : VTypeInfoToWide<VF64M1, VF64M2>;
+ def : VTypeInfoToWide<VF64M2, VF64M4>;
+ def : VTypeInfoToWide<VF64M4, VF64M8>;
+}
+
+multiclass VPseudoVZIP {
+ foreach m = MxListW in
+ defm "" : VPseudoBinaryW_VV<m, Commutable=0>,
+ SchedBinary<"WriteVIWALUV", "ReadVIWALUV", "ReadVIWALUV", m.MX,
+ forcePassthruRead=true>;
+}
+
+multiclass VPseudoVUNZIP {
+ foreach m = MxListW in {
+ defvar mx = m.MX;
+ let VLMul = m.value in {
+ def "_V_" # mx : VPseudoUnaryNoMask<m.vrclass, m.wvrclass>,
+ SchedUnary<"WriteVIALUV", "ReadVIALUV", mx, forcePassthruRead=true>;
+ def "_V_" # mx # "_MASK" :
+ VPseudoUnaryMask<m.vrclass, m.wvrclass>,
+ RISCVMaskedPseudo<MaskIdx=2>,
+ SchedUnary<"WriteVIALUV", "ReadVIALUV", mx, forcePassthruRead=true>;
+ }
+ }
+}
+
+let Predicates = [HasStdExtZvzip],
+ Constraints = "@earlyclobber $rd, $rd = $passthru" in {
+ defm PseudoVZIP : VPseudoVZIP;
+ defm PseudoVUNZIPE : VPseudoVUNZIP;
+ defm PseudoVUNZIPO : VPseudoVUNZIP;
+ defm PseudoVPAIRE : VPseudoVALU_VV;
+ defm PseudoVPAIRO : VPseudoVALU_VV;
+}
+
+multiclass VPatVUNZIPIntrinsic<string intrinsic_name, string instruction_name> {
+ foreach VtiToWti = AllZvzipVectors in {
+ defvar vti = VtiToWti.Vti;
+ defvar wti = VtiToWti.Wti;
+ let Predicates = !listconcat(GetVTypePredicates<wti>.Predicates, [HasStdExtZvzip]) in {
+ def : Pat<(vti.Vector (!cast<Intrinsic>(intrinsic_name)
+ (vti.Vector vti.RegClass:$passthru),
+ (wti.Vector wti.RegClass:$rs2),
+ VLOpFrag)),
+ (!cast<Instruction>(instruction_name#"_V_"#vti.LMul.MX)
+ vti.RegClass:$passthru,
+ wti.RegClass:$rs2,
+ GPR:$vl,
+ vti.Log2SEW,
+ TAIL_AGNOSTIC)>;
+ def : Pat<(vti.Vector (!cast<Intrinsic>(intrinsic_name # "_mask")
+ (vti.Vector vti.RegClass:$passthru),
+ (wti.Vector wti.RegClass:$rs2),
+ (vti.Mask VMV0:$vm),
+ VLOpFrag, (XLenVT timm:$policy))),
+ (!cast<Instruction>(instruction_name#"_V_"#vti.LMul.MX#"_MASK")
+ vti.RegClass:$passthru,
+ wti.RegClass:$rs2,
+ (vti.Mask VMV0:$vm),
+ GPR:$vl,
+ vti.Log2SEW,
+ timm:$policy)>;
----------------
lukel97 wrote:
Can these patterns be replaced with VPatUnaryNoMask/VPatUnaryMask?
https://github.com/llvm/llvm-project/pull/186342
More information about the llvm-commits
mailing list