Skip to content

Conversation

@klausler
Copy link
Contributor

A reduction folding template assumed lower bounds were 1.

Fixes #86935.

A reduction folding template assumed lower bounds were 1.

Fixes llvm#86935.
@llvmbot
Copy link
Member

llvmbot commented Mar 31, 2024

@llvm/pr-subscribers-flang-semantics

Author: Peter Klausler (klausler)

Changes

A reduction folding template assumed lower bounds were 1.

Fixes #86935.


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

2 Files Affected:

  • (modified) flang/lib/Evaluate/fold-reduction.h (+13-11)
  • (added) flang/test/Evaluate/folding32.f90 (+6)
diff --git a/flang/lib/Evaluate/fold-reduction.h b/flang/lib/Evaluate/fold-reduction.h
index 1ee957c0faebd8..c84d35734ab5af 100644
--- a/flang/lib/Evaluate/fold-reduction.h
+++ b/flang/lib/Evaluate/fold-reduction.h
@@ -182,25 +182,27 @@ static Constant<T> DoReduction(const Constant<ARRAY> &array,
     ConstantSubscript &maskDimAt{maskAt[*dim - 1]};
     ConstantSubscript maskDimLbound{maskDimAt};
     for (auto n{GetSize(resultShape)}; n-- > 0;
-         IncrementSubscripts(at, array.shape()),
-         IncrementSubscripts(maskAt, mask.shape())) {
-      dimAt = dimLbound;
-      maskDimAt = maskDimLbound;
+         array.IncrementSubscripts(at), mask.IncrementSubscripts(maskAt)) {
       elements.push_back(identity);
-      bool firstUnmasked{true};
-      for (ConstantSubscript j{0}; j < dimExtent; ++j, ++dimAt, ++maskDimAt) {
-        if (mask.At(maskAt).IsTrue()) {
-          accumulator(elements.back(), at, firstUnmasked);
-          firstUnmasked = false;
+      if (dimExtent > 0) {
+        dimAt = dimLbound;
+        maskDimAt = maskDimLbound;
+        bool firstUnmasked{true};
+        for (ConstantSubscript j{0}; j < dimExtent; ++j, ++dimAt, ++maskDimAt) {
+          if (mask.At(maskAt).IsTrue()) {
+            accumulator(elements.back(), at, firstUnmasked);
+            firstUnmasked = false;
+          }
         }
+        --dimAt, --maskDimAt;
       }
       accumulator.Done(elements.back());
     }
   } else { // no DIM=, result is scalar
     elements.push_back(identity);
     bool firstUnmasked{true};
-    for (auto n{array.size()}; n-- > 0; IncrementSubscripts(at, array.shape()),
-         IncrementSubscripts(maskAt, mask.shape())) {
+    for (auto n{array.size()}; n-- > 0;
+         array.IncrementSubscripts(at), mask.IncrementSubscripts(maskAt)) {
       if (mask.At(maskAt).IsTrue()) {
         accumulator(elements.back(), at, firstUnmasked);
         firstUnmasked = false;
diff --git a/flang/test/Evaluate/folding32.f90 b/flang/test/Evaluate/folding32.f90
new file mode 100644
index 00000000000000..e4c8b26ca8fdc3
--- /dev/null
+++ b/flang/test/Evaluate/folding32.f90
@@ -0,0 +1,6 @@
+! RUN: %python %S/test_folding.py %s %flang_fc1
+! Fold NORM2 reduction of array with non-default lower bound
+module m
+  real, parameter :: a(2:3) = 0.0
+  logical, parameter :: test1 = norm2(a) == 0.
+end

@klausler klausler merged commit b685597 into llvm:main Apr 8, 2024
@klausler klausler deleted the bug86935 branch April 8, 2024 18:54
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

flang:semantics flang Flang issues not falling into any other category

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Flang] fatal internal error: CHECK(j >= lb && j - lb < extent) failed at /root/llvm-project/flang/lib/Evaluate/constant.cpp(76)

3 participants