[llvm] [polly] [delinearize] Extract array dimensions from alloca and global declarations (PR #156342)

Sebastian Pop via llvm-commits llvm-commits at lists.llvm.org
Fri Oct 10 08:30:51 PDT 2025


================
@@ -408,6 +425,145 @@ void llvm::computeAccessFunctions(ScalarEvolution &SE, const SCEV *Expr,
   });
 }
 
+/// Backward compatibility wrapper for the old 4-parameter version.
+void llvm::computeAccessFunctions(ScalarEvolution &SE, const SCEV *Expr,
+                                  SmallVectorImpl<const SCEV *> &Subscripts,
+                                  SmallVectorImpl<const SCEV *> &Sizes) {
+  // Use the element size from the last element in Sizes array (legacy behavior)
+  if (Sizes.empty()) {
+    Subscripts.clear();
+    return;
+  }
+  const SCEV *ElementSize = Sizes.back();
+  computeAccessFunctions(SE, Expr, Subscripts, Sizes, ElementSize);
+}
+
+/// Extract array dimensions from alloca or global variable declarations.
+/// Returns true if array dimensions were successfully extracted.
+static bool
+extractArrayInfoFromAllocaOrGlobal(ScalarEvolution &SE, Value *BasePtr,
+                                   SmallVectorImpl<const SCEV *> &Sizes,
+                                   const SCEV *ElementSize) {
+  // Clear output vector.
+  Sizes.clear();
+
+  LLVM_DEBUG(
+      dbgs() << "extractArrayInfoFromAllocaOrGlobal called with BasePtr: "
+             << *BasePtr << "\n");
+
+  // Distinguish between simple array accesses and complex pointer arithmetic.
+  // Only apply array_info extraction to direct array accesses to avoid
+  // incorrect delinearization of complex pointer arithmetic patterns.
+  if (auto *GEP = dyn_cast<GetElementPtrInst>(BasePtr)) {
+    // Check if this is a simple array access pattern: GEP [N x T]* @array, 0,
+    // idx This represents direct indexing like array[i], which should use array
+    // dimensions.
+    if (GEP->getNumIndices() == 2) {
+      auto *FirstIdx = dyn_cast<ConstantInt>(GEP->getOperand(1));
+      if (FirstIdx && FirstIdx->isZero()) {
+        // Simple array access: extract dimensions from the underlying array
+        // type
+        Value *Source = GEP->getPointerOperand()->stripPointerCasts();
+        return extractArrayInfoFromAllocaOrGlobal(SE, Source, Sizes,
+                                                  ElementSize);
+      }
+    }
+    // Complex GEPs like (&array[offset])[index] represent pointer arithmetic,
+    // not simple array indexing. These should be handled by parametric
+    // delinearization to preserve the linearized byte-offset semantics rather
+    // than treating them as multidimensional array accesses.
+    return false;
+  }
+
+  // Check if BasePtr is from an alloca instruction.
+  Type *ElementType = nullptr;
+  if (auto *AI = dyn_cast<AllocaInst>(BasePtr)) {
+    ElementType = AI->getAllocatedType();
+    LLVM_DEBUG(dbgs() << "Found alloca with type: " << *ElementType << "\n");
+  } else if (auto *GV = dyn_cast<GlobalVariable>(BasePtr)) {
+    ElementType = GV->getValueType();
+    LLVM_DEBUG(dbgs() << "Found global variable with type: " << *ElementType
+                      << "\n");
+  } else {
+    LLVM_DEBUG(dbgs() << "No alloca or global found for base pointer\n");
+    return false;
+  }
+
+  // Extract dimensions from nested array types.
+  Type *I64Ty = Type::getInt64Ty(SE.getContext());
----------------
sebpop wrote:

Could you please elaborate on how using `DataLayout::getIndexSize` would work?

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


More information about the llvm-commits mailing list