[flang-commits] [flang] c8b50b8 - [flang] Prevent character length setting with dangling ac-do-variable.
Slava Zakharin via flang-commits
flang-commits at lists.llvm.org
Mon May 8 16:57:17 PDT 2023
Author: Slava Zakharin
Date: 2023-05-08T16:57:07-07:00
New Revision: c8b50b860068bb9116c17ad3d8b616285eb68c71
URL: https://github.com/llvm/llvm-project/commit/c8b50b860068bb9116c17ad3d8b616285eb68c71
DIFF: https://github.com/llvm/llvm-project/commit/c8b50b860068bb9116c17ad3d8b616285eb68c71.diff
LOG: [flang] Prevent character length setting with dangling ac-do-variable.
This fixes LEN inquiry on array constructors where the length
expression includes references to the ac-do-variable.
Reviewed By: klausler
Differential Revision: https://reviews.llvm.org/D150149
Added:
Modified:
flang/lib/Semantics/expression.cpp
flang/test/Evaluate/rewrite01.f90
Removed:
################################################################################
diff --git a/flang/lib/Semantics/expression.cpp b/flang/lib/Semantics/expression.cpp
index 1440147feecdf..6047f8da441b1 100644
--- a/flang/lib/Semantics/expression.cpp
+++ b/flang/lib/Semantics/expression.cpp
@@ -1475,7 +1475,20 @@ class ArrayConstructorContext {
ArrayConstructor<T> result{MakeSpecific<T>(std::move(values_))};
if constexpr (T::category == TypeCategory::Character) {
if (auto len{type_->LEN()}) {
- if (IsConstantExpr(*len)) {
+ // The ac-do-variables may be treated as constant expressions,
+ // if some conditions on ac-implied-do-control hold (10.1.12 (12)).
+ // At the same time, they may be treated as constant expressions
+ // only in the context of the ac-implied-do, but setting
+ // the character length here may result in complete elimination
+ // of the ac-implied-do. For example:
+ // character(10) :: c
+ // ... len([(c(i:i), integer(8)::i = 1,4)])
+ // would be evaulated into:
+ // ... int(max(0_8,i-i+1_8),kind=4)
+ // with a dangling reference to the ac-do-variable.
+ // Prevent this by checking for the ac-do-variable references
+ // in the 'len' expression.
+ if (!ContainsAnyImpliedDoIndex(*len) && IsConstantExpr(*len)) {
result.set_LEN(std::move(*len));
}
}
diff --git a/flang/test/Evaluate/rewrite01.f90 b/flang/test/Evaluate/rewrite01.f90
index cbcbfb97189c7..0fa3581a3799f 100644
--- a/flang/test/Evaluate/rewrite01.f90
+++ b/flang/test/Evaluate/rewrite01.f90
@@ -234,10 +234,13 @@ function return_allocatable()
subroutine array_ctor_implied_do_index(x, j)
integer :: x(:)
integer(8) :: j
+ character(10) :: c
!CHECK: PRINT *, size([INTEGER(4)::(x(1_8:i:1_8),INTEGER(8)::i=1_8,2_8,1_8)])
print *, size([(x(1:i), integer(8)::i=1,2)])
!CHECK: PRINT *, int(0_8+2_8*(0_8+max((j-1_8+1_8)/1_8,0_8)),kind=4)
print *, size([(x(1:j), integer(8)::i=1,2)])
+ !CHECK: PRINT *, len([(c(i:i),INTEGER(8)::i=1_8,4_8,1_8)])
+ print *, len([(c(i:i), integer(8)::i = 1,4)])
end subroutine
end module
More information about the flang-commits
mailing list