Skip to content

[LoopInterchange] Add tests of 'S' deps (NFC) #125214

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Feb 3, 2025

Conversation

kasuga-fj
Copy link
Contributor

The incorrect handling of scalar dependencies in LoopInterchange was fixed by #119345. This patch adds tests that are relative to the issues fixed by #119345.

The incorrect handling of scalar dependencies in LoopInterchange was
fixed by llvm#119345. This patch adds tests that are relative to the issues
fixed by llvm#119345.
@llvmbot
Copy link
Member

llvmbot commented Jan 31, 2025

@llvm/pr-subscribers-llvm-transforms

Author: Ryotaro Kasuga (kasuga-fj)

Changes

The incorrect handling of scalar dependencies in LoopInterchange was fixed by #119345. This patch adds tests that are relative to the issues fixed by #119345.


Full diff: https://github.com/llvm/llvm-project/pull/125214.diff

1 Files Affected:

  • (added) llvm/test/Transforms/LoopInterchange/legality-for-scalar-deps.ll (+322)
diff --git a/llvm/test/Transforms/LoopInterchange/legality-for-scalar-deps.ll b/llvm/test/Transforms/LoopInterchange/legality-for-scalar-deps.ll
new file mode 100644
index 00000000000000..c30f9a399fed8a
--- /dev/null
+++ b/llvm/test/Transforms/LoopInterchange/legality-for-scalar-deps.ll
@@ -0,0 +1,322 @@
+; RUN: opt < %s -passes=loop-interchange -pass-remarks-output=%t -disable-output
+; RUN: FileCheck -input-file %t %s
+
+; This is a collection of cases where the loops were incorrectly interchanged
+; due to mishandling of scalar dependencies.
+
+;; The original code is as follows, with some simplifications from the one in
+;; the issue #46867. The interchange is illegal due to the dependency of `s`.
+;;
+;; void issue46867(int *s, int c, int ff[4][9]) {
+;;   for (int d = 0; d <= 2; d++) {
+;;     for (int e = 0; e <= 2; e++) {
+;;       if ((long)(ff[e][d] && (*s = 3), c) % 4073709551606)
+;;         ++*s;
+;;     }
+;;   }
+;; }
+
+; CHECK:      --- !Missed
+; CHECK-NEXT: Pass:            loop-interchange
+; CHECK-NEXT: Name:            Dependence
+; CHECK-NEXT: Function:        issue46867
+; CHECK-NEXT: Args:
+; CHECK-NEXT:  - String:       Cannot interchange loops due to dependences.
+; CHECK:      --- !Missed
+; CHECK-NEXT: Pass:            loop-interchange
+; CHECK-NEXT: Name:            Dependence
+; CHECK-NEXT: Function:        issue46867
+; CHECK-NEXT: Args:
+; CHECK-NEXT:  - String:       Cannot interchange loops due to dependences.
+define void @issue46867(ptr noundef captures(none) %s, i32 noundef %c, ptr noundef readonly captures(none) %ff) {
+entry:
+  %tobool7.not = icmp eq i32 %c, 0
+  br i1 %tobool7.not, label %for.cond1.preheader.us.preheader, label %entry.split
+
+for.cond1.preheader.us.preheader:
+  br label %for.cond1.preheader.us
+
+for.cond1.preheader.us:
+  %indvars.iv31 = phi i64 [ 0, %for.cond1.preheader.us.preheader ], [ %indvars.iv.next32, %for.cond.cleanup3.split.us.us ]
+  br label %for.body4.us.us
+
+for.body4.us.us:
+  %indvars.iv27 = phi i64 [ %indvars.iv.next28, %land.end.us.us ], [ 0, %for.cond1.preheader.us ]
+  %arrayidx6.us.us = getelementptr inbounds nuw [9 x i32], ptr %ff, i64 %indvars.iv27, i64 %indvars.iv31
+  %0 = load i32, ptr %arrayidx6.us.us, align 4
+  %tobool.not.us.us = icmp eq i32 %0, 0
+  br i1 %tobool.not.us.us, label %land.end.us.us, label %land.rhs.us.us
+
+land.rhs.us.us:
+  store i32 3, ptr %s, align 4
+  br label %land.end.us.us
+
+land.end.us.us:
+  %indvars.iv.next28 = add nuw nsw i64 %indvars.iv27, 1
+  %exitcond30 = icmp ne i64 %indvars.iv.next28, 3
+  br i1 %exitcond30, label %for.body4.us.us, label %for.cond.cleanup3.split.us.us
+
+for.cond.cleanup3.split.us.us:
+  %indvars.iv.next32 = add nuw nsw i64 %indvars.iv31, 1
+  %exitcond34 = icmp ne i64 %indvars.iv.next32, 3
+  br i1 %exitcond34, label %for.cond1.preheader.us, label %for.cond.cleanup.loopexit
+
+entry.split:
+  %s.promoted19 = load i32, ptr %s, align 4
+  br label %for.cond1.preheader
+
+for.cond1.preheader:
+  %indvars.iv23 = phi i64 [ 0, %entry.split ], [ %indvars.iv.next24, %for.cond.cleanup3.split ]
+  %s.promoted20 = phi i32 [ %s.promoted19, %entry.split ], [ %inc.lcssa, %for.cond.cleanup3.split ]
+  br label %for.body4
+
+for.cond.cleanup.loopexit:
+  br label %for.cond.cleanup
+
+for.cond.cleanup.loopexit21:
+  br label %for.cond.cleanup
+
+for.cond.cleanup:
+  ret void
+
+for.cond.cleanup3.split:
+  %inc.lcssa = phi i32 [ %inc, %land.end ]
+  %indvars.iv.next24 = add nuw nsw i64 %indvars.iv23, 1
+  %exitcond26 = icmp ne i64 %indvars.iv.next24, 3
+  br i1 %exitcond26, label %for.cond1.preheader, label %for.cond.cleanup.loopexit21
+
+for.body4:
+  %indvars.iv = phi i64 [ 0, %for.cond1.preheader ], [ %indvars.iv.next, %land.end ]
+  %1 = phi i32 [ %s.promoted20, %for.cond1.preheader ], [ %inc, %land.end ]
+  %arrayidx6 = getelementptr inbounds nuw [9 x i32], ptr %ff, i64 %indvars.iv, i64 %indvars.iv23
+  %2 = load i32, ptr %arrayidx6, align 4
+  %tobool.not = icmp eq i32 %2, 0
+  br i1 %tobool.not, label %land.end, label %land.rhs
+
+land.rhs:
+  store i32 3, ptr %s, align 4
+  br label %land.end
+
+land.end:
+  %3 = phi i32 [ 3, %land.rhs ], [ %1, %for.body4 ]
+  %inc = add nsw i32 %3, 1
+  store i32 %inc, ptr %s, align 4
+  %indvars.iv.next = add nuw nsw i64 %indvars.iv, 1
+  %exitcond = icmp ne i64 %indvars.iv.next, 3
+  br i1 %exitcond, label %for.body4, label %for.cond.cleanup3.split
+}
+
+
+;; The original code is as follows, with some simplifications from the one in
+;; the issue #47401. The interchange is illegal due to the dependency of `e`.
+;;
+;; void issue47401(int *e, int bb[][8]) {
+;;   for (int c = 0; c <= 7; c++)
+;;     for (int d = 4; d; d--)
+;;       bb[d + 2][c] && (*e = bb[d][0]);
+;; }
+
+; CHECK:      --- !Missed
+; CHECK-NEXT: Pass:            loop-interchange
+; CHECK-NEXT: Name:            Dependence
+; CHECK-NEXT: Function:        issue47401
+; CHECK-NEXT: Args:
+; CHECK-NEXT:  - String:       Cannot interchange loops due to dependences.
+define void @issue47401(ptr noundef writeonly captures(none) %e, ptr noundef readonly captures(none) %bb) {
+entry:
+  br label %for.cond1.preheader
+
+for.cond1.preheader:
+  %indvars.iv22 = phi i64 [ 0, %entry ], [ %indvars.iv.next23, %for.cond.cleanup2 ]
+  br label %for.body3
+
+for.cond.cleanup:
+  ret void
+
+for.cond.cleanup2:
+  %indvars.iv.next23 = add nuw nsw i64 %indvars.iv22, 1
+  %exitcond = icmp ne i64 %indvars.iv.next23, 8
+  br i1 %exitcond, label %for.cond1.preheader, label %for.cond.cleanup
+
+for.body3:
+  %indvars.iv = phi i64 [ 4, %for.cond1.preheader ], [ %indvars.iv.next, %land.end ]
+  %0 = getelementptr [8 x i32], ptr %bb, i64 %indvars.iv
+  %arrayidx = getelementptr i8, ptr %0, i64 64
+  %arrayidx5 = getelementptr inbounds nuw [8 x i32], ptr %arrayidx, i64 0, i64 %indvars.iv22
+  %1 = load i32, ptr %arrayidx5, align 4
+  %tobool6.not = icmp eq i32 %1, 0
+  br i1 %tobool6.not, label %land.end, label %land.rhs
+
+land.rhs:
+  %2 = load i32, ptr %0, align 4
+  store i32 %2, ptr %e, align 4
+  br label %land.end
+
+land.end:
+  %indvars.iv.next = add nsw i64 %indvars.iv, -1
+  %tobool.not = icmp eq i64 %indvars.iv.next, 0
+  br i1 %tobool.not, label %for.cond.cleanup2, label %for.body3
+}
+
+;; The original code is as follows, with some simplifications from the one in
+;; the issue #47295. The interchange is illegal due to the dependency of `f`.
+;;
+;; void issue47295(int *f, int cc[4][4]) {
+;;   for (int i = 0; i <= 3; i++) {
+;;     for (int j = 0; j <= 3; j++) {
+;;       *f ^= 0x1000;
+;;       cc[j][i] = *f;
+;;     }
+;;   }
+;; }
+
+; CHECK:      --- !Missed
+; CHECK-NEXT: Pass:            loop-interchange
+; CHECK-NEXT: Name:            Dependence
+; CHECK-NEXT: Function:        issue47295
+; CHECK-NEXT: Args:
+; CHECK-NEXT:  - String:       Cannot interchange loops due to dependences.
+define void @issue47295(ptr noundef captures(none) %f, ptr noundef writeonly captures(none) %cc) {
+entry:
+  br label %for.cond1.preheader
+
+for.cond1.preheader:
+  %indvars.iv18 = phi i64 [ 0, %entry ], [ %indvars.iv.next19, %for.cond.cleanup3 ]
+  br label %for.body4
+
+for.cond.cleanup:
+  ret void
+
+for.cond.cleanup3:
+  %indvars.iv.next19 = add nuw nsw i64 %indvars.iv18, 1
+  %exitcond21 = icmp ne i64 %indvars.iv.next19, 4
+  br i1 %exitcond21, label %for.cond1.preheader, label %for.cond.cleanup
+
+for.body4:
+  %indvars.iv = phi i64 [ 0, %for.cond1.preheader ], [ %indvars.iv.next, %for.body4 ]
+  %0 = load i32, ptr %f, align 4
+  %xor = xor i32 %0, 4096
+  store i32 %xor, ptr %f, align 4
+  %arrayidx6 = getelementptr inbounds nuw [4 x i32], ptr %cc, i64 %indvars.iv, i64 %indvars.iv18
+  store i32 %xor, ptr %arrayidx6, align 4
+  %indvars.iv.next = add nuw nsw i64 %indvars.iv, 1
+  %exitcond = icmp ne i64 %indvars.iv.next, 4
+  br i1 %exitcond, label %for.body4, label %for.cond.cleanup3
+}
+
+;; The original code is as follows, with some simplifications from the one in
+;; the issue #54176. The interchange is illegal due to the dependency of `aa`.
+;;
+;; void issue54176(int n, int m, float aa[1024][128], float bb[1024][128], float cc[1024][128]) {
+;;   for (int j = 1; j < 128; j++) {
+;;     for (int i = 1; i < 1024; i++) {
+;;       cc[i][j] = aa[1][j];
+;;       aa[1][j-1] += bb[i][j];
+;;     }
+;;   }
+;; }
+
+; CHECK:      --- !Missed
+; CHECK-NEXT: Pass:            loop-interchange
+; CHECK-NEXT: Name:            Dependence
+; CHECK-NEXT: Function:        issue54176
+; CHECK-NEXT: Args:
+; CHECK-NEXT:  - String:       Cannot interchange loops due to dependences.
+define void @issue54176(i32 noundef %n, i32 noundef %m, ptr noundef captures(none) %aa, ptr noundef readonly captures(none) %bb, ptr noundef writeonly captures(none) %cc) {
+
+entry:
+  %arrayidx = getelementptr inbounds nuw i8, ptr %aa, i64 512
+  br label %for.cond1.preheader
+
+for.cond1.preheader:
+  %indvars.iv32 = phi i64 [ 1, %entry ], [ %indvars.iv.next33, %for.cond.cleanup3 ]
+  %arrayidx5 = getelementptr inbounds nuw [128 x float], ptr %arrayidx, i64 0, i64 %indvars.iv32
+  %0 = add nsw i64 %indvars.iv32, -1
+  %arrayidx16 = getelementptr inbounds [128 x float], ptr %arrayidx, i64 0, i64 %0
+  br label %for.body4
+
+for.cond.cleanup3:
+  %indvars.iv.next33 = add nuw nsw i64 %indvars.iv32, 1
+  %exitcond36 = icmp ne i64 %indvars.iv.next33, 128
+  br i1 %exitcond36, label %for.cond1.preheader, label %for.cond.cleanup
+
+for.body4:
+  %indvars.iv = phi i64 [ 1, %for.cond1.preheader ], [ %indvars.iv.next, %for.body4 ]
+  %1 = load float, ptr %arrayidx5, align 4
+  %arrayidx9 = getelementptr inbounds nuw [128 x float], ptr %cc, i64 %indvars.iv, i64 %indvars.iv32
+  store float %1, ptr %arrayidx9, align 4
+  %arrayidx13 = getelementptr inbounds nuw [128 x float], ptr %bb, i64 %indvars.iv, i64 %indvars.iv32
+  %2 = load float, ptr %arrayidx13, align 4
+  %3 = load float, ptr %arrayidx16, align 4
+  %add = fadd float %2, %3
+  store float %add, ptr %arrayidx16, align 4
+  %indvars.iv.next = add nuw nsw i64 %indvars.iv, 1
+  %exitcond = icmp ne i64 %indvars.iv.next, 1024
+  br i1 %exitcond, label %for.body4, label %for.cond.cleanup3
+
+for.cond.cleanup:
+  ret void
+}
+
+;; The original code is as follows, with some simplifications from the one in
+;; the issue #116114. The interchange is illegal due to the dependency of `A`.
+;;
+;; void issue116114(int *A, int x, unsigned N, unsigned M) {
+;;   for (unsigned m = 0; m < M; ++m)
+;;     for (unsigned i = 0U; i < N - 1; ++i) {
+;;       A[i] = A[i + 1] + x;
+;;     }
+;; }
+
+; CHECK:      --- !Missed
+; CHECK-NEXT: Pass:            loop-interchange
+; CHECK-NEXT: Name:            Dependence
+; CHECK-NEXT: Function:        issue116114
+; CHECK-NEXT: Args:
+; CHECK-NEXT:  - String:       Cannot interchange loops due to dependences.
+define void @issue116114(ptr noundef captures(none) %A, i32 noundef %x, i32 noundef %N, i32 noundef %M) {
+entry:
+  %cmp18.not = icmp eq i32 %M, 0
+  br i1 %cmp18.not, label %for.cond.cleanup, label %for.cond1.preheader.lr.ph
+
+for.cond1.preheader.lr.ph:
+  %sub = add i32 %N, -1
+  %cmp216.not = icmp eq i32 %sub, 0
+  br i1 %cmp216.not, label %for.cond1.preheader.preheader, label %for.cond1.preheader.us.preheader
+
+for.cond1.preheader.us.preheader:
+  br label %for.cond1.preheader.us
+
+for.cond1.preheader.preheader:
+  br label %for.cond.cleanup.loopexit
+
+for.cond1.preheader.us:
+  %m.019.us = phi i32 [ %inc9.us, %for.cond1.for.cond.cleanup3_crit_edge.us ], [ 0, %for.cond1.preheader.us.preheader ]
+  %wide.trip.count = zext i32 %sub to i64
+  br label %for.body4.us
+
+for.body4.us:
+  %indvars.iv = phi i64 [ 0, %for.cond1.preheader.us ], [ %indvars.iv.next, %for.body4.us ]
+  %indvars.iv.next = add nuw nsw i64 %indvars.iv, 1
+  %arrayidx.us = getelementptr inbounds nuw i32, ptr %A, i64 %indvars.iv.next
+  %0 = load i32, ptr %arrayidx.us, align 4
+  %add5.us = add nsw i32 %0, %x
+  %arrayidx7.us = getelementptr inbounds nuw i32, ptr %A, i64 %indvars.iv
+  store i32 %add5.us, ptr %arrayidx7.us, align 4
+  %exitcond = icmp ne i64 %indvars.iv.next, %wide.trip.count
+  br i1 %exitcond, label %for.body4.us, label %for.cond1.for.cond.cleanup3_crit_edge.us
+
+for.cond1.for.cond.cleanup3_crit_edge.us:
+  %inc9.us = add nuw i32 %m.019.us, 1
+  %exitcond22 = icmp ne i32 %inc9.us, %M
+  br i1 %exitcond22, label %for.cond1.preheader.us, label %for.cond.cleanup.loopexit20
+
+for.cond.cleanup.loopexit:
+  br label %for.cond.cleanup
+
+for.cond.cleanup.loopexit20:
+  br label %for.cond.cleanup
+
+for.cond.cleanup:
+  ret void
+}

