[llvm] [RISCV] Provide a more efficient lowering for experimental.cttz.elts. (PR #88552)

Luke Lau via llvm-commits llvm-commits at lists.llvm.org
Mon Apr 15 01:06:46 PDT 2024


================
@@ -8718,6 +8723,33 @@ static SDValue lowerGetVectorLength(SDNode *N, SelectionDAG &DAG,
   return DAG.getNode(ISD::TRUNCATE, DL, N->getValueType(0), Res);
 }
 
+static SDValue lowerCttzElts(SDNode *N, SelectionDAG &DAG,
+                             const RISCVSubtarget &Subtarget) {
+  SDValue Op0 = N->getOperand(1);
+  MVT OpVT = Op0.getSimpleValueType();
+  MVT ContainerVT = OpVT;
+  if (OpVT.isFixedLengthVector()) {
+    ContainerVT = getContainerForFixedLengthVector(DAG, OpVT, Subtarget);
+    Op0 = convertToScalableVector(ContainerVT, Op0, DAG, Subtarget);
+  }
+  MVT XLenVT = Subtarget.getXLenVT();
+  SDLoc DL(N);
+  auto [Mask, VL] = getDefaultVLOps(OpVT, ContainerVT, DL, DAG, Subtarget);
+  SDValue Res = DAG.getNode(RISCVISD::VFIRST_VL, DL, XLenVT, Op0, Mask, VL);
+  if (isOneConstant(N->getOperand(2)))
+    return Res;
+
+  // Convert -1 to VL.
+  SDValue Setcc =
+      DAG.getSetCC(DL, XLenVT, Res, DAG.getConstant(0, DL, XLenVT), ISD::SETLT);
+  // We need to use vscale rather than X0 for scalable vectors.
+  if (!OpVT.isFixedLengthVector())
+    VL = DAG.getVScale(
+        DL, XLenVT,
+        APInt(XLenVT.getSizeInBits(), OpVT.getVectorMinNumElements()));
----------------
lukel97 wrote:

I think you can also do
```suggestion
  SDValue VL = DAG.getElementCount(DL, XLenVT, OpVT.getVectorElementCount())
```

https://github.com/llvm/llvm-project/pull/88552


More information about the llvm-commits mailing list