[flang-commits] [flang] f72106e - [flang] Fix an assert when RESHAPE() is called on empty strings
Pete Steinfeld via flang-commits
flang-commits at lists.llvm.org
Wed Jul 22 12:22:20 PDT 2020
Author: Pete Steinfeld
Date: 2020-07-22T12:21:58-07:00
New Revision: f72106e2a35b12ef4bb265e755a6ee33a576c768
URL: https://github.com/llvm/llvm-project/commit/f72106e2a35b12ef4bb265e755a6ee33a576c768
DIFF: https://github.com/llvm/llvm-project/commit/f72106e2a35b12ef4bb265e755a6ee33a576c768.diff
LOG: [flang] Fix an assert when RESHAPE() is called on empty strings
Summary:
When a constant array of empty strings goes through contant folding, the result
is something that contains no bytes. If this array is passed to the intrinsic
function `RESHAPE()`, we were not handling things correctly. I fixed this by
checking for an empty destination when calling the function `CopyFrom()` on an
array of strings.
I also added a test with a couple of different examples that trigger the
problem.
Reviewers: klausler, tskeith, DavidTruby
Subscribers: llvm-commits
Tags: #llvm
Differential Revision: https://reviews.llvm.org/D84352
Added:
Modified:
flang/lib/Evaluate/constant.cpp
flang/test/Semantics/modfile25.f90
Removed:
################################################################################
diff --git a/flang/lib/Evaluate/constant.cpp b/flang/lib/Evaluate/constant.cpp
index ecdcc0ab8e3e..e7497630f596 100644
--- a/flang/lib/Evaluate/constant.cpp
+++ b/flang/lib/Evaluate/constant.cpp
@@ -244,19 +244,26 @@ std::size_t Constant<Type<TypeCategory::Character, KIND>>::CopyFrom(
std::size_t count, ConstantSubscripts &resultSubscripts,
const std::vector<int> *dimOrder) {
CHECK(length_ == source.length_);
- std::size_t copied{0};
- std::size_t elementBytes{length_ * sizeof(decltype(values_[0]))};
- ConstantSubscripts sourceSubscripts{source.lbounds()};
- while (copied < count) {
- auto *dest{&values_.at(SubscriptsToOffset(resultSubscripts) * length_)};
- const auto *src{&source.values_.at(
- source.SubscriptsToOffset(sourceSubscripts) * length_)};
- std::memcpy(dest, src, elementBytes);
- copied++;
- source.IncrementSubscripts(sourceSubscripts);
- IncrementSubscripts(resultSubscripts, dimOrder);
+ if (length_ == 0) {
+ // It's possible that the array of strings consists of all empty strings.
+ // If so, constant folding will result in a string that's completely empty
+ // and the length_ will be zero, and there's nothing to do.
+ return count;
+ } else {
+ std::size_t copied{0};
+ std::size_t elementBytes{length_ * sizeof(decltype(values_[0]))};
+ ConstantSubscripts sourceSubscripts{source.lbounds()};
+ while (copied < count) {
+ auto *dest{&values_.at(SubscriptsToOffset(resultSubscripts) * length_)};
+ const auto *src{&source.values_.at(
+ source.SubscriptsToOffset(sourceSubscripts) * length_)};
+ std::memcpy(dest, src, elementBytes);
+ copied++;
+ source.IncrementSubscripts(sourceSubscripts);
+ IncrementSubscripts(resultSubscripts, dimOrder);
+ }
+ return copied;
}
- return copied;
}
// Constant<SomeDerived> specialization
diff --git a/flang/test/Semantics/modfile25.f90 b/flang/test/Semantics/modfile25.f90
index 850298d54e4d..76dc61a54b6c 100644
--- a/flang/test/Semantics/modfile25.f90
+++ b/flang/test/Semantics/modfile25.f90
@@ -22,6 +22,9 @@ subroutine subr(x,n1,n2)
real, intent(in) :: x(:,:)
integer, intent(in) :: n1(3), n2(:)
real, allocatable :: a(:,:,:)
+ ! the following fail if we don't handle empty strings
+ Character(0) :: ch1(1,2,3) = Reshape([('',n=1,1*2*3)],[1,2,3])
+ Character(0) :: ch2(3) = reshape(['','',''], [3])
a = reshape(x,n1)
a = reshape(x,n2(10:30:9)) ! fails if we can't figure out triplet shape
end subroutine
More information about the flang-commits
mailing list