@sjoerdmeijer
Copy link
Collaborator

The more testing the better, but I wanted to ask how these tests differ from existing S deps test? There are quite a few tests that we had to disable, and I have for example added some tests in #115900. I haven't looked closely how the new tests here differ, or what they add, so just wanted to ask you here.

@kasuga-fj
Copy link
Contributor Author

Ah, sorry, I completely missed the pre-committed tests! I will now check to see if my test is redundant.

@kasuga-fj
Copy link
Contributor Author

IIUIC, existing 'S' deps tests are the cases where we cannot interchange for now, but they are in principle legal to exchange. The original purpose of tests marked as XFAIL is to make sure that the interchange happens as we expect. On the other hand, tests in this patch are cases where interchanging is not allowed because it changes the original semantics, but it was done before #119345 due to the mishandling of 'S' deps. So these are tests to make sure that illegal interchange doesn't happen forever in the future. In other words, these tests can prevent bugs fixed in #119345 from recurring.

Copy link
Collaborator

@sjoerdmeijer sjoerdmeijer left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the clarification, LGTM

@kasuga-fj kasuga-fj merged commit e82f938 into llvm:main Feb 3, 2025
10 checks passed
@llvm-ci
Copy link
Collaborator

llvm-ci commented Feb 3, 2025

LLVM Buildbot has detected a new failure on builder openmp-offload-libc-amdgpu-runtime running on omp-vega20-1 while building llvm at step 7 "Add check check-offload".

