https://github.com/AmrDeveloper updated 
https://github.com/llvm/llvm-project/pull/142315

>From 12c9d3f76360c28efc8ba07ac959af6cf45a6f10 Mon Sep 17 00:00:00 2001
From: AmrDeveloper <am...@programmer.net>
Date: Sun, 1 Jun 2025 19:07:56 +0200
Subject: [PATCH 1/4] [CIR] Implement folder for VecShuffleDynamicOp

---
 clang/include/clang/CIR/Dialect/IR/CIROps.td  |  1 +
 clang/lib/CIR/Dialect/IR/CIRDialect.cpp       | 32 +++++++++++++++++++
 .../Dialect/Transforms/CIRCanonicalize.cpp    |  6 ++--
 .../vector-shuffle-dynamic-fold.cir           | 18 +++++++++++
 4 files changed, 54 insertions(+), 3 deletions(-)
 create mode 100644 clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir

diff --git a/clang/include/clang/CIR/Dialect/IR/CIROps.td 
b/clang/include/clang/CIR/Dialect/IR/CIROps.td
index 237daed32532a..7db6725afb80c 100644
--- a/clang/include/clang/CIR/Dialect/IR/CIROps.td
+++ b/clang/include/clang/CIR/Dialect/IR/CIROps.td
@@ -2192,6 +2192,7 @@ def VecShuffleDynamicOp : CIR_Op<"vec.shuffle.dynamic",
   }];
 
   let hasVerifier = 1;
+  let hasFolder = 1;
 }
 
 #endif // CLANG_CIR_DIALECT_IR_CIROPS_TD
diff --git a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp 
b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
index 36f050de9f8bb..90b32950e4774 100644
--- a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
+++ b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
@@ -1579,6 +1579,38 @@ OpFoldResult cir::VecExtractOp::fold(FoldAdaptor 
adaptor) {
 // VecShuffleDynamicOp
 
//===----------------------------------------------------------------------===//
 
+OpFoldResult cir::VecShuffleDynamicOp::fold(FoldAdaptor adaptor) {
+  mlir::Attribute vec = adaptor.getVec();
+  mlir::Attribute indices = adaptor.getIndices();
+  if (mlir::isa_and_nonnull<cir::ConstVectorAttr>(vec) &&
+      mlir::isa_and_nonnull<cir::ConstVectorAttr>(indices)) {
+    auto vecAttr = mlir::cast<cir::ConstVectorAttr>(vec);
+    auto indicesAttr = mlir::cast<cir::ConstVectorAttr>(indices);
+    auto vecTy = cast<cir::VectorType>(vecAttr.getType());
+
+    mlir::ArrayAttr vecElts = vecAttr.getElts();
+    mlir::ArrayAttr indicesElts = indicesAttr.getElts();
+
+    const uint64_t numElements = vecElts.size();
+
+    SmallVector<mlir::Attribute, 16> elements;
+    elements.reserve(numElements);
+
+    const uint64_t maskBits = llvm::NextPowerOf2(numElements - 1) - 1;
+    for (uint64_t i = 0; i < numElements; i++) {
+      cir::IntAttr idxAttr = mlir::cast<cir::IntAttr>(indicesElts[i]);
+      uint64_t idxValue = idxAttr.getUInt();
+      uint64_t newIdx = idxValue & maskBits;
+      elements.push_back(vecElts[newIdx]);
+    }
+
+    return cir::ConstVectorAttr::get(
+        vecTy, mlir::ArrayAttr::get(getContext(), elements));
+  }
+
+  return {};
+}
+
 LogicalResult cir::VecShuffleDynamicOp::verify() {
   // The number of elements in the two input vectors must match.
   if (getVec().getType().getSize() !=
diff --git a/clang/lib/CIR/Dialect/Transforms/CIRCanonicalize.cpp 
b/clang/lib/CIR/Dialect/Transforms/CIRCanonicalize.cpp
index fb000adee04c6..7d03e374c27e8 100644
--- a/clang/lib/CIR/Dialect/Transforms/CIRCanonicalize.cpp
+++ b/clang/lib/CIR/Dialect/Transforms/CIRCanonicalize.cpp
@@ -138,10 +138,10 @@ void CIRCanonicalizePass::runOnOperation() {
     assert(!cir::MissingFeatures::complexRealOp());
     assert(!cir::MissingFeatures::complexImagOp());
     assert(!cir::MissingFeatures::callOp());
-    // CastOp, UnaryOp and VecExtractOp are here to perform a manual `fold` in
-    // applyOpPatternsGreedily.
+    // CastOp, UnaryOp, VecExtractOp and VecShuffleDynamicOp are here to 
perform
+    // a manual `fold` in applyOpPatternsGreedily.
     if (isa<BrOp, BrCondOp, CastOp, ScopeOp, SwitchOp, SelectOp, UnaryOp,
-            VecExtractOp>(op))
+            VecExtractOp, VecShuffleDynamicOp>(op))
       ops.push_back(op);
   });
 
diff --git a/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir 
b/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir
new file mode 100644
index 0000000000000..db5d6bff04d5b
--- /dev/null
+++ b/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir
@@ -0,0 +1,18 @@
+// RUN: cir-opt %s -cir-canonicalize -o - | FileCheck %s
+
+!s32i = !cir.int<s, 32>
+
+module {
+  cir.func @fold_shuffle_dynamic_vector_op_test() {
+    %alloca = cir.alloca !cir.vector<4 x !s32i>, !cir.ptr<!cir.vector<4 x 
!s32i>>, ["r", init]
+    %vec = cir.const #cir.const_vector<[#cir.int<1> : !s32i, #cir.int<2> : 
!s32i, #cir.int<3> : !s32i, #cir.int<4> : !s32i]> : !cir.vector<4 x !s32i>
+    %indices = cir.const #cir.const_vector<[#cir.int<8> : !s32i, #cir.int<7> : 
!s32i, #cir.int<6> : !s32i, #cir.int<5> : !s32i]> : !cir.vector<4 x !s32i>
+    %new_vec = cir.vec.shuffle.dynamic %vec : !cir.vector<4 x !s32i>, %indices 
: !cir.vector<4 x !s32i>
+    cir.store align(16) %new_vec, %alloca : !cir.vector<4 x !s32i>, 
!cir.ptr<!cir.vector<4 x !s32i>>
+    cir.return
+  }
+
+  // CHECK: %[[NEW_VEC:.*]] = cir.const #cir.const_vector<[#cir.int<1> : 
!s32i, #cir.int<4> : !s32i, #cir.int<3> : !s32i, #cir.int<2> : !s32i]> : 
!cir.vector<4 x !s32i>
+}
+
+

>From 959bf9c766bb56ff5dc6e7d6c26a94a7cfae5d01 Mon Sep 17 00:00:00 2001
From: AmrDeveloper <am...@programmer.net>
Date: Mon, 2 Jun 2025 21:59:54 +0200
Subject: [PATCH 2/4] Address code review comments

---
 clang/lib/CIR/Dialect/IR/CIRDialect.cpp | 7 ++++---
 1 file changed, 4 insertions(+), 3 deletions(-)

diff --git a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp 
b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
index 90b32950e4774..15c76f0755dda 100644
--- a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
+++ b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
@@ -21,6 +21,7 @@
 #include "clang/CIR/Dialect/IR/CIROpsDialect.cpp.inc"
 #include "clang/CIR/Dialect/IR/CIROpsEnums.cpp.inc"
 #include "clang/CIR/MissingFeatures.h"
+
 #include <numeric>
 
 using namespace mlir;
@@ -1597,9 +1598,9 @@ OpFoldResult cir::VecShuffleDynamicOp::fold(FoldAdaptor 
adaptor) {
     elements.reserve(numElements);
 
     const uint64_t maskBits = llvm::NextPowerOf2(numElements - 1) - 1;
-    for (uint64_t i = 0; i < numElements; i++) {
-      cir::IntAttr idxAttr = mlir::cast<cir::IntAttr>(indicesElts[i]);
-      uint64_t idxValue = idxAttr.getUInt();
+    for (const mlir::APInt &idxAttr :
+         indicesElts.getAsValueRange<cir::IntAttr, mlir::APInt>()) {
+      uint64_t idxValue = idxAttr.getZExtValue();
       uint64_t newIdx = idxValue & maskBits;
       elements.push_back(vecElts[newIdx]);
     }

>From ec7d646c052d9cbe30617f2cdb4da48ac059bfce Mon Sep 17 00:00:00 2001
From: AmrDeveloper <am...@programmer.net>
Date: Mon, 2 Jun 2025 23:11:01 +0200
Subject: [PATCH 3/4] Use getAsRange in for range

---
 clang/lib/CIR/Dialect/IR/CIRDialect.cpp | 7 +++----
 1 file changed, 3 insertions(+), 4 deletions(-)

diff --git a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp 
b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
index 15c76f0755dda..26ebe6c1dbcd1 100644
--- a/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
+++ b/clang/lib/CIR/Dialect/IR/CIRDialect.cpp
@@ -1587,7 +1587,7 @@ OpFoldResult cir::VecShuffleDynamicOp::fold(FoldAdaptor 
adaptor) {
       mlir::isa_and_nonnull<cir::ConstVectorAttr>(indices)) {
     auto vecAttr = mlir::cast<cir::ConstVectorAttr>(vec);
     auto indicesAttr = mlir::cast<cir::ConstVectorAttr>(indices);
-    auto vecTy = cast<cir::VectorType>(vecAttr.getType());
+    auto vecTy = mlir::cast<cir::VectorType>(vecAttr.getType());
 
     mlir::ArrayAttr vecElts = vecAttr.getElts();
     mlir::ArrayAttr indicesElts = indicesAttr.getElts();
@@ -1598,9 +1598,8 @@ OpFoldResult cir::VecShuffleDynamicOp::fold(FoldAdaptor 
adaptor) {
     elements.reserve(numElements);
 
     const uint64_t maskBits = llvm::NextPowerOf2(numElements - 1) - 1;
-    for (const mlir::APInt &idxAttr :
-         indicesElts.getAsValueRange<cir::IntAttr, mlir::APInt>()) {
-      uint64_t idxValue = idxAttr.getZExtValue();
+    for (const auto &idxAttr : indicesElts.getAsRange<cir::IntAttr>()) {
+      uint64_t idxValue = idxAttr.getUInt();
       uint64_t newIdx = idxValue & maskBits;
       elements.push_back(vecElts[newIdx]);
     }

>From 2a58fc9df5f91671dfe308ffab561b6fa1f2fad6 Mon Sep 17 00:00:00 2001
From: AmrDeveloper <am...@programmer.net>
Date: Wed, 4 Jun 2025 21:23:33 +0200
Subject: [PATCH 4/4] Extend the folding test

---
 .../vector-shuffle-dynamic-fold.cir           | 23 +++++++++++++++----
 1 file changed, 18 insertions(+), 5 deletions(-)

diff --git a/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir 
b/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir
index db5d6bff04d5b..46ab04502afec 100644
--- a/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir
+++ b/clang/test/CIR/Transforms/vector-shuffle-dynamic-fold.cir
@@ -3,16 +3,29 @@
 !s32i = !cir.int<s, 32>
 
 module {
-  cir.func @fold_shuffle_dynamic_vector_op_test() {
-    %alloca = cir.alloca !cir.vector<4 x !s32i>, !cir.ptr<!cir.vector<4 x 
!s32i>>, ["r", init]
+  cir.func @fold_shuffle_dynamic_vector_op_test() -> !cir.vector<4 x !s32i> {
     %vec = cir.const #cir.const_vector<[#cir.int<1> : !s32i, #cir.int<2> : 
!s32i, #cir.int<3> : !s32i, #cir.int<4> : !s32i]> : !cir.vector<4 x !s32i>
     %indices = cir.const #cir.const_vector<[#cir.int<8> : !s32i, #cir.int<7> : 
!s32i, #cir.int<6> : !s32i, #cir.int<5> : !s32i]> : !cir.vector<4 x !s32i>
     %new_vec = cir.vec.shuffle.dynamic %vec : !cir.vector<4 x !s32i>, %indices 
: !cir.vector<4 x !s32i>
-    cir.store align(16) %new_vec, %alloca : !cir.vector<4 x !s32i>, 
!cir.ptr<!cir.vector<4 x !s32i>>
-    cir.return
+    cir.return %new_vec : !cir.vector<4 x !s32i>
   }
 
-  // CHECK: %[[NEW_VEC:.*]] = cir.const #cir.const_vector<[#cir.int<1> : 
!s32i, #cir.int<4> : !s32i, #cir.int<3> : !s32i, #cir.int<2> : !s32i]> : 
!cir.vector<4 x !s32i>
+  // Masking indices [8, 7, 6, 5] AND 3 = [0, 3, 2, 1]
+  // CHECK: cir.func @fold_shuffle_dynamic_vector_op_test() -> !cir.vector<4 x 
!s32i> {
+  // CHECK-NEXT: %[[NEW_VEC:.*]] = cir.const #cir.const_vector<[#cir.int<1> : 
!s32i, #cir.int<4> : !s32i, #cir.int<3> : !s32i, #cir.int<2> : !s32i]> : 
!cir.vector<4 x !s32i>
+  // CHECK-NEXT: cir.return %[[NEW_VEC:.*]] : !cir.vector<4 x !s32i>
+
+  cir.func @fold_shuffle_dynamic_vector_op_test_2() -> !cir.vector<4 x !s32i> {
+    %vec = cir.const #cir.const_vector<[#cir.int<1> : !s32i, #cir.int<2> : 
!s32i, #cir.int<3> : !s32i, #cir.int<4> : !s32i]> : !cir.vector<4 x !s32i>
+    %indices = cir.const #cir.const_vector<[#cir.int<3> : !s32i, #cir.int<2> : 
!s32i, #cir.int<1> : !s32i, #cir.int<0> : !s32i]> : !cir.vector<4 x !s32i>
+    %new_vec = cir.vec.shuffle.dynamic %vec : !cir.vector<4 x !s32i>, %indices 
: !cir.vector<4 x !s32i>
+    cir.return %new_vec : !cir.vector<4 x !s32i>
+  }
+
+  // Masking indices [3, 2, 1, 0] AND 3 = [3, 2, 1, 0]
+  // CHECK: cir.func @fold_shuffle_dynamic_vector_op_test_2() -> !cir.vector<4 
x !s32i> {
+  // CHECK-NEXT: %[[NEW_VEC:.*]] = cir.const #cir.const_vector<[#cir.int<4> : 
!s32i, #cir.int<3> : !s32i, #cir.int<2> : !s32i, #cir.int<1> : !s32i]> : 
!cir.vector<4 x !s32i>
+  // CHECK-NEXT: cir.return %[[NEW_VEC:.*]] : !cir.vector<4 x !s32i>
 }
 
 

_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to