[llvm] [LAA] Fix incorrect dependency classification. (PR #70819)

Alexandros Lamprineas via llvm-commits llvm-commits at lists.llvm.org
Tue Oct 31 08:30:49 PDT 2023


https://github.com/labrinea created https://github.com/llvm/llvm-project/pull/70819

As shown in #70473, the following loop was not considered safe to vectorize. When determining the memory access dependencies in a loop which has negative iteration step, we invert the source and sink of the dependence. Perhaps we should just invert the operands to getMinusSCEV(). This way the dependency is not regarded to be true.

void vectorizable_Read_Write(int *A) {
  for (unsigned i = 1022; i >= 0; i--)
    A[i+1] = A[i] + 1;
}

>From 77e45128bf710d73c089a17ed447a22ac3af1565 Mon Sep 17 00:00:00 2001
From: Alexandros Lamprineas <alexandros.lamprineas at arm.com>
Date: Tue, 31 Oct 2023 15:23:40 +0000
Subject: [PATCH] [LAA] Fix incorrect dependency classification.

As shown in #70473, the following loop was not considered safe to vectorize.
When determining the memory access dependencies in a loop which has negative
iteration step, we invert the source and sink of the dependence. Perhaps we
should just invert the operands to getMinusSCEV(). This way the dependency
is not regarded to be true.

void vectorizable_Read_Write(int *A) {
  for (unsigned i = 1022; i >= 0; i--)
    A[i+1] = A[i] + 1;
}
---
 llvm/lib/Analysis/LoopAccessAnalysis.cpp             | 12 ++----------
 .../LoopAccessAnalysis/forward-negative-step.ll      |  7 ++-----
 2 files changed, 4 insertions(+), 15 deletions(-)

diff --git a/llvm/lib/Analysis/LoopAccessAnalysis.cpp b/llvm/lib/Analysis/LoopAccessAnalysis.cpp
index 3d1edd5f038a25e..7ab2959c4d88a34 100644
--- a/llvm/lib/Analysis/LoopAccessAnalysis.cpp
+++ b/llvm/lib/Analysis/LoopAccessAnalysis.cpp
@@ -1885,17 +1885,9 @@ MemoryDepChecker::isDependent(const MemAccessInfo &A, unsigned AIdx,
 
   // If the induction step is negative we have to invert source and sink of the
   // dependence.
-  if (StrideAPtr < 0) {
-    std::swap(APtr, BPtr);
-    std::swap(ATy, BTy);
-    std::swap(Src, Sink);
-    std::swap(AIsWrite, BIsWrite);
-    std::swap(AIdx, BIdx);
-    std::swap(StrideAPtr, StrideBPtr);
-  }
-
   ScalarEvolution &SE = *PSE.getSE();
-  const SCEV *Dist = SE.getMinusSCEV(Sink, Src);
+  const SCEV *Dist = StrideAPtr < 0 ? SE.getMinusSCEV(Src, Sink) :
+                                      SE.getMinusSCEV(Sink, Src);
 
   LLVM_DEBUG(dbgs() << "LAA: Src Scev: " << *Src << "Sink Scev: " << *Sink
                     << "(Induction step: " << StrideAPtr << ")\n");
diff --git a/llvm/test/Analysis/LoopAccessAnalysis/forward-negative-step.ll b/llvm/test/Analysis/LoopAccessAnalysis/forward-negative-step.ll
index 89c1737fb730513..683c44be6da87fc 100644
--- a/llvm/test/Analysis/LoopAccessAnalysis/forward-negative-step.ll
+++ b/llvm/test/Analysis/LoopAccessAnalysis/forward-negative-step.ll
@@ -2,8 +2,6 @@
 
 target datalayout = "e-m:e-i64:64-i128:128-n32:64-S128"
 
-; FIXME: This should be vectorizable
-
 ; void vectorizable_Read_Write(int *A) {
 ;  for (unsigned i = 1022; i >= 0; i--)
 ;    A[i+1] = A[i] + 1;
@@ -11,10 +9,9 @@ target datalayout = "e-m:e-i64:64-i128:128-n32:64-S128"
 
 ; CHECK: function 'vectorizable_Read_Write':
 ; CHECK-NEXT:   for.body:
-; CHECK-NEXT:     Report: unsafe dependent memory operations in loop
-; CHECK-NEXT:     Forward loop carried data dependence that prevents store-to-load forwarding.
+; CHECK-NEXT:     Memory dependences are safe
 ; CHECK-NEXT:     Dependences:
-; CHECK-NEXT:       ForwardButPreventsForwarding:
+; CHECK-NEXT:       Forward:
 ; CHECK-NEXT:           %0 = load i32, ptr %arrayidx, align 4 ->
 ; CHECK-NEXT:           store i32 %add, ptr %gep, align 4
 



More information about the llvm-commits mailing list