Skip to content

Commit 82cea79

Browse files
committed
[flang] Re-land PR#97337
Pull request llvm#97337 was reverted by llvm#98612 due to two failing tests in llvm-test-suite -- which I ran, as always, but must have bungled or misinterpreted (mea culpa). The failing tests were llvm-test-suite/Fortran/gfortran/regression/ char_length_{20,21}.f90. They have array constructors with explicit character types whose dynamic length values are negative at runtime and which must be interpreted as zero. This patch extends the original to cover those cases.
1 parent 9f1cfe0 commit 82cea79

File tree

1 file changed

+10
-3
lines changed

1 file changed

+10
-3
lines changed

flang/lib/Semantics/expression.cpp

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ std::optional<Expr<SubscriptInteger>> DynamicTypeWithLength::LEN() const {
6363
}
6464

6565
static std::optional<DynamicTypeWithLength> AnalyzeTypeSpec(
66-
const std::optional<parser::TypeSpec> &spec) {
66+
const std::optional<parser::TypeSpec> &spec, FoldingContext &context) {
6767
if (spec) {
6868
if (const semantics::DeclTypeSpec *typeSpec{spec->declTypeSpec}) {
6969
// Name resolution sets TypeSpec::declTypeSpec only when it's valid
@@ -80,7 +80,13 @@ static std::optional<DynamicTypeWithLength> AnalyzeTypeSpec(
8080
const semantics::ParamValue &len{cts.length()};
8181
// N.B. CHARACTER(LEN=*) is allowed in type-specs in ALLOCATE() &
8282
// type guards, but not in array constructors.
83-
return DynamicTypeWithLength{DynamicType{kind, len}};
83+
DynamicTypeWithLength type{DynamicType{kind, len}};
84+
if (auto lenExpr{type.LEN()}) {
85+
type.length = Fold(context,
86+
AsExpr(Extremum<SubscriptInteger>{Ordering::Greater,
87+
Expr<SubscriptInteger>{0}, std::move(*lenExpr)}));
88+
}
89+
return type;
8490
} else {
8591
return DynamicTypeWithLength{DynamicType{category, kind}};
8692
}
@@ -1940,7 +1946,8 @@ MaybeExpr ArrayConstructorContext::ToExpr() {
19401946

19411947
MaybeExpr ExpressionAnalyzer::Analyze(const parser::ArrayConstructor &array) {
19421948
const parser::AcSpec &acSpec{array.v};
1943-
ArrayConstructorContext acContext{*this, AnalyzeTypeSpec(acSpec.type)};
1949+
ArrayConstructorContext acContext{
1950+
*this, AnalyzeTypeSpec(acSpec.type, GetFoldingContext())};
19441951
for (const parser::AcValue &value : acSpec.values) {
19451952
acContext.Add(value);
19461953
}

0 commit comments

Comments
 (0)