Full details are available at: https://lab.llvm.org/buildbot/#/builders/73/builds/12924

Here is the relevant piece of the build log for the reference
Step 7 (Add check check-offload) failure: test (failure)
******************** TEST 'libomptarget :: amdgcn-amd-amdhsa :: libc/global_ctor_dtor.cpp' FAILED ********************
Exit Code: 2

Command Output (stdout):
--
# RUN: at line 1
/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./bin/clang++ -fopenmp    -I /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test -I /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/openmp/runtime/src -L /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload -L /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./lib -L /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/openmp/runtime/src  -nogpulib -Wl,-rpath,/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload -Wl,-rpath,/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/openmp/runtime/src -Wl,-rpath,/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./lib  -fopenmp-targets=amdgcn-amd-amdhsa /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test/libc/global_ctor_dtor.cpp -o /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload/test/amdgcn-amd-amdhsa/libc/Output/global_ctor_dtor.cpp.tmp -Xoffload-linker -lc -Xoffload-linker -lm /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./lib/libomptarget.devicertl.a && /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload/test/amdgcn-amd-amdhsa/libc/Output/global_ctor_dtor.cpp.tmp | /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./bin/FileCheck /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test/libc/global_ctor_dtor.cpp
# executed command: /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./bin/clang++ -fopenmp -I /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test -I /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/openmp/runtime/src -L /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload -L /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./lib -L /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/openmp/runtime/src -nogpulib -Wl,-rpath,/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload -Wl,-rpath,/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/openmp/runtime/src -Wl,-rpath,/home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./lib -fopenmp-targets=amdgcn-amd-amdhsa /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test/libc/global_ctor_dtor.cpp -o /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload/test/amdgcn-amd-amdhsa/libc/Output/global_ctor_dtor.cpp.tmp -Xoffload-linker -lc -Xoffload-linker -lm /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./lib/libomptarget.devicertl.a
# executed command: /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/runtimes/runtimes-bins/offload/test/amdgcn-amd-amdhsa/libc/Output/global_ctor_dtor.cpp.tmp
# note: command had no output on stdout or stderr
# error: command failed with exit status: -11
# executed command: /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./bin/FileCheck /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test/libc/global_ctor_dtor.cpp
# .---command stderr------------
# | FileCheck error: '<stdin>' is empty.
# | FileCheck command line:  /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.build/./bin/FileCheck /home/ompworker/bbot/openmp-offload-libc-amdgpu-runtime/llvm.src/offload/test/libc/global_ctor_dtor.cpp
# `-----------------------------
# error: command failed with exit status: 2

--

********************


Icohedron pushed a commit to Icohedron/llvm-project that referenced this pull request Feb 11, 2025
The incorrect handling of scalar dependencies in LoopInterchange was
fixed by llvm#119345. This patch adds tests that are relative to the issues
fixed by llvm#119345.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants